1
0
mirror of https://github.com/Optiboot/optiboot.git synced 2025-07-04 16:42:25 +03:00

Handle writing to NRWW locations correctly.

This commit is contained in:
cathedrow
2010-05-11 18:38:17 +00:00
parent a9f28b5f31
commit c49b9cc7b3
24 changed files with 2138 additions and 1920 deletions

View File

@ -63,6 +63,16 @@ override LDFLAGS = -Wl,$(LDSECTION) -Wl,--relax -nostartfiles
OBJCOPY = avr-objcopy OBJCOPY = avr-objcopy
OBJDUMP = avr-objdump OBJDUMP = avr-objdump
# Test platforms
# Virtual boot block test
virboot328: TARGET = atmega328
virboot328: MCU_TARGET = atmega328p
virboot328: CFLAGS += '-DLED_START_FLASHES=3' '-DBAUD_RATE=115200' '-DVIRTUAL_BOOT
virboot328: AVR_FREQ = 16000000L
virboot328: LDSECTION = --section-start=.text=0x7e00
virboot328: $(PROGRAM)_atmega328.hex
virboot328: $(PROGRAM)_atmega328.lst
# 20MHz clocked platforms # 20MHz clocked platforms
# #
# These are capable of 230400 baud, or 115200 baud on PC (Arduino Avrdude issue) # These are capable of 230400 baud, or 115200 baud on PC (Arduino Avrdude issue)

View File

@ -184,10 +184,21 @@ void uartDelay() __attribute__ ((naked));
#endif #endif
void appStart() __attribute__ ((naked)); void appStart() __attribute__ ((naked));
#if defined(__AVR_ATmega168__) || defined(__AVR_ATmega328P__) || (__AVR_ATmega644P__) || defined(__AVR_ATtiny84__) #if defined(__AVR_ATmega168__)
#define RAMSTART (0x100) #define RAMSTART (0x100)
#define NRWWSTART (0x3800)
#elif defined(__AVR_ATmega328P__)
#define RAMSTART (0x100)
#define NRWWSTART (0x7000)
#elif defined (__AVR_ATmega644P__)
#define RAMSTART (0x100)
#define NRWWSTART (0xE000)
#elif defined(__AVR_ATtiny84__)
#define RAMSTART (0x100)
#define NRWWSTART (0x0000)
#elif defined(__AVR_ATmega1280__) #elif defined(__AVR_ATmega1280__)
#define RAMSTART (0x200) #define RAMSTART (0x200)
#define NRWWSTART (0xE000)
#endif #endif
/* C zero initialises all global variables. However, that requires */ /* C zero initialises all global variables. However, that requires */
@ -293,14 +304,18 @@ int main(void) {
getLen(); getLen();
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
while (--length); while (--length);
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();

View File

@ -1,34 +1,36 @@
:020000021000EC :020000021000EC
:10FC000085E08093810082E08093C00088E180934A :10FC000085E08093810082E08093C00088E180934A
:10FC1000C10086E08093C20080E18093C40084B775 :10FC1000C10086E08093C20080E18093C40084B775
:10FC200014BE81FFCFD08DE0C7D0279A86E020E3B5 :10FC200014BE81FFDED08DE0D6D0279A86E020E397
:10FC30003CEF91E0309385002093840096BBB09B0D :10FC30003CEF91E0309385002093840096BBB09B0D
:10FC4000FECF1F9AA8958150A9F7DD24D394A5E093 :10FC4000FECF1F9AA8958150A9F7EE24E394A5E072
:10FC5000EA2EF1E1FF2EA3D0813419F481E0BDD06A :10FC5000DA2EF1E1FF2EB2D0813419F481E0CCD05C
:10FC60008CC0823411F484E103C0853419F485E03A :10FC60009BC0823411F484E103C0853419F485E02B
:10FC7000B4D08AC08535A9F492D0082F10E08FD077 :10FC7000C3D099C08535A9F4A1D0082F10E09ED03B
:10FC800090E0982F8827802B912B292F221F222745 :10FC800090E0982F8827802B912B292F221F222745
:10FC9000221F2BBF880F991F9093010480930004AB :10FC9000221F2BBF880F991F9093010480930004AB
:10FCA00072C0863529F484E098D080E070D06CC0B2 :10FCA00081C0863529F484E0A7D080E07FD07BC076
:10FCB000843609F03FC07BD0E0910004F09101044C :10FCB000843609F04EC08AD0E0910004F09101042E
:10FCC00083E087BFE895C0E0D2E069D08993809156 :10FCC00080EEE030F80718F483E087BFE895C0E0E5
:10FCD00002048150809302048823B9F778D007B6D4 :10FCD000D2E074D089938091020481508093020411
:10FCE00000FCFDCF4091000450910104A0E0B2E07F :10FCE0008823B9F7E0910004F091010480EEE03040
:10FCF0002C9130E011968C91119790E0982F8827E5 :10FCF000F80718F083E087BFE89578D007B600FCD6
:10FD0000822B932B1296FA010C01D7BEE895112491 :10FD0000FDCF4091000450910104A0E0B2E02C919D
:10FD10004E5F5F4FF3E0A030BF0751F7E091000462 :10FD100030E011968C91119790E0982F8827822BD4
:10FD2000F0910104E7BEE89507B600FCFDCFF7BEF1 :10FD2000932B1296FA010C01E7BEE89511244E5F61
:10FD3000E8952AC08437D1F43AD049D0E091000444 :10FD30005F4FF3E0A030BF0751F7E0910004F0916E
:10FD4000F0910104E6918E2F22D0809100049091D1 :10FD40000104D7BEE89507B600FCFDCFF7BEE895E5
:10FD500001040196909301048093000480910204B1 :10FD50002AC08437D1F43AD049D0E0910004F09120
:10FD6000815080930204882349F70EC0853739F407 :10FD60000104E6918E2F22D080910004909101042D
:10FD70002ED08EE10CD087E90AD083E097CF813571 :10FD700001969093010480930004809102048150C5
:10FD800011F488E019D023D080E101D064CF982FFE :10FD800080930204882349F70EC0853739F42ED0BA
:10FD90008091C00085FFFCCF9093C6000895A89580 :10FD90008EE10CD087E90AD083E088CF813511F459
:10FDA0008091C00087FFFCCF8091C6000895F7DFE7 :10FDA00088E019D023D080E101D055CF982F8091E1
:10FDB000F6DF80930204F3CFE0E6F0E098E1908371 :10FDB000C00085FFFCCF9093C6000895A895809160
:10FDC0008083089580E0F8DFEE27FF270994E7DFBE :10FDC000C00087FFFCCF8091C6000895F7DFF6DF03
:10FDD000803209F0F7DF84E1DACF1F93182FDFDFDD :10FDD00080930204F3CFE0E6F0E098E19083808323
:0AFDE0001150E9F7F4DF1F910895B8 :10FDE000089580E0F8DFEE27FF270994E7DF8032EF
:10FDF00009F0F7DF84E1DACF1F93182FDFDF11500E
:08FE0000E9F7F4DF1F910895FA
:040000031000FC00ED :040000031000FC00ED
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_atmega1280.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001ea 0001fc00 0001fc00 00000054 2**1 0 .text 00000208 0001fc00 0001fc00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 0000023e 2**0 1 .debug_aranges 00000028 00000000 00000000 0000025c 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000266 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000284 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000277 00000000 00000000 000002d0 2**0 3 .debug_info 00000278 00000000 00000000 000002ee 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001a1 00000000 00000000 00000547 2**0 4 .debug_abbrev 000001a1 00000000 00000000 00000566 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003eb 00000000 00000000 000006e8 2**0 5 .debug_line 000003f3 00000000 00000000 00000707 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad4 2**2 6 .debug_frame 00000090 00000000 00000000 00000afc 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000135 00000000 00000000 00000b64 2**0 7 .debug_str 00000135 00000000 00000000 00000b8c 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001b1 00000000 00000000 00000c99 2**0 8 .debug_loc 000001b1 00000000 00000000 00000cc1 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e4a 2**0 9 .debug_ranges 00000068 00000000 00000000 00000e72 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
1fc20: 14 be out 0x34, r1 ; 52 1fc20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
1fc22: 81 ff sbrs r24, 1 1fc22: 81 ff sbrs r24, 1
1fc24: cf d0 rcall .+414 ; 0x1fdc4 <appStart> 1fc24: de d0 rcall .+444 ; 0x1fde2 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
1fc26: 8d e0 ldi r24, 0x0D ; 13 1fc26: 8d e0 ldi r24, 0x0D ; 13
1fc28: c7 d0 rcall .+398 ; 0x1fdb8 <watchdogConfig> 1fc28: d6 d0 rcall .+428 ; 0x1fdd6 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -118,8 +118,8 @@ void watchdogReset() {
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
1fc4a: dd 24 eor r13, r13 1fc4a: ee 24 eor r14, r14
1fc4c: d3 94 inc r13 1fc4c: e3 94 inc r14
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
addrPtr += 2; addrPtr += 2;
} while (--ch); } while (--ch);
@ -127,7 +127,7 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
1fc4e: a5 e0 ldi r26, 0x05 ; 5 1fc4e: a5 e0 ldi r26, 0x05 ; 5
1fc50: ea 2e mov r14, r26 1fc50: da 2e mov r13, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
@ -141,7 +141,7 @@ void watchdogReset() {
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
1fc56: a3 d0 rcall .+326 ; 0x1fd9e <getch> 1fc56: b2 d0 rcall .+356 ; 0x1fdbc <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
1fc58: 81 34 cpi r24, 0x41 ; 65 1fc58: 81 34 cpi r24, 0x41 ; 65
@ -149,8 +149,8 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
1fc5c: 81 e0 ldi r24, 0x01 ; 1 1fc5c: 81 e0 ldi r24, 0x01 ; 1
1fc5e: bd d0 rcall .+378 ; 0x1fdda <verifySpace+0xc> 1fc5e: cc d0 rcall .+408 ; 0x1fdf8 <verifySpace+0xc>
1fc60: 8c c0 rjmp .+280 ; 0x1fd7a <main+0x17a> 1fc60: 9b c0 rjmp .+310 ; 0x1fd98 <main+0x198>
putch(0x03); putch(0x03);
} }
else if(ch == STK_SET_DEVICE) { else if(ch == STK_SET_DEVICE) {
@ -167,8 +167,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
1fc6e: 85 e0 ldi r24, 0x05 ; 5 1fc6e: 85 e0 ldi r24, 0x05 ; 5
1fc70: b4 d0 rcall .+360 ; 0x1fdda <verifySpace+0xc> 1fc70: c3 d0 rcall .+390 ; 0x1fdf8 <verifySpace+0xc>
1fc72: 8a c0 rjmp .+276 ; 0x1fd88 <main+0x188> 1fc72: 99 c0 rjmp .+306 ; 0x1fda6 <main+0x1a6>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
1fc74: 85 35 cpi r24, 0x55 ; 85 1fc74: 85 35 cpi r24, 0x55 ; 85
@ -176,11 +176,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
1fc78: 92 d0 rcall .+292 ; 0x1fd9e <getch> 1fc78: a1 d0 rcall .+322 ; 0x1fdbc <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
1fc7a: 08 2f mov r16, r24 1fc7a: 08 2f mov r16, r24
1fc7c: 10 e0 ldi r17, 0x00 ; 0 1fc7c: 10 e0 ldi r17, 0x00 ; 0
1fc7e: 8f d0 rcall .+286 ; 0x1fd9e <getch> 1fc7e: 9e d0 rcall .+316 ; 0x1fdbc <getch>
1fc80: 90 e0 ldi r25, 0x00 ; 0 1fc80: 90 e0 ldi r25, 0x00 ; 0
1fc82: 98 2f mov r25, r24 1fc82: 98 2f mov r25, r24
1fc84: 88 27 eor r24, r24 1fc84: 88 27 eor r24, r24
@ -201,7 +201,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
1fc98: 90 93 01 04 sts 0x0401, r25 1fc98: 90 93 01 04 sts 0x0401, r25
1fc9c: 80 93 00 04 sts 0x0400, r24 1fc9c: 80 93 00 04 sts 0x0400, r24
1fca0: 72 c0 rjmp .+228 ; 0x1fd86 <main+0x186> 1fca0: 81 c0 rjmp .+258 ; 0x1fda4 <main+0x1a4>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -210,324 +210,341 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
1fca6: 84 e0 ldi r24, 0x04 ; 4 1fca6: 84 e0 ldi r24, 0x04 ; 4
1fca8: 98 d0 rcall .+304 ; 0x1fdda <verifySpace+0xc> 1fca8: a7 d0 rcall .+334 ; 0x1fdf8 <verifySpace+0xc>
putch(0x00); putch(0x00);
1fcaa: 80 e0 ldi r24, 0x00 ; 0 1fcaa: 80 e0 ldi r24, 0x00 ; 0
1fcac: 70 d0 rcall .+224 ; 0x1fd8e <putch> 1fcac: 7f d0 rcall .+254 ; 0x1fdac <putch>
1fcae: 6c c0 rjmp .+216 ; 0x1fd88 <main+0x188> 1fcae: 7b c0 rjmp .+246 ; 0x1fda6 <main+0x1a6>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
1fcb0: 84 36 cpi r24, 0x64 ; 100 1fcb0: 84 36 cpi r24, 0x64 ; 100
1fcb2: 09 f0 breq .+2 ; 0x1fcb6 <main+0xb6> 1fcb2: 09 f0 breq .+2 ; 0x1fcb6 <main+0xb6>
1fcb4: 3f c0 rjmp .+126 ; 0x1fd34 <main+0x134> 1fcb4: 4e c0 rjmp .+156 ; 0x1fd52 <main+0x152>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
1fcb6: 7b d0 rcall .+246 ; 0x1fdae <getLen> 1fcb6: 8a d0 rcall .+276 ; 0x1fdcc <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
1fcb8: e0 91 00 04 lds r30, 0x0400 1fcb8: e0 91 00 04 lds r30, 0x0400
1fcbc: f0 91 01 04 lds r31, 0x0401 1fcbc: f0 91 01 04 lds r31, 0x0401
1fcc0: 83 e0 ldi r24, 0x03 ; 3 1fcc0: 80 ee ldi r24, 0xE0 ; 224
1fcc2: 87 bf out 0x37, r24 ; 55 1fcc2: e0 30 cpi r30, 0x00 ; 0
1fcc4: e8 95 spm 1fcc4: f8 07 cpc r31, r24
1fcc6: c0 e0 ldi r28, 0x00 ; 0 1fcc6: 18 f4 brcc .+6 ; 0x1fcce <main+0xce>
1fcc8: d2 e0 ldi r29, 0x02 ; 2 1fcc8: 83 e0 ldi r24, 0x03 ; 3
1fcca: 87 bf out 0x37, r24 ; 55
1fccc: e8 95 spm
1fcce: c0 e0 ldi r28, 0x00 ; 0
1fcd0: d2 e0 ldi r29, 0x02 ; 2
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
1fcca: 69 d0 rcall .+210 ; 0x1fd9e <getch> 1fcd2: 74 d0 rcall .+232 ; 0x1fdbc <getch>
1fccc: 89 93 st Y+, r24 1fcd4: 89 93 st Y+, r24
while (--length); while (--length);
1fcce: 80 91 02 04 lds r24, 0x0402 1fcd6: 80 91 02 04 lds r24, 0x0402
1fcd2: 81 50 subi r24, 0x01 ; 1 1fcda: 81 50 subi r24, 0x01 ; 1
1fcd4: 80 93 02 04 sts 0x0402, r24 1fcdc: 80 93 02 04 sts 0x0402, r24
1fcd8: 88 23 and r24, r24 1fce0: 88 23 and r24, r24
1fcda: b9 f7 brne .-18 ; 0x1fcca <main+0xca> 1fce2: b9 f7 brne .-18 ; 0x1fcd2 <main+0xd2>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
1fce4: e0 91 00 04 lds r30, 0x0400
1fce8: f0 91 01 04 lds r31, 0x0401
1fcec: 80 ee ldi r24, 0xE0 ; 224
1fcee: e0 30 cpi r30, 0x00 ; 0
1fcf0: f8 07 cpc r31, r24
1fcf2: 18 f0 brcs .+6 ; 0x1fcfa <main+0xfa>
1fcf4: 83 e0 ldi r24, 0x03 ; 3
1fcf6: 87 bf out 0x37, r24 ; 55
1fcf8: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
1fcdc: 78 d0 rcall .+240 ; 0x1fdce <verifySpace> 1fcfa: 78 d0 rcall .+240 ; 0x1fdec <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
1fcde: 07 b6 in r0, 0x37 ; 55 1fcfc: 07 b6 in r0, 0x37 ; 55
1fce0: 00 fc sbrc r0, 0 1fcfe: 00 fc sbrc r0, 0
1fce2: fd cf rjmp .-6 ; 0x1fcde <main+0xde> 1fd00: fd cf rjmp .-6 ; 0x1fcfc <main+0xfc>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
1fce4: 40 91 00 04 lds r20, 0x0400 1fd02: 40 91 00 04 lds r20, 0x0400
1fce8: 50 91 01 04 lds r21, 0x0401 1fd06: 50 91 01 04 lds r21, 0x0401
1fcec: a0 e0 ldi r26, 0x00 ; 0 1fd0a: a0 e0 ldi r26, 0x00 ; 0
1fcee: b2 e0 ldi r27, 0x02 ; 2 1fd0c: b2 e0 ldi r27, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
1fcf0: 2c 91 ld r18, X 1fd0e: 2c 91 ld r18, X
1fcf2: 30 e0 ldi r19, 0x00 ; 0 1fd10: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
1fcf4: 11 96 adiw r26, 0x01 ; 1 1fd12: 11 96 adiw r26, 0x01 ; 1
1fcf6: 8c 91 ld r24, X 1fd14: 8c 91 ld r24, X
1fcf8: 11 97 sbiw r26, 0x01 ; 1 1fd16: 11 97 sbiw r26, 0x01 ; 1
1fcfa: 90 e0 ldi r25, 0x00 ; 0 1fd18: 90 e0 ldi r25, 0x00 ; 0
1fcfc: 98 2f mov r25, r24 1fd1a: 98 2f mov r25, r24
1fcfe: 88 27 eor r24, r24 1fd1c: 88 27 eor r24, r24
1fd00: 82 2b or r24, r18 1fd1e: 82 2b or r24, r18
1fd02: 93 2b or r25, r19 1fd20: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
1fd04: 12 96 adiw r26, 0x02 ; 2 1fd22: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
1fd06: fa 01 movw r30, r20 1fd24: fa 01 movw r30, r20
1fd08: 0c 01 movw r0, r24 1fd26: 0c 01 movw r0, r24
1fd0a: d7 be out 0x37, r13 ; 55 1fd28: e7 be out 0x37, r14 ; 55
1fd0c: e8 95 spm 1fd2a: e8 95 spm
1fd0e: 11 24 eor r1, r1 1fd2c: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
1fd10: 4e 5f subi r20, 0xFE ; 254 1fd2e: 4e 5f subi r20, 0xFE ; 254
1fd12: 5f 4f sbci r21, 0xFF ; 255 1fd30: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
1fd14: f3 e0 ldi r31, 0x03 ; 3 1fd32: f3 e0 ldi r31, 0x03 ; 3
1fd16: a0 30 cpi r26, 0x00 ; 0 1fd34: a0 30 cpi r26, 0x00 ; 0
1fd18: bf 07 cpc r27, r31 1fd36: bf 07 cpc r27, r31
1fd1a: 51 f7 brne .-44 ; 0x1fcf0 <main+0xf0> 1fd38: 51 f7 brne .-44 ; 0x1fd0e <main+0x10e>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
1fd1c: e0 91 00 04 lds r30, 0x0400 1fd3a: e0 91 00 04 lds r30, 0x0400
1fd20: f0 91 01 04 lds r31, 0x0401 1fd3e: f0 91 01 04 lds r31, 0x0401
1fd24: e7 be out 0x37, r14 ; 55 1fd42: d7 be out 0x37, r13 ; 55
1fd26: e8 95 spm 1fd44: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
1fd28: 07 b6 in r0, 0x37 ; 55 1fd46: 07 b6 in r0, 0x37 ; 55
1fd2a: 00 fc sbrc r0, 0 1fd48: 00 fc sbrc r0, 0
1fd2c: fd cf rjmp .-6 ; 0x1fd28 <main+0x128> 1fd4a: fd cf rjmp .-6 ; 0x1fd46 <main+0x146>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
1fd2e: f7 be out 0x37, r15 ; 55 1fd4c: f7 be out 0x37, r15 ; 55
1fd30: e8 95 spm 1fd4e: e8 95 spm
1fd32: 2a c0 rjmp .+84 ; 0x1fd88 <main+0x188> 1fd50: 2a c0 rjmp .+84 ; 0x1fda6 <main+0x1a6>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
1fd34: 84 37 cpi r24, 0x74 ; 116 1fd52: 84 37 cpi r24, 0x74 ; 116
1fd36: d1 f4 brne .+52 ; 0x1fd6c <main+0x16c> 1fd54: d1 f4 brne .+52 ; 0x1fd8a <main+0x18a>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
1fd38: 3a d0 rcall .+116 ; 0x1fdae <getLen> 1fd56: 3a d0 rcall .+116 ; 0x1fdcc <getLen>
verifySpace(); verifySpace();
1fd3a: 49 d0 rcall .+146 ; 0x1fdce <verifySpace> 1fd58: 49 d0 rcall .+146 ; 0x1fdec <verifySpace>
#ifdef __AVR_ATmega1280__ #ifdef __AVR_ATmega1280__
// do putch(pgm_read_byte_near(address++)); // do putch(pgm_read_byte_near(address++));
// while (--length); // while (--length);
do { do {
uint8_t result; uint8_t result;
__asm__ ("elpm %0,Z\n":"=r"(result):"z"(address)); __asm__ ("elpm %0,Z\n":"=r"(result):"z"(address));
1fd3c: e0 91 00 04 lds r30, 0x0400 1fd5a: e0 91 00 04 lds r30, 0x0400
1fd40: f0 91 01 04 lds r31, 0x0401 1fd5e: f0 91 01 04 lds r31, 0x0401
1fd44: e6 91 elpm r30, Z+ 1fd62: e6 91 elpm r30, Z+
putch(result); putch(result);
1fd46: 8e 2f mov r24, r30 1fd64: 8e 2f mov r24, r30
1fd48: 22 d0 rcall .+68 ; 0x1fd8e <putch> 1fd66: 22 d0 rcall .+68 ; 0x1fdac <putch>
address++; address++;
1fd4a: 80 91 00 04 lds r24, 0x0400 1fd68: 80 91 00 04 lds r24, 0x0400
1fd4e: 90 91 01 04 lds r25, 0x0401 1fd6c: 90 91 01 04 lds r25, 0x0401
1fd52: 01 96 adiw r24, 0x01 ; 1 1fd70: 01 96 adiw r24, 0x01 ; 1
1fd54: 90 93 01 04 sts 0x0401, r25 1fd72: 90 93 01 04 sts 0x0401, r25
1fd58: 80 93 00 04 sts 0x0400, r24 1fd76: 80 93 00 04 sts 0x0400, r24
} }
while (--length); while (--length);
1fd5c: 80 91 02 04 lds r24, 0x0402 1fd7a: 80 91 02 04 lds r24, 0x0402
1fd60: 81 50 subi r24, 0x01 ; 1 1fd7e: 81 50 subi r24, 0x01 ; 1
1fd62: 80 93 02 04 sts 0x0402, r24 1fd80: 80 93 02 04 sts 0x0402, r24
1fd66: 88 23 and r24, r24 1fd84: 88 23 and r24, r24
1fd68: 49 f7 brne .-46 ; 0x1fd3c <main+0x13c> 1fd86: 49 f7 brne .-46 ; 0x1fd5a <main+0x15a>
1fd6a: 0e c0 rjmp .+28 ; 0x1fd88 <main+0x188> 1fd88: 0e c0 rjmp .+28 ; 0x1fda6 <main+0x1a6>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
1fd6c: 85 37 cpi r24, 0x75 ; 117 1fd8a: 85 37 cpi r24, 0x75 ; 117
1fd6e: 39 f4 brne .+14 ; 0x1fd7e <main+0x17e> 1fd8c: 39 f4 brne .+14 ; 0x1fd9c <main+0x19c>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
1fd70: 2e d0 rcall .+92 ; 0x1fdce <verifySpace> 1fd8e: 2e d0 rcall .+92 ; 0x1fdec <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
1fd72: 8e e1 ldi r24, 0x1E ; 30 1fd90: 8e e1 ldi r24, 0x1E ; 30
1fd74: 0c d0 rcall .+24 ; 0x1fd8e <putch> 1fd92: 0c d0 rcall .+24 ; 0x1fdac <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
1fd76: 87 e9 ldi r24, 0x97 ; 151 1fd94: 87 e9 ldi r24, 0x97 ; 151
1fd78: 0a d0 rcall .+20 ; 0x1fd8e <putch> 1fd96: 0a d0 rcall .+20 ; 0x1fdac <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
1fd7a: 83 e0 ldi r24, 0x03 ; 3 1fd98: 83 e0 ldi r24, 0x03 ; 3
1fd7c: 97 cf rjmp .-210 ; 0x1fcac <main+0xac> 1fd9a: 88 cf rjmp .-240 ; 0x1fcac <main+0xac>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
1fd7e: 81 35 cpi r24, 0x51 ; 81 1fd9c: 81 35 cpi r24, 0x51 ; 81
1fd80: 11 f4 brne .+4 ; 0x1fd86 <main+0x186> 1fd9e: 11 f4 brne .+4 ; 0x1fda4 <main+0x1a4>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
1fd82: 88 e0 ldi r24, 0x08 ; 8 1fda0: 88 e0 ldi r24, 0x08 ; 8
1fd84: 19 d0 rcall .+50 ; 0x1fdb8 <watchdogConfig> 1fda2: 19 d0 rcall .+50 ; 0x1fdd6 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
1fd86: 23 d0 rcall .+70 ; 0x1fdce <verifySpace> 1fda4: 23 d0 rcall .+70 ; 0x1fdec <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
1fd88: 80 e1 ldi r24, 0x10 ; 16 1fda6: 80 e1 ldi r24, 0x10 ; 16
1fd8a: 01 d0 rcall .+2 ; 0x1fd8e <putch> 1fda8: 01 d0 rcall .+2 ; 0x1fdac <putch>
1fd8c: 64 cf rjmp .-312 ; 0x1fc56 <main+0x56> 1fdaa: 55 cf rjmp .-342 ; 0x1fc56 <main+0x56>
0001fd8e <putch>: 0001fdac <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
1fd8e: 98 2f mov r25, r24 1fdac: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
1fd90: 80 91 c0 00 lds r24, 0x00C0 1fdae: 80 91 c0 00 lds r24, 0x00C0
1fd94: 85 ff sbrs r24, 5 1fdb2: 85 ff sbrs r24, 5
1fd96: fc cf rjmp .-8 ; 0x1fd90 <putch+0x2> 1fdb4: fc cf rjmp .-8 ; 0x1fdae <putch+0x2>
UDR0 = ch; UDR0 = ch;
1fd98: 90 93 c6 00 sts 0x00C6, r25 1fdb6: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
1fd9c: 08 95 ret 1fdba: 08 95 ret
0001fd9e <getch>: 0001fdbc <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
1fd9e: a8 95 wdr 1fdbc: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
1fda0: 80 91 c0 00 lds r24, 0x00C0 1fdbe: 80 91 c0 00 lds r24, 0x00C0
1fda4: 87 ff sbrs r24, 7 1fdc2: 87 ff sbrs r24, 7
1fda6: fc cf rjmp .-8 ; 0x1fda0 <getch+0x2> 1fdc4: fc cf rjmp .-8 ; 0x1fdbe <getch+0x2>
ch = UDR0; ch = UDR0;
1fda8: 80 91 c6 00 lds r24, 0x00C6 1fdc6: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
1fdac: 08 95 ret 1fdca: 08 95 ret
0001fdae <getLen>: 0001fdcc <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
1fdae: f7 df rcall .-18 ; 0x1fd9e <getch> 1fdcc: f7 df rcall .-18 ; 0x1fdbc <getch>
length = getch(); length = getch();
1fdb0: f6 df rcall .-20 ; 0x1fd9e <getch> 1fdce: f6 df rcall .-20 ; 0x1fdbc <getch>
1fdb2: 80 93 02 04 sts 0x0402, r24 1fdd0: 80 93 02 04 sts 0x0402, r24
return getch(); return getch();
} }
1fdb6: f3 cf rjmp .-26 ; 0x1fd9e <getch> 1fdd4: f3 cf rjmp .-26 ; 0x1fdbc <getch>
0001fdb8 <watchdogConfig>: 0001fdd6 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
1fdb8: e0 e6 ldi r30, 0x60 ; 96 1fdd6: e0 e6 ldi r30, 0x60 ; 96
1fdba: f0 e0 ldi r31, 0x00 ; 0 1fdd8: f0 e0 ldi r31, 0x00 ; 0
1fdbc: 98 e1 ldi r25, 0x18 ; 24 1fdda: 98 e1 ldi r25, 0x18 ; 24
1fdbe: 90 83 st Z, r25 1fddc: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
1fdc0: 80 83 st Z, r24 1fdde: 80 83 st Z, r24
} }
1fdc2: 08 95 ret 1fde0: 08 95 ret
0001fdc4 <appStart>: 0001fde2 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
1fdc4: 80 e0 ldi r24, 0x00 ; 0 1fde2: 80 e0 ldi r24, 0x00 ; 0
1fdc6: f8 df rcall .-16 ; 0x1fdb8 <watchdogConfig> 1fde4: f8 df rcall .-16 ; 0x1fdd6 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
1fdc8: ee 27 eor r30, r30 1fde6: ee 27 eor r30, r30
1fdca: ff 27 eor r31, r31 1fde8: ff 27 eor r31, r31
1fdcc: 09 94 ijmp 1fdea: 09 94 ijmp
0001fdce <verifySpace>: 0001fdec <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
1fdce: e7 df rcall .-50 ; 0x1fd9e <getch> 1fdec: e7 df rcall .-50 ; 0x1fdbc <getch>
1fdd0: 80 32 cpi r24, 0x20 ; 32 1fdee: 80 32 cpi r24, 0x20 ; 32
1fdd2: 09 f0 breq .+2 ; 0x1fdd6 <verifySpace+0x8> 1fdf0: 09 f0 breq .+2 ; 0x1fdf4 <verifySpace+0x8>
1fdd4: f7 df rcall .-18 ; 0x1fdc4 <appStart> 1fdf2: f7 df rcall .-18 ; 0x1fde2 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
1fdd6: 84 e1 ldi r24, 0x14 ; 20 1fdf4: 84 e1 ldi r24, 0x14 ; 20
} }
1fdd8: da cf rjmp .-76 ; 0x1fd8e <putch> 1fdf6: da cf rjmp .-76 ; 0x1fdac <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
1fdda: 1f 93 push r17 1fdf8: 1f 93 push r17
1fddc: 18 2f mov r17, r24 1fdfa: 18 2f mov r17, r24
0001fdde <getNch>: 0001fdfc <getNch>:
do getch(); while (--count); do getch(); while (--count);
1fdde: df df rcall .-66 ; 0x1fd9e <getch> 1fdfc: df df rcall .-66 ; 0x1fdbc <getch>
1fde0: 11 50 subi r17, 0x01 ; 1 1fdfe: 11 50 subi r17, 0x01 ; 1
1fde2: e9 f7 brne .-6 ; 0x1fdde <getNch> 1fe00: e9 f7 brne .-6 ; 0x1fdfc <getNch>
verifySpace(); verifySpace();
1fde4: f4 df rcall .-24 ; 0x1fdce <verifySpace> 1fe02: f4 df rcall .-24 ; 0x1fdec <verifySpace>
} }
1fde6: 1f 91 pop r17 1fe04: 1f 91 pop r17
1fde8: 08 95 ret 1fe06: 08 95 ret

View File

@ -1,32 +1,34 @@
:107E000085E08093810082E08093C00088E18093C8 :107E000085E08093810082E08093C00088E18093C8
:107E1000C10086E08093C20080E18093C40084B7F3 :107E1000C10086E08093C20080E18093C40084B7F3
:107E200014BE81FFC8D08DE0C0D0259A86E020E343 :107E200014BE81FFD7D08DE0CFD0259A86E020E325
:107E30003CEF91E0309385002093840096BBB09B8B :107E30003CEF91E0309385002093840096BBB09B8B
:107E4000FECF1D9AA8958150A9F7DD24D394A5E013 :107E4000FECF1D9AA8958150A9F7DD24D394A5E013
:107E5000FA2EF1E1EF2E9CD0813421F481E0B6D0EE :107E5000EA2EF1E1FF2EABD0813421F481E0C5D0D0
:107E600083E020C0823411F484E103C0853419F426 :107E600083E020C0823411F484E103C0853419F426
:107E700085E0ACD082C0853581F48AD0082F10E02F :107E700085E0BBD091C0853581F499D0082F10E002
:107E800087D090E0982F8827802B912B880F991FFF :107E800096D090E0982F8827802B912B880F991FF0
:107E900090930102809300026FC0863529F484E03C :107E900090930102809300027EC0863529F484E02D
:107EA00095D080E06DD069C0843609F03FC078D0AD :107EA000A4D080E07CD078C0843609F04EC087D062
:107EB000E0910002F091010283E087BFE895C0E005 :107EB000E0910002F091010280E7E030F80718F449
:107EC000D1E066D0899380910202815080930202B2 :107EC00083E087BFE895C0E0D1E071D089938091CD
:107ED0008823B9F775D007B600FCFDCF40910002AA :107ED00002028150809302028823B9F7E0910002E8
:107EE00050910102A0E0B1E02C9130E011968C910C :107EE000F091010280E7E030F80718F083E087BFE7
:107EF000119790E0982F8827822B932B1296FA01E6 :107EF000E89575D007B600FCFDCF40910002509187
:107F00000C01D7BEE89511244E5F5F4FF1E0A03819 :107F00000102A0E0B1E02C9130E011968C91119724
:107F1000BF0751F7E0910002F0910102F7BEE8952A :107F100090E0982F8827822B932B1296FA010C0160
:107F200007B600FCFDCFE7BEE89527C08437B9F45B :107F2000D7BEE89511244E5F5F4FF1E0A038BF0740
:107F300037D046D0E0910002F09101023196F093E3 :107F300051F7E0910002F0910102E7BEE89507B623
:107F40000102E09300023197E4918E2F19D08091C5 :107F400000FCFDCFF7BEE89527C08437B9F437D0E1
:107F50000202815080930202882361F70EC08537A8 :107F500046D0E0910002F09101023196F0930102C7
:107F600039F42ED08EE10CD085E90AD08FE09ACF7B :107F6000E09300023197E4918E2F19D080910202A4
:107F7000813511F488E019D023D080E101D06BCF96 :107F7000815080930202882361F70EC0853739F45F
:107F8000982F8091C00085FFFCCF9093C600089584 :107F80002ED08EE10CD085E90AD08FE08BCF8135E1
:107F9000A8958091C00087FFFCCF8091C60008950E :107F900011F488E019D023D080E101D05CCF982F74
:107FA000F7DFF6DF80930202F3CFE0E6F0E098E13E :107FA0008091C00085FFFCCF9093C6000895A895EE
:107FB00090838083089580E0F8DFEE27FF270994FF :107FB0008091C00087FFFCCF8091C6000895F7DF55
:107FC000E7DF803209F0F7DF84E1DACF1F93182F63 :107FC000F6DF80930202F3CFE0E6F0E098E19083E1
:0C7FD000DFDF1150E9F7F4DF1F91089586 :107FD0008083089580E0F8DFEE27FF270994E7DF2C
:107FE000803209F0F7DF84E1DACF1F93182FDFDF4B
:0A7FF0001150E9F7F4DF1F91089526
:0400000300007E007B :0400000300007E007B
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_atmega328.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 00007e00 00007e00 00000054 2**1 0 .text 000001fa 00007e00 00007e00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
7e20: 14 be out 0x34, r1 ; 52 7e20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
7e22: 81 ff sbrs r24, 1 7e22: 81 ff sbrs r24, 1
7e24: c8 d0 rcall .+400 ; 0x7fb6 <appStart> 7e24: d7 d0 rcall .+430 ; 0x7fd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
7e26: 8d e0 ldi r24, 0x0D ; 13 7e26: 8d e0 ldi r24, 0x0D ; 13
7e28: c0 d0 rcall .+384 ; 0x7faa <watchdogConfig> 7e28: cf d0 rcall .+414 ; 0x7fc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
7e4e: a5 e0 ldi r26, 0x05 ; 5 7e4e: a5 e0 ldi r26, 0x05 ; 5
7e50: fa 2e mov r15, r26 7e50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
7e52: f1 e1 ldi r31, 0x11 ; 17 7e52: f1 e1 ldi r31, 0x11 ; 17
7e54: ef 2e mov r14, r31 7e54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
7e56: 9c d0 rcall .+312 ; 0x7f90 <getch> 7e56: ab d0 rcall .+342 ; 0x7fae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
7e58: 81 34 cpi r24, 0x41 ; 65 7e58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
7e5c: 81 e0 ldi r24, 0x01 ; 1 7e5c: 81 e0 ldi r24, 0x01 ; 1
7e5e: b6 d0 rcall .+364 ; 0x7fcc <verifySpace+0xc> 7e5e: c5 d0 rcall .+394 ; 0x7fea <verifySpace+0xc>
putch(0x03); putch(0x03);
7e60: 83 e0 ldi r24, 0x03 ; 3 7e60: 83 e0 ldi r24, 0x03 ; 3
7e62: 20 c0 rjmp .+64 ; 0x7ea4 <main+0xa4> 7e62: 20 c0 rjmp .+64 ; 0x7ea4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
7e70: 85 e0 ldi r24, 0x05 ; 5 7e70: 85 e0 ldi r24, 0x05 ; 5
7e72: ac d0 rcall .+344 ; 0x7fcc <verifySpace+0xc> 7e72: bb d0 rcall .+374 ; 0x7fea <verifySpace+0xc>
7e74: 82 c0 rjmp .+260 ; 0x7f7a <main+0x17a> 7e74: 91 c0 rjmp .+290 ; 0x7f98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
7e76: 85 35 cpi r24, 0x55 ; 85 7e76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
7e7a: 8a d0 rcall .+276 ; 0x7f90 <getch> 7e7a: 99 d0 rcall .+306 ; 0x7fae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
7e7c: 08 2f mov r16, r24 7e7c: 08 2f mov r16, r24
7e7e: 10 e0 ldi r17, 0x00 ; 0 7e7e: 10 e0 ldi r17, 0x00 ; 0
7e80: 87 d0 rcall .+270 ; 0x7f90 <getch> 7e80: 96 d0 rcall .+300 ; 0x7fae <getch>
7e82: 90 e0 ldi r25, 0x00 ; 0 7e82: 90 e0 ldi r25, 0x00 ; 0
7e84: 98 2f mov r25, r24 7e84: 98 2f mov r25, r24
7e86: 88 27 eor r24, r24 7e86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
7e90: 90 93 01 02 sts 0x0201, r25 7e90: 90 93 01 02 sts 0x0201, r25
7e94: 80 93 00 02 sts 0x0200, r24 7e94: 80 93 00 02 sts 0x0200, r24
7e98: 6f c0 rjmp .+222 ; 0x7f78 <main+0x178> 7e98: 7e c0 rjmp .+252 ; 0x7f96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
7e9e: 84 e0 ldi r24, 0x04 ; 4 7e9e: 84 e0 ldi r24, 0x04 ; 4
7ea0: 95 d0 rcall .+298 ; 0x7fcc <verifySpace+0xc> 7ea0: a4 d0 rcall .+328 ; 0x7fea <verifySpace+0xc>
putch(0x00); putch(0x00);
7ea2: 80 e0 ldi r24, 0x00 ; 0 7ea2: 80 e0 ldi r24, 0x00 ; 0
7ea4: 6d d0 rcall .+218 ; 0x7f80 <putch> 7ea4: 7c d0 rcall .+248 ; 0x7f9e <putch>
7ea6: 69 c0 rjmp .+210 ; 0x7f7a <main+0x17a> 7ea6: 78 c0 rjmp .+240 ; 0x7f98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
7ea8: 84 36 cpi r24, 0x64 ; 100 7ea8: 84 36 cpi r24, 0x64 ; 100
7eaa: 09 f0 breq .+2 ; 0x7eae <main+0xae> 7eaa: 09 f0 breq .+2 ; 0x7eae <main+0xae>
7eac: 3f c0 rjmp .+126 ; 0x7f2c <main+0x12c> 7eac: 4e c0 rjmp .+156 ; 0x7f4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
7eae: 78 d0 rcall .+240 ; 0x7fa0 <getLen> 7eae: 87 d0 rcall .+270 ; 0x7fbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
7eb0: e0 91 00 02 lds r30, 0x0200 7eb0: e0 91 00 02 lds r30, 0x0200
7eb4: f0 91 01 02 lds r31, 0x0201 7eb4: f0 91 01 02 lds r31, 0x0201
7eb8: 83 e0 ldi r24, 0x03 ; 3 7eb8: 80 e7 ldi r24, 0x70 ; 112
7eba: 87 bf out 0x37, r24 ; 55 7eba: e0 30 cpi r30, 0x00 ; 0
7ebc: e8 95 spm 7ebc: f8 07 cpc r31, r24
7ebe: c0 e0 ldi r28, 0x00 ; 0 7ebe: 18 f4 brcc .+6 ; 0x7ec6 <main+0xc6>
7ec0: d1 e0 ldi r29, 0x01 ; 1 7ec0: 83 e0 ldi r24, 0x03 ; 3
7ec2: 87 bf out 0x37, r24 ; 55
7ec4: e8 95 spm
7ec6: c0 e0 ldi r28, 0x00 ; 0
7ec8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
7ec2: 66 d0 rcall .+204 ; 0x7f90 <getch> 7eca: 71 d0 rcall .+226 ; 0x7fae <getch>
7ec4: 89 93 st Y+, r24 7ecc: 89 93 st Y+, r24
while (--length); while (--length);
7ec6: 80 91 02 02 lds r24, 0x0202 7ece: 80 91 02 02 lds r24, 0x0202
7eca: 81 50 subi r24, 0x01 ; 1 7ed2: 81 50 subi r24, 0x01 ; 1
7ecc: 80 93 02 02 sts 0x0202, r24 7ed4: 80 93 02 02 sts 0x0202, r24
7ed0: 88 23 and r24, r24 7ed8: 88 23 and r24, r24
7ed2: b9 f7 brne .-18 ; 0x7ec2 <main+0xc2> 7eda: b9 f7 brne .-18 ; 0x7eca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
7edc: e0 91 00 02 lds r30, 0x0200
7ee0: f0 91 01 02 lds r31, 0x0201
7ee4: 80 e7 ldi r24, 0x70 ; 112
7ee6: e0 30 cpi r30, 0x00 ; 0
7ee8: f8 07 cpc r31, r24
7eea: 18 f0 brcs .+6 ; 0x7ef2 <main+0xf2>
7eec: 83 e0 ldi r24, 0x03 ; 3
7eee: 87 bf out 0x37, r24 ; 55
7ef0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
7ed4: 75 d0 rcall .+234 ; 0x7fc0 <verifySpace> 7ef2: 75 d0 rcall .+234 ; 0x7fde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
7ed6: 07 b6 in r0, 0x37 ; 55 7ef4: 07 b6 in r0, 0x37 ; 55
7ed8: 00 fc sbrc r0, 0 7ef6: 00 fc sbrc r0, 0
7eda: fd cf rjmp .-6 ; 0x7ed6 <main+0xd6> 7ef8: fd cf rjmp .-6 ; 0x7ef4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
7edc: 40 91 00 02 lds r20, 0x0200 7efa: 40 91 00 02 lds r20, 0x0200
7ee0: 50 91 01 02 lds r21, 0x0201 7efe: 50 91 01 02 lds r21, 0x0201
7ee4: a0 e0 ldi r26, 0x00 ; 0 7f02: a0 e0 ldi r26, 0x00 ; 0
7ee6: b1 e0 ldi r27, 0x01 ; 1 7f04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
7ee8: 2c 91 ld r18, X 7f06: 2c 91 ld r18, X
7eea: 30 e0 ldi r19, 0x00 ; 0 7f08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
7eec: 11 96 adiw r26, 0x01 ; 1 7f0a: 11 96 adiw r26, 0x01 ; 1
7eee: 8c 91 ld r24, X 7f0c: 8c 91 ld r24, X
7ef0: 11 97 sbiw r26, 0x01 ; 1 7f0e: 11 97 sbiw r26, 0x01 ; 1
7ef2: 90 e0 ldi r25, 0x00 ; 0 7f10: 90 e0 ldi r25, 0x00 ; 0
7ef4: 98 2f mov r25, r24 7f12: 98 2f mov r25, r24
7ef6: 88 27 eor r24, r24 7f14: 88 27 eor r24, r24
7ef8: 82 2b or r24, r18 7f16: 82 2b or r24, r18
7efa: 93 2b or r25, r19 7f18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
7efc: 12 96 adiw r26, 0x02 ; 2 7f1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
7efe: fa 01 movw r30, r20 7f1c: fa 01 movw r30, r20
7f00: 0c 01 movw r0, r24 7f1e: 0c 01 movw r0, r24
7f02: d7 be out 0x37, r13 ; 55 7f20: d7 be out 0x37, r13 ; 55
7f04: e8 95 spm 7f22: e8 95 spm
7f06: 11 24 eor r1, r1 7f24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
7f08: 4e 5f subi r20, 0xFE ; 254 7f26: 4e 5f subi r20, 0xFE ; 254
7f0a: 5f 4f sbci r21, 0xFF ; 255 7f28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
7f0c: f1 e0 ldi r31, 0x01 ; 1 7f2a: f1 e0 ldi r31, 0x01 ; 1
7f0e: a0 38 cpi r26, 0x80 ; 128 7f2c: a0 38 cpi r26, 0x80 ; 128
7f10: bf 07 cpc r27, r31 7f2e: bf 07 cpc r27, r31
7f12: 51 f7 brne .-44 ; 0x7ee8 <main+0xe8> 7f30: 51 f7 brne .-44 ; 0x7f06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
7f14: e0 91 00 02 lds r30, 0x0200 7f32: e0 91 00 02 lds r30, 0x0200
7f18: f0 91 01 02 lds r31, 0x0201 7f36: f0 91 01 02 lds r31, 0x0201
7f1c: f7 be out 0x37, r15 ; 55 7f3a: e7 be out 0x37, r14 ; 55
7f1e: e8 95 spm 7f3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
7f20: 07 b6 in r0, 0x37 ; 55 7f3e: 07 b6 in r0, 0x37 ; 55
7f22: 00 fc sbrc r0, 0 7f40: 00 fc sbrc r0, 0
7f24: fd cf rjmp .-6 ; 0x7f20 <main+0x120> 7f42: fd cf rjmp .-6 ; 0x7f3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
7f26: e7 be out 0x37, r14 ; 55 7f44: f7 be out 0x37, r15 ; 55
7f28: e8 95 spm 7f46: e8 95 spm
7f2a: 27 c0 rjmp .+78 ; 0x7f7a <main+0x17a> 7f48: 27 c0 rjmp .+78 ; 0x7f98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
7f2c: 84 37 cpi r24, 0x74 ; 116 7f4a: 84 37 cpi r24, 0x74 ; 116
7f2e: b9 f4 brne .+46 ; 0x7f5e <main+0x15e> 7f4c: b9 f4 brne .+46 ; 0x7f7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
7f30: 37 d0 rcall .+110 ; 0x7fa0 <getLen> 7f4e: 37 d0 rcall .+110 ; 0x7fbe <getLen>
verifySpace(); verifySpace();
7f32: 46 d0 rcall .+140 ; 0x7fc0 <verifySpace> 7f50: 46 d0 rcall .+140 ; 0x7fde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
7f34: e0 91 00 02 lds r30, 0x0200 7f52: e0 91 00 02 lds r30, 0x0200
7f38: f0 91 01 02 lds r31, 0x0201 7f56: f0 91 01 02 lds r31, 0x0201
7f3c: 31 96 adiw r30, 0x01 ; 1 7f5a: 31 96 adiw r30, 0x01 ; 1
7f3e: f0 93 01 02 sts 0x0201, r31 7f5c: f0 93 01 02 sts 0x0201, r31
7f42: e0 93 00 02 sts 0x0200, r30 7f60: e0 93 00 02 sts 0x0200, r30
7f46: 31 97 sbiw r30, 0x01 ; 1 7f64: 31 97 sbiw r30, 0x01 ; 1
7f48: e4 91 lpm r30, Z+ 7f66: e4 91 lpm r30, Z+
7f4a: 8e 2f mov r24, r30 7f68: 8e 2f mov r24, r30
7f4c: 19 d0 rcall .+50 ; 0x7f80 <putch> 7f6a: 19 d0 rcall .+50 ; 0x7f9e <putch>
while (--length); while (--length);
7f4e: 80 91 02 02 lds r24, 0x0202 7f6c: 80 91 02 02 lds r24, 0x0202
7f52: 81 50 subi r24, 0x01 ; 1 7f70: 81 50 subi r24, 0x01 ; 1
7f54: 80 93 02 02 sts 0x0202, r24 7f72: 80 93 02 02 sts 0x0202, r24
7f58: 88 23 and r24, r24 7f76: 88 23 and r24, r24
7f5a: 61 f7 brne .-40 ; 0x7f34 <main+0x134> 7f78: 61 f7 brne .-40 ; 0x7f52 <main+0x152>
7f5c: 0e c0 rjmp .+28 ; 0x7f7a <main+0x17a> 7f7a: 0e c0 rjmp .+28 ; 0x7f98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
7f5e: 85 37 cpi r24, 0x75 ; 117 7f7c: 85 37 cpi r24, 0x75 ; 117
7f60: 39 f4 brne .+14 ; 0x7f70 <main+0x170> 7f7e: 39 f4 brne .+14 ; 0x7f8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
7f62: 2e d0 rcall .+92 ; 0x7fc0 <verifySpace> 7f80: 2e d0 rcall .+92 ; 0x7fde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
7f64: 8e e1 ldi r24, 0x1E ; 30 7f82: 8e e1 ldi r24, 0x1E ; 30
7f66: 0c d0 rcall .+24 ; 0x7f80 <putch> 7f84: 0c d0 rcall .+24 ; 0x7f9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
7f68: 85 e9 ldi r24, 0x95 ; 149 7f86: 85 e9 ldi r24, 0x95 ; 149
7f6a: 0a d0 rcall .+20 ; 0x7f80 <putch> 7f88: 0a d0 rcall .+20 ; 0x7f9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
7f6c: 8f e0 ldi r24, 0x0F ; 15 7f8a: 8f e0 ldi r24, 0x0F ; 15
7f6e: 9a cf rjmp .-204 ; 0x7ea4 <main+0xa4> 7f8c: 8b cf rjmp .-234 ; 0x7ea4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
7f70: 81 35 cpi r24, 0x51 ; 81 7f8e: 81 35 cpi r24, 0x51 ; 81
7f72: 11 f4 brne .+4 ; 0x7f78 <main+0x178> 7f90: 11 f4 brne .+4 ; 0x7f96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
7f74: 88 e0 ldi r24, 0x08 ; 8 7f92: 88 e0 ldi r24, 0x08 ; 8
7f76: 19 d0 rcall .+50 ; 0x7faa <watchdogConfig> 7f94: 19 d0 rcall .+50 ; 0x7fc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
7f78: 23 d0 rcall .+70 ; 0x7fc0 <verifySpace> 7f96: 23 d0 rcall .+70 ; 0x7fde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
7f7a: 80 e1 ldi r24, 0x10 ; 16 7f98: 80 e1 ldi r24, 0x10 ; 16
7f7c: 01 d0 rcall .+2 ; 0x7f80 <putch> 7f9a: 01 d0 rcall .+2 ; 0x7f9e <putch>
7f7e: 6b cf rjmp .-298 ; 0x7e56 <main+0x56> 7f9c: 5c cf rjmp .-328 ; 0x7e56 <main+0x56>
00007f80 <putch>: 00007f9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
7f80: 98 2f mov r25, r24 7f9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
7f82: 80 91 c0 00 lds r24, 0x00C0 7fa0: 80 91 c0 00 lds r24, 0x00C0
7f86: 85 ff sbrs r24, 5 7fa4: 85 ff sbrs r24, 5
7f88: fc cf rjmp .-8 ; 0x7f82 <putch+0x2> 7fa6: fc cf rjmp .-8 ; 0x7fa0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
7f8a: 90 93 c6 00 sts 0x00C6, r25 7fa8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
7f8e: 08 95 ret 7fac: 08 95 ret
00007f90 <getch>: 00007fae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
7f90: a8 95 wdr 7fae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
7f92: 80 91 c0 00 lds r24, 0x00C0 7fb0: 80 91 c0 00 lds r24, 0x00C0
7f96: 87 ff sbrs r24, 7 7fb4: 87 ff sbrs r24, 7
7f98: fc cf rjmp .-8 ; 0x7f92 <getch+0x2> 7fb6: fc cf rjmp .-8 ; 0x7fb0 <getch+0x2>
ch = UDR0; ch = UDR0;
7f9a: 80 91 c6 00 lds r24, 0x00C6 7fb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
7f9e: 08 95 ret 7fbc: 08 95 ret
00007fa0 <getLen>: 00007fbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
7fa0: f7 df rcall .-18 ; 0x7f90 <getch> 7fbe: f7 df rcall .-18 ; 0x7fae <getch>
length = getch(); length = getch();
7fa2: f6 df rcall .-20 ; 0x7f90 <getch> 7fc0: f6 df rcall .-20 ; 0x7fae <getch>
7fa4: 80 93 02 02 sts 0x0202, r24 7fc2: 80 93 02 02 sts 0x0202, r24
return getch(); return getch();
} }
7fa8: f3 cf rjmp .-26 ; 0x7f90 <getch> 7fc6: f3 cf rjmp .-26 ; 0x7fae <getch>
00007faa <watchdogConfig>: 00007fc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
7faa: e0 e6 ldi r30, 0x60 ; 96 7fc8: e0 e6 ldi r30, 0x60 ; 96
7fac: f0 e0 ldi r31, 0x00 ; 0 7fca: f0 e0 ldi r31, 0x00 ; 0
7fae: 98 e1 ldi r25, 0x18 ; 24 7fcc: 98 e1 ldi r25, 0x18 ; 24
7fb0: 90 83 st Z, r25 7fce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
7fb2: 80 83 st Z, r24 7fd0: 80 83 st Z, r24
} }
7fb4: 08 95 ret 7fd2: 08 95 ret
00007fb6 <appStart>: 00007fd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
7fb6: 80 e0 ldi r24, 0x00 ; 0 7fd4: 80 e0 ldi r24, 0x00 ; 0
7fb8: f8 df rcall .-16 ; 0x7faa <watchdogConfig> 7fd6: f8 df rcall .-16 ; 0x7fc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
7fba: ee 27 eor r30, r30 7fd8: ee 27 eor r30, r30
7fbc: ff 27 eor r31, r31 7fda: ff 27 eor r31, r31
7fbe: 09 94 ijmp 7fdc: 09 94 ijmp
00007fc0 <verifySpace>: 00007fde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
7fc0: e7 df rcall .-50 ; 0x7f90 <getch> 7fde: e7 df rcall .-50 ; 0x7fae <getch>
7fc2: 80 32 cpi r24, 0x20 ; 32 7fe0: 80 32 cpi r24, 0x20 ; 32
7fc4: 09 f0 breq .+2 ; 0x7fc8 <verifySpace+0x8> 7fe2: 09 f0 breq .+2 ; 0x7fe6 <verifySpace+0x8>
7fc6: f7 df rcall .-18 ; 0x7fb6 <appStart> 7fe4: f7 df rcall .-18 ; 0x7fd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
7fc8: 84 e1 ldi r24, 0x14 ; 20 7fe6: 84 e1 ldi r24, 0x14 ; 20
} }
7fca: da cf rjmp .-76 ; 0x7f80 <putch> 7fe8: da cf rjmp .-76 ; 0x7f9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
7fcc: 1f 93 push r17 7fea: 1f 93 push r17
7fce: 18 2f mov r17, r24 7fec: 18 2f mov r17, r24
00007fd0 <getNch>: 00007fee <getNch>:
do getch(); while (--count); do getch(); while (--count);
7fd0: df df rcall .-66 ; 0x7f90 <getch> 7fee: df df rcall .-66 ; 0x7fae <getch>
7fd2: 11 50 subi r17, 0x01 ; 1 7ff0: 11 50 subi r17, 0x01 ; 1
7fd4: e9 f7 brne .-6 ; 0x7fd0 <getNch> 7ff2: e9 f7 brne .-6 ; 0x7fee <getNch>
verifySpace(); verifySpace();
7fd6: f4 df rcall .-24 ; 0x7fc0 <verifySpace> 7ff4: f4 df rcall .-24 ; 0x7fde <verifySpace>
} }
7fd8: 1f 91 pop r17 7ff6: 1f 91 pop r17
7fda: 08 95 ret 7ff8: 08 95 ret

View File

@ -1,32 +1,34 @@
:107E000085E08093810082E08093C00088E18093C8 :107E000085E08093810082E08093C00088E18093C8
:107E1000C10086E08093C20088E08093C40084B7EC :107E1000C10086E08093C20088E08093C40084B7EC
:107E200014BE81FFC8D08DE0C0D0259A86E028E13D :107E200014BE81FFD7D08DE0CFD0259A86E028E11F
:107E30003EEF91E0309385002093840096BBB09B89 :107E30003EEF91E0309385002093840096BBB09B89
:107E4000FECF1D9AA8958150A9F7DD24D394A5E013 :107E4000FECF1D9AA8958150A9F7DD24D394A5E013
:107E5000FA2EF1E1EF2E9CD0813421F481E0B6D0EE :107E5000EA2EF1E1FF2EABD0813421F481E0C5D0D0
:107E600083E020C0823411F484E103C0853419F426 :107E600083E020C0823411F484E103C0853419F426
:107E700085E0ACD082C0853581F48AD0082F10E02F :107E700085E0BBD091C0853581F499D0082F10E002
:107E800087D090E0982F8827802B912B880F991FFF :107E800096D090E0982F8827802B912B880F991FF0
:107E900090930102809300026FC0863529F484E03C :107E900090930102809300027EC0863529F484E02D
:107EA00095D080E06DD069C0843609F03FC078D0AD :107EA000A4D080E07CD078C0843609F04EC087D062
:107EB000E0910002F091010283E087BFE895C0E005 :107EB000E0910002F091010280E7E030F80718F449
:107EC000D1E066D0899380910202815080930202B2 :107EC00083E087BFE895C0E0D1E071D089938091CD
:107ED0008823B9F775D007B600FCFDCF40910002AA :107ED00002028150809302028823B9F7E0910002E8
:107EE00050910102A0E0B1E02C9130E011968C910C :107EE000F091010280E7E030F80718F083E087BFE7
:107EF000119790E0982F8827822B932B1296FA01E6 :107EF000E89575D007B600FCFDCF40910002509187
:107F00000C01D7BEE89511244E5F5F4FF1E0A03819 :107F00000102A0E0B1E02C9130E011968C91119724
:107F1000BF0751F7E0910002F0910102F7BEE8952A :107F100090E0982F8827822B932B1296FA010C0160
:107F200007B600FCFDCFE7BEE89527C08437B9F45B :107F2000D7BEE89511244E5F5F4FF1E0A038BF0740
:107F300037D046D0E0910002F09101023196F093E3 :107F300051F7E0910002F0910102E7BEE89507B623
:107F40000102E09300023197E4918E2F19D08091C5 :107F400000FCFDCFF7BEE89527C08437B9F437D0E1
:107F50000202815080930202882361F70EC08537A8 :107F500046D0E0910002F09101023196F0930102C7
:107F600039F42ED08EE10CD085E90AD08FE09ACF7B :107F6000E09300023197E4918E2F19D080910202A4
:107F7000813511F488E019D023D080E101D06BCF96 :107F7000815080930202882361F70EC0853739F45F
:107F8000982F8091C00085FFFCCF9093C600089584 :107F80002ED08EE10CD085E90AD08FE08BCF8135E1
:107F9000A8958091C00087FFFCCF8091C60008950E :107F900011F488E019D023D080E101D05CCF982F74
:107FA000F7DFF6DF80930202F3CFE0E6F0E098E13E :107FA0008091C00085FFFCCF9093C6000895A895EE
:107FB00090838083089580E0F8DFEE27FF270994FF :107FB0008091C00087FFFCCF8091C6000895F7DF55
:107FC000E7DF803209F0F7DF84E1DACF1F93182F63 :107FC000F6DF80930202F3CFE0E6F0E098E19083E1
:0C7FD000DFDF1150E9F7F4DF1F91089586 :107FD0008083089580E0F8DFEE27FF270994E7DF2C
:107FE000803209F0F7DF84E1DACF1F93182FDFDF4B
:0A7FF0001150E9F7F4DF1F91089526
:0400000300007E007B :0400000300007E007B
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_atmega328_pro_8MHz.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 00007e00 00007e00 00000054 2**1 0 .text 000001fa 00007e00 00007e00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
7e20: 14 be out 0x34, r1 ; 52 7e20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
7e22: 81 ff sbrs r24, 1 7e22: 81 ff sbrs r24, 1
7e24: c8 d0 rcall .+400 ; 0x7fb6 <appStart> 7e24: d7 d0 rcall .+430 ; 0x7fd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
7e26: 8d e0 ldi r24, 0x0D ; 13 7e26: 8d e0 ldi r24, 0x0D ; 13
7e28: c0 d0 rcall .+384 ; 0x7faa <watchdogConfig> 7e28: cf d0 rcall .+414 ; 0x7fc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
7e4e: a5 e0 ldi r26, 0x05 ; 5 7e4e: a5 e0 ldi r26, 0x05 ; 5
7e50: fa 2e mov r15, r26 7e50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
7e52: f1 e1 ldi r31, 0x11 ; 17 7e52: f1 e1 ldi r31, 0x11 ; 17
7e54: ef 2e mov r14, r31 7e54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
7e56: 9c d0 rcall .+312 ; 0x7f90 <getch> 7e56: ab d0 rcall .+342 ; 0x7fae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
7e58: 81 34 cpi r24, 0x41 ; 65 7e58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
7e5c: 81 e0 ldi r24, 0x01 ; 1 7e5c: 81 e0 ldi r24, 0x01 ; 1
7e5e: b6 d0 rcall .+364 ; 0x7fcc <verifySpace+0xc> 7e5e: c5 d0 rcall .+394 ; 0x7fea <verifySpace+0xc>
putch(0x03); putch(0x03);
7e60: 83 e0 ldi r24, 0x03 ; 3 7e60: 83 e0 ldi r24, 0x03 ; 3
7e62: 20 c0 rjmp .+64 ; 0x7ea4 <main+0xa4> 7e62: 20 c0 rjmp .+64 ; 0x7ea4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
7e70: 85 e0 ldi r24, 0x05 ; 5 7e70: 85 e0 ldi r24, 0x05 ; 5
7e72: ac d0 rcall .+344 ; 0x7fcc <verifySpace+0xc> 7e72: bb d0 rcall .+374 ; 0x7fea <verifySpace+0xc>
7e74: 82 c0 rjmp .+260 ; 0x7f7a <main+0x17a> 7e74: 91 c0 rjmp .+290 ; 0x7f98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
7e76: 85 35 cpi r24, 0x55 ; 85 7e76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
7e7a: 8a d0 rcall .+276 ; 0x7f90 <getch> 7e7a: 99 d0 rcall .+306 ; 0x7fae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
7e7c: 08 2f mov r16, r24 7e7c: 08 2f mov r16, r24
7e7e: 10 e0 ldi r17, 0x00 ; 0 7e7e: 10 e0 ldi r17, 0x00 ; 0
7e80: 87 d0 rcall .+270 ; 0x7f90 <getch> 7e80: 96 d0 rcall .+300 ; 0x7fae <getch>
7e82: 90 e0 ldi r25, 0x00 ; 0 7e82: 90 e0 ldi r25, 0x00 ; 0
7e84: 98 2f mov r25, r24 7e84: 98 2f mov r25, r24
7e86: 88 27 eor r24, r24 7e86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
7e90: 90 93 01 02 sts 0x0201, r25 7e90: 90 93 01 02 sts 0x0201, r25
7e94: 80 93 00 02 sts 0x0200, r24 7e94: 80 93 00 02 sts 0x0200, r24
7e98: 6f c0 rjmp .+222 ; 0x7f78 <main+0x178> 7e98: 7e c0 rjmp .+252 ; 0x7f96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
7e9e: 84 e0 ldi r24, 0x04 ; 4 7e9e: 84 e0 ldi r24, 0x04 ; 4
7ea0: 95 d0 rcall .+298 ; 0x7fcc <verifySpace+0xc> 7ea0: a4 d0 rcall .+328 ; 0x7fea <verifySpace+0xc>
putch(0x00); putch(0x00);
7ea2: 80 e0 ldi r24, 0x00 ; 0 7ea2: 80 e0 ldi r24, 0x00 ; 0
7ea4: 6d d0 rcall .+218 ; 0x7f80 <putch> 7ea4: 7c d0 rcall .+248 ; 0x7f9e <putch>
7ea6: 69 c0 rjmp .+210 ; 0x7f7a <main+0x17a> 7ea6: 78 c0 rjmp .+240 ; 0x7f98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
7ea8: 84 36 cpi r24, 0x64 ; 100 7ea8: 84 36 cpi r24, 0x64 ; 100
7eaa: 09 f0 breq .+2 ; 0x7eae <main+0xae> 7eaa: 09 f0 breq .+2 ; 0x7eae <main+0xae>
7eac: 3f c0 rjmp .+126 ; 0x7f2c <main+0x12c> 7eac: 4e c0 rjmp .+156 ; 0x7f4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
7eae: 78 d0 rcall .+240 ; 0x7fa0 <getLen> 7eae: 87 d0 rcall .+270 ; 0x7fbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
7eb0: e0 91 00 02 lds r30, 0x0200 7eb0: e0 91 00 02 lds r30, 0x0200
7eb4: f0 91 01 02 lds r31, 0x0201 7eb4: f0 91 01 02 lds r31, 0x0201
7eb8: 83 e0 ldi r24, 0x03 ; 3 7eb8: 80 e7 ldi r24, 0x70 ; 112
7eba: 87 bf out 0x37, r24 ; 55 7eba: e0 30 cpi r30, 0x00 ; 0
7ebc: e8 95 spm 7ebc: f8 07 cpc r31, r24
7ebe: c0 e0 ldi r28, 0x00 ; 0 7ebe: 18 f4 brcc .+6 ; 0x7ec6 <main+0xc6>
7ec0: d1 e0 ldi r29, 0x01 ; 1 7ec0: 83 e0 ldi r24, 0x03 ; 3
7ec2: 87 bf out 0x37, r24 ; 55
7ec4: e8 95 spm
7ec6: c0 e0 ldi r28, 0x00 ; 0
7ec8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
7ec2: 66 d0 rcall .+204 ; 0x7f90 <getch> 7eca: 71 d0 rcall .+226 ; 0x7fae <getch>
7ec4: 89 93 st Y+, r24 7ecc: 89 93 st Y+, r24
while (--length); while (--length);
7ec6: 80 91 02 02 lds r24, 0x0202 7ece: 80 91 02 02 lds r24, 0x0202
7eca: 81 50 subi r24, 0x01 ; 1 7ed2: 81 50 subi r24, 0x01 ; 1
7ecc: 80 93 02 02 sts 0x0202, r24 7ed4: 80 93 02 02 sts 0x0202, r24
7ed0: 88 23 and r24, r24 7ed8: 88 23 and r24, r24
7ed2: b9 f7 brne .-18 ; 0x7ec2 <main+0xc2> 7eda: b9 f7 brne .-18 ; 0x7eca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
7edc: e0 91 00 02 lds r30, 0x0200
7ee0: f0 91 01 02 lds r31, 0x0201
7ee4: 80 e7 ldi r24, 0x70 ; 112
7ee6: e0 30 cpi r30, 0x00 ; 0
7ee8: f8 07 cpc r31, r24
7eea: 18 f0 brcs .+6 ; 0x7ef2 <main+0xf2>
7eec: 83 e0 ldi r24, 0x03 ; 3
7eee: 87 bf out 0x37, r24 ; 55
7ef0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
7ed4: 75 d0 rcall .+234 ; 0x7fc0 <verifySpace> 7ef2: 75 d0 rcall .+234 ; 0x7fde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
7ed6: 07 b6 in r0, 0x37 ; 55 7ef4: 07 b6 in r0, 0x37 ; 55
7ed8: 00 fc sbrc r0, 0 7ef6: 00 fc sbrc r0, 0
7eda: fd cf rjmp .-6 ; 0x7ed6 <main+0xd6> 7ef8: fd cf rjmp .-6 ; 0x7ef4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
7edc: 40 91 00 02 lds r20, 0x0200 7efa: 40 91 00 02 lds r20, 0x0200
7ee0: 50 91 01 02 lds r21, 0x0201 7efe: 50 91 01 02 lds r21, 0x0201
7ee4: a0 e0 ldi r26, 0x00 ; 0 7f02: a0 e0 ldi r26, 0x00 ; 0
7ee6: b1 e0 ldi r27, 0x01 ; 1 7f04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
7ee8: 2c 91 ld r18, X 7f06: 2c 91 ld r18, X
7eea: 30 e0 ldi r19, 0x00 ; 0 7f08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
7eec: 11 96 adiw r26, 0x01 ; 1 7f0a: 11 96 adiw r26, 0x01 ; 1
7eee: 8c 91 ld r24, X 7f0c: 8c 91 ld r24, X
7ef0: 11 97 sbiw r26, 0x01 ; 1 7f0e: 11 97 sbiw r26, 0x01 ; 1
7ef2: 90 e0 ldi r25, 0x00 ; 0 7f10: 90 e0 ldi r25, 0x00 ; 0
7ef4: 98 2f mov r25, r24 7f12: 98 2f mov r25, r24
7ef6: 88 27 eor r24, r24 7f14: 88 27 eor r24, r24
7ef8: 82 2b or r24, r18 7f16: 82 2b or r24, r18
7efa: 93 2b or r25, r19 7f18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
7efc: 12 96 adiw r26, 0x02 ; 2 7f1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
7efe: fa 01 movw r30, r20 7f1c: fa 01 movw r30, r20
7f00: 0c 01 movw r0, r24 7f1e: 0c 01 movw r0, r24
7f02: d7 be out 0x37, r13 ; 55 7f20: d7 be out 0x37, r13 ; 55
7f04: e8 95 spm 7f22: e8 95 spm
7f06: 11 24 eor r1, r1 7f24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
7f08: 4e 5f subi r20, 0xFE ; 254 7f26: 4e 5f subi r20, 0xFE ; 254
7f0a: 5f 4f sbci r21, 0xFF ; 255 7f28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
7f0c: f1 e0 ldi r31, 0x01 ; 1 7f2a: f1 e0 ldi r31, 0x01 ; 1
7f0e: a0 38 cpi r26, 0x80 ; 128 7f2c: a0 38 cpi r26, 0x80 ; 128
7f10: bf 07 cpc r27, r31 7f2e: bf 07 cpc r27, r31
7f12: 51 f7 brne .-44 ; 0x7ee8 <main+0xe8> 7f30: 51 f7 brne .-44 ; 0x7f06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
7f14: e0 91 00 02 lds r30, 0x0200 7f32: e0 91 00 02 lds r30, 0x0200
7f18: f0 91 01 02 lds r31, 0x0201 7f36: f0 91 01 02 lds r31, 0x0201
7f1c: f7 be out 0x37, r15 ; 55 7f3a: e7 be out 0x37, r14 ; 55
7f1e: e8 95 spm 7f3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
7f20: 07 b6 in r0, 0x37 ; 55 7f3e: 07 b6 in r0, 0x37 ; 55
7f22: 00 fc sbrc r0, 0 7f40: 00 fc sbrc r0, 0
7f24: fd cf rjmp .-6 ; 0x7f20 <main+0x120> 7f42: fd cf rjmp .-6 ; 0x7f3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
7f26: e7 be out 0x37, r14 ; 55 7f44: f7 be out 0x37, r15 ; 55
7f28: e8 95 spm 7f46: e8 95 spm
7f2a: 27 c0 rjmp .+78 ; 0x7f7a <main+0x17a> 7f48: 27 c0 rjmp .+78 ; 0x7f98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
7f2c: 84 37 cpi r24, 0x74 ; 116 7f4a: 84 37 cpi r24, 0x74 ; 116
7f2e: b9 f4 brne .+46 ; 0x7f5e <main+0x15e> 7f4c: b9 f4 brne .+46 ; 0x7f7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
7f30: 37 d0 rcall .+110 ; 0x7fa0 <getLen> 7f4e: 37 d0 rcall .+110 ; 0x7fbe <getLen>
verifySpace(); verifySpace();
7f32: 46 d0 rcall .+140 ; 0x7fc0 <verifySpace> 7f50: 46 d0 rcall .+140 ; 0x7fde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
7f34: e0 91 00 02 lds r30, 0x0200 7f52: e0 91 00 02 lds r30, 0x0200
7f38: f0 91 01 02 lds r31, 0x0201 7f56: f0 91 01 02 lds r31, 0x0201
7f3c: 31 96 adiw r30, 0x01 ; 1 7f5a: 31 96 adiw r30, 0x01 ; 1
7f3e: f0 93 01 02 sts 0x0201, r31 7f5c: f0 93 01 02 sts 0x0201, r31
7f42: e0 93 00 02 sts 0x0200, r30 7f60: e0 93 00 02 sts 0x0200, r30
7f46: 31 97 sbiw r30, 0x01 ; 1 7f64: 31 97 sbiw r30, 0x01 ; 1
7f48: e4 91 lpm r30, Z+ 7f66: e4 91 lpm r30, Z+
7f4a: 8e 2f mov r24, r30 7f68: 8e 2f mov r24, r30
7f4c: 19 d0 rcall .+50 ; 0x7f80 <putch> 7f6a: 19 d0 rcall .+50 ; 0x7f9e <putch>
while (--length); while (--length);
7f4e: 80 91 02 02 lds r24, 0x0202 7f6c: 80 91 02 02 lds r24, 0x0202
7f52: 81 50 subi r24, 0x01 ; 1 7f70: 81 50 subi r24, 0x01 ; 1
7f54: 80 93 02 02 sts 0x0202, r24 7f72: 80 93 02 02 sts 0x0202, r24
7f58: 88 23 and r24, r24 7f76: 88 23 and r24, r24
7f5a: 61 f7 brne .-40 ; 0x7f34 <main+0x134> 7f78: 61 f7 brne .-40 ; 0x7f52 <main+0x152>
7f5c: 0e c0 rjmp .+28 ; 0x7f7a <main+0x17a> 7f7a: 0e c0 rjmp .+28 ; 0x7f98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
7f5e: 85 37 cpi r24, 0x75 ; 117 7f7c: 85 37 cpi r24, 0x75 ; 117
7f60: 39 f4 brne .+14 ; 0x7f70 <main+0x170> 7f7e: 39 f4 brne .+14 ; 0x7f8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
7f62: 2e d0 rcall .+92 ; 0x7fc0 <verifySpace> 7f80: 2e d0 rcall .+92 ; 0x7fde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
7f64: 8e e1 ldi r24, 0x1E ; 30 7f82: 8e e1 ldi r24, 0x1E ; 30
7f66: 0c d0 rcall .+24 ; 0x7f80 <putch> 7f84: 0c d0 rcall .+24 ; 0x7f9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
7f68: 85 e9 ldi r24, 0x95 ; 149 7f86: 85 e9 ldi r24, 0x95 ; 149
7f6a: 0a d0 rcall .+20 ; 0x7f80 <putch> 7f88: 0a d0 rcall .+20 ; 0x7f9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
7f6c: 8f e0 ldi r24, 0x0F ; 15 7f8a: 8f e0 ldi r24, 0x0F ; 15
7f6e: 9a cf rjmp .-204 ; 0x7ea4 <main+0xa4> 7f8c: 8b cf rjmp .-234 ; 0x7ea4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
7f70: 81 35 cpi r24, 0x51 ; 81 7f8e: 81 35 cpi r24, 0x51 ; 81
7f72: 11 f4 brne .+4 ; 0x7f78 <main+0x178> 7f90: 11 f4 brne .+4 ; 0x7f96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
7f74: 88 e0 ldi r24, 0x08 ; 8 7f92: 88 e0 ldi r24, 0x08 ; 8
7f76: 19 d0 rcall .+50 ; 0x7faa <watchdogConfig> 7f94: 19 d0 rcall .+50 ; 0x7fc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
7f78: 23 d0 rcall .+70 ; 0x7fc0 <verifySpace> 7f96: 23 d0 rcall .+70 ; 0x7fde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
7f7a: 80 e1 ldi r24, 0x10 ; 16 7f98: 80 e1 ldi r24, 0x10 ; 16
7f7c: 01 d0 rcall .+2 ; 0x7f80 <putch> 7f9a: 01 d0 rcall .+2 ; 0x7f9e <putch>
7f7e: 6b cf rjmp .-298 ; 0x7e56 <main+0x56> 7f9c: 5c cf rjmp .-328 ; 0x7e56 <main+0x56>
00007f80 <putch>: 00007f9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
7f80: 98 2f mov r25, r24 7f9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
7f82: 80 91 c0 00 lds r24, 0x00C0 7fa0: 80 91 c0 00 lds r24, 0x00C0
7f86: 85 ff sbrs r24, 5 7fa4: 85 ff sbrs r24, 5
7f88: fc cf rjmp .-8 ; 0x7f82 <putch+0x2> 7fa6: fc cf rjmp .-8 ; 0x7fa0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
7f8a: 90 93 c6 00 sts 0x00C6, r25 7fa8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
7f8e: 08 95 ret 7fac: 08 95 ret
00007f90 <getch>: 00007fae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
7f90: a8 95 wdr 7fae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
7f92: 80 91 c0 00 lds r24, 0x00C0 7fb0: 80 91 c0 00 lds r24, 0x00C0
7f96: 87 ff sbrs r24, 7 7fb4: 87 ff sbrs r24, 7
7f98: fc cf rjmp .-8 ; 0x7f92 <getch+0x2> 7fb6: fc cf rjmp .-8 ; 0x7fb0 <getch+0x2>
ch = UDR0; ch = UDR0;
7f9a: 80 91 c6 00 lds r24, 0x00C6 7fb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
7f9e: 08 95 ret 7fbc: 08 95 ret
00007fa0 <getLen>: 00007fbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
7fa0: f7 df rcall .-18 ; 0x7f90 <getch> 7fbe: f7 df rcall .-18 ; 0x7fae <getch>
length = getch(); length = getch();
7fa2: f6 df rcall .-20 ; 0x7f90 <getch> 7fc0: f6 df rcall .-20 ; 0x7fae <getch>
7fa4: 80 93 02 02 sts 0x0202, r24 7fc2: 80 93 02 02 sts 0x0202, r24
return getch(); return getch();
} }
7fa8: f3 cf rjmp .-26 ; 0x7f90 <getch> 7fc6: f3 cf rjmp .-26 ; 0x7fae <getch>
00007faa <watchdogConfig>: 00007fc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
7faa: e0 e6 ldi r30, 0x60 ; 96 7fc8: e0 e6 ldi r30, 0x60 ; 96
7fac: f0 e0 ldi r31, 0x00 ; 0 7fca: f0 e0 ldi r31, 0x00 ; 0
7fae: 98 e1 ldi r25, 0x18 ; 24 7fcc: 98 e1 ldi r25, 0x18 ; 24
7fb0: 90 83 st Z, r25 7fce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
7fb2: 80 83 st Z, r24 7fd0: 80 83 st Z, r24
} }
7fb4: 08 95 ret 7fd2: 08 95 ret
00007fb6 <appStart>: 00007fd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
7fb6: 80 e0 ldi r24, 0x00 ; 0 7fd4: 80 e0 ldi r24, 0x00 ; 0
7fb8: f8 df rcall .-16 ; 0x7faa <watchdogConfig> 7fd6: f8 df rcall .-16 ; 0x7fc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
7fba: ee 27 eor r30, r30 7fd8: ee 27 eor r30, r30
7fbc: ff 27 eor r31, r31 7fda: ff 27 eor r31, r31
7fbe: 09 94 ijmp 7fdc: 09 94 ijmp
00007fc0 <verifySpace>: 00007fde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
7fc0: e7 df rcall .-50 ; 0x7f90 <getch> 7fde: e7 df rcall .-50 ; 0x7fae <getch>
7fc2: 80 32 cpi r24, 0x20 ; 32 7fe0: 80 32 cpi r24, 0x20 ; 32
7fc4: 09 f0 breq .+2 ; 0x7fc8 <verifySpace+0x8> 7fe2: 09 f0 breq .+2 ; 0x7fe6 <verifySpace+0x8>
7fc6: f7 df rcall .-18 ; 0x7fb6 <appStart> 7fe4: f7 df rcall .-18 ; 0x7fd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
7fc8: 84 e1 ldi r24, 0x14 ; 20 7fe6: 84 e1 ldi r24, 0x14 ; 20
} }
7fca: da cf rjmp .-76 ; 0x7f80 <putch> 7fe8: da cf rjmp .-76 ; 0x7f9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
7fcc: 1f 93 push r17 7fea: 1f 93 push r17
7fce: 18 2f mov r17, r24 7fec: 18 2f mov r17, r24
00007fd0 <getNch>: 00007fee <getNch>:
do getch(); while (--count); do getch(); while (--count);
7fd0: df df rcall .-66 ; 0x7f90 <getch> 7fee: df df rcall .-66 ; 0x7fae <getch>
7fd2: 11 50 subi r17, 0x01 ; 1 7ff0: 11 50 subi r17, 0x01 ; 1
7fd4: e9 f7 brne .-6 ; 0x7fd0 <getNch> 7ff2: e9 f7 brne .-6 ; 0x7fee <getNch>
verifySpace(); verifySpace();
7fd6: f4 df rcall .-24 ; 0x7fc0 <verifySpace> 7ff4: f4 df rcall .-24 ; 0x7fde <verifySpace>
} }
7fd8: 1f 91 pop r17 7ff6: 1f 91 pop r17
7fda: 08 95 ret 7ff8: 08 95 ret

View File

@ -1,32 +1,34 @@
:10FC000085E08093810082E08093C00088E180934A :10FC000085E08093810082E08093C00088E180934A
:10FC1000C10086E08093C20080E18093C40084B775 :10FC1000C10086E08093C20080E18093C40084B775
:10FC200014BE81FFC8D08DE0C0D0209A86E020E3CA :10FC200014BE81FFD7D08DE0CFD0209A86E020E3AC
:10FC30003CEF91E0309385002093840096BBB09B0D :10FC30003CEF91E0309385002093840096BBB09B0D
:10FC4000FECF189AA8958150A9F7DD24D394A5E09A :10FC4000FECF189AA8958150A9F7DD24D394A5E09A
:10FC5000FA2EF1E1EF2E9CD0813421F481E0B6D070 :10FC5000EA2EF1E1FF2EABD0813421F481E0C5D052
:10FC600083E020C0823411F484E103C0853419F4A8 :10FC600083E020C0823411F484E103C0853419F4A8
:10FC700085E0ACD082C0853581F48AD0082F10E0B1 :10FC700085E0BBD091C0853581F499D0082F10E084
:10FC800087D090E0982F8827802B912B880F991F81 :10FC800096D090E0982F8827802B912B880F991F72
:10FC900090930103809300036FC0863529F484E0BC :10FC900090930103809300037EC0863529F484E0AD
:10FCA00095D080E06DD069C0843609F03FC078D02F :10FCA000A4D080E07CD078C0843609F04EC087D0E4
:10FCB000E0910003F091010383E087BFE895C0E085 :10FCB000E0910003F091010380EEE030F80718F4C2
:10FCC000D1E066D089938091020381508093020332 :10FCC00083E087BFE895C0E0D1E071D0899380914F
:10FCD0008823B9F775D007B600FCFDCF409100032B :10FCD00002038150809302038823B9F7E091000367
:10FCE00050910103A0E0B1E02C9130E011968C918D :10FCE000F091010380EEE030F80718F083E087BF61
:10FCF000119790E0982F8827822B932B1296FA0168 :10FCF000E89575D007B600FCFDCF40910003509108
:10FD00000C01D7BEE89511244E5F5F4FF2E0A030A2 :10FD00000103A0E0B1E02C9130E011968C911197A5
:10FD1000BF0751F7E0910003F0910103F7BEE895AA :10FD100090E0982F8827822B932B1296FA010C01E2
:10FD200007B600FCFDCFE7BEE89527C08437B9F4DD :10FD2000D7BEE89511244E5F5F4FF2E0A030BF07C9
:10FD300037D046D0E0910003F09101033196F09363 :10FD300051F7E0910003F0910103E7BEE89507B6A3
:10FD40000103E09300033197E4918E2F19D0809145 :10FD400000FCFDCFF7BEE89527C08437B9F437D063
:10FD50000203815080930203882361F70EC0853728 :10FD500046D0E0910003F09101033196F093010346
:10FD600039F42ED08EE10CD086E90AD08AE09ACF01 :10FD6000E09300033197E4918E2F19D08091020324
:10FD7000813511F488E019D023D080E101D06BCF18 :10FD7000815080930203882361F70EC0853739F4E0
:10FD8000982F8091C00085FFFCCF9093C600089506 :10FD80002ED08EE10CD086E90AD08AE08BCF813567
:10FD9000A8958091C00087FFFCCF8091C600089590 :10FD900011F488E019D023D080E101D05CCF982FF6
:10FDA000F7DFF6DF80930203F3CFE0E6F0E098E1BF :10FDA0008091C00085FFFCCF9093C6000895A89570
:10FDB00090838083089580E0F8DFEE27FF27099481 :10FDB0008091C00087FFFCCF8091C6000895F7DFD7
:10FDC000E7DF803209F0F7DF84E1DACF1F93182FE5 :10FDC000F6DF80930203F3CFE0E6F0E098E1908362
:0CFDD000DFDF1150E9F7F4DF1F91089508 :10FDD0008083089580E0F8DFEE27FF270994E7DFAE
:10FDE000803209F0F7DF84E1DACF1F93182FDFDFCD
:0AFDF0001150E9F7F4DF1F910895A8
:040000030000FC00FD :040000030000FC00FD
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_atmega644p.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 0000fc00 0000fc00 00000054 2**1 0 .text 000001fa 0000fc00 0000fc00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
fc20: 14 be out 0x34, r1 ; 52 fc20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
fc22: 81 ff sbrs r24, 1 fc22: 81 ff sbrs r24, 1
fc24: c8 d0 rcall .+400 ; 0xfdb6 <appStart> fc24: d7 d0 rcall .+430 ; 0xfdd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
fc26: 8d e0 ldi r24, 0x0D ; 13 fc26: 8d e0 ldi r24, 0x0D ; 13
fc28: c0 d0 rcall .+384 ; 0xfdaa <watchdogConfig> fc28: cf d0 rcall .+414 ; 0xfdc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
fc4e: a5 e0 ldi r26, 0x05 ; 5 fc4e: a5 e0 ldi r26, 0x05 ; 5
fc50: fa 2e mov r15, r26 fc50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
fc52: f1 e1 ldi r31, 0x11 ; 17 fc52: f1 e1 ldi r31, 0x11 ; 17
fc54: ef 2e mov r14, r31 fc54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
fc56: 9c d0 rcall .+312 ; 0xfd90 <getch> fc56: ab d0 rcall .+342 ; 0xfdae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
fc58: 81 34 cpi r24, 0x41 ; 65 fc58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
fc5c: 81 e0 ldi r24, 0x01 ; 1 fc5c: 81 e0 ldi r24, 0x01 ; 1
fc5e: b6 d0 rcall .+364 ; 0xfdcc <verifySpace+0xc> fc5e: c5 d0 rcall .+394 ; 0xfdea <verifySpace+0xc>
putch(0x03); putch(0x03);
fc60: 83 e0 ldi r24, 0x03 ; 3 fc60: 83 e0 ldi r24, 0x03 ; 3
fc62: 20 c0 rjmp .+64 ; 0xfca4 <main+0xa4> fc62: 20 c0 rjmp .+64 ; 0xfca4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
fc70: 85 e0 ldi r24, 0x05 ; 5 fc70: 85 e0 ldi r24, 0x05 ; 5
fc72: ac d0 rcall .+344 ; 0xfdcc <verifySpace+0xc> fc72: bb d0 rcall .+374 ; 0xfdea <verifySpace+0xc>
fc74: 82 c0 rjmp .+260 ; 0xfd7a <main+0x17a> fc74: 91 c0 rjmp .+290 ; 0xfd98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
fc76: 85 35 cpi r24, 0x55 ; 85 fc76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
fc7a: 8a d0 rcall .+276 ; 0xfd90 <getch> fc7a: 99 d0 rcall .+306 ; 0xfdae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
fc7c: 08 2f mov r16, r24 fc7c: 08 2f mov r16, r24
fc7e: 10 e0 ldi r17, 0x00 ; 0 fc7e: 10 e0 ldi r17, 0x00 ; 0
fc80: 87 d0 rcall .+270 ; 0xfd90 <getch> fc80: 96 d0 rcall .+300 ; 0xfdae <getch>
fc82: 90 e0 ldi r25, 0x00 ; 0 fc82: 90 e0 ldi r25, 0x00 ; 0
fc84: 98 2f mov r25, r24 fc84: 98 2f mov r25, r24
fc86: 88 27 eor r24, r24 fc86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
fc90: 90 93 01 03 sts 0x0301, r25 fc90: 90 93 01 03 sts 0x0301, r25
fc94: 80 93 00 03 sts 0x0300, r24 fc94: 80 93 00 03 sts 0x0300, r24
fc98: 6f c0 rjmp .+222 ; 0xfd78 <main+0x178> fc98: 7e c0 rjmp .+252 ; 0xfd96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
fc9e: 84 e0 ldi r24, 0x04 ; 4 fc9e: 84 e0 ldi r24, 0x04 ; 4
fca0: 95 d0 rcall .+298 ; 0xfdcc <verifySpace+0xc> fca0: a4 d0 rcall .+328 ; 0xfdea <verifySpace+0xc>
putch(0x00); putch(0x00);
fca2: 80 e0 ldi r24, 0x00 ; 0 fca2: 80 e0 ldi r24, 0x00 ; 0
fca4: 6d d0 rcall .+218 ; 0xfd80 <putch> fca4: 7c d0 rcall .+248 ; 0xfd9e <putch>
fca6: 69 c0 rjmp .+210 ; 0xfd7a <main+0x17a> fca6: 78 c0 rjmp .+240 ; 0xfd98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
fca8: 84 36 cpi r24, 0x64 ; 100 fca8: 84 36 cpi r24, 0x64 ; 100
fcaa: 09 f0 breq .+2 ; 0xfcae <main+0xae> fcaa: 09 f0 breq .+2 ; 0xfcae <main+0xae>
fcac: 3f c0 rjmp .+126 ; 0xfd2c <main+0x12c> fcac: 4e c0 rjmp .+156 ; 0xfd4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
fcae: 78 d0 rcall .+240 ; 0xfda0 <getLen> fcae: 87 d0 rcall .+270 ; 0xfdbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
fcb0: e0 91 00 03 lds r30, 0x0300 fcb0: e0 91 00 03 lds r30, 0x0300
fcb4: f0 91 01 03 lds r31, 0x0301 fcb4: f0 91 01 03 lds r31, 0x0301
fcb8: 83 e0 ldi r24, 0x03 ; 3 fcb8: 80 ee ldi r24, 0xE0 ; 224
fcba: 87 bf out 0x37, r24 ; 55 fcba: e0 30 cpi r30, 0x00 ; 0
fcbc: e8 95 spm fcbc: f8 07 cpc r31, r24
fcbe: c0 e0 ldi r28, 0x00 ; 0 fcbe: 18 f4 brcc .+6 ; 0xfcc6 <main+0xc6>
fcc0: d1 e0 ldi r29, 0x01 ; 1 fcc0: 83 e0 ldi r24, 0x03 ; 3
fcc2: 87 bf out 0x37, r24 ; 55
fcc4: e8 95 spm
fcc6: c0 e0 ldi r28, 0x00 ; 0
fcc8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
fcc2: 66 d0 rcall .+204 ; 0xfd90 <getch> fcca: 71 d0 rcall .+226 ; 0xfdae <getch>
fcc4: 89 93 st Y+, r24 fccc: 89 93 st Y+, r24
while (--length); while (--length);
fcc6: 80 91 02 03 lds r24, 0x0302 fcce: 80 91 02 03 lds r24, 0x0302
fcca: 81 50 subi r24, 0x01 ; 1 fcd2: 81 50 subi r24, 0x01 ; 1
fccc: 80 93 02 03 sts 0x0302, r24 fcd4: 80 93 02 03 sts 0x0302, r24
fcd0: 88 23 and r24, r24 fcd8: 88 23 and r24, r24
fcd2: b9 f7 brne .-18 ; 0xfcc2 <main+0xc2> fcda: b9 f7 brne .-18 ; 0xfcca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
fcdc: e0 91 00 03 lds r30, 0x0300
fce0: f0 91 01 03 lds r31, 0x0301
fce4: 80 ee ldi r24, 0xE0 ; 224
fce6: e0 30 cpi r30, 0x00 ; 0
fce8: f8 07 cpc r31, r24
fcea: 18 f0 brcs .+6 ; 0xfcf2 <main+0xf2>
fcec: 83 e0 ldi r24, 0x03 ; 3
fcee: 87 bf out 0x37, r24 ; 55
fcf0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
fcd4: 75 d0 rcall .+234 ; 0xfdc0 <verifySpace> fcf2: 75 d0 rcall .+234 ; 0xfdde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
fcd6: 07 b6 in r0, 0x37 ; 55 fcf4: 07 b6 in r0, 0x37 ; 55
fcd8: 00 fc sbrc r0, 0 fcf6: 00 fc sbrc r0, 0
fcda: fd cf rjmp .-6 ; 0xfcd6 <main+0xd6> fcf8: fd cf rjmp .-6 ; 0xfcf4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
fcdc: 40 91 00 03 lds r20, 0x0300 fcfa: 40 91 00 03 lds r20, 0x0300
fce0: 50 91 01 03 lds r21, 0x0301 fcfe: 50 91 01 03 lds r21, 0x0301
fce4: a0 e0 ldi r26, 0x00 ; 0 fd02: a0 e0 ldi r26, 0x00 ; 0
fce6: b1 e0 ldi r27, 0x01 ; 1 fd04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
fce8: 2c 91 ld r18, X fd06: 2c 91 ld r18, X
fcea: 30 e0 ldi r19, 0x00 ; 0 fd08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
fcec: 11 96 adiw r26, 0x01 ; 1 fd0a: 11 96 adiw r26, 0x01 ; 1
fcee: 8c 91 ld r24, X fd0c: 8c 91 ld r24, X
fcf0: 11 97 sbiw r26, 0x01 ; 1 fd0e: 11 97 sbiw r26, 0x01 ; 1
fcf2: 90 e0 ldi r25, 0x00 ; 0 fd10: 90 e0 ldi r25, 0x00 ; 0
fcf4: 98 2f mov r25, r24 fd12: 98 2f mov r25, r24
fcf6: 88 27 eor r24, r24 fd14: 88 27 eor r24, r24
fcf8: 82 2b or r24, r18 fd16: 82 2b or r24, r18
fcfa: 93 2b or r25, r19 fd18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
fcfc: 12 96 adiw r26, 0x02 ; 2 fd1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
fcfe: fa 01 movw r30, r20 fd1c: fa 01 movw r30, r20
fd00: 0c 01 movw r0, r24 fd1e: 0c 01 movw r0, r24
fd02: d7 be out 0x37, r13 ; 55 fd20: d7 be out 0x37, r13 ; 55
fd04: e8 95 spm fd22: e8 95 spm
fd06: 11 24 eor r1, r1 fd24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
fd08: 4e 5f subi r20, 0xFE ; 254 fd26: 4e 5f subi r20, 0xFE ; 254
fd0a: 5f 4f sbci r21, 0xFF ; 255 fd28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
fd0c: f2 e0 ldi r31, 0x02 ; 2 fd2a: f2 e0 ldi r31, 0x02 ; 2
fd0e: a0 30 cpi r26, 0x00 ; 0 fd2c: a0 30 cpi r26, 0x00 ; 0
fd10: bf 07 cpc r27, r31 fd2e: bf 07 cpc r27, r31
fd12: 51 f7 brne .-44 ; 0xfce8 <main+0xe8> fd30: 51 f7 brne .-44 ; 0xfd06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
fd14: e0 91 00 03 lds r30, 0x0300 fd32: e0 91 00 03 lds r30, 0x0300
fd18: f0 91 01 03 lds r31, 0x0301 fd36: f0 91 01 03 lds r31, 0x0301
fd1c: f7 be out 0x37, r15 ; 55 fd3a: e7 be out 0x37, r14 ; 55
fd1e: e8 95 spm fd3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
fd20: 07 b6 in r0, 0x37 ; 55 fd3e: 07 b6 in r0, 0x37 ; 55
fd22: 00 fc sbrc r0, 0 fd40: 00 fc sbrc r0, 0
fd24: fd cf rjmp .-6 ; 0xfd20 <main+0x120> fd42: fd cf rjmp .-6 ; 0xfd3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
fd26: e7 be out 0x37, r14 ; 55 fd44: f7 be out 0x37, r15 ; 55
fd28: e8 95 spm fd46: e8 95 spm
fd2a: 27 c0 rjmp .+78 ; 0xfd7a <main+0x17a> fd48: 27 c0 rjmp .+78 ; 0xfd98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
fd2c: 84 37 cpi r24, 0x74 ; 116 fd4a: 84 37 cpi r24, 0x74 ; 116
fd2e: b9 f4 brne .+46 ; 0xfd5e <main+0x15e> fd4c: b9 f4 brne .+46 ; 0xfd7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
fd30: 37 d0 rcall .+110 ; 0xfda0 <getLen> fd4e: 37 d0 rcall .+110 ; 0xfdbe <getLen>
verifySpace(); verifySpace();
fd32: 46 d0 rcall .+140 ; 0xfdc0 <verifySpace> fd50: 46 d0 rcall .+140 ; 0xfdde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
fd34: e0 91 00 03 lds r30, 0x0300 fd52: e0 91 00 03 lds r30, 0x0300
fd38: f0 91 01 03 lds r31, 0x0301 fd56: f0 91 01 03 lds r31, 0x0301
fd3c: 31 96 adiw r30, 0x01 ; 1 fd5a: 31 96 adiw r30, 0x01 ; 1
fd3e: f0 93 01 03 sts 0x0301, r31 fd5c: f0 93 01 03 sts 0x0301, r31
fd42: e0 93 00 03 sts 0x0300, r30 fd60: e0 93 00 03 sts 0x0300, r30
fd46: 31 97 sbiw r30, 0x01 ; 1 fd64: 31 97 sbiw r30, 0x01 ; 1
fd48: e4 91 lpm r30, Z+ fd66: e4 91 lpm r30, Z+
fd4a: 8e 2f mov r24, r30 fd68: 8e 2f mov r24, r30
fd4c: 19 d0 rcall .+50 ; 0xfd80 <putch> fd6a: 19 d0 rcall .+50 ; 0xfd9e <putch>
while (--length); while (--length);
fd4e: 80 91 02 03 lds r24, 0x0302 fd6c: 80 91 02 03 lds r24, 0x0302
fd52: 81 50 subi r24, 0x01 ; 1 fd70: 81 50 subi r24, 0x01 ; 1
fd54: 80 93 02 03 sts 0x0302, r24 fd72: 80 93 02 03 sts 0x0302, r24
fd58: 88 23 and r24, r24 fd76: 88 23 and r24, r24
fd5a: 61 f7 brne .-40 ; 0xfd34 <main+0x134> fd78: 61 f7 brne .-40 ; 0xfd52 <main+0x152>
fd5c: 0e c0 rjmp .+28 ; 0xfd7a <main+0x17a> fd7a: 0e c0 rjmp .+28 ; 0xfd98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
fd5e: 85 37 cpi r24, 0x75 ; 117 fd7c: 85 37 cpi r24, 0x75 ; 117
fd60: 39 f4 brne .+14 ; 0xfd70 <main+0x170> fd7e: 39 f4 brne .+14 ; 0xfd8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
fd62: 2e d0 rcall .+92 ; 0xfdc0 <verifySpace> fd80: 2e d0 rcall .+92 ; 0xfdde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
fd64: 8e e1 ldi r24, 0x1E ; 30 fd82: 8e e1 ldi r24, 0x1E ; 30
fd66: 0c d0 rcall .+24 ; 0xfd80 <putch> fd84: 0c d0 rcall .+24 ; 0xfd9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
fd68: 86 e9 ldi r24, 0x96 ; 150 fd86: 86 e9 ldi r24, 0x96 ; 150
fd6a: 0a d0 rcall .+20 ; 0xfd80 <putch> fd88: 0a d0 rcall .+20 ; 0xfd9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
fd6c: 8a e0 ldi r24, 0x0A ; 10 fd8a: 8a e0 ldi r24, 0x0A ; 10
fd6e: 9a cf rjmp .-204 ; 0xfca4 <main+0xa4> fd8c: 8b cf rjmp .-234 ; 0xfca4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
fd70: 81 35 cpi r24, 0x51 ; 81 fd8e: 81 35 cpi r24, 0x51 ; 81
fd72: 11 f4 brne .+4 ; 0xfd78 <main+0x178> fd90: 11 f4 brne .+4 ; 0xfd96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
fd74: 88 e0 ldi r24, 0x08 ; 8 fd92: 88 e0 ldi r24, 0x08 ; 8
fd76: 19 d0 rcall .+50 ; 0xfdaa <watchdogConfig> fd94: 19 d0 rcall .+50 ; 0xfdc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
fd78: 23 d0 rcall .+70 ; 0xfdc0 <verifySpace> fd96: 23 d0 rcall .+70 ; 0xfdde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
fd7a: 80 e1 ldi r24, 0x10 ; 16 fd98: 80 e1 ldi r24, 0x10 ; 16
fd7c: 01 d0 rcall .+2 ; 0xfd80 <putch> fd9a: 01 d0 rcall .+2 ; 0xfd9e <putch>
fd7e: 6b cf rjmp .-298 ; 0xfc56 <main+0x56> fd9c: 5c cf rjmp .-328 ; 0xfc56 <main+0x56>
0000fd80 <putch>: 0000fd9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
fd80: 98 2f mov r25, r24 fd9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
fd82: 80 91 c0 00 lds r24, 0x00C0 fda0: 80 91 c0 00 lds r24, 0x00C0
fd86: 85 ff sbrs r24, 5 fda4: 85 ff sbrs r24, 5
fd88: fc cf rjmp .-8 ; 0xfd82 <putch+0x2> fda6: fc cf rjmp .-8 ; 0xfda0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
fd8a: 90 93 c6 00 sts 0x00C6, r25 fda8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
fd8e: 08 95 ret fdac: 08 95 ret
0000fd90 <getch>: 0000fdae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
fd90: a8 95 wdr fdae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
fd92: 80 91 c0 00 lds r24, 0x00C0 fdb0: 80 91 c0 00 lds r24, 0x00C0
fd96: 87 ff sbrs r24, 7 fdb4: 87 ff sbrs r24, 7
fd98: fc cf rjmp .-8 ; 0xfd92 <getch+0x2> fdb6: fc cf rjmp .-8 ; 0xfdb0 <getch+0x2>
ch = UDR0; ch = UDR0;
fd9a: 80 91 c6 00 lds r24, 0x00C6 fdb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
fd9e: 08 95 ret fdbc: 08 95 ret
0000fda0 <getLen>: 0000fdbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
fda0: f7 df rcall .-18 ; 0xfd90 <getch> fdbe: f7 df rcall .-18 ; 0xfdae <getch>
length = getch(); length = getch();
fda2: f6 df rcall .-20 ; 0xfd90 <getch> fdc0: f6 df rcall .-20 ; 0xfdae <getch>
fda4: 80 93 02 03 sts 0x0302, r24 fdc2: 80 93 02 03 sts 0x0302, r24
return getch(); return getch();
} }
fda8: f3 cf rjmp .-26 ; 0xfd90 <getch> fdc6: f3 cf rjmp .-26 ; 0xfdae <getch>
0000fdaa <watchdogConfig>: 0000fdc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
fdaa: e0 e6 ldi r30, 0x60 ; 96 fdc8: e0 e6 ldi r30, 0x60 ; 96
fdac: f0 e0 ldi r31, 0x00 ; 0 fdca: f0 e0 ldi r31, 0x00 ; 0
fdae: 98 e1 ldi r25, 0x18 ; 24 fdcc: 98 e1 ldi r25, 0x18 ; 24
fdb0: 90 83 st Z, r25 fdce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
fdb2: 80 83 st Z, r24 fdd0: 80 83 st Z, r24
} }
fdb4: 08 95 ret fdd2: 08 95 ret
0000fdb6 <appStart>: 0000fdd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
fdb6: 80 e0 ldi r24, 0x00 ; 0 fdd4: 80 e0 ldi r24, 0x00 ; 0
fdb8: f8 df rcall .-16 ; 0xfdaa <watchdogConfig> fdd6: f8 df rcall .-16 ; 0xfdc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
fdba: ee 27 eor r30, r30 fdd8: ee 27 eor r30, r30
fdbc: ff 27 eor r31, r31 fdda: ff 27 eor r31, r31
fdbe: 09 94 ijmp fddc: 09 94 ijmp
0000fdc0 <verifySpace>: 0000fdde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
fdc0: e7 df rcall .-50 ; 0xfd90 <getch> fdde: e7 df rcall .-50 ; 0xfdae <getch>
fdc2: 80 32 cpi r24, 0x20 ; 32 fde0: 80 32 cpi r24, 0x20 ; 32
fdc4: 09 f0 breq .+2 ; 0xfdc8 <verifySpace+0x8> fde2: 09 f0 breq .+2 ; 0xfde6 <verifySpace+0x8>
fdc6: f7 df rcall .-18 ; 0xfdb6 <appStart> fde4: f7 df rcall .-18 ; 0xfdd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
fdc8: 84 e1 ldi r24, 0x14 ; 20 fde6: 84 e1 ldi r24, 0x14 ; 20
} }
fdca: da cf rjmp .-76 ; 0xfd80 <putch> fde8: da cf rjmp .-76 ; 0xfd9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
fdcc: 1f 93 push r17 fdea: 1f 93 push r17
fdce: 18 2f mov r17, r24 fdec: 18 2f mov r17, r24
0000fdd0 <getNch>: 0000fdee <getNch>:
do getch(); while (--count); do getch(); while (--count);
fdd0: df df rcall .-66 ; 0xfd90 <getch> fdee: df df rcall .-66 ; 0xfdae <getch>
fdd2: 11 50 subi r17, 0x01 ; 1 fdf0: 11 50 subi r17, 0x01 ; 1
fdd4: e9 f7 brne .-6 ; 0xfdd0 <getNch> fdf2: e9 f7 brne .-6 ; 0xfdee <getNch>
verifySpace(); verifySpace();
fdd6: f4 df rcall .-24 ; 0xfdc0 <verifySpace> fdf4: f4 df rcall .-24 ; 0xfdde <verifySpace>
} }
fdd8: 1f 91 pop r17 fdf6: 1f 91 pop r17
fdda: 08 95 ret fdf8: 08 95 ret

View File

@ -1,32 +1,34 @@
:103E000085E08093810082E08093C00088E1809308 :103E000085E08093810082E08093C00088E1809308
:103E1000C10086E08093C20080E18093C40084B733 :103E1000C10086E08093C20080E18093C40084B733
:103E200014BE81FFC8D08DE0C0D0259A86E020E383 :103E200014BE81FFD7D08DE0CFD0259A86E020E365
:103E30003CEF91E0309385002093840096BBB09BCB :103E30003CEF91E0309385002093840096BBB09BCB
:103E4000FECF1D9AA8958150A9F7DD24D394A5E053 :103E4000FECF1D9AA8958150A9F7DD24D394A5E053
:103E5000FA2EF1E1EF2E9CD0813421F481E0B6D02E :103E5000EA2EF1E1FF2EABD0813421F481E0C5D010
:103E600083E020C0823411F484E103C0853419F466 :103E600083E020C0823411F484E103C0853419F466
:103E700085E0ACD082C0853581F48AD0082F10E06F :103E700085E0BBD091C0853581F499D0082F10E042
:103E800087D090E0982F8827802B912B880F991F3F :103E800096D090E0982F8827802B912B880F991F30
:103E900090930102809300026FC0863529F484E07C :103E900090930102809300027EC0863529F484E06D
:103EA00095D080E06DD069C0843609F03FC078D0ED :103EA000A4D080E07CD078C0843609F04EC087D0A2
:103EB000E0910002F091010283E087BFE895C0E045 :103EB000E0910002F091010288E3E030F80718F485
:103EC000D1E066D0899380910202815080930202F2 :103EC00083E087BFE895C0E0D1E071D0899380910D
:103ED0008823B9F775D007B600FCFDCF40910002EA :103ED00002028150809302028823B9F7E091000228
:103EE00050910102A0E0B1E02C9130E011968C914C :103EE000F091010288E3E030F80718F083E087BF23
:103EF000119790E0982F8827822B932B1296FA0126 :103EF000E89575D007B600FCFDCF409100025091C7
:103F00000C01D7BEE89511244E5F5F4FF1E0A03859 :103F00000102A0E0B1E02C9130E011968C91119764
:103F1000BF0751F7E0910002F0910102F7BEE8956A :103F100090E0982F8827822B932B1296FA010C01A0
:103F200007B600FCFDCFE7BEE89527C08437B9F49B :103F2000D7BEE89511244E5F5F4FF1E0A038BF0780
:103F300037D046D0E0910002F09101023196F09323 :103F300051F7E0910002F0910102E7BEE89507B663
:103F40000102E09300023197E4918E2F19D0809105 :103F400000FCFDCFF7BEE89527C08437B9F437D021
:103F50000202815080930202882361F70EC08537E8 :103F500046D0E0910002F09101023196F093010207
:103F600039F42ED08EE10CD084E90AD086E09ACFC5 :103F6000E09300023197E4918E2F19D080910202E4
:103F7000813511F488E019D023D080E101D06BCFD6 :103F7000815080930202882361F70EC0853739F49F
:103F8000982F8091C00085FFFCCF9093C6000895C4 :103F80002ED08EE10CD084E90AD086E08BCF81352B
:103F9000A8958091C00087FFFCCF8091C60008954E :103F900011F488E019D023D080E101D05CCF982FB4
:103FA000F7DFF6DF80930202F3CFE0E6F0E098E17E :103FA0008091C00085FFFCCF9093C6000895A8952E
:103FB00090838083089580E0F8DFEE27FF2709943F :103FB0008091C00087FFFCCF8091C6000895F7DF95
:103FC000E7DF803209F0F7DF84E1DACF1F93182FA3 :103FC000F6DF80930202F3CFE0E6F0E098E1908321
:0C3FD000DFDF1150E9F7F4DF1F910895C6 :103FD0008083089580E0F8DFEE27FF270994E7DF6C
:103FE000803209F0F7DF84E1DACF1F93182FDFDF8B
:0A3FF0001150E9F7F4DF1F91089566
:0400000300003E00BB :0400000300003E00BB
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_diecimila.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 00003e00 00003e00 00000054 2**1 0 .text 000001fa 00003e00 00003e00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
3e20: 14 be out 0x34, r1 ; 52 3e20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
3e22: 81 ff sbrs r24, 1 3e22: 81 ff sbrs r24, 1
3e24: c8 d0 rcall .+400 ; 0x3fb6 <appStart> 3e24: d7 d0 rcall .+430 ; 0x3fd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
3e26: 8d e0 ldi r24, 0x0D ; 13 3e26: 8d e0 ldi r24, 0x0D ; 13
3e28: c0 d0 rcall .+384 ; 0x3faa <watchdogConfig> 3e28: cf d0 rcall .+414 ; 0x3fc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3e4e: a5 e0 ldi r26, 0x05 ; 5 3e4e: a5 e0 ldi r26, 0x05 ; 5
3e50: fa 2e mov r15, r26 3e50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3e52: f1 e1 ldi r31, 0x11 ; 17 3e52: f1 e1 ldi r31, 0x11 ; 17
3e54: ef 2e mov r14, r31 3e54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
3e56: 9c d0 rcall .+312 ; 0x3f90 <getch> 3e56: ab d0 rcall .+342 ; 0x3fae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
3e58: 81 34 cpi r24, 0x41 ; 65 3e58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
3e5c: 81 e0 ldi r24, 0x01 ; 1 3e5c: 81 e0 ldi r24, 0x01 ; 1
3e5e: b6 d0 rcall .+364 ; 0x3fcc <verifySpace+0xc> 3e5e: c5 d0 rcall .+394 ; 0x3fea <verifySpace+0xc>
putch(0x03); putch(0x03);
3e60: 83 e0 ldi r24, 0x03 ; 3 3e60: 83 e0 ldi r24, 0x03 ; 3
3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4> 3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
3e70: 85 e0 ldi r24, 0x05 ; 5 3e70: 85 e0 ldi r24, 0x05 ; 5
3e72: ac d0 rcall .+344 ; 0x3fcc <verifySpace+0xc> 3e72: bb d0 rcall .+374 ; 0x3fea <verifySpace+0xc>
3e74: 82 c0 rjmp .+260 ; 0x3f7a <main+0x17a> 3e74: 91 c0 rjmp .+290 ; 0x3f98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
3e76: 85 35 cpi r24, 0x55 ; 85 3e76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
3e7a: 8a d0 rcall .+276 ; 0x3f90 <getch> 3e7a: 99 d0 rcall .+306 ; 0x3fae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
3e7c: 08 2f mov r16, r24 3e7c: 08 2f mov r16, r24
3e7e: 10 e0 ldi r17, 0x00 ; 0 3e7e: 10 e0 ldi r17, 0x00 ; 0
3e80: 87 d0 rcall .+270 ; 0x3f90 <getch> 3e80: 96 d0 rcall .+300 ; 0x3fae <getch>
3e82: 90 e0 ldi r25, 0x00 ; 0 3e82: 90 e0 ldi r25, 0x00 ; 0
3e84: 98 2f mov r25, r24 3e84: 98 2f mov r25, r24
3e86: 88 27 eor r24, r24 3e86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
3e90: 90 93 01 02 sts 0x0201, r25 3e90: 90 93 01 02 sts 0x0201, r25
3e94: 80 93 00 02 sts 0x0200, r24 3e94: 80 93 00 02 sts 0x0200, r24
3e98: 6f c0 rjmp .+222 ; 0x3f78 <main+0x178> 3e98: 7e c0 rjmp .+252 ; 0x3f96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
3e9e: 84 e0 ldi r24, 0x04 ; 4 3e9e: 84 e0 ldi r24, 0x04 ; 4
3ea0: 95 d0 rcall .+298 ; 0x3fcc <verifySpace+0xc> 3ea0: a4 d0 rcall .+328 ; 0x3fea <verifySpace+0xc>
putch(0x00); putch(0x00);
3ea2: 80 e0 ldi r24, 0x00 ; 0 3ea2: 80 e0 ldi r24, 0x00 ; 0
3ea4: 6d d0 rcall .+218 ; 0x3f80 <putch> 3ea4: 7c d0 rcall .+248 ; 0x3f9e <putch>
3ea6: 69 c0 rjmp .+210 ; 0x3f7a <main+0x17a> 3ea6: 78 c0 rjmp .+240 ; 0x3f98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
3ea8: 84 36 cpi r24, 0x64 ; 100 3ea8: 84 36 cpi r24, 0x64 ; 100
3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae> 3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae>
3eac: 3f c0 rjmp .+126 ; 0x3f2c <main+0x12c> 3eac: 4e c0 rjmp .+156 ; 0x3f4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
3eae: 78 d0 rcall .+240 ; 0x3fa0 <getLen> 3eae: 87 d0 rcall .+270 ; 0x3fbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3eb0: e0 91 00 02 lds r30, 0x0200 3eb0: e0 91 00 02 lds r30, 0x0200
3eb4: f0 91 01 02 lds r31, 0x0201 3eb4: f0 91 01 02 lds r31, 0x0201
3eb8: 83 e0 ldi r24, 0x03 ; 3 3eb8: 88 e3 ldi r24, 0x38 ; 56
3eba: 87 bf out 0x37, r24 ; 55 3eba: e0 30 cpi r30, 0x00 ; 0
3ebc: e8 95 spm 3ebc: f8 07 cpc r31, r24
3ebe: c0 e0 ldi r28, 0x00 ; 0 3ebe: 18 f4 brcc .+6 ; 0x3ec6 <main+0xc6>
3ec0: d1 e0 ldi r29, 0x01 ; 1 3ec0: 83 e0 ldi r24, 0x03 ; 3
3ec2: 87 bf out 0x37, r24 ; 55
3ec4: e8 95 spm
3ec6: c0 e0 ldi r28, 0x00 ; 0
3ec8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
3ec2: 66 d0 rcall .+204 ; 0x3f90 <getch> 3eca: 71 d0 rcall .+226 ; 0x3fae <getch>
3ec4: 89 93 st Y+, r24 3ecc: 89 93 st Y+, r24
while (--length); while (--length);
3ec6: 80 91 02 02 lds r24, 0x0202 3ece: 80 91 02 02 lds r24, 0x0202
3eca: 81 50 subi r24, 0x01 ; 1 3ed2: 81 50 subi r24, 0x01 ; 1
3ecc: 80 93 02 02 sts 0x0202, r24 3ed4: 80 93 02 02 sts 0x0202, r24
3ed0: 88 23 and r24, r24 3ed8: 88 23 and r24, r24
3ed2: b9 f7 brne .-18 ; 0x3ec2 <main+0xc2> 3eda: b9 f7 brne .-18 ; 0x3eca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3edc: e0 91 00 02 lds r30, 0x0200
3ee0: f0 91 01 02 lds r31, 0x0201
3ee4: 88 e3 ldi r24, 0x38 ; 56
3ee6: e0 30 cpi r30, 0x00 ; 0
3ee8: f8 07 cpc r31, r24
3eea: 18 f0 brcs .+6 ; 0x3ef2 <main+0xf2>
3eec: 83 e0 ldi r24, 0x03 ; 3
3eee: 87 bf out 0x37, r24 ; 55
3ef0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
3ed4: 75 d0 rcall .+234 ; 0x3fc0 <verifySpace> 3ef2: 75 d0 rcall .+234 ; 0x3fde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
3ed6: 07 b6 in r0, 0x37 ; 55 3ef4: 07 b6 in r0, 0x37 ; 55
3ed8: 00 fc sbrc r0, 0 3ef6: 00 fc sbrc r0, 0
3eda: fd cf rjmp .-6 ; 0x3ed6 <main+0xd6> 3ef8: fd cf rjmp .-6 ; 0x3ef4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
3edc: 40 91 00 02 lds r20, 0x0200 3efa: 40 91 00 02 lds r20, 0x0200
3ee0: 50 91 01 02 lds r21, 0x0201 3efe: 50 91 01 02 lds r21, 0x0201
3ee4: a0 e0 ldi r26, 0x00 ; 0 3f02: a0 e0 ldi r26, 0x00 ; 0
3ee6: b1 e0 ldi r27, 0x01 ; 1 3f04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
3ee8: 2c 91 ld r18, X 3f06: 2c 91 ld r18, X
3eea: 30 e0 ldi r19, 0x00 ; 0 3f08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
3eec: 11 96 adiw r26, 0x01 ; 1 3f0a: 11 96 adiw r26, 0x01 ; 1
3eee: 8c 91 ld r24, X 3f0c: 8c 91 ld r24, X
3ef0: 11 97 sbiw r26, 0x01 ; 1 3f0e: 11 97 sbiw r26, 0x01 ; 1
3ef2: 90 e0 ldi r25, 0x00 ; 0 3f10: 90 e0 ldi r25, 0x00 ; 0
3ef4: 98 2f mov r25, r24 3f12: 98 2f mov r25, r24
3ef6: 88 27 eor r24, r24 3f14: 88 27 eor r24, r24
3ef8: 82 2b or r24, r18 3f16: 82 2b or r24, r18
3efa: 93 2b or r25, r19 3f18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
3efc: 12 96 adiw r26, 0x02 ; 2 3f1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
3efe: fa 01 movw r30, r20 3f1c: fa 01 movw r30, r20
3f00: 0c 01 movw r0, r24 3f1e: 0c 01 movw r0, r24
3f02: d7 be out 0x37, r13 ; 55 3f20: d7 be out 0x37, r13 ; 55
3f04: e8 95 spm 3f22: e8 95 spm
3f06: 11 24 eor r1, r1 3f24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
3f08: 4e 5f subi r20, 0xFE ; 254 3f26: 4e 5f subi r20, 0xFE ; 254
3f0a: 5f 4f sbci r21, 0xFF ; 255 3f28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
3f0c: f1 e0 ldi r31, 0x01 ; 1 3f2a: f1 e0 ldi r31, 0x01 ; 1
3f0e: a0 38 cpi r26, 0x80 ; 128 3f2c: a0 38 cpi r26, 0x80 ; 128
3f10: bf 07 cpc r27, r31 3f2e: bf 07 cpc r27, r31
3f12: 51 f7 brne .-44 ; 0x3ee8 <main+0xe8> 3f30: 51 f7 brne .-44 ; 0x3f06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3f14: e0 91 00 02 lds r30, 0x0200 3f32: e0 91 00 02 lds r30, 0x0200
3f18: f0 91 01 02 lds r31, 0x0201 3f36: f0 91 01 02 lds r31, 0x0201
3f1c: f7 be out 0x37, r15 ; 55 3f3a: e7 be out 0x37, r14 ; 55
3f1e: e8 95 spm 3f3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
3f20: 07 b6 in r0, 0x37 ; 55 3f3e: 07 b6 in r0, 0x37 ; 55
3f22: 00 fc sbrc r0, 0 3f40: 00 fc sbrc r0, 0
3f24: fd cf rjmp .-6 ; 0x3f20 <main+0x120> 3f42: fd cf rjmp .-6 ; 0x3f3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3f26: e7 be out 0x37, r14 ; 55 3f44: f7 be out 0x37, r15 ; 55
3f28: e8 95 spm 3f46: e8 95 spm
3f2a: 27 c0 rjmp .+78 ; 0x3f7a <main+0x17a> 3f48: 27 c0 rjmp .+78 ; 0x3f98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
3f2c: 84 37 cpi r24, 0x74 ; 116 3f4a: 84 37 cpi r24, 0x74 ; 116
3f2e: b9 f4 brne .+46 ; 0x3f5e <main+0x15e> 3f4c: b9 f4 brne .+46 ; 0x3f7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
3f30: 37 d0 rcall .+110 ; 0x3fa0 <getLen> 3f4e: 37 d0 rcall .+110 ; 0x3fbe <getLen>
verifySpace(); verifySpace();
3f32: 46 d0 rcall .+140 ; 0x3fc0 <verifySpace> 3f50: 46 d0 rcall .+140 ; 0x3fde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
3f34: e0 91 00 02 lds r30, 0x0200 3f52: e0 91 00 02 lds r30, 0x0200
3f38: f0 91 01 02 lds r31, 0x0201 3f56: f0 91 01 02 lds r31, 0x0201
3f3c: 31 96 adiw r30, 0x01 ; 1 3f5a: 31 96 adiw r30, 0x01 ; 1
3f3e: f0 93 01 02 sts 0x0201, r31 3f5c: f0 93 01 02 sts 0x0201, r31
3f42: e0 93 00 02 sts 0x0200, r30 3f60: e0 93 00 02 sts 0x0200, r30
3f46: 31 97 sbiw r30, 0x01 ; 1 3f64: 31 97 sbiw r30, 0x01 ; 1
3f48: e4 91 lpm r30, Z+ 3f66: e4 91 lpm r30, Z+
3f4a: 8e 2f mov r24, r30 3f68: 8e 2f mov r24, r30
3f4c: 19 d0 rcall .+50 ; 0x3f80 <putch> 3f6a: 19 d0 rcall .+50 ; 0x3f9e <putch>
while (--length); while (--length);
3f4e: 80 91 02 02 lds r24, 0x0202 3f6c: 80 91 02 02 lds r24, 0x0202
3f52: 81 50 subi r24, 0x01 ; 1 3f70: 81 50 subi r24, 0x01 ; 1
3f54: 80 93 02 02 sts 0x0202, r24 3f72: 80 93 02 02 sts 0x0202, r24
3f58: 88 23 and r24, r24 3f76: 88 23 and r24, r24
3f5a: 61 f7 brne .-40 ; 0x3f34 <main+0x134> 3f78: 61 f7 brne .-40 ; 0x3f52 <main+0x152>
3f5c: 0e c0 rjmp .+28 ; 0x3f7a <main+0x17a> 3f7a: 0e c0 rjmp .+28 ; 0x3f98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
3f5e: 85 37 cpi r24, 0x75 ; 117 3f7c: 85 37 cpi r24, 0x75 ; 117
3f60: 39 f4 brne .+14 ; 0x3f70 <main+0x170> 3f7e: 39 f4 brne .+14 ; 0x3f8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
3f62: 2e d0 rcall .+92 ; 0x3fc0 <verifySpace> 3f80: 2e d0 rcall .+92 ; 0x3fde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
3f64: 8e e1 ldi r24, 0x1E ; 30 3f82: 8e e1 ldi r24, 0x1E ; 30
3f66: 0c d0 rcall .+24 ; 0x3f80 <putch> 3f84: 0c d0 rcall .+24 ; 0x3f9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
3f68: 84 e9 ldi r24, 0x94 ; 148 3f86: 84 e9 ldi r24, 0x94 ; 148
3f6a: 0a d0 rcall .+20 ; 0x3f80 <putch> 3f88: 0a d0 rcall .+20 ; 0x3f9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
3f6c: 86 e0 ldi r24, 0x06 ; 6 3f8a: 86 e0 ldi r24, 0x06 ; 6
3f6e: 9a cf rjmp .-204 ; 0x3ea4 <main+0xa4> 3f8c: 8b cf rjmp .-234 ; 0x3ea4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
3f70: 81 35 cpi r24, 0x51 ; 81 3f8e: 81 35 cpi r24, 0x51 ; 81
3f72: 11 f4 brne .+4 ; 0x3f78 <main+0x178> 3f90: 11 f4 brne .+4 ; 0x3f96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
3f74: 88 e0 ldi r24, 0x08 ; 8 3f92: 88 e0 ldi r24, 0x08 ; 8
3f76: 19 d0 rcall .+50 ; 0x3faa <watchdogConfig> 3f94: 19 d0 rcall .+50 ; 0x3fc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
3f78: 23 d0 rcall .+70 ; 0x3fc0 <verifySpace> 3f96: 23 d0 rcall .+70 ; 0x3fde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
3f7a: 80 e1 ldi r24, 0x10 ; 16 3f98: 80 e1 ldi r24, 0x10 ; 16
3f7c: 01 d0 rcall .+2 ; 0x3f80 <putch> 3f9a: 01 d0 rcall .+2 ; 0x3f9e <putch>
3f7e: 6b cf rjmp .-298 ; 0x3e56 <main+0x56> 3f9c: 5c cf rjmp .-328 ; 0x3e56 <main+0x56>
00003f80 <putch>: 00003f9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
3f80: 98 2f mov r25, r24 3f9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
3f82: 80 91 c0 00 lds r24, 0x00C0 3fa0: 80 91 c0 00 lds r24, 0x00C0
3f86: 85 ff sbrs r24, 5 3fa4: 85 ff sbrs r24, 5
3f88: fc cf rjmp .-8 ; 0x3f82 <putch+0x2> 3fa6: fc cf rjmp .-8 ; 0x3fa0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
3f8a: 90 93 c6 00 sts 0x00C6, r25 3fa8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
3f8e: 08 95 ret 3fac: 08 95 ret
00003f90 <getch>: 00003fae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
3f90: a8 95 wdr 3fae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
3f92: 80 91 c0 00 lds r24, 0x00C0 3fb0: 80 91 c0 00 lds r24, 0x00C0
3f96: 87 ff sbrs r24, 7 3fb4: 87 ff sbrs r24, 7
3f98: fc cf rjmp .-8 ; 0x3f92 <getch+0x2> 3fb6: fc cf rjmp .-8 ; 0x3fb0 <getch+0x2>
ch = UDR0; ch = UDR0;
3f9a: 80 91 c6 00 lds r24, 0x00C6 3fb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
3f9e: 08 95 ret 3fbc: 08 95 ret
00003fa0 <getLen>: 00003fbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
3fa0: f7 df rcall .-18 ; 0x3f90 <getch> 3fbe: f7 df rcall .-18 ; 0x3fae <getch>
length = getch(); length = getch();
3fa2: f6 df rcall .-20 ; 0x3f90 <getch> 3fc0: f6 df rcall .-20 ; 0x3fae <getch>
3fa4: 80 93 02 02 sts 0x0202, r24 3fc2: 80 93 02 02 sts 0x0202, r24
return getch(); return getch();
} }
3fa8: f3 cf rjmp .-26 ; 0x3f90 <getch> 3fc6: f3 cf rjmp .-26 ; 0x3fae <getch>
00003faa <watchdogConfig>: 00003fc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
3faa: e0 e6 ldi r30, 0x60 ; 96 3fc8: e0 e6 ldi r30, 0x60 ; 96
3fac: f0 e0 ldi r31, 0x00 ; 0 3fca: f0 e0 ldi r31, 0x00 ; 0
3fae: 98 e1 ldi r25, 0x18 ; 24 3fcc: 98 e1 ldi r25, 0x18 ; 24
3fb0: 90 83 st Z, r25 3fce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
3fb2: 80 83 st Z, r24 3fd0: 80 83 st Z, r24
} }
3fb4: 08 95 ret 3fd2: 08 95 ret
00003fb6 <appStart>: 00003fd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
3fb6: 80 e0 ldi r24, 0x00 ; 0 3fd4: 80 e0 ldi r24, 0x00 ; 0
3fb8: f8 df rcall .-16 ; 0x3faa <watchdogConfig> 3fd6: f8 df rcall .-16 ; 0x3fc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
3fba: ee 27 eor r30, r30 3fd8: ee 27 eor r30, r30
3fbc: ff 27 eor r31, r31 3fda: ff 27 eor r31, r31
3fbe: 09 94 ijmp 3fdc: 09 94 ijmp
00003fc0 <verifySpace>: 00003fde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
3fc0: e7 df rcall .-50 ; 0x3f90 <getch> 3fde: e7 df rcall .-50 ; 0x3fae <getch>
3fc2: 80 32 cpi r24, 0x20 ; 32 3fe0: 80 32 cpi r24, 0x20 ; 32
3fc4: 09 f0 breq .+2 ; 0x3fc8 <verifySpace+0x8> 3fe2: 09 f0 breq .+2 ; 0x3fe6 <verifySpace+0x8>
3fc6: f7 df rcall .-18 ; 0x3fb6 <appStart> 3fe4: f7 df rcall .-18 ; 0x3fd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
3fc8: 84 e1 ldi r24, 0x14 ; 20 3fe6: 84 e1 ldi r24, 0x14 ; 20
} }
3fca: da cf rjmp .-76 ; 0x3f80 <putch> 3fe8: da cf rjmp .-76 ; 0x3f9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
3fcc: 1f 93 push r17 3fea: 1f 93 push r17
3fce: 18 2f mov r17, r24 3fec: 18 2f mov r17, r24
00003fd0 <getNch>: 00003fee <getNch>:
do getch(); while (--count); do getch(); while (--count);
3fd0: df df rcall .-66 ; 0x3f90 <getch> 3fee: df df rcall .-66 ; 0x3fae <getch>
3fd2: 11 50 subi r17, 0x01 ; 1 3ff0: 11 50 subi r17, 0x01 ; 1
3fd4: e9 f7 brne .-6 ; 0x3fd0 <getNch> 3ff2: e9 f7 brne .-6 ; 0x3fee <getNch>
verifySpace(); verifySpace();
3fd6: f4 df rcall .-24 ; 0x3fc0 <verifySpace> 3ff4: f4 df rcall .-24 ; 0x3fde <verifySpace>
} }
3fd8: 1f 91 pop r17 3ff6: 1f 91 pop r17
3fda: 08 95 ret 3ff8: 08 95 ret

View File

@ -1,32 +1,34 @@
:103E000085E08093810082E08093C00088E1809308 :103E000085E08093810082E08093C00088E1809308
:103E1000C10086E08093C20088E08093C40084B72C :103E1000C10086E08093C20088E08093C40084B72C
:103E200014BE81FFC8D08DE0C0D0259A86E028E17D :103E200014BE81FFD7D08DE0CFD0259A86E028E15F
:103E30003EEF91E0309385002093840096BBB09BC9 :103E30003EEF91E0309385002093840096BBB09BC9
:103E4000FECF1D9AA8958150A9F7DD24D394A5E053 :103E4000FECF1D9AA8958150A9F7DD24D394A5E053
:103E5000FA2EF1E1EF2E9CD0813421F481E0B6D02E :103E5000EA2EF1E1FF2EABD0813421F481E0C5D010
:103E600083E020C0823411F484E103C0853419F466 :103E600083E020C0823411F484E103C0853419F466
:103E700085E0ACD082C0853581F48AD0082F10E06F :103E700085E0BBD091C0853581F499D0082F10E042
:103E800087D090E0982F8827802B912B880F991F3F :103E800096D090E0982F8827802B912B880F991F30
:103E900090930102809300026FC0863529F484E07C :103E900090930102809300027EC0863529F484E06D
:103EA00095D080E06DD069C0843609F03FC078D0ED :103EA000A4D080E07CD078C0843609F04EC087D0A2
:103EB000E0910002F091010283E087BFE895C0E045 :103EB000E0910002F091010288E3E030F80718F485
:103EC000D1E066D0899380910202815080930202F2 :103EC00083E087BFE895C0E0D1E071D0899380910D
:103ED0008823B9F775D007B600FCFDCF40910002EA :103ED00002028150809302028823B9F7E091000228
:103EE00050910102A0E0B1E02C9130E011968C914C :103EE000F091010288E3E030F80718F083E087BF23
:103EF000119790E0982F8827822B932B1296FA0126 :103EF000E89575D007B600FCFDCF409100025091C7
:103F00000C01D7BEE89511244E5F5F4FF1E0A03859 :103F00000102A0E0B1E02C9130E011968C91119764
:103F1000BF0751F7E0910002F0910102F7BEE8956A :103F100090E0982F8827822B932B1296FA010C01A0
:103F200007B600FCFDCFE7BEE89527C08437B9F49B :103F2000D7BEE89511244E5F5F4FF1E0A038BF0780
:103F300037D046D0E0910002F09101023196F09323 :103F300051F7E0910002F0910102E7BEE89507B663
:103F40000102E09300023197E4918E2F19D0809105 :103F400000FCFDCFF7BEE89527C08437B9F437D021
:103F50000202815080930202882361F70EC08537E8 :103F500046D0E0910002F09101023196F093010207
:103F600039F42ED08EE10CD084E90AD086E09ACFC5 :103F6000E09300023197E4918E2F19D080910202E4
:103F7000813511F488E019D023D080E101D06BCFD6 :103F7000815080930202882361F70EC0853739F49F
:103F8000982F8091C00085FFFCCF9093C6000895C4 :103F80002ED08EE10CD084E90AD086E08BCF81352B
:103F9000A8958091C00087FFFCCF8091C60008954E :103F900011F488E019D023D080E101D05CCF982FB4
:103FA000F7DFF6DF80930202F3CFE0E6F0E098E17E :103FA0008091C00085FFFCCF9093C6000895A8952E
:103FB00090838083089580E0F8DFEE27FF2709943F :103FB0008091C00087FFFCCF8091C6000895F7DF95
:103FC000E7DF803209F0F7DF84E1DACF1F93182FA3 :103FC000F6DF80930202F3CFE0E6F0E098E1908321
:0C3FD000DFDF1150E9F7F4DF1F910895C6 :103FD0008083089580E0F8DFEE27FF270994E7DF6C
:103FE000803209F0F7DF84E1DACF1F93182FDFDF8B
:0A3FF0001150E9F7F4DF1F91089566
:0400000300003E00BB :0400000300003E00BB
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_lilypad.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 00003e00 00003e00 00000054 2**1 0 .text 000001fa 00003e00 00003e00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
3e20: 14 be out 0x34, r1 ; 52 3e20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
3e22: 81 ff sbrs r24, 1 3e22: 81 ff sbrs r24, 1
3e24: c8 d0 rcall .+400 ; 0x3fb6 <appStart> 3e24: d7 d0 rcall .+430 ; 0x3fd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
3e26: 8d e0 ldi r24, 0x0D ; 13 3e26: 8d e0 ldi r24, 0x0D ; 13
3e28: c0 d0 rcall .+384 ; 0x3faa <watchdogConfig> 3e28: cf d0 rcall .+414 ; 0x3fc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3e4e: a5 e0 ldi r26, 0x05 ; 5 3e4e: a5 e0 ldi r26, 0x05 ; 5
3e50: fa 2e mov r15, r26 3e50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3e52: f1 e1 ldi r31, 0x11 ; 17 3e52: f1 e1 ldi r31, 0x11 ; 17
3e54: ef 2e mov r14, r31 3e54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
3e56: 9c d0 rcall .+312 ; 0x3f90 <getch> 3e56: ab d0 rcall .+342 ; 0x3fae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
3e58: 81 34 cpi r24, 0x41 ; 65 3e58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
3e5c: 81 e0 ldi r24, 0x01 ; 1 3e5c: 81 e0 ldi r24, 0x01 ; 1
3e5e: b6 d0 rcall .+364 ; 0x3fcc <verifySpace+0xc> 3e5e: c5 d0 rcall .+394 ; 0x3fea <verifySpace+0xc>
putch(0x03); putch(0x03);
3e60: 83 e0 ldi r24, 0x03 ; 3 3e60: 83 e0 ldi r24, 0x03 ; 3
3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4> 3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
3e70: 85 e0 ldi r24, 0x05 ; 5 3e70: 85 e0 ldi r24, 0x05 ; 5
3e72: ac d0 rcall .+344 ; 0x3fcc <verifySpace+0xc> 3e72: bb d0 rcall .+374 ; 0x3fea <verifySpace+0xc>
3e74: 82 c0 rjmp .+260 ; 0x3f7a <main+0x17a> 3e74: 91 c0 rjmp .+290 ; 0x3f98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
3e76: 85 35 cpi r24, 0x55 ; 85 3e76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
3e7a: 8a d0 rcall .+276 ; 0x3f90 <getch> 3e7a: 99 d0 rcall .+306 ; 0x3fae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
3e7c: 08 2f mov r16, r24 3e7c: 08 2f mov r16, r24
3e7e: 10 e0 ldi r17, 0x00 ; 0 3e7e: 10 e0 ldi r17, 0x00 ; 0
3e80: 87 d0 rcall .+270 ; 0x3f90 <getch> 3e80: 96 d0 rcall .+300 ; 0x3fae <getch>
3e82: 90 e0 ldi r25, 0x00 ; 0 3e82: 90 e0 ldi r25, 0x00 ; 0
3e84: 98 2f mov r25, r24 3e84: 98 2f mov r25, r24
3e86: 88 27 eor r24, r24 3e86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
3e90: 90 93 01 02 sts 0x0201, r25 3e90: 90 93 01 02 sts 0x0201, r25
3e94: 80 93 00 02 sts 0x0200, r24 3e94: 80 93 00 02 sts 0x0200, r24
3e98: 6f c0 rjmp .+222 ; 0x3f78 <main+0x178> 3e98: 7e c0 rjmp .+252 ; 0x3f96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
3e9e: 84 e0 ldi r24, 0x04 ; 4 3e9e: 84 e0 ldi r24, 0x04 ; 4
3ea0: 95 d0 rcall .+298 ; 0x3fcc <verifySpace+0xc> 3ea0: a4 d0 rcall .+328 ; 0x3fea <verifySpace+0xc>
putch(0x00); putch(0x00);
3ea2: 80 e0 ldi r24, 0x00 ; 0 3ea2: 80 e0 ldi r24, 0x00 ; 0
3ea4: 6d d0 rcall .+218 ; 0x3f80 <putch> 3ea4: 7c d0 rcall .+248 ; 0x3f9e <putch>
3ea6: 69 c0 rjmp .+210 ; 0x3f7a <main+0x17a> 3ea6: 78 c0 rjmp .+240 ; 0x3f98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
3ea8: 84 36 cpi r24, 0x64 ; 100 3ea8: 84 36 cpi r24, 0x64 ; 100
3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae> 3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae>
3eac: 3f c0 rjmp .+126 ; 0x3f2c <main+0x12c> 3eac: 4e c0 rjmp .+156 ; 0x3f4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
3eae: 78 d0 rcall .+240 ; 0x3fa0 <getLen> 3eae: 87 d0 rcall .+270 ; 0x3fbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3eb0: e0 91 00 02 lds r30, 0x0200 3eb0: e0 91 00 02 lds r30, 0x0200
3eb4: f0 91 01 02 lds r31, 0x0201 3eb4: f0 91 01 02 lds r31, 0x0201
3eb8: 83 e0 ldi r24, 0x03 ; 3 3eb8: 88 e3 ldi r24, 0x38 ; 56
3eba: 87 bf out 0x37, r24 ; 55 3eba: e0 30 cpi r30, 0x00 ; 0
3ebc: e8 95 spm 3ebc: f8 07 cpc r31, r24
3ebe: c0 e0 ldi r28, 0x00 ; 0 3ebe: 18 f4 brcc .+6 ; 0x3ec6 <main+0xc6>
3ec0: d1 e0 ldi r29, 0x01 ; 1 3ec0: 83 e0 ldi r24, 0x03 ; 3
3ec2: 87 bf out 0x37, r24 ; 55
3ec4: e8 95 spm
3ec6: c0 e0 ldi r28, 0x00 ; 0
3ec8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
3ec2: 66 d0 rcall .+204 ; 0x3f90 <getch> 3eca: 71 d0 rcall .+226 ; 0x3fae <getch>
3ec4: 89 93 st Y+, r24 3ecc: 89 93 st Y+, r24
while (--length); while (--length);
3ec6: 80 91 02 02 lds r24, 0x0202 3ece: 80 91 02 02 lds r24, 0x0202
3eca: 81 50 subi r24, 0x01 ; 1 3ed2: 81 50 subi r24, 0x01 ; 1
3ecc: 80 93 02 02 sts 0x0202, r24 3ed4: 80 93 02 02 sts 0x0202, r24
3ed0: 88 23 and r24, r24 3ed8: 88 23 and r24, r24
3ed2: b9 f7 brne .-18 ; 0x3ec2 <main+0xc2> 3eda: b9 f7 brne .-18 ; 0x3eca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3edc: e0 91 00 02 lds r30, 0x0200
3ee0: f0 91 01 02 lds r31, 0x0201
3ee4: 88 e3 ldi r24, 0x38 ; 56
3ee6: e0 30 cpi r30, 0x00 ; 0
3ee8: f8 07 cpc r31, r24
3eea: 18 f0 brcs .+6 ; 0x3ef2 <main+0xf2>
3eec: 83 e0 ldi r24, 0x03 ; 3
3eee: 87 bf out 0x37, r24 ; 55
3ef0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
3ed4: 75 d0 rcall .+234 ; 0x3fc0 <verifySpace> 3ef2: 75 d0 rcall .+234 ; 0x3fde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
3ed6: 07 b6 in r0, 0x37 ; 55 3ef4: 07 b6 in r0, 0x37 ; 55
3ed8: 00 fc sbrc r0, 0 3ef6: 00 fc sbrc r0, 0
3eda: fd cf rjmp .-6 ; 0x3ed6 <main+0xd6> 3ef8: fd cf rjmp .-6 ; 0x3ef4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
3edc: 40 91 00 02 lds r20, 0x0200 3efa: 40 91 00 02 lds r20, 0x0200
3ee0: 50 91 01 02 lds r21, 0x0201 3efe: 50 91 01 02 lds r21, 0x0201
3ee4: a0 e0 ldi r26, 0x00 ; 0 3f02: a0 e0 ldi r26, 0x00 ; 0
3ee6: b1 e0 ldi r27, 0x01 ; 1 3f04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
3ee8: 2c 91 ld r18, X 3f06: 2c 91 ld r18, X
3eea: 30 e0 ldi r19, 0x00 ; 0 3f08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
3eec: 11 96 adiw r26, 0x01 ; 1 3f0a: 11 96 adiw r26, 0x01 ; 1
3eee: 8c 91 ld r24, X 3f0c: 8c 91 ld r24, X
3ef0: 11 97 sbiw r26, 0x01 ; 1 3f0e: 11 97 sbiw r26, 0x01 ; 1
3ef2: 90 e0 ldi r25, 0x00 ; 0 3f10: 90 e0 ldi r25, 0x00 ; 0
3ef4: 98 2f mov r25, r24 3f12: 98 2f mov r25, r24
3ef6: 88 27 eor r24, r24 3f14: 88 27 eor r24, r24
3ef8: 82 2b or r24, r18 3f16: 82 2b or r24, r18
3efa: 93 2b or r25, r19 3f18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
3efc: 12 96 adiw r26, 0x02 ; 2 3f1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
3efe: fa 01 movw r30, r20 3f1c: fa 01 movw r30, r20
3f00: 0c 01 movw r0, r24 3f1e: 0c 01 movw r0, r24
3f02: d7 be out 0x37, r13 ; 55 3f20: d7 be out 0x37, r13 ; 55
3f04: e8 95 spm 3f22: e8 95 spm
3f06: 11 24 eor r1, r1 3f24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
3f08: 4e 5f subi r20, 0xFE ; 254 3f26: 4e 5f subi r20, 0xFE ; 254
3f0a: 5f 4f sbci r21, 0xFF ; 255 3f28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
3f0c: f1 e0 ldi r31, 0x01 ; 1 3f2a: f1 e0 ldi r31, 0x01 ; 1
3f0e: a0 38 cpi r26, 0x80 ; 128 3f2c: a0 38 cpi r26, 0x80 ; 128
3f10: bf 07 cpc r27, r31 3f2e: bf 07 cpc r27, r31
3f12: 51 f7 brne .-44 ; 0x3ee8 <main+0xe8> 3f30: 51 f7 brne .-44 ; 0x3f06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3f14: e0 91 00 02 lds r30, 0x0200 3f32: e0 91 00 02 lds r30, 0x0200
3f18: f0 91 01 02 lds r31, 0x0201 3f36: f0 91 01 02 lds r31, 0x0201
3f1c: f7 be out 0x37, r15 ; 55 3f3a: e7 be out 0x37, r14 ; 55
3f1e: e8 95 spm 3f3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
3f20: 07 b6 in r0, 0x37 ; 55 3f3e: 07 b6 in r0, 0x37 ; 55
3f22: 00 fc sbrc r0, 0 3f40: 00 fc sbrc r0, 0
3f24: fd cf rjmp .-6 ; 0x3f20 <main+0x120> 3f42: fd cf rjmp .-6 ; 0x3f3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3f26: e7 be out 0x37, r14 ; 55 3f44: f7 be out 0x37, r15 ; 55
3f28: e8 95 spm 3f46: e8 95 spm
3f2a: 27 c0 rjmp .+78 ; 0x3f7a <main+0x17a> 3f48: 27 c0 rjmp .+78 ; 0x3f98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
3f2c: 84 37 cpi r24, 0x74 ; 116 3f4a: 84 37 cpi r24, 0x74 ; 116
3f2e: b9 f4 brne .+46 ; 0x3f5e <main+0x15e> 3f4c: b9 f4 brne .+46 ; 0x3f7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
3f30: 37 d0 rcall .+110 ; 0x3fa0 <getLen> 3f4e: 37 d0 rcall .+110 ; 0x3fbe <getLen>
verifySpace(); verifySpace();
3f32: 46 d0 rcall .+140 ; 0x3fc0 <verifySpace> 3f50: 46 d0 rcall .+140 ; 0x3fde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
3f34: e0 91 00 02 lds r30, 0x0200 3f52: e0 91 00 02 lds r30, 0x0200
3f38: f0 91 01 02 lds r31, 0x0201 3f56: f0 91 01 02 lds r31, 0x0201
3f3c: 31 96 adiw r30, 0x01 ; 1 3f5a: 31 96 adiw r30, 0x01 ; 1
3f3e: f0 93 01 02 sts 0x0201, r31 3f5c: f0 93 01 02 sts 0x0201, r31
3f42: e0 93 00 02 sts 0x0200, r30 3f60: e0 93 00 02 sts 0x0200, r30
3f46: 31 97 sbiw r30, 0x01 ; 1 3f64: 31 97 sbiw r30, 0x01 ; 1
3f48: e4 91 lpm r30, Z+ 3f66: e4 91 lpm r30, Z+
3f4a: 8e 2f mov r24, r30 3f68: 8e 2f mov r24, r30
3f4c: 19 d0 rcall .+50 ; 0x3f80 <putch> 3f6a: 19 d0 rcall .+50 ; 0x3f9e <putch>
while (--length); while (--length);
3f4e: 80 91 02 02 lds r24, 0x0202 3f6c: 80 91 02 02 lds r24, 0x0202
3f52: 81 50 subi r24, 0x01 ; 1 3f70: 81 50 subi r24, 0x01 ; 1
3f54: 80 93 02 02 sts 0x0202, r24 3f72: 80 93 02 02 sts 0x0202, r24
3f58: 88 23 and r24, r24 3f76: 88 23 and r24, r24
3f5a: 61 f7 brne .-40 ; 0x3f34 <main+0x134> 3f78: 61 f7 brne .-40 ; 0x3f52 <main+0x152>
3f5c: 0e c0 rjmp .+28 ; 0x3f7a <main+0x17a> 3f7a: 0e c0 rjmp .+28 ; 0x3f98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
3f5e: 85 37 cpi r24, 0x75 ; 117 3f7c: 85 37 cpi r24, 0x75 ; 117
3f60: 39 f4 brne .+14 ; 0x3f70 <main+0x170> 3f7e: 39 f4 brne .+14 ; 0x3f8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
3f62: 2e d0 rcall .+92 ; 0x3fc0 <verifySpace> 3f80: 2e d0 rcall .+92 ; 0x3fde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
3f64: 8e e1 ldi r24, 0x1E ; 30 3f82: 8e e1 ldi r24, 0x1E ; 30
3f66: 0c d0 rcall .+24 ; 0x3f80 <putch> 3f84: 0c d0 rcall .+24 ; 0x3f9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
3f68: 84 e9 ldi r24, 0x94 ; 148 3f86: 84 e9 ldi r24, 0x94 ; 148
3f6a: 0a d0 rcall .+20 ; 0x3f80 <putch> 3f88: 0a d0 rcall .+20 ; 0x3f9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
3f6c: 86 e0 ldi r24, 0x06 ; 6 3f8a: 86 e0 ldi r24, 0x06 ; 6
3f6e: 9a cf rjmp .-204 ; 0x3ea4 <main+0xa4> 3f8c: 8b cf rjmp .-234 ; 0x3ea4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
3f70: 81 35 cpi r24, 0x51 ; 81 3f8e: 81 35 cpi r24, 0x51 ; 81
3f72: 11 f4 brne .+4 ; 0x3f78 <main+0x178> 3f90: 11 f4 brne .+4 ; 0x3f96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
3f74: 88 e0 ldi r24, 0x08 ; 8 3f92: 88 e0 ldi r24, 0x08 ; 8
3f76: 19 d0 rcall .+50 ; 0x3faa <watchdogConfig> 3f94: 19 d0 rcall .+50 ; 0x3fc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
3f78: 23 d0 rcall .+70 ; 0x3fc0 <verifySpace> 3f96: 23 d0 rcall .+70 ; 0x3fde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
3f7a: 80 e1 ldi r24, 0x10 ; 16 3f98: 80 e1 ldi r24, 0x10 ; 16
3f7c: 01 d0 rcall .+2 ; 0x3f80 <putch> 3f9a: 01 d0 rcall .+2 ; 0x3f9e <putch>
3f7e: 6b cf rjmp .-298 ; 0x3e56 <main+0x56> 3f9c: 5c cf rjmp .-328 ; 0x3e56 <main+0x56>
00003f80 <putch>: 00003f9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
3f80: 98 2f mov r25, r24 3f9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
3f82: 80 91 c0 00 lds r24, 0x00C0 3fa0: 80 91 c0 00 lds r24, 0x00C0
3f86: 85 ff sbrs r24, 5 3fa4: 85 ff sbrs r24, 5
3f88: fc cf rjmp .-8 ; 0x3f82 <putch+0x2> 3fa6: fc cf rjmp .-8 ; 0x3fa0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
3f8a: 90 93 c6 00 sts 0x00C6, r25 3fa8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
3f8e: 08 95 ret 3fac: 08 95 ret
00003f90 <getch>: 00003fae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
3f90: a8 95 wdr 3fae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
3f92: 80 91 c0 00 lds r24, 0x00C0 3fb0: 80 91 c0 00 lds r24, 0x00C0
3f96: 87 ff sbrs r24, 7 3fb4: 87 ff sbrs r24, 7
3f98: fc cf rjmp .-8 ; 0x3f92 <getch+0x2> 3fb6: fc cf rjmp .-8 ; 0x3fb0 <getch+0x2>
ch = UDR0; ch = UDR0;
3f9a: 80 91 c6 00 lds r24, 0x00C6 3fb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
3f9e: 08 95 ret 3fbc: 08 95 ret
00003fa0 <getLen>: 00003fbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
3fa0: f7 df rcall .-18 ; 0x3f90 <getch> 3fbe: f7 df rcall .-18 ; 0x3fae <getch>
length = getch(); length = getch();
3fa2: f6 df rcall .-20 ; 0x3f90 <getch> 3fc0: f6 df rcall .-20 ; 0x3fae <getch>
3fa4: 80 93 02 02 sts 0x0202, r24 3fc2: 80 93 02 02 sts 0x0202, r24
return getch(); return getch();
} }
3fa8: f3 cf rjmp .-26 ; 0x3f90 <getch> 3fc6: f3 cf rjmp .-26 ; 0x3fae <getch>
00003faa <watchdogConfig>: 00003fc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
3faa: e0 e6 ldi r30, 0x60 ; 96 3fc8: e0 e6 ldi r30, 0x60 ; 96
3fac: f0 e0 ldi r31, 0x00 ; 0 3fca: f0 e0 ldi r31, 0x00 ; 0
3fae: 98 e1 ldi r25, 0x18 ; 24 3fcc: 98 e1 ldi r25, 0x18 ; 24
3fb0: 90 83 st Z, r25 3fce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
3fb2: 80 83 st Z, r24 3fd0: 80 83 st Z, r24
} }
3fb4: 08 95 ret 3fd2: 08 95 ret
00003fb6 <appStart>: 00003fd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
3fb6: 80 e0 ldi r24, 0x00 ; 0 3fd4: 80 e0 ldi r24, 0x00 ; 0
3fb8: f8 df rcall .-16 ; 0x3faa <watchdogConfig> 3fd6: f8 df rcall .-16 ; 0x3fc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
3fba: ee 27 eor r30, r30 3fd8: ee 27 eor r30, r30
3fbc: ff 27 eor r31, r31 3fda: ff 27 eor r31, r31
3fbe: 09 94 ijmp 3fdc: 09 94 ijmp
00003fc0 <verifySpace>: 00003fde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
3fc0: e7 df rcall .-50 ; 0x3f90 <getch> 3fde: e7 df rcall .-50 ; 0x3fae <getch>
3fc2: 80 32 cpi r24, 0x20 ; 32 3fe0: 80 32 cpi r24, 0x20 ; 32
3fc4: 09 f0 breq .+2 ; 0x3fc8 <verifySpace+0x8> 3fe2: 09 f0 breq .+2 ; 0x3fe6 <verifySpace+0x8>
3fc6: f7 df rcall .-18 ; 0x3fb6 <appStart> 3fe4: f7 df rcall .-18 ; 0x3fd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
3fc8: 84 e1 ldi r24, 0x14 ; 20 3fe6: 84 e1 ldi r24, 0x14 ; 20
} }
3fca: da cf rjmp .-76 ; 0x3f80 <putch> 3fe8: da cf rjmp .-76 ; 0x3f9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
3fcc: 1f 93 push r17 3fea: 1f 93 push r17
3fce: 18 2f mov r17, r24 3fec: 18 2f mov r17, r24
00003fd0 <getNch>: 00003fee <getNch>:
do getch(); while (--count); do getch(); while (--count);
3fd0: df df rcall .-66 ; 0x3f90 <getch> 3fee: df df rcall .-66 ; 0x3fae <getch>
3fd2: 11 50 subi r17, 0x01 ; 1 3ff0: 11 50 subi r17, 0x01 ; 1
3fd4: e9 f7 brne .-6 ; 0x3fd0 <getNch> 3ff2: e9 f7 brne .-6 ; 0x3fee <getNch>
verifySpace(); verifySpace();
3fd6: f4 df rcall .-24 ; 0x3fc0 <verifySpace> 3ff4: f4 df rcall .-24 ; 0x3fde <verifySpace>
} }
3fd8: 1f 91 pop r17 3ff6: 1f 91 pop r17
3fda: 08 95 ret 3ff8: 08 95 ret

View File

@ -1,32 +1,34 @@
:103E000085E08093810082E08093C00088E1809308 :103E000085E08093810082E08093C00088E1809308
:103E1000C10086E08093C20088E08093C40084B72C :103E1000C10086E08093C20088E08093C40084B72C
:103E200014BE81FFC8D08DE0C0D0259A86E028E17D :103E200014BE81FFD7D08DE0CFD0259A86E028E15F
:103E30003EEF91E0309385002093840096BBB09BC9 :103E30003EEF91E0309385002093840096BBB09BC9
:103E4000FECF1D9AA8958150A9F7DD24D394A5E053 :103E4000FECF1D9AA8958150A9F7DD24D394A5E053
:103E5000FA2EF1E1EF2E9CD0813421F481E0B6D02E :103E5000EA2EF1E1FF2EABD0813421F481E0C5D010
:103E600083E020C0823411F484E103C0853419F466 :103E600083E020C0823411F484E103C0853419F466
:103E700085E0ACD082C0853581F48AD0082F10E06F :103E700085E0BBD091C0853581F499D0082F10E042
:103E800087D090E0982F8827802B912B880F991F3F :103E800096D090E0982F8827802B912B880F991F30
:103E900090930102809300026FC0863529F484E07C :103E900090930102809300027EC0863529F484E06D
:103EA00095D080E06DD069C0843609F03FC078D0ED :103EA000A4D080E07CD078C0843609F04EC087D0A2
:103EB000E0910002F091010283E087BFE895C0E045 :103EB000E0910002F091010288E3E030F80718F485
:103EC000D1E066D0899380910202815080930202F2 :103EC00083E087BFE895C0E0D1E071D0899380910D
:103ED0008823B9F775D007B600FCFDCF40910002EA :103ED00002028150809302028823B9F7E091000228
:103EE00050910102A0E0B1E02C9130E011968C914C :103EE000F091010288E3E030F80718F083E087BF23
:103EF000119790E0982F8827822B932B1296FA0126 :103EF000E89575D007B600FCFDCF409100025091C7
:103F00000C01D7BEE89511244E5F5F4FF1E0A03859 :103F00000102A0E0B1E02C9130E011968C91119764
:103F1000BF0751F7E0910002F0910102F7BEE8956A :103F100090E0982F8827822B932B1296FA010C01A0
:103F200007B600FCFDCFE7BEE89527C08437B9F49B :103F2000D7BEE89511244E5F5F4FF1E0A038BF0780
:103F300037D046D0E0910002F09101023196F09323 :103F300051F7E0910002F0910102E7BEE89507B663
:103F40000102E09300023197E4918E2F19D0809105 :103F400000FCFDCFF7BEE89527C08437B9F437D021
:103F50000202815080930202882361F70EC08537E8 :103F500046D0E0910002F09101023196F093010207
:103F600039F42ED08EE10CD084E90AD086E09ACFC5 :103F6000E09300023197E4918E2F19D080910202E4
:103F7000813511F488E019D023D080E101D06BCFD6 :103F7000815080930202882361F70EC0853739F49F
:103F8000982F8091C00085FFFCCF9093C6000895C4 :103F80002ED08EE10CD084E90AD086E08BCF81352B
:103F9000A8958091C00087FFFCCF8091C60008954E :103F900011F488E019D023D080E101D05CCF982FB4
:103FA000F7DFF6DF80930202F3CFE0E6F0E098E17E :103FA0008091C00085FFFCCF9093C6000895A8952E
:103FB00090838083089580E0F8DFEE27FF2709943F :103FB0008091C00087FFFCCF8091C6000895F7DF95
:103FC000E7DF803209F0F7DF84E1DACF1F93182FA3 :103FC000F6DF80930202F3CFE0E6F0E098E1908321
:0C3FD000DFDF1150E9F7F4DF1F910895C6 :103FD0008083089580E0F8DFEE27FF270994E7DF6C
:103FE000803209F0F7DF84E1DACF1F93182FDFDF8B
:0A3FF0001150E9F7F4DF1F91089566
:0400000300003E00BB :0400000300003E00BB
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_lilypad_resonator.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 00003e00 00003e00 00000054 2**1 0 .text 000001fa 00003e00 00003e00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
3e20: 14 be out 0x34, r1 ; 52 3e20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
3e22: 81 ff sbrs r24, 1 3e22: 81 ff sbrs r24, 1
3e24: c8 d0 rcall .+400 ; 0x3fb6 <appStart> 3e24: d7 d0 rcall .+430 ; 0x3fd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
3e26: 8d e0 ldi r24, 0x0D ; 13 3e26: 8d e0 ldi r24, 0x0D ; 13
3e28: c0 d0 rcall .+384 ; 0x3faa <watchdogConfig> 3e28: cf d0 rcall .+414 ; 0x3fc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3e4e: a5 e0 ldi r26, 0x05 ; 5 3e4e: a5 e0 ldi r26, 0x05 ; 5
3e50: fa 2e mov r15, r26 3e50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3e52: f1 e1 ldi r31, 0x11 ; 17 3e52: f1 e1 ldi r31, 0x11 ; 17
3e54: ef 2e mov r14, r31 3e54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
3e56: 9c d0 rcall .+312 ; 0x3f90 <getch> 3e56: ab d0 rcall .+342 ; 0x3fae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
3e58: 81 34 cpi r24, 0x41 ; 65 3e58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
3e5c: 81 e0 ldi r24, 0x01 ; 1 3e5c: 81 e0 ldi r24, 0x01 ; 1
3e5e: b6 d0 rcall .+364 ; 0x3fcc <verifySpace+0xc> 3e5e: c5 d0 rcall .+394 ; 0x3fea <verifySpace+0xc>
putch(0x03); putch(0x03);
3e60: 83 e0 ldi r24, 0x03 ; 3 3e60: 83 e0 ldi r24, 0x03 ; 3
3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4> 3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
3e70: 85 e0 ldi r24, 0x05 ; 5 3e70: 85 e0 ldi r24, 0x05 ; 5
3e72: ac d0 rcall .+344 ; 0x3fcc <verifySpace+0xc> 3e72: bb d0 rcall .+374 ; 0x3fea <verifySpace+0xc>
3e74: 82 c0 rjmp .+260 ; 0x3f7a <main+0x17a> 3e74: 91 c0 rjmp .+290 ; 0x3f98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
3e76: 85 35 cpi r24, 0x55 ; 85 3e76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
3e7a: 8a d0 rcall .+276 ; 0x3f90 <getch> 3e7a: 99 d0 rcall .+306 ; 0x3fae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
3e7c: 08 2f mov r16, r24 3e7c: 08 2f mov r16, r24
3e7e: 10 e0 ldi r17, 0x00 ; 0 3e7e: 10 e0 ldi r17, 0x00 ; 0
3e80: 87 d0 rcall .+270 ; 0x3f90 <getch> 3e80: 96 d0 rcall .+300 ; 0x3fae <getch>
3e82: 90 e0 ldi r25, 0x00 ; 0 3e82: 90 e0 ldi r25, 0x00 ; 0
3e84: 98 2f mov r25, r24 3e84: 98 2f mov r25, r24
3e86: 88 27 eor r24, r24 3e86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
3e90: 90 93 01 02 sts 0x0201, r25 3e90: 90 93 01 02 sts 0x0201, r25
3e94: 80 93 00 02 sts 0x0200, r24 3e94: 80 93 00 02 sts 0x0200, r24
3e98: 6f c0 rjmp .+222 ; 0x3f78 <main+0x178> 3e98: 7e c0 rjmp .+252 ; 0x3f96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
3e9e: 84 e0 ldi r24, 0x04 ; 4 3e9e: 84 e0 ldi r24, 0x04 ; 4
3ea0: 95 d0 rcall .+298 ; 0x3fcc <verifySpace+0xc> 3ea0: a4 d0 rcall .+328 ; 0x3fea <verifySpace+0xc>
putch(0x00); putch(0x00);
3ea2: 80 e0 ldi r24, 0x00 ; 0 3ea2: 80 e0 ldi r24, 0x00 ; 0
3ea4: 6d d0 rcall .+218 ; 0x3f80 <putch> 3ea4: 7c d0 rcall .+248 ; 0x3f9e <putch>
3ea6: 69 c0 rjmp .+210 ; 0x3f7a <main+0x17a> 3ea6: 78 c0 rjmp .+240 ; 0x3f98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
3ea8: 84 36 cpi r24, 0x64 ; 100 3ea8: 84 36 cpi r24, 0x64 ; 100
3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae> 3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae>
3eac: 3f c0 rjmp .+126 ; 0x3f2c <main+0x12c> 3eac: 4e c0 rjmp .+156 ; 0x3f4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
3eae: 78 d0 rcall .+240 ; 0x3fa0 <getLen> 3eae: 87 d0 rcall .+270 ; 0x3fbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3eb0: e0 91 00 02 lds r30, 0x0200 3eb0: e0 91 00 02 lds r30, 0x0200
3eb4: f0 91 01 02 lds r31, 0x0201 3eb4: f0 91 01 02 lds r31, 0x0201
3eb8: 83 e0 ldi r24, 0x03 ; 3 3eb8: 88 e3 ldi r24, 0x38 ; 56
3eba: 87 bf out 0x37, r24 ; 55 3eba: e0 30 cpi r30, 0x00 ; 0
3ebc: e8 95 spm 3ebc: f8 07 cpc r31, r24
3ebe: c0 e0 ldi r28, 0x00 ; 0 3ebe: 18 f4 brcc .+6 ; 0x3ec6 <main+0xc6>
3ec0: d1 e0 ldi r29, 0x01 ; 1 3ec0: 83 e0 ldi r24, 0x03 ; 3
3ec2: 87 bf out 0x37, r24 ; 55
3ec4: e8 95 spm
3ec6: c0 e0 ldi r28, 0x00 ; 0
3ec8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
3ec2: 66 d0 rcall .+204 ; 0x3f90 <getch> 3eca: 71 d0 rcall .+226 ; 0x3fae <getch>
3ec4: 89 93 st Y+, r24 3ecc: 89 93 st Y+, r24
while (--length); while (--length);
3ec6: 80 91 02 02 lds r24, 0x0202 3ece: 80 91 02 02 lds r24, 0x0202
3eca: 81 50 subi r24, 0x01 ; 1 3ed2: 81 50 subi r24, 0x01 ; 1
3ecc: 80 93 02 02 sts 0x0202, r24 3ed4: 80 93 02 02 sts 0x0202, r24
3ed0: 88 23 and r24, r24 3ed8: 88 23 and r24, r24
3ed2: b9 f7 brne .-18 ; 0x3ec2 <main+0xc2> 3eda: b9 f7 brne .-18 ; 0x3eca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3edc: e0 91 00 02 lds r30, 0x0200
3ee0: f0 91 01 02 lds r31, 0x0201
3ee4: 88 e3 ldi r24, 0x38 ; 56
3ee6: e0 30 cpi r30, 0x00 ; 0
3ee8: f8 07 cpc r31, r24
3eea: 18 f0 brcs .+6 ; 0x3ef2 <main+0xf2>
3eec: 83 e0 ldi r24, 0x03 ; 3
3eee: 87 bf out 0x37, r24 ; 55
3ef0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
3ed4: 75 d0 rcall .+234 ; 0x3fc0 <verifySpace> 3ef2: 75 d0 rcall .+234 ; 0x3fde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
3ed6: 07 b6 in r0, 0x37 ; 55 3ef4: 07 b6 in r0, 0x37 ; 55
3ed8: 00 fc sbrc r0, 0 3ef6: 00 fc sbrc r0, 0
3eda: fd cf rjmp .-6 ; 0x3ed6 <main+0xd6> 3ef8: fd cf rjmp .-6 ; 0x3ef4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
3edc: 40 91 00 02 lds r20, 0x0200 3efa: 40 91 00 02 lds r20, 0x0200
3ee0: 50 91 01 02 lds r21, 0x0201 3efe: 50 91 01 02 lds r21, 0x0201
3ee4: a0 e0 ldi r26, 0x00 ; 0 3f02: a0 e0 ldi r26, 0x00 ; 0
3ee6: b1 e0 ldi r27, 0x01 ; 1 3f04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
3ee8: 2c 91 ld r18, X 3f06: 2c 91 ld r18, X
3eea: 30 e0 ldi r19, 0x00 ; 0 3f08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
3eec: 11 96 adiw r26, 0x01 ; 1 3f0a: 11 96 adiw r26, 0x01 ; 1
3eee: 8c 91 ld r24, X 3f0c: 8c 91 ld r24, X
3ef0: 11 97 sbiw r26, 0x01 ; 1 3f0e: 11 97 sbiw r26, 0x01 ; 1
3ef2: 90 e0 ldi r25, 0x00 ; 0 3f10: 90 e0 ldi r25, 0x00 ; 0
3ef4: 98 2f mov r25, r24 3f12: 98 2f mov r25, r24
3ef6: 88 27 eor r24, r24 3f14: 88 27 eor r24, r24
3ef8: 82 2b or r24, r18 3f16: 82 2b or r24, r18
3efa: 93 2b or r25, r19 3f18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
3efc: 12 96 adiw r26, 0x02 ; 2 3f1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
3efe: fa 01 movw r30, r20 3f1c: fa 01 movw r30, r20
3f00: 0c 01 movw r0, r24 3f1e: 0c 01 movw r0, r24
3f02: d7 be out 0x37, r13 ; 55 3f20: d7 be out 0x37, r13 ; 55
3f04: e8 95 spm 3f22: e8 95 spm
3f06: 11 24 eor r1, r1 3f24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
3f08: 4e 5f subi r20, 0xFE ; 254 3f26: 4e 5f subi r20, 0xFE ; 254
3f0a: 5f 4f sbci r21, 0xFF ; 255 3f28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
3f0c: f1 e0 ldi r31, 0x01 ; 1 3f2a: f1 e0 ldi r31, 0x01 ; 1
3f0e: a0 38 cpi r26, 0x80 ; 128 3f2c: a0 38 cpi r26, 0x80 ; 128
3f10: bf 07 cpc r27, r31 3f2e: bf 07 cpc r27, r31
3f12: 51 f7 brne .-44 ; 0x3ee8 <main+0xe8> 3f30: 51 f7 brne .-44 ; 0x3f06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3f14: e0 91 00 02 lds r30, 0x0200 3f32: e0 91 00 02 lds r30, 0x0200
3f18: f0 91 01 02 lds r31, 0x0201 3f36: f0 91 01 02 lds r31, 0x0201
3f1c: f7 be out 0x37, r15 ; 55 3f3a: e7 be out 0x37, r14 ; 55
3f1e: e8 95 spm 3f3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
3f20: 07 b6 in r0, 0x37 ; 55 3f3e: 07 b6 in r0, 0x37 ; 55
3f22: 00 fc sbrc r0, 0 3f40: 00 fc sbrc r0, 0
3f24: fd cf rjmp .-6 ; 0x3f20 <main+0x120> 3f42: fd cf rjmp .-6 ; 0x3f3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3f26: e7 be out 0x37, r14 ; 55 3f44: f7 be out 0x37, r15 ; 55
3f28: e8 95 spm 3f46: e8 95 spm
3f2a: 27 c0 rjmp .+78 ; 0x3f7a <main+0x17a> 3f48: 27 c0 rjmp .+78 ; 0x3f98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
3f2c: 84 37 cpi r24, 0x74 ; 116 3f4a: 84 37 cpi r24, 0x74 ; 116
3f2e: b9 f4 brne .+46 ; 0x3f5e <main+0x15e> 3f4c: b9 f4 brne .+46 ; 0x3f7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
3f30: 37 d0 rcall .+110 ; 0x3fa0 <getLen> 3f4e: 37 d0 rcall .+110 ; 0x3fbe <getLen>
verifySpace(); verifySpace();
3f32: 46 d0 rcall .+140 ; 0x3fc0 <verifySpace> 3f50: 46 d0 rcall .+140 ; 0x3fde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
3f34: e0 91 00 02 lds r30, 0x0200 3f52: e0 91 00 02 lds r30, 0x0200
3f38: f0 91 01 02 lds r31, 0x0201 3f56: f0 91 01 02 lds r31, 0x0201
3f3c: 31 96 adiw r30, 0x01 ; 1 3f5a: 31 96 adiw r30, 0x01 ; 1
3f3e: f0 93 01 02 sts 0x0201, r31 3f5c: f0 93 01 02 sts 0x0201, r31
3f42: e0 93 00 02 sts 0x0200, r30 3f60: e0 93 00 02 sts 0x0200, r30
3f46: 31 97 sbiw r30, 0x01 ; 1 3f64: 31 97 sbiw r30, 0x01 ; 1
3f48: e4 91 lpm r30, Z+ 3f66: e4 91 lpm r30, Z+
3f4a: 8e 2f mov r24, r30 3f68: 8e 2f mov r24, r30
3f4c: 19 d0 rcall .+50 ; 0x3f80 <putch> 3f6a: 19 d0 rcall .+50 ; 0x3f9e <putch>
while (--length); while (--length);
3f4e: 80 91 02 02 lds r24, 0x0202 3f6c: 80 91 02 02 lds r24, 0x0202
3f52: 81 50 subi r24, 0x01 ; 1 3f70: 81 50 subi r24, 0x01 ; 1
3f54: 80 93 02 02 sts 0x0202, r24 3f72: 80 93 02 02 sts 0x0202, r24
3f58: 88 23 and r24, r24 3f76: 88 23 and r24, r24
3f5a: 61 f7 brne .-40 ; 0x3f34 <main+0x134> 3f78: 61 f7 brne .-40 ; 0x3f52 <main+0x152>
3f5c: 0e c0 rjmp .+28 ; 0x3f7a <main+0x17a> 3f7a: 0e c0 rjmp .+28 ; 0x3f98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
3f5e: 85 37 cpi r24, 0x75 ; 117 3f7c: 85 37 cpi r24, 0x75 ; 117
3f60: 39 f4 brne .+14 ; 0x3f70 <main+0x170> 3f7e: 39 f4 brne .+14 ; 0x3f8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
3f62: 2e d0 rcall .+92 ; 0x3fc0 <verifySpace> 3f80: 2e d0 rcall .+92 ; 0x3fde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
3f64: 8e e1 ldi r24, 0x1E ; 30 3f82: 8e e1 ldi r24, 0x1E ; 30
3f66: 0c d0 rcall .+24 ; 0x3f80 <putch> 3f84: 0c d0 rcall .+24 ; 0x3f9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
3f68: 84 e9 ldi r24, 0x94 ; 148 3f86: 84 e9 ldi r24, 0x94 ; 148
3f6a: 0a d0 rcall .+20 ; 0x3f80 <putch> 3f88: 0a d0 rcall .+20 ; 0x3f9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
3f6c: 86 e0 ldi r24, 0x06 ; 6 3f8a: 86 e0 ldi r24, 0x06 ; 6
3f6e: 9a cf rjmp .-204 ; 0x3ea4 <main+0xa4> 3f8c: 8b cf rjmp .-234 ; 0x3ea4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
3f70: 81 35 cpi r24, 0x51 ; 81 3f8e: 81 35 cpi r24, 0x51 ; 81
3f72: 11 f4 brne .+4 ; 0x3f78 <main+0x178> 3f90: 11 f4 brne .+4 ; 0x3f96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
3f74: 88 e0 ldi r24, 0x08 ; 8 3f92: 88 e0 ldi r24, 0x08 ; 8
3f76: 19 d0 rcall .+50 ; 0x3faa <watchdogConfig> 3f94: 19 d0 rcall .+50 ; 0x3fc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
3f78: 23 d0 rcall .+70 ; 0x3fc0 <verifySpace> 3f96: 23 d0 rcall .+70 ; 0x3fde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
3f7a: 80 e1 ldi r24, 0x10 ; 16 3f98: 80 e1 ldi r24, 0x10 ; 16
3f7c: 01 d0 rcall .+2 ; 0x3f80 <putch> 3f9a: 01 d0 rcall .+2 ; 0x3f9e <putch>
3f7e: 6b cf rjmp .-298 ; 0x3e56 <main+0x56> 3f9c: 5c cf rjmp .-328 ; 0x3e56 <main+0x56>
00003f80 <putch>: 00003f9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
3f80: 98 2f mov r25, r24 3f9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
3f82: 80 91 c0 00 lds r24, 0x00C0 3fa0: 80 91 c0 00 lds r24, 0x00C0
3f86: 85 ff sbrs r24, 5 3fa4: 85 ff sbrs r24, 5
3f88: fc cf rjmp .-8 ; 0x3f82 <putch+0x2> 3fa6: fc cf rjmp .-8 ; 0x3fa0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
3f8a: 90 93 c6 00 sts 0x00C6, r25 3fa8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
3f8e: 08 95 ret 3fac: 08 95 ret
00003f90 <getch>: 00003fae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
3f90: a8 95 wdr 3fae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
3f92: 80 91 c0 00 lds r24, 0x00C0 3fb0: 80 91 c0 00 lds r24, 0x00C0
3f96: 87 ff sbrs r24, 7 3fb4: 87 ff sbrs r24, 7
3f98: fc cf rjmp .-8 ; 0x3f92 <getch+0x2> 3fb6: fc cf rjmp .-8 ; 0x3fb0 <getch+0x2>
ch = UDR0; ch = UDR0;
3f9a: 80 91 c6 00 lds r24, 0x00C6 3fb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
3f9e: 08 95 ret 3fbc: 08 95 ret
00003fa0 <getLen>: 00003fbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
3fa0: f7 df rcall .-18 ; 0x3f90 <getch> 3fbe: f7 df rcall .-18 ; 0x3fae <getch>
length = getch(); length = getch();
3fa2: f6 df rcall .-20 ; 0x3f90 <getch> 3fc0: f6 df rcall .-20 ; 0x3fae <getch>
3fa4: 80 93 02 02 sts 0x0202, r24 3fc2: 80 93 02 02 sts 0x0202, r24
return getch(); return getch();
} }
3fa8: f3 cf rjmp .-26 ; 0x3f90 <getch> 3fc6: f3 cf rjmp .-26 ; 0x3fae <getch>
00003faa <watchdogConfig>: 00003fc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
3faa: e0 e6 ldi r30, 0x60 ; 96 3fc8: e0 e6 ldi r30, 0x60 ; 96
3fac: f0 e0 ldi r31, 0x00 ; 0 3fca: f0 e0 ldi r31, 0x00 ; 0
3fae: 98 e1 ldi r25, 0x18 ; 24 3fcc: 98 e1 ldi r25, 0x18 ; 24
3fb0: 90 83 st Z, r25 3fce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
3fb2: 80 83 st Z, r24 3fd0: 80 83 st Z, r24
} }
3fb4: 08 95 ret 3fd2: 08 95 ret
00003fb6 <appStart>: 00003fd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
3fb6: 80 e0 ldi r24, 0x00 ; 0 3fd4: 80 e0 ldi r24, 0x00 ; 0
3fb8: f8 df rcall .-16 ; 0x3faa <watchdogConfig> 3fd6: f8 df rcall .-16 ; 0x3fc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
3fba: ee 27 eor r30, r30 3fd8: ee 27 eor r30, r30
3fbc: ff 27 eor r31, r31 3fda: ff 27 eor r31, r31
3fbe: 09 94 ijmp 3fdc: 09 94 ijmp
00003fc0 <verifySpace>: 00003fde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
3fc0: e7 df rcall .-50 ; 0x3f90 <getch> 3fde: e7 df rcall .-50 ; 0x3fae <getch>
3fc2: 80 32 cpi r24, 0x20 ; 32 3fe0: 80 32 cpi r24, 0x20 ; 32
3fc4: 09 f0 breq .+2 ; 0x3fc8 <verifySpace+0x8> 3fe2: 09 f0 breq .+2 ; 0x3fe6 <verifySpace+0x8>
3fc6: f7 df rcall .-18 ; 0x3fb6 <appStart> 3fe4: f7 df rcall .-18 ; 0x3fd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
3fc8: 84 e1 ldi r24, 0x14 ; 20 3fe6: 84 e1 ldi r24, 0x14 ; 20
} }
3fca: da cf rjmp .-76 ; 0x3f80 <putch> 3fe8: da cf rjmp .-76 ; 0x3f9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
3fcc: 1f 93 push r17 3fea: 1f 93 push r17
3fce: 18 2f mov r17, r24 3fec: 18 2f mov r17, r24
00003fd0 <getNch>: 00003fee <getNch>:
do getch(); while (--count); do getch(); while (--count);
3fd0: df df rcall .-66 ; 0x3f90 <getch> 3fee: df df rcall .-66 ; 0x3fae <getch>
3fd2: 11 50 subi r17, 0x01 ; 1 3ff0: 11 50 subi r17, 0x01 ; 1
3fd4: e9 f7 brne .-6 ; 0x3fd0 <getNch> 3ff2: e9 f7 brne .-6 ; 0x3fee <getNch>
verifySpace(); verifySpace();
3fd6: f4 df rcall .-24 ; 0x3fc0 <verifySpace> 3ff4: f4 df rcall .-24 ; 0x3fde <verifySpace>
} }
3fd8: 1f 91 pop r17 3ff6: 1f 91 pop r17
3fda: 08 95 ret 3ff8: 08 95 ret

View File

@ -7,9 +7,9 @@
:101D600081F4D7D0082F10E0D4D090E0982F8827A6 :101D600081F4D7D0082F10E0D4D090E0982F8827A6
:101D7000802B912B880F991F909381018093800174 :101D7000802B912B880F991F909381018093800174
:101D8000B5C0863529F484E0ECD080E0B3D0AFC094 :101D8000B5C0863529F484E0ECD080E0B3D0AFC094
:101D9000843609F06BC0D1D0E0918001F0918101CF :101D9000843609F06BC0D1D0C0E0D1E0BAD08993CD
:101DA00083E087BFE895C0E0D1E0B3D0899380910C :101DA000809182018150809382018823B9F7E0916C
:101DB00082018150809382018823B9F7CCD007B685 :101DB0008001F091810183E087BFE895CCD007B620
:101DC00000FCFDCF8091800190918101892B41F52C :101DC00000FCFDCF8091800190918101892B41F52C
:101DD000809100012091010130E0322F222790E014 :101DD000809100012091010130E0322F222790E014
:101DE000282B392B309385012093840140910801E1 :101DE000282B392B309385012093840140910801E1

View File

@ -9,11 +9,11 @@ Idx Name Size VMA LMA File off Algn
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 00000078 00000000 00000000 000002ee 2**0 2 .debug_pubnames 00000078 00000000 00000000 000002ee 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 000002a3 00000000 00000000 00000366 2**0 3 .debug_info 000002a4 00000000 00000000 00000366 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ac 00000000 00000000 00000609 2**0 4 .debug_abbrev 000001ac 00000000 00000000 0000060a 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 0000043d 00000000 00000000 000007b5 2**0 5 .debug_line 0000043d 00000000 00000000 000007b6 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 000000a0 00000000 00000000 00000bf4 2**2 6 .debug_frame 000000a0 00000000 00000000 00000bf4 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
@ -217,28 +217,31 @@ void watchdogReset() {
getLen(); getLen();
1d96: d1 d0 rcall .+418 ; 0x1f3a <getLen> 1d96: d1 d0 rcall .+418 ; 0x1f3a <getLen>
1d98: c0 e0 ldi r28, 0x00 ; 0
// Immediately start page erase - this will 4.5ms 1d9a: d1 e0 ldi r29, 0x01 ; 1
__boot_page_erase_short((uint16_t)(void*)address); // If we are in RWW section, immediately start page erase
1d98: e0 91 80 01 lds r30, 0x0180 if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
1d9c: f0 91 81 01 lds r31, 0x0181
1da0: 83 e0 ldi r24, 0x03 ; 3
1da2: 87 bf out 0x37, r24 ; 55
1da4: e8 95 spm
1da6: c0 e0 ldi r28, 0x00 ; 0
1da8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
1daa: b3 d0 rcall .+358 ; 0x1f12 <getch> 1d9c: ba d0 rcall .+372 ; 0x1f12 <getch>
1dac: 89 93 st Y+, r24 1d9e: 89 93 st Y+, r24
while (--length); while (--length);
1dae: 80 91 82 01 lds r24, 0x0182 1da0: 80 91 82 01 lds r24, 0x0182
1db2: 81 50 subi r24, 0x01 ; 1 1da4: 81 50 subi r24, 0x01 ; 1
1db4: 80 93 82 01 sts 0x0182, r24 1da6: 80 93 82 01 sts 0x0182, r24
1db8: 88 23 and r24, r24 1daa: 88 23 and r24, r24
1dba: b9 f7 brne .-18 ; 0x1daa <main+0xaa> 1dac: b9 f7 brne .-18 ; 0x1d9c <main+0x9c>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
1dae: e0 91 80 01 lds r30, 0x0180
1db2: f0 91 81 01 lds r31, 0x0181
1db6: 83 e0 ldi r24, 0x03 ; 3
1db8: 87 bf out 0x37, r24 ; 55
1dba: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();

View File

@ -1,32 +1,34 @@
:103E000085E08093810082E08093C00088E1809308 :103E000085E08093810082E08093C00088E1809308
:103E1000C10086E08093C20080E18093C40084B733 :103E1000C10086E08093C20080E18093C40084B733
:103E200014BE81FFC8D08DE0C0D0259A86E020E383 :103E200014BE81FFD7D08DE0CFD0259A86E020E365
:103E30003CEF91E0309385002093840096BBB09BCB :103E30003CEF91E0309385002093840096BBB09BCB
:103E4000FECF1D9AA8958150A9F7DD24D394A5E053 :103E4000FECF1D9AA8958150A9F7DD24D394A5E053
:103E5000FA2EF1E1EF2E9CD0813421F481E0B6D02E :103E5000EA2EF1E1FF2EABD0813421F481E0C5D010
:103E600083E020C0823411F484E103C0853419F466 :103E600083E020C0823411F484E103C0853419F466
:103E700085E0ACD082C0853581F48AD0082F10E06F :103E700085E0BBD091C0853581F499D0082F10E042
:103E800087D090E0982F8827802B912B880F991F3F :103E800096D090E0982F8827802B912B880F991F30
:103E900090930102809300026FC0863529F484E07C :103E900090930102809300027EC0863529F484E06D
:103EA00095D080E06DD069C0843609F03FC078D0ED :103EA000A4D080E07CD078C0843609F04EC087D0A2
:103EB000E0910002F091010283E087BFE895C0E045 :103EB000E0910002F091010288E3E030F80718F485
:103EC000D1E066D0899380910202815080930202F2 :103EC00083E087BFE895C0E0D1E071D0899380910D
:103ED0008823B9F775D007B600FCFDCF40910002EA :103ED00002028150809302028823B9F7E091000228
:103EE00050910102A0E0B1E02C9130E011968C914C :103EE000F091010288E3E030F80718F083E087BF23
:103EF000119790E0982F8827822B932B1296FA0126 :103EF000E89575D007B600FCFDCF409100025091C7
:103F00000C01D7BEE89511244E5F5F4FF1E0A03859 :103F00000102A0E0B1E02C9130E011968C91119764
:103F1000BF0751F7E0910002F0910102F7BEE8956A :103F100090E0982F8827822B932B1296FA010C01A0
:103F200007B600FCFDCFE7BEE89527C08437B9F49B :103F2000D7BEE89511244E5F5F4FF1E0A038BF0780
:103F300037D046D0E0910002F09101023196F09323 :103F300051F7E0910002F0910102E7BEE89507B663
:103F40000102E09300023197E4918E2F19D0809105 :103F400000FCFDCFF7BEE89527C08437B9F437D021
:103F50000202815080930202882361F70EC08537E8 :103F500046D0E0910002F09101023196F093010207
:103F600039F42ED08EE10CD084E90AD086E09ACFC5 :103F6000E09300023197E4918E2F19D080910202E4
:103F7000813511F488E019D023D080E101D06BCFD6 :103F7000815080930202882361F70EC0853739F49F
:103F8000982F8091C00085FFFCCF9093C6000895C4 :103F80002ED08EE10CD084E90AD086E08BCF81352B
:103F9000A8958091C00087FFFCCF8091C60008954E :103F900011F488E019D023D080E101D05CCF982FB4
:103FA000F7DFF6DF80930202F3CFE0E6F0E098E17E :103FA0008091C00085FFFCCF9093C6000895A8952E
:103FB00090838083089580E0F8DFEE27FF2709943F :103FB0008091C00087FFFCCF8091C6000895F7DF95
:103FC000E7DF803209F0F7DF84E1DACF1F93182FA3 :103FC000F6DF80930202F3CFE0E6F0E098E1908321
:0C3FD000DFDF1150E9F7F4DF1F910895C6 :103FD0008083089580E0F8DFEE27FF270994E7DF6C
:103FE000803209F0F7DF84E1DACF1F93182FDFDF8B
:0A3FF0001150E9F7F4DF1F91089566
:0400000300003E00BB :0400000300003E00BB
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_pro_16MHz.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 00003e00 00003e00 00000054 2**1 0 .text 000001fa 00003e00 00003e00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
3e20: 14 be out 0x34, r1 ; 52 3e20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
3e22: 81 ff sbrs r24, 1 3e22: 81 ff sbrs r24, 1
3e24: c8 d0 rcall .+400 ; 0x3fb6 <appStart> 3e24: d7 d0 rcall .+430 ; 0x3fd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
3e26: 8d e0 ldi r24, 0x0D ; 13 3e26: 8d e0 ldi r24, 0x0D ; 13
3e28: c0 d0 rcall .+384 ; 0x3faa <watchdogConfig> 3e28: cf d0 rcall .+414 ; 0x3fc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3e4e: a5 e0 ldi r26, 0x05 ; 5 3e4e: a5 e0 ldi r26, 0x05 ; 5
3e50: fa 2e mov r15, r26 3e50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3e52: f1 e1 ldi r31, 0x11 ; 17 3e52: f1 e1 ldi r31, 0x11 ; 17
3e54: ef 2e mov r14, r31 3e54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
3e56: 9c d0 rcall .+312 ; 0x3f90 <getch> 3e56: ab d0 rcall .+342 ; 0x3fae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
3e58: 81 34 cpi r24, 0x41 ; 65 3e58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
3e5c: 81 e0 ldi r24, 0x01 ; 1 3e5c: 81 e0 ldi r24, 0x01 ; 1
3e5e: b6 d0 rcall .+364 ; 0x3fcc <verifySpace+0xc> 3e5e: c5 d0 rcall .+394 ; 0x3fea <verifySpace+0xc>
putch(0x03); putch(0x03);
3e60: 83 e0 ldi r24, 0x03 ; 3 3e60: 83 e0 ldi r24, 0x03 ; 3
3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4> 3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
3e70: 85 e0 ldi r24, 0x05 ; 5 3e70: 85 e0 ldi r24, 0x05 ; 5
3e72: ac d0 rcall .+344 ; 0x3fcc <verifySpace+0xc> 3e72: bb d0 rcall .+374 ; 0x3fea <verifySpace+0xc>
3e74: 82 c0 rjmp .+260 ; 0x3f7a <main+0x17a> 3e74: 91 c0 rjmp .+290 ; 0x3f98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
3e76: 85 35 cpi r24, 0x55 ; 85 3e76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
3e7a: 8a d0 rcall .+276 ; 0x3f90 <getch> 3e7a: 99 d0 rcall .+306 ; 0x3fae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
3e7c: 08 2f mov r16, r24 3e7c: 08 2f mov r16, r24
3e7e: 10 e0 ldi r17, 0x00 ; 0 3e7e: 10 e0 ldi r17, 0x00 ; 0
3e80: 87 d0 rcall .+270 ; 0x3f90 <getch> 3e80: 96 d0 rcall .+300 ; 0x3fae <getch>
3e82: 90 e0 ldi r25, 0x00 ; 0 3e82: 90 e0 ldi r25, 0x00 ; 0
3e84: 98 2f mov r25, r24 3e84: 98 2f mov r25, r24
3e86: 88 27 eor r24, r24 3e86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
3e90: 90 93 01 02 sts 0x0201, r25 3e90: 90 93 01 02 sts 0x0201, r25
3e94: 80 93 00 02 sts 0x0200, r24 3e94: 80 93 00 02 sts 0x0200, r24
3e98: 6f c0 rjmp .+222 ; 0x3f78 <main+0x178> 3e98: 7e c0 rjmp .+252 ; 0x3f96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
3e9e: 84 e0 ldi r24, 0x04 ; 4 3e9e: 84 e0 ldi r24, 0x04 ; 4
3ea0: 95 d0 rcall .+298 ; 0x3fcc <verifySpace+0xc> 3ea0: a4 d0 rcall .+328 ; 0x3fea <verifySpace+0xc>
putch(0x00); putch(0x00);
3ea2: 80 e0 ldi r24, 0x00 ; 0 3ea2: 80 e0 ldi r24, 0x00 ; 0
3ea4: 6d d0 rcall .+218 ; 0x3f80 <putch> 3ea4: 7c d0 rcall .+248 ; 0x3f9e <putch>
3ea6: 69 c0 rjmp .+210 ; 0x3f7a <main+0x17a> 3ea6: 78 c0 rjmp .+240 ; 0x3f98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
3ea8: 84 36 cpi r24, 0x64 ; 100 3ea8: 84 36 cpi r24, 0x64 ; 100
3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae> 3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae>
3eac: 3f c0 rjmp .+126 ; 0x3f2c <main+0x12c> 3eac: 4e c0 rjmp .+156 ; 0x3f4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
3eae: 78 d0 rcall .+240 ; 0x3fa0 <getLen> 3eae: 87 d0 rcall .+270 ; 0x3fbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3eb0: e0 91 00 02 lds r30, 0x0200 3eb0: e0 91 00 02 lds r30, 0x0200
3eb4: f0 91 01 02 lds r31, 0x0201 3eb4: f0 91 01 02 lds r31, 0x0201
3eb8: 83 e0 ldi r24, 0x03 ; 3 3eb8: 88 e3 ldi r24, 0x38 ; 56
3eba: 87 bf out 0x37, r24 ; 55 3eba: e0 30 cpi r30, 0x00 ; 0
3ebc: e8 95 spm 3ebc: f8 07 cpc r31, r24
3ebe: c0 e0 ldi r28, 0x00 ; 0 3ebe: 18 f4 brcc .+6 ; 0x3ec6 <main+0xc6>
3ec0: d1 e0 ldi r29, 0x01 ; 1 3ec0: 83 e0 ldi r24, 0x03 ; 3
3ec2: 87 bf out 0x37, r24 ; 55
3ec4: e8 95 spm
3ec6: c0 e0 ldi r28, 0x00 ; 0
3ec8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
3ec2: 66 d0 rcall .+204 ; 0x3f90 <getch> 3eca: 71 d0 rcall .+226 ; 0x3fae <getch>
3ec4: 89 93 st Y+, r24 3ecc: 89 93 st Y+, r24
while (--length); while (--length);
3ec6: 80 91 02 02 lds r24, 0x0202 3ece: 80 91 02 02 lds r24, 0x0202
3eca: 81 50 subi r24, 0x01 ; 1 3ed2: 81 50 subi r24, 0x01 ; 1
3ecc: 80 93 02 02 sts 0x0202, r24 3ed4: 80 93 02 02 sts 0x0202, r24
3ed0: 88 23 and r24, r24 3ed8: 88 23 and r24, r24
3ed2: b9 f7 brne .-18 ; 0x3ec2 <main+0xc2> 3eda: b9 f7 brne .-18 ; 0x3eca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3edc: e0 91 00 02 lds r30, 0x0200
3ee0: f0 91 01 02 lds r31, 0x0201
3ee4: 88 e3 ldi r24, 0x38 ; 56
3ee6: e0 30 cpi r30, 0x00 ; 0
3ee8: f8 07 cpc r31, r24
3eea: 18 f0 brcs .+6 ; 0x3ef2 <main+0xf2>
3eec: 83 e0 ldi r24, 0x03 ; 3
3eee: 87 bf out 0x37, r24 ; 55
3ef0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
3ed4: 75 d0 rcall .+234 ; 0x3fc0 <verifySpace> 3ef2: 75 d0 rcall .+234 ; 0x3fde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
3ed6: 07 b6 in r0, 0x37 ; 55 3ef4: 07 b6 in r0, 0x37 ; 55
3ed8: 00 fc sbrc r0, 0 3ef6: 00 fc sbrc r0, 0
3eda: fd cf rjmp .-6 ; 0x3ed6 <main+0xd6> 3ef8: fd cf rjmp .-6 ; 0x3ef4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
3edc: 40 91 00 02 lds r20, 0x0200 3efa: 40 91 00 02 lds r20, 0x0200
3ee0: 50 91 01 02 lds r21, 0x0201 3efe: 50 91 01 02 lds r21, 0x0201
3ee4: a0 e0 ldi r26, 0x00 ; 0 3f02: a0 e0 ldi r26, 0x00 ; 0
3ee6: b1 e0 ldi r27, 0x01 ; 1 3f04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
3ee8: 2c 91 ld r18, X 3f06: 2c 91 ld r18, X
3eea: 30 e0 ldi r19, 0x00 ; 0 3f08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
3eec: 11 96 adiw r26, 0x01 ; 1 3f0a: 11 96 adiw r26, 0x01 ; 1
3eee: 8c 91 ld r24, X 3f0c: 8c 91 ld r24, X
3ef0: 11 97 sbiw r26, 0x01 ; 1 3f0e: 11 97 sbiw r26, 0x01 ; 1
3ef2: 90 e0 ldi r25, 0x00 ; 0 3f10: 90 e0 ldi r25, 0x00 ; 0
3ef4: 98 2f mov r25, r24 3f12: 98 2f mov r25, r24
3ef6: 88 27 eor r24, r24 3f14: 88 27 eor r24, r24
3ef8: 82 2b or r24, r18 3f16: 82 2b or r24, r18
3efa: 93 2b or r25, r19 3f18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
3efc: 12 96 adiw r26, 0x02 ; 2 3f1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
3efe: fa 01 movw r30, r20 3f1c: fa 01 movw r30, r20
3f00: 0c 01 movw r0, r24 3f1e: 0c 01 movw r0, r24
3f02: d7 be out 0x37, r13 ; 55 3f20: d7 be out 0x37, r13 ; 55
3f04: e8 95 spm 3f22: e8 95 spm
3f06: 11 24 eor r1, r1 3f24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
3f08: 4e 5f subi r20, 0xFE ; 254 3f26: 4e 5f subi r20, 0xFE ; 254
3f0a: 5f 4f sbci r21, 0xFF ; 255 3f28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
3f0c: f1 e0 ldi r31, 0x01 ; 1 3f2a: f1 e0 ldi r31, 0x01 ; 1
3f0e: a0 38 cpi r26, 0x80 ; 128 3f2c: a0 38 cpi r26, 0x80 ; 128
3f10: bf 07 cpc r27, r31 3f2e: bf 07 cpc r27, r31
3f12: 51 f7 brne .-44 ; 0x3ee8 <main+0xe8> 3f30: 51 f7 brne .-44 ; 0x3f06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3f14: e0 91 00 02 lds r30, 0x0200 3f32: e0 91 00 02 lds r30, 0x0200
3f18: f0 91 01 02 lds r31, 0x0201 3f36: f0 91 01 02 lds r31, 0x0201
3f1c: f7 be out 0x37, r15 ; 55 3f3a: e7 be out 0x37, r14 ; 55
3f1e: e8 95 spm 3f3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
3f20: 07 b6 in r0, 0x37 ; 55 3f3e: 07 b6 in r0, 0x37 ; 55
3f22: 00 fc sbrc r0, 0 3f40: 00 fc sbrc r0, 0
3f24: fd cf rjmp .-6 ; 0x3f20 <main+0x120> 3f42: fd cf rjmp .-6 ; 0x3f3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3f26: e7 be out 0x37, r14 ; 55 3f44: f7 be out 0x37, r15 ; 55
3f28: e8 95 spm 3f46: e8 95 spm
3f2a: 27 c0 rjmp .+78 ; 0x3f7a <main+0x17a> 3f48: 27 c0 rjmp .+78 ; 0x3f98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
3f2c: 84 37 cpi r24, 0x74 ; 116 3f4a: 84 37 cpi r24, 0x74 ; 116
3f2e: b9 f4 brne .+46 ; 0x3f5e <main+0x15e> 3f4c: b9 f4 brne .+46 ; 0x3f7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
3f30: 37 d0 rcall .+110 ; 0x3fa0 <getLen> 3f4e: 37 d0 rcall .+110 ; 0x3fbe <getLen>
verifySpace(); verifySpace();
3f32: 46 d0 rcall .+140 ; 0x3fc0 <verifySpace> 3f50: 46 d0 rcall .+140 ; 0x3fde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
3f34: e0 91 00 02 lds r30, 0x0200 3f52: e0 91 00 02 lds r30, 0x0200
3f38: f0 91 01 02 lds r31, 0x0201 3f56: f0 91 01 02 lds r31, 0x0201
3f3c: 31 96 adiw r30, 0x01 ; 1 3f5a: 31 96 adiw r30, 0x01 ; 1
3f3e: f0 93 01 02 sts 0x0201, r31 3f5c: f0 93 01 02 sts 0x0201, r31
3f42: e0 93 00 02 sts 0x0200, r30 3f60: e0 93 00 02 sts 0x0200, r30
3f46: 31 97 sbiw r30, 0x01 ; 1 3f64: 31 97 sbiw r30, 0x01 ; 1
3f48: e4 91 lpm r30, Z+ 3f66: e4 91 lpm r30, Z+
3f4a: 8e 2f mov r24, r30 3f68: 8e 2f mov r24, r30
3f4c: 19 d0 rcall .+50 ; 0x3f80 <putch> 3f6a: 19 d0 rcall .+50 ; 0x3f9e <putch>
while (--length); while (--length);
3f4e: 80 91 02 02 lds r24, 0x0202 3f6c: 80 91 02 02 lds r24, 0x0202
3f52: 81 50 subi r24, 0x01 ; 1 3f70: 81 50 subi r24, 0x01 ; 1
3f54: 80 93 02 02 sts 0x0202, r24 3f72: 80 93 02 02 sts 0x0202, r24
3f58: 88 23 and r24, r24 3f76: 88 23 and r24, r24
3f5a: 61 f7 brne .-40 ; 0x3f34 <main+0x134> 3f78: 61 f7 brne .-40 ; 0x3f52 <main+0x152>
3f5c: 0e c0 rjmp .+28 ; 0x3f7a <main+0x17a> 3f7a: 0e c0 rjmp .+28 ; 0x3f98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
3f5e: 85 37 cpi r24, 0x75 ; 117 3f7c: 85 37 cpi r24, 0x75 ; 117
3f60: 39 f4 brne .+14 ; 0x3f70 <main+0x170> 3f7e: 39 f4 brne .+14 ; 0x3f8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
3f62: 2e d0 rcall .+92 ; 0x3fc0 <verifySpace> 3f80: 2e d0 rcall .+92 ; 0x3fde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
3f64: 8e e1 ldi r24, 0x1E ; 30 3f82: 8e e1 ldi r24, 0x1E ; 30
3f66: 0c d0 rcall .+24 ; 0x3f80 <putch> 3f84: 0c d0 rcall .+24 ; 0x3f9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
3f68: 84 e9 ldi r24, 0x94 ; 148 3f86: 84 e9 ldi r24, 0x94 ; 148
3f6a: 0a d0 rcall .+20 ; 0x3f80 <putch> 3f88: 0a d0 rcall .+20 ; 0x3f9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
3f6c: 86 e0 ldi r24, 0x06 ; 6 3f8a: 86 e0 ldi r24, 0x06 ; 6
3f6e: 9a cf rjmp .-204 ; 0x3ea4 <main+0xa4> 3f8c: 8b cf rjmp .-234 ; 0x3ea4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
3f70: 81 35 cpi r24, 0x51 ; 81 3f8e: 81 35 cpi r24, 0x51 ; 81
3f72: 11 f4 brne .+4 ; 0x3f78 <main+0x178> 3f90: 11 f4 brne .+4 ; 0x3f96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
3f74: 88 e0 ldi r24, 0x08 ; 8 3f92: 88 e0 ldi r24, 0x08 ; 8
3f76: 19 d0 rcall .+50 ; 0x3faa <watchdogConfig> 3f94: 19 d0 rcall .+50 ; 0x3fc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
3f78: 23 d0 rcall .+70 ; 0x3fc0 <verifySpace> 3f96: 23 d0 rcall .+70 ; 0x3fde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
3f7a: 80 e1 ldi r24, 0x10 ; 16 3f98: 80 e1 ldi r24, 0x10 ; 16
3f7c: 01 d0 rcall .+2 ; 0x3f80 <putch> 3f9a: 01 d0 rcall .+2 ; 0x3f9e <putch>
3f7e: 6b cf rjmp .-298 ; 0x3e56 <main+0x56> 3f9c: 5c cf rjmp .-328 ; 0x3e56 <main+0x56>
00003f80 <putch>: 00003f9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
3f80: 98 2f mov r25, r24 3f9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
3f82: 80 91 c0 00 lds r24, 0x00C0 3fa0: 80 91 c0 00 lds r24, 0x00C0
3f86: 85 ff sbrs r24, 5 3fa4: 85 ff sbrs r24, 5
3f88: fc cf rjmp .-8 ; 0x3f82 <putch+0x2> 3fa6: fc cf rjmp .-8 ; 0x3fa0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
3f8a: 90 93 c6 00 sts 0x00C6, r25 3fa8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
3f8e: 08 95 ret 3fac: 08 95 ret
00003f90 <getch>: 00003fae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
3f90: a8 95 wdr 3fae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
3f92: 80 91 c0 00 lds r24, 0x00C0 3fb0: 80 91 c0 00 lds r24, 0x00C0
3f96: 87 ff sbrs r24, 7 3fb4: 87 ff sbrs r24, 7
3f98: fc cf rjmp .-8 ; 0x3f92 <getch+0x2> 3fb6: fc cf rjmp .-8 ; 0x3fb0 <getch+0x2>
ch = UDR0; ch = UDR0;
3f9a: 80 91 c6 00 lds r24, 0x00C6 3fb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
3f9e: 08 95 ret 3fbc: 08 95 ret
00003fa0 <getLen>: 00003fbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
3fa0: f7 df rcall .-18 ; 0x3f90 <getch> 3fbe: f7 df rcall .-18 ; 0x3fae <getch>
length = getch(); length = getch();
3fa2: f6 df rcall .-20 ; 0x3f90 <getch> 3fc0: f6 df rcall .-20 ; 0x3fae <getch>
3fa4: 80 93 02 02 sts 0x0202, r24 3fc2: 80 93 02 02 sts 0x0202, r24
return getch(); return getch();
} }
3fa8: f3 cf rjmp .-26 ; 0x3f90 <getch> 3fc6: f3 cf rjmp .-26 ; 0x3fae <getch>
00003faa <watchdogConfig>: 00003fc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
3faa: e0 e6 ldi r30, 0x60 ; 96 3fc8: e0 e6 ldi r30, 0x60 ; 96
3fac: f0 e0 ldi r31, 0x00 ; 0 3fca: f0 e0 ldi r31, 0x00 ; 0
3fae: 98 e1 ldi r25, 0x18 ; 24 3fcc: 98 e1 ldi r25, 0x18 ; 24
3fb0: 90 83 st Z, r25 3fce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
3fb2: 80 83 st Z, r24 3fd0: 80 83 st Z, r24
} }
3fb4: 08 95 ret 3fd2: 08 95 ret
00003fb6 <appStart>: 00003fd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
3fb6: 80 e0 ldi r24, 0x00 ; 0 3fd4: 80 e0 ldi r24, 0x00 ; 0
3fb8: f8 df rcall .-16 ; 0x3faa <watchdogConfig> 3fd6: f8 df rcall .-16 ; 0x3fc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
3fba: ee 27 eor r30, r30 3fd8: ee 27 eor r30, r30
3fbc: ff 27 eor r31, r31 3fda: ff 27 eor r31, r31
3fbe: 09 94 ijmp 3fdc: 09 94 ijmp
00003fc0 <verifySpace>: 00003fde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
3fc0: e7 df rcall .-50 ; 0x3f90 <getch> 3fde: e7 df rcall .-50 ; 0x3fae <getch>
3fc2: 80 32 cpi r24, 0x20 ; 32 3fe0: 80 32 cpi r24, 0x20 ; 32
3fc4: 09 f0 breq .+2 ; 0x3fc8 <verifySpace+0x8> 3fe2: 09 f0 breq .+2 ; 0x3fe6 <verifySpace+0x8>
3fc6: f7 df rcall .-18 ; 0x3fb6 <appStart> 3fe4: f7 df rcall .-18 ; 0x3fd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
3fc8: 84 e1 ldi r24, 0x14 ; 20 3fe6: 84 e1 ldi r24, 0x14 ; 20
} }
3fca: da cf rjmp .-76 ; 0x3f80 <putch> 3fe8: da cf rjmp .-76 ; 0x3f9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
3fcc: 1f 93 push r17 3fea: 1f 93 push r17
3fce: 18 2f mov r17, r24 3fec: 18 2f mov r17, r24
00003fd0 <getNch>: 00003fee <getNch>:
do getch(); while (--count); do getch(); while (--count);
3fd0: df df rcall .-66 ; 0x3f90 <getch> 3fee: df df rcall .-66 ; 0x3fae <getch>
3fd2: 11 50 subi r17, 0x01 ; 1 3ff0: 11 50 subi r17, 0x01 ; 1
3fd4: e9 f7 brne .-6 ; 0x3fd0 <getNch> 3ff2: e9 f7 brne .-6 ; 0x3fee <getNch>
verifySpace(); verifySpace();
3fd6: f4 df rcall .-24 ; 0x3fc0 <verifySpace> 3ff4: f4 df rcall .-24 ; 0x3fde <verifySpace>
} }
3fd8: 1f 91 pop r17 3ff6: 1f 91 pop r17
3fda: 08 95 ret 3ff8: 08 95 ret

View File

@ -1,32 +1,34 @@
:103E000085E08093810082E08093C00088E1809308 :103E000085E08093810082E08093C00088E1809308
:103E1000C10086E08093C20085E18093C40084B72E :103E1000C10086E08093C20085E18093C40084B72E
:103E200014BE81FFC8D08DE0C0D0259A86E02CE377 :103E200014BE81FFD7D08DE0CFD0259A86E02CE359
:103E30003BEF91E0309385002093840096BBB09BCC :103E30003BEF91E0309385002093840096BBB09BCC
:103E4000FECF1D9AA8958150A9F7DD24D394A5E053 :103E4000FECF1D9AA8958150A9F7DD24D394A5E053
:103E5000FA2EF1E1EF2E9CD0813421F481E0B6D02E :103E5000EA2EF1E1FF2EABD0813421F481E0C5D010
:103E600083E020C0823411F484E103C0853419F466 :103E600083E020C0823411F484E103C0853419F466
:103E700085E0ACD082C0853581F48AD0082F10E06F :103E700085E0BBD091C0853581F499D0082F10E042
:103E800087D090E0982F8827802B912B880F991F3F :103E800096D090E0982F8827802B912B880F991F30
:103E900090930102809300026FC0863529F484E07C :103E900090930102809300027EC0863529F484E06D
:103EA00095D080E06DD069C0843609F03FC078D0ED :103EA000A4D080E07CD078C0843609F04EC087D0A2
:103EB000E0910002F091010283E087BFE895C0E045 :103EB000E0910002F091010288E3E030F80718F485
:103EC000D1E066D0899380910202815080930202F2 :103EC00083E087BFE895C0E0D1E071D0899380910D
:103ED0008823B9F775D007B600FCFDCF40910002EA :103ED00002028150809302028823B9F7E091000228
:103EE00050910102A0E0B1E02C9130E011968C914C :103EE000F091010288E3E030F80718F083E087BF23
:103EF000119790E0982F8827822B932B1296FA0126 :103EF000E89575D007B600FCFDCF409100025091C7
:103F00000C01D7BEE89511244E5F5F4FF1E0A03859 :103F00000102A0E0B1E02C9130E011968C91119764
:103F1000BF0751F7E0910002F0910102F7BEE8956A :103F100090E0982F8827822B932B1296FA010C01A0
:103F200007B600FCFDCFE7BEE89527C08437B9F49B :103F2000D7BEE89511244E5F5F4FF1E0A038BF0780
:103F300037D046D0E0910002F09101023196F09323 :103F300051F7E0910002F0910102E7BEE89507B663
:103F40000102E09300023197E4918E2F19D0809105 :103F400000FCFDCFF7BEE89527C08437B9F437D021
:103F50000202815080930202882361F70EC08537E8 :103F500046D0E0910002F09101023196F093010207
:103F600039F42ED08EE10CD084E90AD086E09ACFC5 :103F6000E09300023197E4918E2F19D080910202E4
:103F7000813511F488E019D023D080E101D06BCFD6 :103F7000815080930202882361F70EC0853739F49F
:103F8000982F8091C00085FFFCCF9093C6000895C4 :103F80002ED08EE10CD084E90AD086E08BCF81352B
:103F9000A8958091C00087FFFCCF8091C60008954E :103F900011F488E019D023D080E101D05CCF982FB4
:103FA000F7DFF6DF80930202F3CFE0E6F0E098E17E :103FA0008091C00085FFFCCF9093C6000895A8952E
:103FB00090838083089580E0F8DFEE27FF2709943F :103FB0008091C00087FFFCCF8091C6000895F7DF95
:103FC000E7DF803209F0F7DF84E1DACF1F93182FA3 :103FC000F6DF80930202F3CFE0E6F0E098E1908321
:0C3FD000DFDF1150E9F7F4DF1F910895C6 :103FD0008083089580E0F8DFEE27FF270994E7DF6C
:103FE000803209F0F7DF84E1DACF1F93182FDFDF8B
:0A3FF0001150E9F7F4DF1F91089566
:0400000300003E00BB :0400000300003E00BB
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_pro_20mhz.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 00003e00 00003e00 00000054 2**1 0 .text 000001fa 00003e00 00003e00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
3e20: 14 be out 0x34, r1 ; 52 3e20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
3e22: 81 ff sbrs r24, 1 3e22: 81 ff sbrs r24, 1
3e24: c8 d0 rcall .+400 ; 0x3fb6 <appStart> 3e24: d7 d0 rcall .+430 ; 0x3fd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
3e26: 8d e0 ldi r24, 0x0D ; 13 3e26: 8d e0 ldi r24, 0x0D ; 13
3e28: c0 d0 rcall .+384 ; 0x3faa <watchdogConfig> 3e28: cf d0 rcall .+414 ; 0x3fc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3e4e: a5 e0 ldi r26, 0x05 ; 5 3e4e: a5 e0 ldi r26, 0x05 ; 5
3e50: fa 2e mov r15, r26 3e50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3e52: f1 e1 ldi r31, 0x11 ; 17 3e52: f1 e1 ldi r31, 0x11 ; 17
3e54: ef 2e mov r14, r31 3e54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
3e56: 9c d0 rcall .+312 ; 0x3f90 <getch> 3e56: ab d0 rcall .+342 ; 0x3fae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
3e58: 81 34 cpi r24, 0x41 ; 65 3e58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
3e5c: 81 e0 ldi r24, 0x01 ; 1 3e5c: 81 e0 ldi r24, 0x01 ; 1
3e5e: b6 d0 rcall .+364 ; 0x3fcc <verifySpace+0xc> 3e5e: c5 d0 rcall .+394 ; 0x3fea <verifySpace+0xc>
putch(0x03); putch(0x03);
3e60: 83 e0 ldi r24, 0x03 ; 3 3e60: 83 e0 ldi r24, 0x03 ; 3
3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4> 3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
3e70: 85 e0 ldi r24, 0x05 ; 5 3e70: 85 e0 ldi r24, 0x05 ; 5
3e72: ac d0 rcall .+344 ; 0x3fcc <verifySpace+0xc> 3e72: bb d0 rcall .+374 ; 0x3fea <verifySpace+0xc>
3e74: 82 c0 rjmp .+260 ; 0x3f7a <main+0x17a> 3e74: 91 c0 rjmp .+290 ; 0x3f98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
3e76: 85 35 cpi r24, 0x55 ; 85 3e76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
3e7a: 8a d0 rcall .+276 ; 0x3f90 <getch> 3e7a: 99 d0 rcall .+306 ; 0x3fae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
3e7c: 08 2f mov r16, r24 3e7c: 08 2f mov r16, r24
3e7e: 10 e0 ldi r17, 0x00 ; 0 3e7e: 10 e0 ldi r17, 0x00 ; 0
3e80: 87 d0 rcall .+270 ; 0x3f90 <getch> 3e80: 96 d0 rcall .+300 ; 0x3fae <getch>
3e82: 90 e0 ldi r25, 0x00 ; 0 3e82: 90 e0 ldi r25, 0x00 ; 0
3e84: 98 2f mov r25, r24 3e84: 98 2f mov r25, r24
3e86: 88 27 eor r24, r24 3e86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
3e90: 90 93 01 02 sts 0x0201, r25 3e90: 90 93 01 02 sts 0x0201, r25
3e94: 80 93 00 02 sts 0x0200, r24 3e94: 80 93 00 02 sts 0x0200, r24
3e98: 6f c0 rjmp .+222 ; 0x3f78 <main+0x178> 3e98: 7e c0 rjmp .+252 ; 0x3f96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
3e9e: 84 e0 ldi r24, 0x04 ; 4 3e9e: 84 e0 ldi r24, 0x04 ; 4
3ea0: 95 d0 rcall .+298 ; 0x3fcc <verifySpace+0xc> 3ea0: a4 d0 rcall .+328 ; 0x3fea <verifySpace+0xc>
putch(0x00); putch(0x00);
3ea2: 80 e0 ldi r24, 0x00 ; 0 3ea2: 80 e0 ldi r24, 0x00 ; 0
3ea4: 6d d0 rcall .+218 ; 0x3f80 <putch> 3ea4: 7c d0 rcall .+248 ; 0x3f9e <putch>
3ea6: 69 c0 rjmp .+210 ; 0x3f7a <main+0x17a> 3ea6: 78 c0 rjmp .+240 ; 0x3f98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
3ea8: 84 36 cpi r24, 0x64 ; 100 3ea8: 84 36 cpi r24, 0x64 ; 100
3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae> 3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae>
3eac: 3f c0 rjmp .+126 ; 0x3f2c <main+0x12c> 3eac: 4e c0 rjmp .+156 ; 0x3f4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
3eae: 78 d0 rcall .+240 ; 0x3fa0 <getLen> 3eae: 87 d0 rcall .+270 ; 0x3fbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3eb0: e0 91 00 02 lds r30, 0x0200 3eb0: e0 91 00 02 lds r30, 0x0200
3eb4: f0 91 01 02 lds r31, 0x0201 3eb4: f0 91 01 02 lds r31, 0x0201
3eb8: 83 e0 ldi r24, 0x03 ; 3 3eb8: 88 e3 ldi r24, 0x38 ; 56
3eba: 87 bf out 0x37, r24 ; 55 3eba: e0 30 cpi r30, 0x00 ; 0
3ebc: e8 95 spm 3ebc: f8 07 cpc r31, r24
3ebe: c0 e0 ldi r28, 0x00 ; 0 3ebe: 18 f4 brcc .+6 ; 0x3ec6 <main+0xc6>
3ec0: d1 e0 ldi r29, 0x01 ; 1 3ec0: 83 e0 ldi r24, 0x03 ; 3
3ec2: 87 bf out 0x37, r24 ; 55
3ec4: e8 95 spm
3ec6: c0 e0 ldi r28, 0x00 ; 0
3ec8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
3ec2: 66 d0 rcall .+204 ; 0x3f90 <getch> 3eca: 71 d0 rcall .+226 ; 0x3fae <getch>
3ec4: 89 93 st Y+, r24 3ecc: 89 93 st Y+, r24
while (--length); while (--length);
3ec6: 80 91 02 02 lds r24, 0x0202 3ece: 80 91 02 02 lds r24, 0x0202
3eca: 81 50 subi r24, 0x01 ; 1 3ed2: 81 50 subi r24, 0x01 ; 1
3ecc: 80 93 02 02 sts 0x0202, r24 3ed4: 80 93 02 02 sts 0x0202, r24
3ed0: 88 23 and r24, r24 3ed8: 88 23 and r24, r24
3ed2: b9 f7 brne .-18 ; 0x3ec2 <main+0xc2> 3eda: b9 f7 brne .-18 ; 0x3eca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3edc: e0 91 00 02 lds r30, 0x0200
3ee0: f0 91 01 02 lds r31, 0x0201
3ee4: 88 e3 ldi r24, 0x38 ; 56
3ee6: e0 30 cpi r30, 0x00 ; 0
3ee8: f8 07 cpc r31, r24
3eea: 18 f0 brcs .+6 ; 0x3ef2 <main+0xf2>
3eec: 83 e0 ldi r24, 0x03 ; 3
3eee: 87 bf out 0x37, r24 ; 55
3ef0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
3ed4: 75 d0 rcall .+234 ; 0x3fc0 <verifySpace> 3ef2: 75 d0 rcall .+234 ; 0x3fde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
3ed6: 07 b6 in r0, 0x37 ; 55 3ef4: 07 b6 in r0, 0x37 ; 55
3ed8: 00 fc sbrc r0, 0 3ef6: 00 fc sbrc r0, 0
3eda: fd cf rjmp .-6 ; 0x3ed6 <main+0xd6> 3ef8: fd cf rjmp .-6 ; 0x3ef4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
3edc: 40 91 00 02 lds r20, 0x0200 3efa: 40 91 00 02 lds r20, 0x0200
3ee0: 50 91 01 02 lds r21, 0x0201 3efe: 50 91 01 02 lds r21, 0x0201
3ee4: a0 e0 ldi r26, 0x00 ; 0 3f02: a0 e0 ldi r26, 0x00 ; 0
3ee6: b1 e0 ldi r27, 0x01 ; 1 3f04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
3ee8: 2c 91 ld r18, X 3f06: 2c 91 ld r18, X
3eea: 30 e0 ldi r19, 0x00 ; 0 3f08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
3eec: 11 96 adiw r26, 0x01 ; 1 3f0a: 11 96 adiw r26, 0x01 ; 1
3eee: 8c 91 ld r24, X 3f0c: 8c 91 ld r24, X
3ef0: 11 97 sbiw r26, 0x01 ; 1 3f0e: 11 97 sbiw r26, 0x01 ; 1
3ef2: 90 e0 ldi r25, 0x00 ; 0 3f10: 90 e0 ldi r25, 0x00 ; 0
3ef4: 98 2f mov r25, r24 3f12: 98 2f mov r25, r24
3ef6: 88 27 eor r24, r24 3f14: 88 27 eor r24, r24
3ef8: 82 2b or r24, r18 3f16: 82 2b or r24, r18
3efa: 93 2b or r25, r19 3f18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
3efc: 12 96 adiw r26, 0x02 ; 2 3f1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
3efe: fa 01 movw r30, r20 3f1c: fa 01 movw r30, r20
3f00: 0c 01 movw r0, r24 3f1e: 0c 01 movw r0, r24
3f02: d7 be out 0x37, r13 ; 55 3f20: d7 be out 0x37, r13 ; 55
3f04: e8 95 spm 3f22: e8 95 spm
3f06: 11 24 eor r1, r1 3f24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
3f08: 4e 5f subi r20, 0xFE ; 254 3f26: 4e 5f subi r20, 0xFE ; 254
3f0a: 5f 4f sbci r21, 0xFF ; 255 3f28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
3f0c: f1 e0 ldi r31, 0x01 ; 1 3f2a: f1 e0 ldi r31, 0x01 ; 1
3f0e: a0 38 cpi r26, 0x80 ; 128 3f2c: a0 38 cpi r26, 0x80 ; 128
3f10: bf 07 cpc r27, r31 3f2e: bf 07 cpc r27, r31
3f12: 51 f7 brne .-44 ; 0x3ee8 <main+0xe8> 3f30: 51 f7 brne .-44 ; 0x3f06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3f14: e0 91 00 02 lds r30, 0x0200 3f32: e0 91 00 02 lds r30, 0x0200
3f18: f0 91 01 02 lds r31, 0x0201 3f36: f0 91 01 02 lds r31, 0x0201
3f1c: f7 be out 0x37, r15 ; 55 3f3a: e7 be out 0x37, r14 ; 55
3f1e: e8 95 spm 3f3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
3f20: 07 b6 in r0, 0x37 ; 55 3f3e: 07 b6 in r0, 0x37 ; 55
3f22: 00 fc sbrc r0, 0 3f40: 00 fc sbrc r0, 0
3f24: fd cf rjmp .-6 ; 0x3f20 <main+0x120> 3f42: fd cf rjmp .-6 ; 0x3f3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3f26: e7 be out 0x37, r14 ; 55 3f44: f7 be out 0x37, r15 ; 55
3f28: e8 95 spm 3f46: e8 95 spm
3f2a: 27 c0 rjmp .+78 ; 0x3f7a <main+0x17a> 3f48: 27 c0 rjmp .+78 ; 0x3f98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
3f2c: 84 37 cpi r24, 0x74 ; 116 3f4a: 84 37 cpi r24, 0x74 ; 116
3f2e: b9 f4 brne .+46 ; 0x3f5e <main+0x15e> 3f4c: b9 f4 brne .+46 ; 0x3f7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
3f30: 37 d0 rcall .+110 ; 0x3fa0 <getLen> 3f4e: 37 d0 rcall .+110 ; 0x3fbe <getLen>
verifySpace(); verifySpace();
3f32: 46 d0 rcall .+140 ; 0x3fc0 <verifySpace> 3f50: 46 d0 rcall .+140 ; 0x3fde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
3f34: e0 91 00 02 lds r30, 0x0200 3f52: e0 91 00 02 lds r30, 0x0200
3f38: f0 91 01 02 lds r31, 0x0201 3f56: f0 91 01 02 lds r31, 0x0201
3f3c: 31 96 adiw r30, 0x01 ; 1 3f5a: 31 96 adiw r30, 0x01 ; 1
3f3e: f0 93 01 02 sts 0x0201, r31 3f5c: f0 93 01 02 sts 0x0201, r31
3f42: e0 93 00 02 sts 0x0200, r30 3f60: e0 93 00 02 sts 0x0200, r30
3f46: 31 97 sbiw r30, 0x01 ; 1 3f64: 31 97 sbiw r30, 0x01 ; 1
3f48: e4 91 lpm r30, Z+ 3f66: e4 91 lpm r30, Z+
3f4a: 8e 2f mov r24, r30 3f68: 8e 2f mov r24, r30
3f4c: 19 d0 rcall .+50 ; 0x3f80 <putch> 3f6a: 19 d0 rcall .+50 ; 0x3f9e <putch>
while (--length); while (--length);
3f4e: 80 91 02 02 lds r24, 0x0202 3f6c: 80 91 02 02 lds r24, 0x0202
3f52: 81 50 subi r24, 0x01 ; 1 3f70: 81 50 subi r24, 0x01 ; 1
3f54: 80 93 02 02 sts 0x0202, r24 3f72: 80 93 02 02 sts 0x0202, r24
3f58: 88 23 and r24, r24 3f76: 88 23 and r24, r24
3f5a: 61 f7 brne .-40 ; 0x3f34 <main+0x134> 3f78: 61 f7 brne .-40 ; 0x3f52 <main+0x152>
3f5c: 0e c0 rjmp .+28 ; 0x3f7a <main+0x17a> 3f7a: 0e c0 rjmp .+28 ; 0x3f98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
3f5e: 85 37 cpi r24, 0x75 ; 117 3f7c: 85 37 cpi r24, 0x75 ; 117
3f60: 39 f4 brne .+14 ; 0x3f70 <main+0x170> 3f7e: 39 f4 brne .+14 ; 0x3f8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
3f62: 2e d0 rcall .+92 ; 0x3fc0 <verifySpace> 3f80: 2e d0 rcall .+92 ; 0x3fde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
3f64: 8e e1 ldi r24, 0x1E ; 30 3f82: 8e e1 ldi r24, 0x1E ; 30
3f66: 0c d0 rcall .+24 ; 0x3f80 <putch> 3f84: 0c d0 rcall .+24 ; 0x3f9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
3f68: 84 e9 ldi r24, 0x94 ; 148 3f86: 84 e9 ldi r24, 0x94 ; 148
3f6a: 0a d0 rcall .+20 ; 0x3f80 <putch> 3f88: 0a d0 rcall .+20 ; 0x3f9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
3f6c: 86 e0 ldi r24, 0x06 ; 6 3f8a: 86 e0 ldi r24, 0x06 ; 6
3f6e: 9a cf rjmp .-204 ; 0x3ea4 <main+0xa4> 3f8c: 8b cf rjmp .-234 ; 0x3ea4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
3f70: 81 35 cpi r24, 0x51 ; 81 3f8e: 81 35 cpi r24, 0x51 ; 81
3f72: 11 f4 brne .+4 ; 0x3f78 <main+0x178> 3f90: 11 f4 brne .+4 ; 0x3f96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
3f74: 88 e0 ldi r24, 0x08 ; 8 3f92: 88 e0 ldi r24, 0x08 ; 8
3f76: 19 d0 rcall .+50 ; 0x3faa <watchdogConfig> 3f94: 19 d0 rcall .+50 ; 0x3fc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
3f78: 23 d0 rcall .+70 ; 0x3fc0 <verifySpace> 3f96: 23 d0 rcall .+70 ; 0x3fde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
3f7a: 80 e1 ldi r24, 0x10 ; 16 3f98: 80 e1 ldi r24, 0x10 ; 16
3f7c: 01 d0 rcall .+2 ; 0x3f80 <putch> 3f9a: 01 d0 rcall .+2 ; 0x3f9e <putch>
3f7e: 6b cf rjmp .-298 ; 0x3e56 <main+0x56> 3f9c: 5c cf rjmp .-328 ; 0x3e56 <main+0x56>
00003f80 <putch>: 00003f9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
3f80: 98 2f mov r25, r24 3f9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
3f82: 80 91 c0 00 lds r24, 0x00C0 3fa0: 80 91 c0 00 lds r24, 0x00C0
3f86: 85 ff sbrs r24, 5 3fa4: 85 ff sbrs r24, 5
3f88: fc cf rjmp .-8 ; 0x3f82 <putch+0x2> 3fa6: fc cf rjmp .-8 ; 0x3fa0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
3f8a: 90 93 c6 00 sts 0x00C6, r25 3fa8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
3f8e: 08 95 ret 3fac: 08 95 ret
00003f90 <getch>: 00003fae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
3f90: a8 95 wdr 3fae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
3f92: 80 91 c0 00 lds r24, 0x00C0 3fb0: 80 91 c0 00 lds r24, 0x00C0
3f96: 87 ff sbrs r24, 7 3fb4: 87 ff sbrs r24, 7
3f98: fc cf rjmp .-8 ; 0x3f92 <getch+0x2> 3fb6: fc cf rjmp .-8 ; 0x3fb0 <getch+0x2>
ch = UDR0; ch = UDR0;
3f9a: 80 91 c6 00 lds r24, 0x00C6 3fb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
3f9e: 08 95 ret 3fbc: 08 95 ret
00003fa0 <getLen>: 00003fbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
3fa0: f7 df rcall .-18 ; 0x3f90 <getch> 3fbe: f7 df rcall .-18 ; 0x3fae <getch>
length = getch(); length = getch();
3fa2: f6 df rcall .-20 ; 0x3f90 <getch> 3fc0: f6 df rcall .-20 ; 0x3fae <getch>
3fa4: 80 93 02 02 sts 0x0202, r24 3fc2: 80 93 02 02 sts 0x0202, r24
return getch(); return getch();
} }
3fa8: f3 cf rjmp .-26 ; 0x3f90 <getch> 3fc6: f3 cf rjmp .-26 ; 0x3fae <getch>
00003faa <watchdogConfig>: 00003fc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
3faa: e0 e6 ldi r30, 0x60 ; 96 3fc8: e0 e6 ldi r30, 0x60 ; 96
3fac: f0 e0 ldi r31, 0x00 ; 0 3fca: f0 e0 ldi r31, 0x00 ; 0
3fae: 98 e1 ldi r25, 0x18 ; 24 3fcc: 98 e1 ldi r25, 0x18 ; 24
3fb0: 90 83 st Z, r25 3fce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
3fb2: 80 83 st Z, r24 3fd0: 80 83 st Z, r24
} }
3fb4: 08 95 ret 3fd2: 08 95 ret
00003fb6 <appStart>: 00003fd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
3fb6: 80 e0 ldi r24, 0x00 ; 0 3fd4: 80 e0 ldi r24, 0x00 ; 0
3fb8: f8 df rcall .-16 ; 0x3faa <watchdogConfig> 3fd6: f8 df rcall .-16 ; 0x3fc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
3fba: ee 27 eor r30, r30 3fd8: ee 27 eor r30, r30
3fbc: ff 27 eor r31, r31 3fda: ff 27 eor r31, r31
3fbe: 09 94 ijmp 3fdc: 09 94 ijmp
00003fc0 <verifySpace>: 00003fde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
3fc0: e7 df rcall .-50 ; 0x3f90 <getch> 3fde: e7 df rcall .-50 ; 0x3fae <getch>
3fc2: 80 32 cpi r24, 0x20 ; 32 3fe0: 80 32 cpi r24, 0x20 ; 32
3fc4: 09 f0 breq .+2 ; 0x3fc8 <verifySpace+0x8> 3fe2: 09 f0 breq .+2 ; 0x3fe6 <verifySpace+0x8>
3fc6: f7 df rcall .-18 ; 0x3fb6 <appStart> 3fe4: f7 df rcall .-18 ; 0x3fd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
3fc8: 84 e1 ldi r24, 0x14 ; 20 3fe6: 84 e1 ldi r24, 0x14 ; 20
} }
3fca: da cf rjmp .-76 ; 0x3f80 <putch> 3fe8: da cf rjmp .-76 ; 0x3f9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
3fcc: 1f 93 push r17 3fea: 1f 93 push r17
3fce: 18 2f mov r17, r24 3fec: 18 2f mov r17, r24
00003fd0 <getNch>: 00003fee <getNch>:
do getch(); while (--count); do getch(); while (--count);
3fd0: df df rcall .-66 ; 0x3f90 <getch> 3fee: df df rcall .-66 ; 0x3fae <getch>
3fd2: 11 50 subi r17, 0x01 ; 1 3ff0: 11 50 subi r17, 0x01 ; 1
3fd4: e9 f7 brne .-6 ; 0x3fd0 <getNch> 3ff2: e9 f7 brne .-6 ; 0x3fee <getNch>
verifySpace(); verifySpace();
3fd6: f4 df rcall .-24 ; 0x3fc0 <verifySpace> 3ff4: f4 df rcall .-24 ; 0x3fde <verifySpace>
} }
3fd8: 1f 91 pop r17 3ff6: 1f 91 pop r17
3fda: 08 95 ret 3ff8: 08 95 ret

View File

@ -1,32 +1,34 @@
:103E000085E08093810082E08093C00088E1809308 :103E000085E08093810082E08093C00088E1809308
:103E1000C10086E08093C20088E08093C40084B72C :103E1000C10086E08093C20088E08093C40084B72C
:103E200014BE81FFC8D08DE0C0D0259A86E028E17D :103E200014BE81FFD7D08DE0CFD0259A86E028E15F
:103E30003EEF91E0309385002093840096BBB09BC9 :103E30003EEF91E0309385002093840096BBB09BC9
:103E4000FECF1D9AA8958150A9F7DD24D394A5E053 :103E4000FECF1D9AA8958150A9F7DD24D394A5E053
:103E5000FA2EF1E1EF2E9CD0813421F481E0B6D02E :103E5000EA2EF1E1FF2EABD0813421F481E0C5D010
:103E600083E020C0823411F484E103C0853419F466 :103E600083E020C0823411F484E103C0853419F466
:103E700085E0ACD082C0853581F48AD0082F10E06F :103E700085E0BBD091C0853581F499D0082F10E042
:103E800087D090E0982F8827802B912B880F991F3F :103E800096D090E0982F8827802B912B880F991F30
:103E900090930102809300026FC0863529F484E07C :103E900090930102809300027EC0863529F484E06D
:103EA00095D080E06DD069C0843609F03FC078D0ED :103EA000A4D080E07CD078C0843609F04EC087D0A2
:103EB000E0910002F091010283E087BFE895C0E045 :103EB000E0910002F091010288E3E030F80718F485
:103EC000D1E066D0899380910202815080930202F2 :103EC00083E087BFE895C0E0D1E071D0899380910D
:103ED0008823B9F775D007B600FCFDCF40910002EA :103ED00002028150809302028823B9F7E091000228
:103EE00050910102A0E0B1E02C9130E011968C914C :103EE000F091010288E3E030F80718F083E087BF23
:103EF000119790E0982F8827822B932B1296FA0126 :103EF000E89575D007B600FCFDCF409100025091C7
:103F00000C01D7BEE89511244E5F5F4FF1E0A03859 :103F00000102A0E0B1E02C9130E011968C91119764
:103F1000BF0751F7E0910002F0910102F7BEE8956A :103F100090E0982F8827822B932B1296FA010C01A0
:103F200007B600FCFDCFE7BEE89527C08437B9F49B :103F2000D7BEE89511244E5F5F4FF1E0A038BF0780
:103F300037D046D0E0910002F09101023196F09323 :103F300051F7E0910002F0910102E7BEE89507B663
:103F40000102E09300023197E4918E2F19D0809105 :103F400000FCFDCFF7BEE89527C08437B9F437D021
:103F50000202815080930202882361F70EC08537E8 :103F500046D0E0910002F09101023196F093010207
:103F600039F42ED08EE10CD084E90AD086E09ACFC5 :103F6000E09300023197E4918E2F19D080910202E4
:103F7000813511F488E019D023D080E101D06BCFD6 :103F7000815080930202882361F70EC0853739F49F
:103F8000982F8091C00085FFFCCF9093C6000895C4 :103F80002ED08EE10CD084E90AD086E08BCF81352B
:103F9000A8958091C00087FFFCCF8091C60008954E :103F900011F488E019D023D080E101D05CCF982FB4
:103FA000F7DFF6DF80930202F3CFE0E6F0E098E17E :103FA0008091C00085FFFCCF9093C6000895A8952E
:103FB00090838083089580E0F8DFEE27FF2709943F :103FB0008091C00087FFFCCF8091C6000895F7DF95
:103FC000E7DF803209F0F7DF84E1DACF1F93182FA3 :103FC000F6DF80930202F3CFE0E6F0E098E1908321
:0C3FD000DFDF1150E9F7F4DF1F910895C6 :103FD0008083089580E0F8DFEE27FF270994E7DF6C
:103FE000803209F0F7DF84E1DACF1F93182FDFDF8B
:0A3FF0001150E9F7F4DF1F91089566
:0400000300003E00BB :0400000300003E00BB
:00000001FF :00000001FF

View File

@ -3,25 +3,25 @@ optiboot_pro_8MHz.elf: file format elf32-avr
Sections: Sections:
Idx Name Size VMA LMA File off Algn Idx Name Size VMA LMA File off Algn
0 .text 000001dc 00003e00 00003e00 00000054 2**1 0 .text 000001fa 00003e00 00003e00 00000054 2**1
CONTENTS, ALLOC, LOAD, READONLY, CODE CONTENTS, ALLOC, LOAD, READONLY, CODE
1 .debug_aranges 00000028 00000000 00000000 00000230 2**0 1 .debug_aranges 00000028 00000000 00000000 0000024e 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
2 .debug_pubnames 0000006a 00000000 00000000 00000258 2**0 2 .debug_pubnames 0000006a 00000000 00000000 00000276 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
3 .debug_info 00000283 00000000 00000000 000002c2 2**0 3 .debug_info 00000284 00000000 00000000 000002e0 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
4 .debug_abbrev 000001ae 00000000 00000000 00000545 2**0 4 .debug_abbrev 000001ae 00000000 00000000 00000564 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
5 .debug_line 000003db 00000000 00000000 000006f3 2**0 5 .debug_line 000003e3 00000000 00000000 00000712 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
6 .debug_frame 00000090 00000000 00000000 00000ad0 2**2 6 .debug_frame 00000090 00000000 00000000 00000af8 2**2
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
7 .debug_str 00000140 00000000 00000000 00000b60 2**0 7 .debug_str 00000140 00000000 00000000 00000b88 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
8 .debug_loc 000001d1 00000000 00000000 00000ca0 2**0 8 .debug_loc 000001e1 00000000 00000000 00000cc8 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
9 .debug_ranges 00000068 00000000 00000000 00000e71 2**0 9 .debug_ranges 00000068 00000000 00000000 00000ea9 2**0
CONTENTS, READONLY, DEBUGGING CONTENTS, READONLY, DEBUGGING
Disassembly of section .text: Disassembly of section .text:
@ -61,12 +61,12 @@ int main(void) {
3e20: 14 be out 0x34, r1 ; 52 3e20: 14 be out 0x34, r1 ; 52
if (!(ch & _BV(EXTRF))) appStart(); if (!(ch & _BV(EXTRF))) appStart();
3e22: 81 ff sbrs r24, 1 3e22: 81 ff sbrs r24, 1
3e24: c8 d0 rcall .+400 ; 0x3fb6 <appStart> 3e24: d7 d0 rcall .+430 ; 0x3fd4 <appStart>
// Set up watchdog to trigger after 500ms // Set up watchdog to trigger after 500ms
watchdogConfig(WATCHDOG_500MS); watchdogConfig(WATCHDOG_500MS);
3e26: 8d e0 ldi r24, 0x0D ; 13 3e26: 8d e0 ldi r24, 0x0D ; 13
3e28: c0 d0 rcall .+384 ; 0x3faa <watchdogConfig> 3e28: cf d0 rcall .+414 ; 0x3fc8 <watchdogConfig>
/* Set LED pin as output */ /* Set LED pin as output */
LED_DDR |= _BV(LED); LED_DDR |= _BV(LED);
@ -127,21 +127,21 @@ void watchdogReset() {
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3e4e: a5 e0 ldi r26, 0x05 ; 5 3e4e: a5 e0 ldi r26, 0x05 ; 5
3e50: fa 2e mov r15, r26 3e50: ea 2e mov r14, r26
boot_spm_busy_wait(); boot_spm_busy_wait();
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3e52: f1 e1 ldi r31, 0x11 ; 17 3e52: f1 e1 ldi r31, 0x11 ; 17
3e54: ef 2e mov r14, r31 3e54: ff 2e mov r15, r31
#endif #endif
/* Forever loop */ /* Forever loop */
for (;;) { for (;;) {
/* get character from UART */ /* get character from UART */
ch = getch(); ch = getch();
3e56: 9c d0 rcall .+312 ; 0x3f90 <getch> 3e56: ab d0 rcall .+342 ; 0x3fae <getch>
if(ch == STK_GET_PARAMETER) { if(ch == STK_GET_PARAMETER) {
3e58: 81 34 cpi r24, 0x41 ; 65 3e58: 81 34 cpi r24, 0x41 ; 65
@ -149,7 +149,7 @@ void watchdogReset() {
// GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy // GET PARAMETER returns a generic 0x03 reply - enough to keep Avrdude happy
getNch(1); getNch(1);
3e5c: 81 e0 ldi r24, 0x01 ; 1 3e5c: 81 e0 ldi r24, 0x01 ; 1
3e5e: b6 d0 rcall .+364 ; 0x3fcc <verifySpace+0xc> 3e5e: c5 d0 rcall .+394 ; 0x3fea <verifySpace+0xc>
putch(0x03); putch(0x03);
3e60: 83 e0 ldi r24, 0x03 ; 3 3e60: 83 e0 ldi r24, 0x03 ; 3
3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4> 3e62: 20 c0 rjmp .+64 ; 0x3ea4 <main+0xa4>
@ -168,8 +168,8 @@ void watchdogReset() {
// SET DEVICE EXT is ignored // SET DEVICE EXT is ignored
getNch(5); getNch(5);
3e70: 85 e0 ldi r24, 0x05 ; 5 3e70: 85 e0 ldi r24, 0x05 ; 5
3e72: ac d0 rcall .+344 ; 0x3fcc <verifySpace+0xc> 3e72: bb d0 rcall .+374 ; 0x3fea <verifySpace+0xc>
3e74: 82 c0 rjmp .+260 ; 0x3f7a <main+0x17a> 3e74: 91 c0 rjmp .+290 ; 0x3f98 <main+0x198>
} }
else if(ch == STK_LOAD_ADDRESS) { else if(ch == STK_LOAD_ADDRESS) {
3e76: 85 35 cpi r24, 0x55 ; 85 3e76: 85 35 cpi r24, 0x55 ; 85
@ -177,11 +177,11 @@ void watchdogReset() {
// LOAD ADDRESS // LOAD ADDRESS
uint16_t newAddress; uint16_t newAddress;
newAddress = getch(); newAddress = getch();
3e7a: 8a d0 rcall .+276 ; 0x3f90 <getch> 3e7a: 99 d0 rcall .+306 ; 0x3fae <getch>
newAddress = (newAddress & 0xff) | (getch() << 8); newAddress = (newAddress & 0xff) | (getch() << 8);
3e7c: 08 2f mov r16, r24 3e7c: 08 2f mov r16, r24
3e7e: 10 e0 ldi r17, 0x00 ; 0 3e7e: 10 e0 ldi r17, 0x00 ; 0
3e80: 87 d0 rcall .+270 ; 0x3f90 <getch> 3e80: 96 d0 rcall .+300 ; 0x3fae <getch>
3e82: 90 e0 ldi r25, 0x00 ; 0 3e82: 90 e0 ldi r25, 0x00 ; 0
3e84: 98 2f mov r25, r24 3e84: 98 2f mov r25, r24
3e86: 88 27 eor r24, r24 3e86: 88 27 eor r24, r24
@ -197,7 +197,7 @@ void watchdogReset() {
address = newAddress; address = newAddress;
3e90: 90 93 01 02 sts 0x0201, r25 3e90: 90 93 01 02 sts 0x0201, r25
3e94: 80 93 00 02 sts 0x0200, r24 3e94: 80 93 00 02 sts 0x0200, r24
3e98: 6f c0 rjmp .+222 ; 0x3f78 <main+0x178> 3e98: 7e c0 rjmp .+252 ; 0x3f96 <main+0x196>
verifySpace(); verifySpace();
} }
else if(ch == STK_UNIVERSAL) { else if(ch == STK_UNIVERSAL) {
@ -206,320 +206,337 @@ void watchdogReset() {
// UNIVERSAL command is ignored // UNIVERSAL command is ignored
getNch(4); getNch(4);
3e9e: 84 e0 ldi r24, 0x04 ; 4 3e9e: 84 e0 ldi r24, 0x04 ; 4
3ea0: 95 d0 rcall .+298 ; 0x3fcc <verifySpace+0xc> 3ea0: a4 d0 rcall .+328 ; 0x3fea <verifySpace+0xc>
putch(0x00); putch(0x00);
3ea2: 80 e0 ldi r24, 0x00 ; 0 3ea2: 80 e0 ldi r24, 0x00 ; 0
3ea4: 6d d0 rcall .+218 ; 0x3f80 <putch> 3ea4: 7c d0 rcall .+248 ; 0x3f9e <putch>
3ea6: 69 c0 rjmp .+210 ; 0x3f7a <main+0x17a> 3ea6: 78 c0 rjmp .+240 ; 0x3f98 <main+0x198>
} }
/* Write memory, length is big endian and is in bytes */ /* Write memory, length is big endian and is in bytes */
else if(ch == STK_PROG_PAGE) { else if(ch == STK_PROG_PAGE) {
3ea8: 84 36 cpi r24, 0x64 ; 100 3ea8: 84 36 cpi r24, 0x64 ; 100
3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae> 3eaa: 09 f0 breq .+2 ; 0x3eae <main+0xae>
3eac: 3f c0 rjmp .+126 ; 0x3f2c <main+0x12c> 3eac: 4e c0 rjmp .+156 ; 0x3f4a <main+0x14a>
// PROGRAM PAGE - we support flash programming only, not EEPROM // PROGRAM PAGE - we support flash programming only, not EEPROM
uint8_t *bufPtr; uint8_t *bufPtr;
uint16_t addrPtr; uint16_t addrPtr;
getLen(); getLen();
3eae: 78 d0 rcall .+240 ; 0x3fa0 <getLen> 3eae: 87 d0 rcall .+270 ; 0x3fbe <getLen>
// Immediately start page erase - this will 4.5ms // If we are in RWW section, immediately start page erase
__boot_page_erase_short((uint16_t)(void*)address); if (address < NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3eb0: e0 91 00 02 lds r30, 0x0200 3eb0: e0 91 00 02 lds r30, 0x0200
3eb4: f0 91 01 02 lds r31, 0x0201 3eb4: f0 91 01 02 lds r31, 0x0201
3eb8: 83 e0 ldi r24, 0x03 ; 3 3eb8: 88 e3 ldi r24, 0x38 ; 56
3eba: 87 bf out 0x37, r24 ; 55 3eba: e0 30 cpi r30, 0x00 ; 0
3ebc: e8 95 spm 3ebc: f8 07 cpc r31, r24
3ebe: c0 e0 ldi r28, 0x00 ; 0 3ebe: 18 f4 brcc .+6 ; 0x3ec6 <main+0xc6>
3ec0: d1 e0 ldi r29, 0x01 ; 1 3ec0: 83 e0 ldi r24, 0x03 ; 3
3ec2: 87 bf out 0x37, r24 ; 55
3ec4: e8 95 spm
3ec6: c0 e0 ldi r28, 0x00 ; 0
3ec8: d1 e0 ldi r29, 0x01 ; 1
// While that is going on, read in page contents // While that is going on, read in page contents
bufPtr = buff; bufPtr = buff;
do *bufPtr++ = getch(); do *bufPtr++ = getch();
3ec2: 66 d0 rcall .+204 ; 0x3f90 <getch> 3eca: 71 d0 rcall .+226 ; 0x3fae <getch>
3ec4: 89 93 st Y+, r24 3ecc: 89 93 st Y+, r24
while (--length); while (--length);
3ec6: 80 91 02 02 lds r24, 0x0202 3ece: 80 91 02 02 lds r24, 0x0202
3eca: 81 50 subi r24, 0x01 ; 1 3ed2: 81 50 subi r24, 0x01 ; 1
3ecc: 80 93 02 02 sts 0x0202, r24 3ed4: 80 93 02 02 sts 0x0202, r24
3ed0: 88 23 and r24, r24 3ed8: 88 23 and r24, r24
3ed2: b9 f7 brne .-18 ; 0x3ec2 <main+0xc2> 3eda: b9 f7 brne .-18 ; 0x3eca <main+0xca>
// If we are in NRWW section, page erase has to be delayed until now.
// Todo: Take RAMPZ into account
if (address >= NRWWSTART) __boot_page_erase_short((uint16_t)(void*)address);
3edc: e0 91 00 02 lds r30, 0x0200
3ee0: f0 91 01 02 lds r31, 0x0201
3ee4: 88 e3 ldi r24, 0x38 ; 56
3ee6: e0 30 cpi r30, 0x00 ; 0
3ee8: f8 07 cpc r31, r24
3eea: 18 f0 brcs .+6 ; 0x3ef2 <main+0xf2>
3eec: 83 e0 ldi r24, 0x03 ; 3
3eee: 87 bf out 0x37, r24 ; 55
3ef0: e8 95 spm
// Read command terminator, start reply // Read command terminator, start reply
verifySpace(); verifySpace();
3ed4: 75 d0 rcall .+234 ; 0x3fc0 <verifySpace> 3ef2: 75 d0 rcall .+234 ; 0x3fde <verifySpace>
// If only a partial page is to be programmed, the erase might not be complete. // If only a partial page is to be programmed, the erase might not be complete.
// So check that here // So check that here
boot_spm_busy_wait(); boot_spm_busy_wait();
3ed6: 07 b6 in r0, 0x37 ; 55 3ef4: 07 b6 in r0, 0x37 ; 55
3ed8: 00 fc sbrc r0, 0 3ef6: 00 fc sbrc r0, 0
3eda: fd cf rjmp .-6 ; 0x3ed6 <main+0xd6> 3ef8: fd cf rjmp .-6 ; 0x3ef4 <main+0xf4>
} }
#endif #endif
// Copy buffer into programming buffer // Copy buffer into programming buffer
bufPtr = buff; bufPtr = buff;
addrPtr = (uint16_t)(void*)address; addrPtr = (uint16_t)(void*)address;
3edc: 40 91 00 02 lds r20, 0x0200 3efa: 40 91 00 02 lds r20, 0x0200
3ee0: 50 91 01 02 lds r21, 0x0201 3efe: 50 91 01 02 lds r21, 0x0201
3ee4: a0 e0 ldi r26, 0x00 ; 0 3f02: a0 e0 ldi r26, 0x00 ; 0
3ee6: b1 e0 ldi r27, 0x01 ; 1 3f04: b1 e0 ldi r27, 0x01 ; 1
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
3ee8: 2c 91 ld r18, X 3f06: 2c 91 ld r18, X
3eea: 30 e0 ldi r19, 0x00 ; 0 3f08: 30 e0 ldi r19, 0x00 ; 0
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
3eec: 11 96 adiw r26, 0x01 ; 1 3f0a: 11 96 adiw r26, 0x01 ; 1
3eee: 8c 91 ld r24, X 3f0c: 8c 91 ld r24, X
3ef0: 11 97 sbiw r26, 0x01 ; 1 3f0e: 11 97 sbiw r26, 0x01 ; 1
3ef2: 90 e0 ldi r25, 0x00 ; 0 3f10: 90 e0 ldi r25, 0x00 ; 0
3ef4: 98 2f mov r25, r24 3f12: 98 2f mov r25, r24
3ef6: 88 27 eor r24, r24 3f14: 88 27 eor r24, r24
3ef8: 82 2b or r24, r18 3f16: 82 2b or r24, r18
3efa: 93 2b or r25, r19 3f18: 93 2b or r25, r19
#define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4)) #define rstVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+4))
#define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6)) #define wdtVect (*(uint16_t*)(RAMSTART+SPM_PAGESIZE*2+6))
#endif #endif
/* main program starts here */ /* main program starts here */
int main(void) { int main(void) {
3efc: 12 96 adiw r26, 0x02 ; 2 3f1a: 12 96 adiw r26, 0x02 ; 2
ch = SPM_PAGESIZE / 2; ch = SPM_PAGESIZE / 2;
do { do {
uint16_t a; uint16_t a;
a = *bufPtr++; a = *bufPtr++;
a |= (*bufPtr++) << 8; a |= (*bufPtr++) << 8;
__boot_page_fill_short((uint16_t)(void*)addrPtr,a); __boot_page_fill_short((uint16_t)(void*)addrPtr,a);
3efe: fa 01 movw r30, r20 3f1c: fa 01 movw r30, r20
3f00: 0c 01 movw r0, r24 3f1e: 0c 01 movw r0, r24
3f02: d7 be out 0x37, r13 ; 55 3f20: d7 be out 0x37, r13 ; 55
3f04: e8 95 spm 3f22: e8 95 spm
3f06: 11 24 eor r1, r1 3f24: 11 24 eor r1, r1
addrPtr += 2; addrPtr += 2;
3f08: 4e 5f subi r20, 0xFE ; 254 3f26: 4e 5f subi r20, 0xFE ; 254
3f0a: 5f 4f sbci r21, 0xFF ; 255 3f28: 5f 4f sbci r21, 0xFF ; 255
} while (--ch); } while (--ch);
3f0c: f1 e0 ldi r31, 0x01 ; 1 3f2a: f1 e0 ldi r31, 0x01 ; 1
3f0e: a0 38 cpi r26, 0x80 ; 128 3f2c: a0 38 cpi r26, 0x80 ; 128
3f10: bf 07 cpc r27, r31 3f2e: bf 07 cpc r27, r31
3f12: 51 f7 brne .-44 ; 0x3ee8 <main+0xe8> 3f30: 51 f7 brne .-44 ; 0x3f06 <main+0x106>
// Write from programming buffer // Write from programming buffer
__boot_page_write_short((uint16_t)(void*)address); __boot_page_write_short((uint16_t)(void*)address);
3f14: e0 91 00 02 lds r30, 0x0200 3f32: e0 91 00 02 lds r30, 0x0200
3f18: f0 91 01 02 lds r31, 0x0201 3f36: f0 91 01 02 lds r31, 0x0201
3f1c: f7 be out 0x37, r15 ; 55 3f3a: e7 be out 0x37, r14 ; 55
3f1e: e8 95 spm 3f3c: e8 95 spm
boot_spm_busy_wait(); boot_spm_busy_wait();
3f20: 07 b6 in r0, 0x37 ; 55 3f3e: 07 b6 in r0, 0x37 ; 55
3f22: 00 fc sbrc r0, 0 3f40: 00 fc sbrc r0, 0
3f24: fd cf rjmp .-6 ; 0x3f20 <main+0x120> 3f42: fd cf rjmp .-6 ; 0x3f3e <main+0x13e>
#if defined(RWWSRE) #if defined(RWWSRE)
// Reenable read access to flash // Reenable read access to flash
boot_rww_enable(); boot_rww_enable();
3f26: e7 be out 0x37, r14 ; 55 3f44: f7 be out 0x37, r15 ; 55
3f28: e8 95 spm 3f46: e8 95 spm
3f2a: 27 c0 rjmp .+78 ; 0x3f7a <main+0x17a> 3f48: 27 c0 rjmp .+78 ; 0x3f98 <main+0x198>
#endif #endif
} }
/* Read memory block mode, length is big endian. */ /* Read memory block mode, length is big endian. */
else if(ch == STK_READ_PAGE) { else if(ch == STK_READ_PAGE) {
3f2c: 84 37 cpi r24, 0x74 ; 116 3f4a: 84 37 cpi r24, 0x74 ; 116
3f2e: b9 f4 brne .+46 ; 0x3f5e <main+0x15e> 3f4c: b9 f4 brne .+46 ; 0x3f7c <main+0x17c>
// READ PAGE - we only read flash // READ PAGE - we only read flash
getLen(); getLen();
3f30: 37 d0 rcall .+110 ; 0x3fa0 <getLen> 3f4e: 37 d0 rcall .+110 ; 0x3fbe <getLen>
verifySpace(); verifySpace();
3f32: 46 d0 rcall .+140 ; 0x3fc0 <verifySpace> 3f50: 46 d0 rcall .+140 ; 0x3fde <verifySpace>
putch(result); putch(result);
address++; address++;
} }
while (--length); while (--length);
#else #else
do putch(pgm_read_byte_near(address++)); do putch(pgm_read_byte_near(address++));
3f34: e0 91 00 02 lds r30, 0x0200 3f52: e0 91 00 02 lds r30, 0x0200
3f38: f0 91 01 02 lds r31, 0x0201 3f56: f0 91 01 02 lds r31, 0x0201
3f3c: 31 96 adiw r30, 0x01 ; 1 3f5a: 31 96 adiw r30, 0x01 ; 1
3f3e: f0 93 01 02 sts 0x0201, r31 3f5c: f0 93 01 02 sts 0x0201, r31
3f42: e0 93 00 02 sts 0x0200, r30 3f60: e0 93 00 02 sts 0x0200, r30
3f46: 31 97 sbiw r30, 0x01 ; 1 3f64: 31 97 sbiw r30, 0x01 ; 1
3f48: e4 91 lpm r30, Z+ 3f66: e4 91 lpm r30, Z+
3f4a: 8e 2f mov r24, r30 3f68: 8e 2f mov r24, r30
3f4c: 19 d0 rcall .+50 ; 0x3f80 <putch> 3f6a: 19 d0 rcall .+50 ; 0x3f9e <putch>
while (--length); while (--length);
3f4e: 80 91 02 02 lds r24, 0x0202 3f6c: 80 91 02 02 lds r24, 0x0202
3f52: 81 50 subi r24, 0x01 ; 1 3f70: 81 50 subi r24, 0x01 ; 1
3f54: 80 93 02 02 sts 0x0202, r24 3f72: 80 93 02 02 sts 0x0202, r24
3f58: 88 23 and r24, r24 3f76: 88 23 and r24, r24
3f5a: 61 f7 brne .-40 ; 0x3f34 <main+0x134> 3f78: 61 f7 brne .-40 ; 0x3f52 <main+0x152>
3f5c: 0e c0 rjmp .+28 ; 0x3f7a <main+0x17a> 3f7a: 0e c0 rjmp .+28 ; 0x3f98 <main+0x198>
#endif #endif
#endif #endif
} }
/* Get device signature bytes */ /* Get device signature bytes */
else if(ch == STK_READ_SIGN) { else if(ch == STK_READ_SIGN) {
3f5e: 85 37 cpi r24, 0x75 ; 117 3f7c: 85 37 cpi r24, 0x75 ; 117
3f60: 39 f4 brne .+14 ; 0x3f70 <main+0x170> 3f7e: 39 f4 brne .+14 ; 0x3f8e <main+0x18e>
// READ SIGN - return what Avrdude wants to hear // READ SIGN - return what Avrdude wants to hear
verifySpace(); verifySpace();
3f62: 2e d0 rcall .+92 ; 0x3fc0 <verifySpace> 3f80: 2e d0 rcall .+92 ; 0x3fde <verifySpace>
putch(SIGNATURE_0); putch(SIGNATURE_0);
3f64: 8e e1 ldi r24, 0x1E ; 30 3f82: 8e e1 ldi r24, 0x1E ; 30
3f66: 0c d0 rcall .+24 ; 0x3f80 <putch> 3f84: 0c d0 rcall .+24 ; 0x3f9e <putch>
putch(SIGNATURE_1); putch(SIGNATURE_1);
3f68: 84 e9 ldi r24, 0x94 ; 148 3f86: 84 e9 ldi r24, 0x94 ; 148
3f6a: 0a d0 rcall .+20 ; 0x3f80 <putch> 3f88: 0a d0 rcall .+20 ; 0x3f9e <putch>
putch(SIGNATURE_2); putch(SIGNATURE_2);
3f6c: 86 e0 ldi r24, 0x06 ; 6 3f8a: 86 e0 ldi r24, 0x06 ; 6
3f6e: 9a cf rjmp .-204 ; 0x3ea4 <main+0xa4> 3f8c: 8b cf rjmp .-234 ; 0x3ea4 <main+0xa4>
} }
else if (ch == 'Q') { else if (ch == 'Q') {
3f70: 81 35 cpi r24, 0x51 ; 81 3f8e: 81 35 cpi r24, 0x51 ; 81
3f72: 11 f4 brne .+4 ; 0x3f78 <main+0x178> 3f90: 11 f4 brne .+4 ; 0x3f96 <main+0x196>
// Adaboot no-wait mod // Adaboot no-wait mod
watchdogConfig(WATCHDOG_16MS); watchdogConfig(WATCHDOG_16MS);
3f74: 88 e0 ldi r24, 0x08 ; 8 3f92: 88 e0 ldi r24, 0x08 ; 8
3f76: 19 d0 rcall .+50 ; 0x3faa <watchdogConfig> 3f94: 19 d0 rcall .+50 ; 0x3fc8 <watchdogConfig>
verifySpace(); verifySpace();
} }
else { else {
// This covers the response to commands like STK_ENTER_PROGMODE // This covers the response to commands like STK_ENTER_PROGMODE
verifySpace(); verifySpace();
3f78: 23 d0 rcall .+70 ; 0x3fc0 <verifySpace> 3f96: 23 d0 rcall .+70 ; 0x3fde <verifySpace>
} }
putch(STK_OK); putch(STK_OK);
3f7a: 80 e1 ldi r24, 0x10 ; 16 3f98: 80 e1 ldi r24, 0x10 ; 16
3f7c: 01 d0 rcall .+2 ; 0x3f80 <putch> 3f9a: 01 d0 rcall .+2 ; 0x3f9e <putch>
3f7e: 6b cf rjmp .-298 ; 0x3e56 <main+0x56> 3f9c: 5c cf rjmp .-328 ; 0x3e56 <main+0x56>
00003f80 <putch>: 00003f9e <putch>:
} }
} }
void putch(char ch) { void putch(char ch) {
3f80: 98 2f mov r25, r24 3f9e: 98 2f mov r25, r24
#ifndef SOFT_UART #ifndef SOFT_UART
while (!(UCSR0A & _BV(UDRE0))); while (!(UCSR0A & _BV(UDRE0)));
3f82: 80 91 c0 00 lds r24, 0x00C0 3fa0: 80 91 c0 00 lds r24, 0x00C0
3f86: 85 ff sbrs r24, 5 3fa4: 85 ff sbrs r24, 5
3f88: fc cf rjmp .-8 ; 0x3f82 <putch+0x2> 3fa6: fc cf rjmp .-8 ; 0x3fa0 <putch+0x2>
UDR0 = ch; UDR0 = ch;
3f8a: 90 93 c6 00 sts 0x00C6, r25 3fa8: 90 93 c6 00 sts 0x00C6, r25
[uartBit] "I" (UART_TX_BIT) [uartBit] "I" (UART_TX_BIT)
: :
"r25" "r25"
); );
#endif #endif
} }
3f8e: 08 95 ret 3fac: 08 95 ret
00003f90 <getch>: 00003fae <getch>:
return getch(); return getch();
} }
// Watchdog functions. These are only safe with interrupts turned off. // Watchdog functions. These are only safe with interrupts turned off.
void watchdogReset() { void watchdogReset() {
__asm__ __volatile__ ( __asm__ __volatile__ (
3f90: a8 95 wdr 3fae: a8 95 wdr
[uartBit] "I" (UART_RX_BIT) [uartBit] "I" (UART_RX_BIT)
: :
"r25" "r25"
); );
#else #else
while(!(UCSR0A & _BV(RXC0))); while(!(UCSR0A & _BV(RXC0)));
3f92: 80 91 c0 00 lds r24, 0x00C0 3fb0: 80 91 c0 00 lds r24, 0x00C0
3f96: 87 ff sbrs r24, 7 3fb4: 87 ff sbrs r24, 7
3f98: fc cf rjmp .-8 ; 0x3f92 <getch+0x2> 3fb6: fc cf rjmp .-8 ; 0x3fb0 <getch+0x2>
ch = UDR0; ch = UDR0;
3f9a: 80 91 c6 00 lds r24, 0x00C6 3fb8: 80 91 c6 00 lds r24, 0x00C6
#ifdef LED_DATA_FLASH #ifdef LED_DATA_FLASH
LED_PIN |= _BV(LED); LED_PIN |= _BV(LED);
#endif #endif
return ch; return ch;
} }
3f9e: 08 95 ret 3fbc: 08 95 ret
00003fa0 <getLen>: 00003fbe <getLen>:
} while (--count); } while (--count);
} }
#endif #endif
uint8_t getLen() { uint8_t getLen() {
getch(); getch();
3fa0: f7 df rcall .-18 ; 0x3f90 <getch> 3fbe: f7 df rcall .-18 ; 0x3fae <getch>
length = getch(); length = getch();
3fa2: f6 df rcall .-20 ; 0x3f90 <getch> 3fc0: f6 df rcall .-20 ; 0x3fae <getch>
3fa4: 80 93 02 02 sts 0x0202, r24 3fc2: 80 93 02 02 sts 0x0202, r24
return getch(); return getch();
} }
3fa8: f3 cf rjmp .-26 ; 0x3f90 <getch> 3fc6: f3 cf rjmp .-26 ; 0x3fae <getch>
00003faa <watchdogConfig>: 00003fc8 <watchdogConfig>:
"wdr\n" "wdr\n"
); );
} }
void watchdogConfig(uint8_t x) { void watchdogConfig(uint8_t x) {
WDTCSR = _BV(WDCE) | _BV(WDE); WDTCSR = _BV(WDCE) | _BV(WDE);
3faa: e0 e6 ldi r30, 0x60 ; 96 3fc8: e0 e6 ldi r30, 0x60 ; 96
3fac: f0 e0 ldi r31, 0x00 ; 0 3fca: f0 e0 ldi r31, 0x00 ; 0
3fae: 98 e1 ldi r25, 0x18 ; 24 3fcc: 98 e1 ldi r25, 0x18 ; 24
3fb0: 90 83 st Z, r25 3fce: 90 83 st Z, r25
WDTCSR = x; WDTCSR = x;
3fb2: 80 83 st Z, r24 3fd0: 80 83 st Z, r24
} }
3fb4: 08 95 ret 3fd2: 08 95 ret
00003fb6 <appStart>: 00003fd4 <appStart>:
void appStart() { void appStart() {
watchdogConfig(WATCHDOG_OFF); watchdogConfig(WATCHDOG_OFF);
3fb6: 80 e0 ldi r24, 0x00 ; 0 3fd4: 80 e0 ldi r24, 0x00 ; 0
3fb8: f8 df rcall .-16 ; 0x3faa <watchdogConfig> 3fd6: f8 df rcall .-16 ; 0x3fc8 <watchdogConfig>
__asm__ __volatile__ ( __asm__ __volatile__ (
3fba: ee 27 eor r30, r30 3fd8: ee 27 eor r30, r30
3fbc: ff 27 eor r31, r31 3fda: ff 27 eor r31, r31
3fbe: 09 94 ijmp 3fdc: 09 94 ijmp
00003fc0 <verifySpace>: 00003fde <verifySpace>:
do getch(); while (--count); do getch(); while (--count);
verifySpace(); verifySpace();
} }
void verifySpace() { void verifySpace() {
if (getch() != CRC_EOP) appStart(); if (getch() != CRC_EOP) appStart();
3fc0: e7 df rcall .-50 ; 0x3f90 <getch> 3fde: e7 df rcall .-50 ; 0x3fae <getch>
3fc2: 80 32 cpi r24, 0x20 ; 32 3fe0: 80 32 cpi r24, 0x20 ; 32
3fc4: 09 f0 breq .+2 ; 0x3fc8 <verifySpace+0x8> 3fe2: 09 f0 breq .+2 ; 0x3fe6 <verifySpace+0x8>
3fc6: f7 df rcall .-18 ; 0x3fb6 <appStart> 3fe4: f7 df rcall .-18 ; 0x3fd4 <appStart>
putch(STK_INSYNC); putch(STK_INSYNC);
3fc8: 84 e1 ldi r24, 0x14 ; 20 3fe6: 84 e1 ldi r24, 0x14 ; 20
} }
3fca: da cf rjmp .-76 ; 0x3f80 <putch> 3fe8: da cf rjmp .-76 ; 0x3f9e <putch>
::[count] "M" (UART_B_VALUE) ::[count] "M" (UART_B_VALUE)
); );
} }
#endif #endif
void getNch(uint8_t count) { void getNch(uint8_t count) {
3fcc: 1f 93 push r17 3fea: 1f 93 push r17
3fce: 18 2f mov r17, r24 3fec: 18 2f mov r17, r24
00003fd0 <getNch>: 00003fee <getNch>:
do getch(); while (--count); do getch(); while (--count);
3fd0: df df rcall .-66 ; 0x3f90 <getch> 3fee: df df rcall .-66 ; 0x3fae <getch>
3fd2: 11 50 subi r17, 0x01 ; 1 3ff0: 11 50 subi r17, 0x01 ; 1
3fd4: e9 f7 brne .-6 ; 0x3fd0 <getNch> 3ff2: e9 f7 brne .-6 ; 0x3fee <getNch>
verifySpace(); verifySpace();
3fd6: f4 df rcall .-24 ; 0x3fc0 <verifySpace> 3ff4: f4 df rcall .-24 ; 0x3fde <verifySpace>
} }
3fd8: 1f 91 pop r17 3ff6: 1f 91 pop r17
3fda: 08 95 ret 3ff8: 08 95 ret