rjw | 6c1fd8f | 2022-11-30 14:33:01 +0800 | [diff] [blame] | 1 | #!/usr/bin/perl |
| 2 | # |
| 3 | # Copyright Statement: |
| 4 | # -------------------- |
| 5 | # This software is protected by Copyright and the information contained |
| 6 | # herein is confidential. The software may not be copied and the information |
| 7 | # contained herein may not be used or disclosed except with the written |
| 8 | # permission of MediaTek Inc. (C) 2018 |
| 9 | # |
| 10 | # BY OPENING THIS FILE, BUYER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES |
| 11 | # THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE") |
| 12 | # RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO BUYER ON |
| 13 | # AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES, |
| 14 | # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF |
| 15 | # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT. |
| 16 | # NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE |
| 17 | # SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR |
| 18 | # SUPPLIED WITH THE MEDIATEK SOFTWARE, AND BUYER AGREES TO LOOK ONLY TO SUCH |
| 19 | # THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. MEDIATEK SHALL ALSO |
| 20 | # NOT BE RESPONSIBLE FOR ANY MEDIATEK SOFTWARE RELEASES MADE TO BUYER'S |
| 21 | # SPECIFICATION OR TO CONFORM TO A PARTICULAR STANDARD OR OPEN FORUM. |
| 22 | # |
| 23 | # BUYER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND CUMULATIVE |
| 24 | # LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL BE, |
| 25 | # AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT ISSUE, |
| 26 | # OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY BUYER TO |
| 27 | # MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE. |
| 28 | # |
| 29 | # THE TRANSACTION CONTEMPLATED HEREUNDER SHALL BE CONSTRUED IN ACCORDANCE |
| 30 | # WITH THE LAWS OF THE STATE OF CALIFORNIA, USA, EXCLUDING ITS CONFLICT OF |
| 31 | # LAWS PRINCIPLES. ANY DISPUTES, CONTROVERSIES OR CLAIMS ARISING THEREOF AND |
| 32 | # RELATED THERETO SHALL BE SETTLED BY ARBITRATION IN SAN FRANCISCO, CA, UNDER |
| 33 | # THE RULES OF THE INTERNATIONAL CHAMBER OF COMMERCE (ICC). |
| 34 | # |
| 35 | #***************************************************************************** |
| 36 | #* |
| 37 | #* Filename: |
| 38 | #* --------- |
| 39 | #* update_dump_table.pl |
| 40 | #* |
| 41 | #* Project: |
| 42 | #* -------- |
| 43 | #* |
| 44 | #* |
| 45 | #* Description: |
| 46 | #* ------------ |
| 47 | #* This script is to update the value of dump table. |
| 48 | #* |
| 49 | #* Author: |
| 50 | #* ------- |
| 51 | #* Yao Liu (mtk15073) |
| 52 | #* |
| 53 | #****************************************************************************/ |
| 54 | |
| 55 | use strict; |
| 56 | use warnings; |
| 57 | BEGIN { push @INC, './tools/', './tools/MemoryUtility/' } |
| 58 | use FileInfoParser; |
| 59 | use constant { |
| 60 | Section_Size =>0, |
| 61 | Section_VMA =>1, |
| 62 | Section_LMA =>2, |
| 63 | Section_Fileoffset =>3, |
| 64 | Symbol_VMA =>0, |
| 65 | Symbol_Section =>1, |
| 66 | Symbol_Size =>2, |
| 67 | }; |
| 68 | #**************************************************************************** |
| 69 | # Input |
| 70 | #**************************************************************************** |
| 71 | my $debug = 1; |
| 72 | &msg_handler("Fatal", "Wrong Parameters, Usage: update_drdi_table.pl <ELF_FILE> <SYM_FILE> <DUMP_FILE> <MAKEFILE>", __LINE__) if($#ARGV != 3); |
| 73 | |
| 74 | my ($elf_file, $sym_file, $dump_file, $makefile) = @ARGV; |
| 75 | |
| 76 | my $templog = "Input: ELF is $elf_file\nSYM is $sym_file\nDUMP_TABLE is $dump_file\nmakefile is $makefile\n\n"; |
| 77 | &msg_handler("Log", $templog, __LINE__); |
| 78 | |
| 79 | my %g_MAKEFILE_OPTIONS; |
| 80 | &msg_handler("Fatal", "Failed to parse makefile!!!\n", __LINE__) if(1!=&FileInfo::Parse_MAKEFILE($makefile, \%g_MAKEFILE_OPTIONS)); |
| 81 | &msg_handler("Log", "This load do not support DHL!!!\n", __LINE__) if(FileInfo::is("DHL_SUPPORT", "FALSE")); |
| 82 | exit 0 if(FileInfo::is("DHL_SUPPORT", "FALSE")); |
| 83 | |
| 84 | my @symbol_array = qw/dhl_dump_profile/; |
| 85 | |
| 86 | my %sym_file_hash; |
| 87 | map{ $sym_file_hash{'symbol_info'}->{$_} = 0 } (@symbol_array); |
| 88 | &parse_sym_file(); |
| 89 | |
| 90 | my @CRC32_Table; |
| 91 | &Init_CRC32_Table(); |
| 92 | |
| 93 | my $init = 0x1A424650; |
| 94 | my $constant = 1; #If the value of $init is not 0xFFFFFFFF, please set $constant to 1. |
| 95 | my $update_content = &get_table_info(); |
| 96 | |
| 97 | &dump_update_elf(); |
| 98 | |
| 99 | exit 0; |
| 100 | |
| 101 | sub parse_sym_file |
| 102 | { |
| 103 | my ($bBegin, $sum_hit_sym) = (undef, 0); |
| 104 | open SYM, "< $sym_file" or &msg_handler("Fatal", "fail to open $sym_file", __LINE__); |
| 105 | while(my $line = <SYM>) { |
| 106 | $bBegin = 1 if($line =~ /^Sections:$/); |
| 107 | $bBegin = 2 if($line =~ /^SYMBOL TABLE:$/); |
| 108 | next unless(defined $bBegin); |
| 109 | |
| 110 | #Idx Name Size VMA LMA File off Algn |
| 111 | # 0 ROM_GFH 0000084c 00000000 00000000 00000fd4 2**2 |
| 112 | if($bBegin == 1 and $line =~ /\s*(\d+)\s+(\S+)\s+(\w+)\s+(\w+)\s+(\w+)\s+(\w+)\s+(\S+)/) { |
| 113 | my $section_name = $2; |
| 114 | $sym_file_hash{'section_info'}->{$section_name} = [$3, $4, $5, $6]; |
| 115 | } |
| 116 | #91437ed0 g O ROM 00000180 DRDI_RCUCS_Array |
| 117 | elsif($bBegin == 2 and $line =~ /^([0-9a-fA-F]{8})\s+g\s+O\s+(\S+)\s+(\S+)\s+(?:\S+\s+)?(\S+)$/) { |
| 118 | my $symbol_name = $4; |
| 119 | next unless(exists $sym_file_hash{'symbol_info'}->{$symbol_name}); |
| 120 | $sym_file_hash{'symbol_info'}->{$symbol_name} = [$1, $2, hex($3)]; |
| 121 | &msg_handler("Log", "[Symbol]:$symbol_name [VMA]:0x$1 [Section]:$2 [Size]:0x$3\n", __LINE__) if($debug); |
| 122 | last if(($sum_hit_sym ++) == $#symbol_array); |
| 123 | } |
| 124 | } |
| 125 | close SYM; |
| 126 | map {&msg_handler("Fatal", "can't find symbol: $_!!!", __LINE__) if ($sym_file_hash{'symbol_info'}->{$_} == 0)} (@symbol_array); |
| 127 | } |
| 128 | |
| 129 | sub get_table_info |
| 130 | { |
| 131 | my @temp = stat($dump_file); |
| 132 | #Check total size |
| 133 | &msg_handler("Fatal", "The sie of $dump_file is biffer than symbol size!!!\n", __LINE__) if($temp[7] > $sym_file_hash{'symbol_info'}->{"dhl_dump_profile"}->[Symbol_Size]); |
| 134 | |
| 135 | my $header = unpack("V", read_memory_from_file($dump_file, 0, 4,__LINE__)); |
| 136 | my $table_value = read_memory_from_file($dump_file, 0, ($temp[7] - 4),__LINE__); |
| 137 | my $check_sum = unpack("V", read_memory_from_file($dump_file, ($temp[7] - 4), 4,__LINE__)); |
| 138 | my $content = read_memory_from_file($dump_file, 0, $temp[7],__LINE__); |
| 139 | |
| 140 | #Check header |
| 141 | &msg_handler("Fatal", "The magic pattern mismatch!!!\n", __LINE__) if($header != 0x1A424650); |
| 142 | #Check CRC32 checksum |
| 143 | my $check_value = CRC32_CheckSum($table_value); |
| 144 | &msg_handler("Log", "[File Size]:$temp[7] [Old CHecksum]:$check_sum [New Checksum]:$check_value\n", __LINE__) if($debug); |
| 145 | |
| 146 | &msg_handler("Fatal", "The checksum mismatch!!!\n", __LINE__) if($check_value != $check_sum); |
| 147 | return $content; |
| 148 | } |
| 149 | |
| 150 | sub dump_update_elf |
| 151 | { |
| 152 | open (ELF_FILE, "+< $elf_file") or &msg_handler("Fatal", "Open $elf_file file failed!!!\n", __LINE__); |
| 153 | binmode ELF_FILE; |
| 154 | foreach my $symbol (@symbol_array) { |
| 155 | if($sym_file_hash{'symbol_info'}->{$symbol} == 0) { |
| 156 | &msg_handler("Fatal", "can't find symbol: $symbol", __LINE__); |
| 157 | next; |
| 158 | } |
| 159 | my $sym_region = $sym_file_hash{'symbol_info'}->{$symbol}->[Symbol_Section]; |
| 160 | my $offset = (hex($sym_file_hash{'symbol_info'}->{$symbol}->[Symbol_VMA]) - hex($sym_file_hash{'section_info'}->{$sym_region}->[Section_VMA])) + |
| 161 | hex($sym_file_hash{'section_info'}->{$sym_region}->[Section_Fileoffset]); |
| 162 | &msg_handler("Log", "The addr of symbol in ELF is $offset.\n", __LINE__); |
| 163 | |
| 164 | seek ELF_FILE, $offset, 0; |
| 165 | print ELF_FILE $update_content; |
| 166 | } |
| 167 | close ELF_FILE; |
| 168 | &msg_handler("Log", "\n\nUpdate Elf succeed ^O^", __LINE__); |
| 169 | } |
| 170 | |
| 171 | sub read_memory_from_file |
| 172 | { |
| 173 | &msg_handler("Fatal", "[Error]: argument of $0 is insufficient\n", __LINE__) if(@_ != 4); |
| 174 | my ($file,$off,$len,$file_line_no) = @_; |
| 175 | |
| 176 | my $content; |
| 177 | open(FH, $file) or &msg_handler("Fatal", "Fail to open $file: $!\n", __LINE__); |
| 178 | binmode FH; |
| 179 | &msg_handler("Fatal", "Can not seek to $off\n", __LINE__) if not seek FH, $off, 0; |
| 180 | &msg_handler("Fatal", "At line $file_line_no! Can't read offset $off, length $len from file $file\n", __LINE__) if read(FH, $content, $len) != $len; |
| 181 | close FH; |
| 182 | return $content; |
| 183 | } |
| 184 | |
| 185 | sub Init_CRC32_Table |
| 186 | { |
| 187 | foreach my $index (0..255){ |
| 188 | my $crc = $index; |
| 189 | foreach (0..7){ |
| 190 | $crc = ($crc >> 1) ^ ($crc & 1 && 0xEDB88320); |
| 191 | } |
| 192 | my $value = $crc & 2 ** 32 - 1; |
| 193 | push @CRC32_Table, $value; |
| 194 | } |
| 195 | } |
| 196 | |
| 197 | sub CRC32_CheckSum |
| 198 | { |
| 199 | my ($data) = @_; |
| 200 | $init ^= 0xFFFFFFFF if ($constant); |
| 201 | my $check_sum = $init; |
| 202 | my $len = length $data; |
| 203 | foreach my $pos (0..$len-1){ |
| 204 | my $temp = ($check_sum ^ ord(substr($data, $pos, 1))) & 0xFF; |
| 205 | $check_sum = ($check_sum >> 8) ^ $CRC32_Table[$temp]; |
| 206 | } |
| 207 | $check_sum ^= 0xFFFFFFFF; |
| 208 | return ($check_sum & 0xFFFFFFFF); |
| 209 | } |
| 210 | |
| 211 | sub msg_handler |
| 212 | { |
| 213 | my ($type, $msg, $line_no) = (@_); |
| 214 | my $prompt_prefix; |
| 215 | if($type eq "Log") { |
| 216 | print $msg . "\n"; |
| 217 | } |
| 218 | elsif($type eq "Warning") { |
| 219 | $prompt_prefix = ">> Warning : "; |
| 220 | print "\n" . $prompt_prefix . "[at line $line_no] " . $msg . "\n"; |
| 221 | } |
| 222 | elsif($type eq "Fatal") { |
| 223 | $prompt_prefix = ">> Fatal : "; |
| 224 | die $prompt_prefix . "[at line $line_no] " . "$msg" . "\n"; |
| 225 | } |
| 226 | } |
| 227 | |
| 228 | |