diff options
Diffstat (limited to 'oncology/dpfhack_display/reverse')
-rw-r--r-- | oncology/dpfhack_display/reverse/Makefile | 76 | ||||
-rw-r--r-- | oncology/dpfhack_display/reverse/README | 169 | ||||
-rw-r--r-- | oncology/dpfhack_display/reverse/common.in | 213 | ||||
-rw-r--r-- | oncology/dpfhack_display/reverse/dump.py | 470 |
4 files changed, 0 insertions, 928 deletions
diff --git a/oncology/dpfhack_display/reverse/Makefile b/oncology/dpfhack_display/reverse/Makefile deleted file mode 100644 index d0a28b68..00000000 --- a/oncology/dpfhack_display/reverse/Makefile +++ /dev/null @@ -1,76 +0,0 @@ -# Makefile for DPF firmware analysis - - -CFLAGS = -g - -ASFLAGS = -plosgff - -ifndef DUMP - DUMP = -d -endif - -VERSION = 0.01develop - -AS = asx8051 - -INFILES = $(wildcard code*.in) $(wildcard dump*.in) $(wildcard data*.in) - -ASMFILES = $(INFILES:%.in=%.asm) -BINFILES = $(INFILES:%.in=%.bin) - -all: $(ASMFILES) - -show: - echo $(ASMFILES) - -all.asm: $(ASMFILES) - @echo concatenating all ASM files into $@ - @cat $(ASMFILES) > $@ - -%.rel : %.asm - $(AS) $(ASFLAGS) $< - -# Fixup format: -%.asm: %.d52 - @echo Generating $@ - @sed 's/\.equ/=/g;s/^\s*end/; END/g' $< > $@ - -test: main.o - $(CC) -o $@ $< - -clean: cleanimages - rm -f test *.ctl *.asm dump*.bin code*.bin *.d52 *.lst *.rel *.sym - -common.in: - ln -s ../common.in . - -dump%.ctl: dump%.in common.in - @cat $< common.in >$@ - -code_%.ctl: code_%.in common.in - @cat $< common.in >$@ - -data_%.ctl: data_%.in - @cp $< $@ - -%.d52: %.bin %.ctl - @d52 -p -b $(DUMP) -n $< # >/dev/null - -cleanimages: - rm -fr images/* - -RAWFILES = $(wildcard *.raw) - -IMAGES = $(RAWFILES:%.raw=images/%.png) - -images/%.png: %.raw - convert -size 128x128 -depth 1 gray:$< $@ - -images: $(IMAGES) - -dump: - PWD=`pwd`; BASE=`basename $$PWD`; \ - echo $$BASE; \ - python ../dump.py $$BASE full_image.bin - -.PHONY: dump diff --git a/oncology/dpfhack_display/reverse/README b/oncology/dpfhack_display/reverse/README deleted file mode 100644 index c70fa49e..00000000 --- a/oncology/dpfhack_display/reverse/README +++ /dev/null @@ -1,169 +0,0 @@ -Reverse engineering HOWTO ----------------------------------------------------------------------------- - -Here it is, the long awaited hacking howto for the AX206 DPFs. - -BIG FAT WARNING: You have to be able to read 8051 assembly code and you -HAVE TO know what it is doing. Otherwise you will likely brick your frame -and we will all laugh at you. - -Also you should know something about the SPI flash layout, have a look -at the m25p80 datasheets found all over the web. Basically you should -remember that the flashes are organized in sectors of 0x10000 size. - -Since the boot loader mode is a big secret, we have to exploit the hardware -somewhat to get into the "Developer Mode" (hacking is a ugly word). -To implement developer mode, we normally use the strategy to modify the -powerdown routine such that when USB is plugged in and you press and hold -MENU for a few seconds, it will enter the modified state. -This allows us to return to the original firmware by pressing RESET. - -To get started, you need a few tools and items: -- A dump of your DPFs firmware (look for fulldump.py script from the - dpfhack-*.tgz archive to create one) -- The d52 disassembler: http://www.8052.com/users/disasm/ -- Installed Python package - -The dump binary first needs to be split up into single modules. -Why modules? The memory of the AX206 isn't big enough to store a full -program, thus a bank switching technique is used. A bank switched call -looks like: - - mov a,#0x1e ; 13a2 74 1e t. - mov dptr,#mod31_1330; 13a4 90 13 30 ..0 - lcall tramp_jsr ; 13a7 12 19 38 ..8 - -The number moved into 'a' is the module number minus one. The dump.py -script analyses the code, so you will only have to look at the modXX_XXXX -function. This is the target function called in the according module. -The loading on demand and calling of the function is handled by -tramp_jsr(). - - -1. First, you copy the generated dump (full.bin) into a folder, like - dpf/reverse/new and rename it to full_dump.bin -2. Run the makefile: - > make -f ../Makefile dump" - You will end up with a number of - *.in files in the current directory if this was successful. -3. Run make again: - > make -f ../Makefile - Now you should have a few *.asm files in the working directory. -4. Identify the powerdown module. Normally, it helps to grep for p2up: - > grep p2up *.asm - That should list a module with number around 36 or 37. -5. The powerdown ROUTINE is the function that is called most often from many - modules, but most probably NOT called from module 1 (dump01). In many - cases, this turned out to be mod37_1330. - -WARNING: You have to make sure that this module does not live in sector -0x000000 of the flash (see "dump file offset" tag in the header of the -assembly file). If it lives in sector 0x000000, the described method -will NOT work and you will brick your DPF. - -5. Find the splash screen routine that is called from the powerdown. - This is normally the routine called at the beginning of the powerdown - routine and contains code like: - - mov G_lcd_cxH,a ; 1509 f5 78 ux - mov G_lcd_cyL,a ; 150b f5 79 uy - mov G_lcd_cyH,a ; 150d f5 7a uz - mov G_lcd_dxL,a ; 150f f5 7b u{ - -6. This routine you can patch. Take a p_start_*.s from an already hacked frame - and make sure you understand what is happening. Adapt the .org statements - to the locations where YOUR patched code can safely live. - -7. The final jump into the patched firmware occurs at the bottom of the - patch, looking like - - mov a,#(53 - 1) - mov dptr,#entry_addr - ljmp tramp_jmp - - The module number in here will be the number of the last module you - extracted, PLUS ONE - because we are gonna add an extra module. - For this, the jump table will need to be modified. - -8. We do not touch the original jump table, but make a copy of it (because - it lives in sector 0x000000). The jump table record for this extra module - will be stored in the end table tag which can be read clear text in the - dump00.asm as "-EndTbl-". Have a look at a jmptbl_*.s file, the .org - statement - i.e. the address offset - has to be the offset address of the - "-EndTbl-" string. - -9. Have a look at the hackit.py script. The critical function overwriting - data on the flash is the .patchSector() method, called like - - d.patchSector(start, flashaddr, hexfile) - - start is the relocation start address of the hexfile that the flash is - patched with, it is normally identical with the first .org offset specified - in the *.s file. - flashaddr is where it is stored on the flash. - hexfile is the intel hex data file the flash is patched with. - - The hackit.py framework will take care of the patching, so you merely - will need to add another configuration record in profiles.py. - - This is an example record: - -patch_pink = [ - (COPY, [0x000000, 0x3f0000]), # Copy sector 0 - (PATCH, [0x0, 0x3f0000], "jmptbl_pink.ihx"), - (BINARY, [0x0, 0x390000], "font4x8.bin"), - (PATCH, [0x0, 0x380000], "fw_pink.ihx"), - (37, [ 0x87f37fa6, 0xc8c55832, 0x27b13328 ] , "p_start_pink.ihx"), -] - - The first COPY statement tells hackit to make a copy of the first sector - to the specified address, which should be at the end of the flash. - The PATCH statements patch the given sector address with the hex file - specified. - The BINARY option just copies a plain binary to the given address. - Finally, the very critical patching of the powerdown routine. - The first number (here 37) is the module number of the powerdown routine - as identified by you. Then, a list of known CRC32 checksums follow. - If the sector to be patched here is unknown by its CRC32, it will refuse - to patch it and print out the non matching CRC32. - - When you are ABSOLUTELY sure your hack will not overwrite anything crucial, - you can insert this CRC32 as first number in the list. - -10. Did you do the paranoia check of all addresses and offsets, do you - understand where things will go? If in doubt, make a dry run with the - patchSector function on an empty/unused sector, preferrably at the - end of your flash. Then analyze the dump again. - -Finally, you can try hacking your DPF with the hackit.py. -Once it is hacked, it will again print out a non matching CRC32 if you -run the hackit.py again. This CRC32 you insert as LAST number (mycrc) -in the list: - - (37, [ original_crc, my_crc ] , "p_start_mine.ihx"), - -Now you can test your hack and publish the profiles.py on success. - ----------------------------------------------------------------------------- - -A few advices: - -REMEMBER: Never touch sector zero (address 0x000000 - 0x010000). Never ever. - -If you bricked your frame, don't throw it away YET. Maybe some day -we'll discover how the bootloader works. And you could still use the -display for tinkering. If you have any knowledge of the boot loader, -speak up! - -Don't ask us to help you with the hacking. Try it yourself or use one of -the DPFs that are known to work. -It can take a few months to learn 8051 assembly from scratch, -but don't give up, it will be a great learning experience and later -help you to get a good job :-) - -Just read the source, duke. - ----------------------------------------------------------------------------- -Brought to you by: - -- hackfin, the evil fish, and others diff --git a/oncology/dpfhack_display/reverse/common.in b/oncology/dpfhack_display/reverse/common.in deleted file mode 100644 index 8b64196c..00000000 --- a/oncology/dpfhack_display/reverse/common.in +++ /dev/null @@ -1,213 +0,0 @@ -; ---- END USER DEFINED ---- -; Common stuff: seems mostly common to all firmware. No guarantee -; about correctness of the global variables for all firmwares. -; Routines in ROM: - -l 001e rom_001e - -; might not exist: -l 0911 rom_0911 - -; Likely some JPEG decoding -l 0a27 rom_0a27 -l 0a85 rom_0a85 -l 0add rom_0add -l 0d38 rom_0d38 -l 0d65 rom_0d65 -l 0e02 rom_0e02 -l 0f5c rom_0f5c -l 0fa9 rom_0fa9 - -l 0c0a rom_bootload - -; Called from IRQ routines: -l 0e1a rom_0e1a -l 0e72 rom_0e72 -l 0ef4 rom_0ef4 -l 0f16 rom_0f16 - -; Writes a byte to the LCD port p3 -l 0f25 rom_lcdwrite -; Probably alternative write function -l 0f34 rom_0f34 - -; Called from bank switching code: -l 0fae rom_0fae - -s 0e00 common_xdata_0e00 -s 0e40 common_xdata_0e40 -s 0e80 common_xdata_0e80 -s 1600 common_xdata_0e00_cseg -; s 1640 common_xdata_0e40_cseg -; s 1680 common_xdata_0e80_cseg - -; Common functions that seem to be called from all modules: - -l 124a g_var0 -l 1280 lcd_setcontext - -; Those might differ between different DPF firmware -s 1800 common_usb_1800 -s 1818 common_usb_resume_1818 - -; Most important: module loader trampoline -l 1934 tramp_return -l 1938 tramp_jsr -l 193a tramp_jmp -l 193e tramp_dyn - -; Global register variables(flags): -; _oi: Probably initialized in OTP -; G_: Very likely global over all modules (not overlayed) -; g_: Global (shared) among some modules, may be overlayed -; i_: Accessed from IRQ handler -r 0f G_ptr0_oi -r 10 G_count0 -r 11 G_adcbufadr -r 12 G_count1 -r 13 G_curp_l -r 14 G_curp_h -r 19 G_seconds? -r 1b G_internal -r 1d G_var -r 1e G_button -r 1f G_bankno -r 20 i_G_f -r 21 G_adc_flags -r 22 G_irqh6_flags -r 25 G_usbflg -r 26 g_sector_h -r 27 g_sector_m -r 28 g_sector_l -r 29 flags_29 -r 2a flags_2a -r 2b flags_2b -r 2c flags_2c -r 2d flags_2d -r 2e flags_2e -r 2f flags_2f -r 73 G_language -; The following registers denote the LCD controller context area -; See lcd_setcontext() -r 77 G_lcd_cxL -r 78 G_lcd_cxH -r 79 G_lcd_cyL -r 7a G_lcd_cyH -r 7b G_lcd_dxL -r 7c G_lcd_dxH -r 7d G_lcd_dyL -r 7e G_lcd_dyH - -; AX206 SFRs - -f 86 dpcon -f 87 pcon - -f 91 _mulres0 -f 92 _mulres1 -f 93 _mulres2 -f 94 _mulres3 -f 9a _wkpnd -f 9b _wken -f 9c _wkedg -f a4 _pie -f a5 _ckcon -f a8 _ien0 -f b0 _p3 -f b1 _tmr0con -f b3 _tmr0cnt -f b4 _tmr0pr -f b5 _tmr0psr -f b8 _ip -f bb _wdtcon -f c0 _p4 -f c1 _tmr2con -f c2 _tmr2cntl -f c3 _tmr2cnth -f c4 _tmr2perl -f c5 _tmr2perh -f c6 _tmr2pwml -f c7 _tmr2pwmh -f c8 _usbcon0 -f c9 _usbdata -f ca _usbaddr -f d1 _rtcnt -f d2 _adccon -f d3 _adcbaud -f d4 _adcbufh -f d6 _spibaud -f d7 _spibuf -f d8 _spicon -f dc _adcbufl -f e1 _tmr1con -f e2 _tmr1cntl -f e3 _tmr1cnth -f e4 _tmr1perl -f e5 _tmr1perh -f e6 _tmr1pwml -f e7 _tmr1pwmh -f e8 _eif0 -f e9 _p0dir -f ea _p1dir -f eb _p2dir -f ec _p3dir -f ed _p4dir -f f1 _uartsta -f f2 _uartcon -f f3 _uartbaud -f f4 _uartbuf -f f8 _tmr3con -f f9 _p0up -f fa _p1up -f fb _p2up -f fc _p3up -f fd _p4up - -; Addressable bits: -m 00 i_G_f.0 -m 01 i_G_f.1 -m 02 i_G_f.adcready -m 03 i_G_f.usbon -m 04 i_G_f.usbact -m 05 i_G_f.wkup -m 06 i_G_f.6 -m 07 i_G_f.7 -m 0f G_rtc2_flags.7 -m 10 sflags.0 -m 11 i_G_flag.1 -m 12 g_sflags.2 -m 13 sflags.3 -m 14 sflags.4 -m 15 sflags.5 -m 16 sflags.6 -m 17 sflags.7 -m 18 G_flags23.0 -m 19 G_flags23.1 -m 1a G_flags23.2 -m 20 bit_24.0 -m 21 bit_24.1 -m 22 bit_24.2 -m 23 bit_24.3 -m 24 bit_24.4 -m 25 bit_24.5 -m 26 bit_24.6 -m 27 bit_24.7 -m 28 G_usbflg.0 -m 29 G_usbflg.1 -m 2a G_usbflg.2 -m 2b G_usbflg.3 -m 2c G_usbflg.4 -m 2d G_usbflg.5 - -; I/O mappings: -k 86 _BUT_MENU -k 90 _LCD_RST -k 91 _LCD_WR -k 92 _LCD_RD -k 94 _LCD_A0 -k a0 _SPI_CS -k a1 _LCD_CS -k ce _USB_DONE -k df _SPIPND -k fb _T3CP -k e8 _T0P diff --git a/oncology/dpfhack_display/reverse/dump.py b/oncology/dpfhack_display/reverse/dump.py deleted file mode 100644 index cbbc563b..00000000 --- a/oncology/dpfhack_display/reverse/dump.py +++ /dev/null @@ -1,470 +0,0 @@ -# DPF dump splitter -# <hackfin@section5.ch> -# -# Takes a binary dump of the DPF and splits it into the banked modules -# Usage: -# 1. First, simply run this script after having dumped your entire DPF -# into full_image.bin. It will generate a lot of dump* files. -# 2. Then analyze the addresses in dump00.asm. The code is loading more -# common code segments from other addresses. To extract this code, -# enhance or create a record in g_dpfs. Later on, we'll add some -# firmware version detection... -# - -import os -import sys -import struct -# import scantool - -IMGLEN1 = 128 * 128 / 8 -IMGLEN16 = 128 * 128 * 2 - -# menu table in code memory: -table_addr = 0x1600 - -g_dpfs = { - 'default' : [ - [], [], [], [], - ], - 'silver2' : [ - [ - (0x2f0, 0x1934, 0x19f2), - (0x3ae, 0x1003, 0x1270), - (0x6a0, 0x1280, 0x12bc), - ], - [], - [], - [], - ], - 'black' : [ - [ - (0x2e0, 0x1934, 0x19f2), - (0x39e, 0x1003, 0x1270), - (0x682, 0x1280, 0x12d0), - ], - [], - [], - [], - ], - 'white' : [ - [ - (0x2f0, 0x1934, 0x19f2), - (0x3ae, 0x1003, 0x1270), - (0x69c, 0x1280, 0x12d0), - (0x2fec, 0x1800, 0x189d), - ], - [], - [], - [], - ], - 'visualland' : [ - [ - (0x2c0, 0x1934, 0x19f2), - (0x37e, 0x1003, 0x1270), - (0x662, 0x1280, 0x12d0), - ], - [], - [], - [], - ], - 'blue' : [ - [ # special code segments: fileoffset, start, end - (0x2c0, 0x1934, 0x19f2), - (0x37e, 0x1003, 0x1270), - (0x662, 0x1280, 0x12d8), - (0x3474, 0x1800, 0x189d), - - # Dynamic jump table: - (0x0e54, 0xce7 + 0x800, 0xce7 + 0x800 + 0x2c2), - ], - [ # images: name, fileoffset, rel_start, rel_end - ("img0", 0x55bbb, 0x0, IMGLEN16), - ("img1", 0x4eb89, 0x0, IMGLEN1), - ("usb_conn", 0x4ec89, 0x0, 0x80 * 0x48), - ("menu0", 0x4e289, 0x0, IMGLEN1), - ("menu1", 0x4e389, 0x0, IMGLEN1), - ("menu2", 0x4ee89, 0x0, IMGLEN1), - ("menu3", 0x4e489, 0x0, IMGLEN1), - ("menu4", 0x4e589, 0x0, IMGLEN1), - ("menu5", 0x4e789, 0x0, IMGLEN1), - ("menu7", 0x4e989, 0x0, IMGLEN1), - ("menu8", 0x4ea89, 0x0, IMGLEN1), - ("menu9", 0x4e889, 0x0, IMGLEN1), - ("mainmenu", 0x4c7f9, 0x0, IMGLEN1), - ("mainmenu-ch", 0x4f589, 0x0, IMGLEN1), - ("jpgx", 0x4b744, 0x0, IMGLEN16), # mod13 - ("menu0", 0x4daf9, 0x0, IMGLEN1), - ], - [ # data buffers: fileoffset, start, end - (0x1b02 + 4, table_addr, table_addr + 0x28a), # Menu bitmap indices? - (0x1874 + 4, table_addr, table_addr + 0x28a), # Menu bitmap indices? - (0x53557, 0xfd7, 0xfd7 + 64), - ], - [ # Dynamic applet load: reloc, fileoffset, , size - (0x14e7, 0x0e54, 15 ) - ] - ], - 'silver' : [ - [ # special code segments: fileoffset, start, end - (0x2c0, 0x1934, 0x19f2), - (0x37e, 0x1003, 0x1270), - (0x662, 0x1280, 0x12d8), - ], - [], - [], - [], - ], - 'pink' : [ - [ # code segments: - (0x2f0, 0x1934, 0x19f2), - (0x3ae, 0x1003, 0x1270), - (0x69c, 0x1280, 0x12d1), - (0x2fc0, 0x1800, 0x189d), # USB main loop, -> mod18_145b - - (0x0e88, 0xce7 + 0x800, 0xce7 + 0x800 + 0x2c2), - ], - [ # images - ("img0", 0x5320b, 0x0, IMGLEN16), - ("img1", 0x54f4b, 0x0, IMGLEN1), - ("lowpower", 0x51a3b, 0x0, IMGLEN1), - ("img2", 0x4c244, 0x0, IMGLEN16), - ("title", 0x4f03b, 0x0, IMGLEN1), - ("title", 0x4f13b, 0x0, IMGLEN1), - ("title", 0x4f23b, 0x0, IMGLEN1), - ], - # data: - [], - # dynamic: - [ - (0x14e7, 0x0e88, 15 ) - ] - ], - 'focal' : [ - [ # code segments: - (0x2e0, 0x1934, 0x19f2), - (0x39e, 0x1003, 0x1279), - (0x682, 0x1280, 0x12f3), - (0x3056, 0x1800, 0x189d), # USB main loop, -> mod17_145b - - (0x0e88, 0xce7 + 0x800, 0xce7 + 0x800 + 0x2c2), - ], - [ # images - ("img0", 0x5320b, 0x0, IMGLEN16), - ], - # data: - [], - # dynamic: - [ - (0x14e7, 0x0e88, 15 ) - ] - ], - 'pearl' : [ - [ # code segments: - (0x2e0, 0x1934, 0x19f2), - (0x39e, 0x1003, 0x1279), - (0x682, 0x1280, 0x12f3), - (0x3056, 0x1800, 0x189d), # USB main loop, -> mod17_145b - - (0x0e88, 0xce7 + 0x800, 0xce7 + 0x800 + 0x2c2), - ], - [ # images - ("img0", 0x5320b, 0x0, IMGLEN16), - ], - # data: - [], - # dynamic: - [ - (0x14e7, 0x0e88, 15 ) - ] - ], - 'micca' : [ - [ # code segments: - (0x2e0, 0x1934, 0x19f2), - (0x39e, 0x1003, 0x1279), - (0x682, 0x1280, 0x12f3), - (0x3056, 0x1800, 0x189d), # USB main loop, -> mod17_145b - - (0x0e88, 0xce7 + 0x800, 0xce7 + 0x800 + 0x2c2), - ], - [ # images - ("img0", 0x5320b, 0x0, IMGLEN16), - ], - # data: - [], - # dynamic: - [ - (0x14e7, 0x0e88, 15 ) - ] - ], - -} - -RET = chr(0x22) -LJMP = chr(0x02) -LCALL = chr(0x12) - -bswap = lambda x: ( (x >> 8) & 0xff ) | ((x << 8) & 0xff00) - -class ProcEntry: - format = "<HHI" - - def __init__(self): - self.start = 0 - self.end = 0 - self.offset = 0 - self.size = struct.calcsize(self.format) - - def fromBuffer(self, b): - start, end, self.offset, = struct.unpack(self.format, b) - self.start = bswap(start) - self.end = bswap(end) - - - def __repr__(self): - return "< %04x, %04x, %08x >" % (self.start, self.end, self.offset) - -def extract_code(data, fname): - out = data - outf = open(fname, "w") - outf.write(out) - outf.close() - -def write_ctl(name, offset, fileoffset, size = 0): - outf = open(name, "w") - outf.write("; control file -- autogenerated\n") - outf.write("; file offset: %08x\n" % fileoffset) - outf.write("# %04x\n" % offset) - outf.write("# %04x dump file offset: %08x\n" % (offset, fileoffset)) - outf.write("o %04x\n" % offset) - if size: - outf.write("b %04x-%04x\n" % (offset, offset + size - 1)) - outf.close() - -def exists(file): - try: - a = os.stat(file) - return 1 - except: - return 0 - -def generate_ctl(which, prefix, record, entries): - fname = "%s%02d.in" % (prefix, which) - if exists(fname): - print "%s exists, not creating" % fname - return - - outf = open(fname, "w") - outf.write("; control file for %s%d.bin -- autogenerated\n" % (prefix, which)) - outf.write("; file offset: %08x\n" % int(record.offset)) - offset = 0x800 + record.start - outf.write("# %04x ----- SNIP : mod%d -----\n" % (offset, which)) - outf.write("# %04x\n" % offset) - outf.write("# %04x dump file offset: %08x\n" % (offset, int(record.offset))) - outf.write("o %04x\n" % offset) - for i in entries: - outf.write("%s\n" % i) - outf.close() - -def build_tab(data, start, end): - l = [] - - offset = start - - i = 0 - - while 1: - e = ProcEntry() - d = data[offset : offset + e.size] - e.fromBuffer(d) - if d == "-EndTbl-" or offset > end: - break - offset += e.size - l.append(e) - i += 1 - - return l - -val = lambda x: ord(x) - -# Some codes to scan for: - -scan_banksw = [ - 0x74, val, 0x90, val, val, val, 0x19, val -] - -scan_loadcode = [ - 0x90, val, val, 0x7b, val, 0x7c, val, 0x7d, val, 0x7e, val , 0x7f, val -] - - -# Stolen from scantool: -class Scanner: - def __init__(self, data, seq): - self.data = data - self.args = [] - self.scansequence = seq - - def scan(self, context, cb): - p = 0 - n = 0 - while p < len(self.data): - if type(self.scansequence[n]) == type(val): - args.append(val(data[p])) - n += 1 - elif chr(self.scansequence[n]) == data[p]: - n += 1 - else: - n = 0 - args = [] - - if n == len(self.scansequence): - cb(context, args, p) - n = 0 - args = [] - - p += 1 - -def make_symentry(context, args, p): - e, offset = context - if args[3] in [0x12, 0x02]: - e.append("x %04x mod%d_%04x" % (offset + p - 4, args[0] + 1, (args[1] << 8) + args[2])) - - -# TODO: Use scantool stuff -def analyze(data, offset): - e = [] - - scanner = Scanner(data, scan_loadcode) - scanner.scan((e, offset), make_symentry) - - return e - -def make_record(context, args, p): - e, rec = context - r = args[0] << 8 | args[1] - e.append("s %04x code_%04x" % (r, r + 0x800)) - r = args[2] << 8 | args[3] - s = (args[4] << 16) | (args[5] << 8) | args[6] - e.append("# %04x load code from %06x to xmem:%04x" % (rec.start + 0x800 + p - 9, s, r)) - - -def analyze_bootblock(data): - rec = ProcEntry() - - e = [] - s = struct.unpack(">H", data[5:7])[0] # start code in flash - reloc = struct.unpack(">H", data[2:4])[0] # relocation - - print hex(reloc), hex(s) - - rec.start = reloc - s - 0x800 - rec.offset = s - - offset = reloc - s - - e.append("b %04x-%04x" % (offset, (reloc - 1))) - e.append("l %04x start" % reloc) - e.append("l %04x jumptable" % (offset + 0x88)) - - # Just copy the scan hack -- no more scantool - scanner = Scanner(data, scan_loadcode) - scanner.scan((e, rec), make_record) - - return rec, e - - -def write_rawimage(d, fname): - outf = open(fname, "wb") - outf.write(d) - outf.close() - -try: - # Choose here which DPF to dump: - dpf = g_dpfs[sys.argv[1]] - f = open(sys.argv[2], "r") -except (KeyError, IndexError): - print "Usage: %s <frameid>" % sys.argv[0] - print "where frameid is one of:" - for i in g_dpfs.keys(): - print " ", i - print "No DPF specified given, running basic dump" - dpf = g_dpfs['default'] - f = open("full_image.bin", "r") - - -data = f.read() -f.close() - - -for i in dpf[0]: - o, start, end = i - end += 1 - d = data[o:o + end - start] - extract_code(d, "code_%04x.bin" % start) - write_ctl("code_%04x.ctl" % start, start, o) - -for i in dpf[1]: - name, o, start, end = i - end += 1 - d = data[o:o + end - start] - write_rawimage(d, "img_%s-%06x.raw" % (name, o)) - -for i in dpf[2]: - o, start, end = i - end += 1 - d = data[o:o + end - start] - extract_code(d, "data_%04x.bin" % o) - write_ctl("data_%04x.ctl" % o, start, o, end - start) - -for i in dpf[3]: - codeoffs, foffs, n = i - c0 = codeoffs - c1 = codeoffs - foffs - labels = {} - for j in range(n): - sz = [0,0] - offs = [0, 0] - o = foffs + j * 8 - d = data[o:o + 8] - - sz[0] = ord(d[0]) + (ord(d[1]) << 8) - offs[0] = foffs + ord(d[2]) + (ord(d[3]) << 8) - sz[1] = ord(d[4]) + (ord(d[5]) << 8) - offs[1] = foffs + ord(d[6]) + (ord(d[7]) << 8) - - p = (c0 + j * 8 + 7, offs[0], sz[0], offs[1], sz[1]) - print "! %04x dyn_%04x[%d], dyn_%04x[%d]" % p - labels[c1 + offs[0]] = "dyn_%04x" % offs[0] - labels[c1 + offs[1]] = "dyn_%04x" % offs[1] - for j in labels.keys(): - print "l %04x %s" % (j, labels[j]) - -format = ">HHBH" -s = struct.unpack(format, data[:7]) -imem_loadaddr, code_startaddr, dummy, startcode = s - -l = build_tab(data, 0x88, startcode) - -print 80 * "-" - -start = l[0].offset -d = data[0:start] -extract_code(d, "dump00.bin") -rec, entries = analyze_bootblock(d) -generate_ctl(0, "dump", rec, entries) - -index = 1 -for i in l: - size = i.end - i.start - d = data[i.offset: i.offset + size] - print "[dump%d] %04x %04x %08x (%d)" % (index, i.start, i.end, i.offset, size) - extract_code(d, "dump%02d.bin" % index) - entries = analyze(d, i.start + 0x800) - generate_ctl(index, "dump", i, entries) - index += 1 - - -# No scantool here. -# scantool.guess(scantool.MC8052, data, "dump") - - |