avrdudes / avrdude

AVRDUDE is a utility to program AVR microcontrollers
GNU General Public License v2.0
704 stars 136 forks source link

Optiboot without EEPROM support returns flash on EEPROM request #1227

Closed mcuee closed 1 year ago

mcuee commented 1 year ago

I think this may not be a real issue but kind of strange behavior of the optiboot bootloader firmware.

I jusgt bought a few Uno Clones with CH340. Apparently due to chip shortages the boards come with ATmega328PB and not ATmega328P. The 4.4 version of Optiboot Arduino FW is still used wihout any changes. It does not support EEPROM and it is meant for ATmega328P. https://github.com/arduino/ArduinoCore-avr/blob/master/bootloaders/optiboot/optiboot_atmega328.hex

A few interesting behaviors here.

1) -c arduino and -c urclock will insist that the chip connected is ATmega328P and not ATmega328PB. I think this is because of the bootloader firmware and we can not do anything about it.

2) -c arduino will read Flash contents as EEPROM contents. -c urclock will do that as well if I specify -xeepromrw. @stefanrueger Do you think if No. 2 is a problem for avrdude? If yes what can we do here? Is it also the limitation of the paticular old optiboot firmware shipped by Arduino?

PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump flash 0 0x10" | .\avrdude -c avrisp2 -p m328pb -qqt
avrdude> dump flash 0 0x10
0000  0c 94 61 00 0c 94 7e 00  0c 94 7e 00 0c 94 7e 00  | .a. .~. .~. .~.|

avrdude>
avrdude>
PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c avrisp2 -p m328pb -qqt
avrdude> dump eeprom 0 0x10
0000  ff ff ff ff ff ff ff ff  ff ff ff ff ff ff ff ff  |................|

avrdude>
avrdude>
PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c urclock -P COM17 -p m328p -qqt -xeepromrw
avrdude> dump eeprom 0 0x10
0000  0c 94 61 00 0c 94 7e 00  0c 94 7e 00 0c 94 7e 00  | .a. .~. .~. .~.|

avrdude>
avrdude>
PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c arduino -P COM17 -p m328p -qqt
avrdude> dump eeprom 0 0x10
0000  0c 94 61 00 0c 94 7e 00  0c 94 7e 00 0c 94 7e 00  | .a. .~. .~. .~.|

avrdude>
avrdude>

PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c urclock -P COM17 -p m328pb -qqt -xeepromrw
avrdude error: connected part ATmega328P signature does not match -p ATmega328PB's (override with -F or use -p ATmega328P)
avrdude error: unable to read signature data for part ATmega328PB, rc=-1
avrdude error: unable to read signature data, rc=-1

PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c arduino -P COM17 -p m328pb -qqt
avrdude error: expected signature for ATmega328PB is 1E 95 16
        double check chip or use -F to override this check
mcuee commented 1 year ago

Even if I change the bootloader FW to @MCUdude's MiniCore and specified the right chip (ATmega328PB), then the first behavior is gone but the second behavior is still there.

PS C:\work\avr\avrdude_test\avrdude_bin> .\avrdude -c urclock -P COM5 -p m328pb -qq -xbootsize=512 -xshowall
0 0000-00-00 00.00  application 0 store 0 meta 0 boot 512 o8.0 -?s-?-r-- vector 0 (RESET) ATmega328PB

PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c urclock -P COM5 -p m328pb -qqt -xbootsize=512
avrdude> dump eeprom 0 0x10
avrdude error: bootloader does not seem to have paged EEPROM read capability
avrdude error: bootloader does not seem to have EEPROM access capability
avrdude error: unable to read eeprom page at addr 0x0000
avrdude error: (dump) error reading eeprom address 0x00000 of part ATmega328PB
               read operation not supported on memory type eeprom
avrdude>
avrdude>

PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c urclock -P COM5 -p m328pb -qqt -xbootsize=512 -xeepromrw
avrdude> dump eeprom 0 0x10
0000  0c 94 8f 00 0c 94 a1 00  0c 94 a1 00 0c 94 a1 00  | ... ... ... ...|

avrdude>
avrdude>
PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c arduino -P COM5 -p m328pb -qqt
avrdude> dump eeprom 0 0x10
0000  0c 94 8f 00 0c 94 a1 00  0c 94 a1 00 0c 94 a1 00  | ... ... ... ...|

avrdude>
avrdude>

PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c usbasp -p m328pb -qqt
avrdude> dump eeprom 0 0x10
0000  ff ff ff ff ff ff ff ff  ff ff ff ff ff ff ff ff  |................|

avrdude>
avrdude>
PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump flash 0 0x10" | .\avrdude -c usbasp -p m328pb -qqt
avrdude> dump flash 0 0x10
0000  0c 94 8f 00 0c 94 a1 00  0c 94 a1 00 0c 94 a1 00  | ... ... ... ...|

avrdude>
avrdude>
mcuee commented 1 year ago

Same for an Nano Clone with ATmega328P with the original 4.4 Optiboot bootloader FW.

PS C:\work\avr\avrdude_test\avrdude_bin> .\avrdude -c urclock -P COM10 -p m328p -qq -xbootsize=512 -xshowall
0 0000-00-00 00.00  application 0 store 0 meta 0 boot 512 o4.4 -?s-?-r-- vector 0 (RESET) ATmega328P
PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c urclock -P COM10 -p m328p -qqt -xbootsize=512 -xeepromrw
avrdude> dump eeprom 0 0x10
0000  0c 94 5c 00 0c 94 6e 00  0c 94 6e 00 0c 94 6e 00  | .\. .n. .n. .n.|

avrdude>
avrdude>
PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c arduino -P COM10 -p m328p -qqt
avrdude> dump eeprom 0 0x10
0000  0c 94 5c 00 0c 94 6e 00  0c 94 6e 00 0c 94 6e 00  | .\. .n. .n. .n.|

avrdude>
avrdude>
mcuee commented 1 year ago

@stefanrueger

Now I actually think the second issue is a bug for -c arduino and it is arguable for -c urclock. What is your opinion?

stefanrueger commented 1 year ago

1) -c arduino and -c urclock will insist that the chip connected is ATmega328P and not ATmega328PB. I think this is because of the bootloader firmware and we can not do anything about it.

Correct. The bootloader firmware actually does not read the signature memory of the part. The bootloader returns hard-coded signature bytes of the part for which it was compiled. This is normal bootloader practice to save space. If the user burns an ATmega328P bootloader onto an ATmega328PB chip then AVRDUDE will see an m328p signature.

2) -c arduino will read Flash contents as EEPROM contents. -c urclock will do that as well if I specify -xeepromrw. @stefanrueger Do you think if No. 2 is a problem for avrdude? If yes what can we do here? Is it also the limitation of the paticular old optiboot firmware shipped by Arduino?

This is a well-known optiboot bug. It returns flash for EEPROM if optiboot has been compiled to not handle EEPROM. This bug has been around for a long time (and possibly still is today but defo was 2016 when I last looked closely at optiboot).

It is not actually AVRDUDE's job to invent workarounds for all the bugs in bootloaders or programmer FW (though I have provided a fair deal of workarounds in the past). In this specific case, knowing about this bug, -c urclock uses the justified and sane default assumption that optiboot cannot deal EEPROM unless there is evidence to the contrary either by

Now, @mcuee, your example is one where the user tells AVRDUDE -xeepromrw that indeed the bootloader can handle EEPROM only to be given flash by the buggy optiboot that actually cannot handle EEPROM.

Soooooo, can you guess what my opinion is?

Ditch optiboot. Never look back. Use urboot. Be happy ever after.

As there is a good alternative in this case I believe we should not spend our energy dancing around optiboot bugs.

mcuee commented 1 year ago

@stefanrueger

Haha, I support urboot. We need to get avrdude 7.1 released to enable -c urclock.

Hopefully @MCUdude can start to distribute urboot early next year to make urboot more popular.

MCUdude commented 1 year ago

Hopefully @MCUdude can start to distribute urboot early next year to make urboot more popular.

Yes, this is the plan. However, I need to make sure that my cores will continue to support legacy optiboot bootloaders while using -c urclock, so users aren't forced to replace their bootloaders, even though it's highly recommended. It's also important that potential bugs found by mass-testing urboot gets fixed quickly.

stefanrueger commented 1 year ago

legacy optiboot bootloaders while using -c urclock

You are welcome to add to the hash table those legacy optiboot bootloaders that were shipped with your boards and/or frequently downloaded from your github core; I am happy to help you compute the hashes if you struggle with that.

And our legacy bootloaders will continue to work with -c arduino though with fewer benefits than -c urclock

urboot gets fixed quickly

That is my intention...

MCUdude commented 1 year ago

You are welcome to add to the hash table those legacy optiboot bootloaders that were shipped with your boards and/or frequently downloaded from your github core; I am happy to help you compute the hashes if you struggle with that.

Is this something you could help me automate? The optiboot flash repo is pretty easy for a script to run through.

From what I know, these are the most popular bootloaders:

20 MHz, 115200 baud 16 MHz, 115200 baud 8 MHz, 57600 baud 8 MHz 38400 baud 1 MHz 9600 baud

For UART 0, 1, 2, and 3 where present.

The only parts that should not be added are the AT90USB* parts, as I provide no Arduino core for them.

stefanrueger commented 1 year ago

The bootloader-hashes script finds all bootloaders recursively in the current directory and outputs the hash lines that can be cut and paste into the table. Sounds like the only thing you'd need to do is grep out the ones you are interested in. BTW, I think the bootloaders for 16 MHz, 115200 baud are probably identical to the ones 8 MHz, 57600 baud (so will have the same hash)

MCUdude commented 1 year ago

@stefanrueger this is the list of bootloader combinations I think are the most common. However, some of the files have the same hash, even though they are different parts. I've not removed any duplicates, but you can easily spot the duplicated by using sort -k 5 on the list below:

Optiboot flash hash ``` { 512, 0, 0x2afe013b, 0x5775955f }, // optiboot_flash_atmega169_UART0_38400_8000000L_B5.hex { 512, 0, 0x2afe013b, 0xd5de2de6 }, // optiboot_flash_atmega169_UART0_57600_8000000L_B5.hex { 512, 0, 0x7de5e119, 0xecba44da }, // optiboot_flash_atmega169_UART0_9600_1000000L_B5.hex { 512, 0, 0x2afe013b, 0x0ebf1682 }, // optiboot_flash_atmega169_UART0_115200_20000000L_B5.hex { 512, 0, 0x2afe013b, 0xee9f5b33 }, // optiboot_flash_atmega169_UART0_115200_16000000L_B5.hex { 1024, 1, 0x5790d602, 0x728c740e }, // optiboot_flash_at90can64_UART1_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x5419d99f }, // optiboot_flash_at90can64_UART1_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x9ff3235b }, // optiboot_flash_at90can64_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0xd1e8d0b9 }, // optiboot_flash_at90can64_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x74b9c238, 0xc76f76e5 }, // optiboot_flash_at90can64_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x74b9c238, 0xeafeb59b }, // optiboot_flash_at90can64_UART1_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x4ad22f5b }, // optiboot_flash_at90can64_UART1_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0xb495f1ea }, // optiboot_flash_at90can64_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x246dbc35 }, // optiboot_flash_at90can64_UART1_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0xd92f11b5 }, // optiboot_flash_at90can64_UART0_115200_16000000L_B5_BIGBOOT.hex { 512, 0, 0xb83f0d83, 0x3d3da465 }, // optiboot_flash_atmega32_UART0_57600_8000000L_B7.hex { 512, 0, 0x8790003e, 0x9f82a66b }, // optiboot_flash_atmega32_UART0_57600_8000000L_B0.hex { 512, 0, 0x8790003e, 0x65d86300 }, // optiboot_flash_atmega32_UART0_38400_8000000L_B0.hex { 512, 0, 0xb83f0d83, 0x87ac0178 }, // optiboot_flash_atmega32_UART0_38400_8000000L_B7.hex { 512, 0, 0xb83f0d83, 0xfae2fc26 }, // optiboot_flash_atmega32_UART0_9600_1000000L_B7.hex { 512, 0, 0x8790003e, 0x333e86ec }, // optiboot_flash_atmega32_UART0_9600_1000000L_B0.hex { 512, 0, 0x8790003e, 0xc286cdc8 }, // optiboot_flash_atmega32_UART0_115200_20000000L_B0.hex { 512, 0, 0xb83f0d83, 0x3330e675 }, // optiboot_flash_atmega32_UART0_115200_20000000L_B7.hex { 512, 0, 0x8790003e, 0x55b98295 }, // optiboot_flash_atmega32_UART0_115200_16000000L_B0.hex { 512, 0, 0xb83f0d83, 0xde792fb2 }, // optiboot_flash_atmega32_UART0_115200_16000000L_B7.hex { 512, 0, 0x9e762fa8, 0xe2724ea2 }, // optiboot_flash_atmega3250p_UART0_57600_8000000L_B7.hex { 512, 0, 0x9e762fa8, 0xb21ddc89 }, // optiboot_flash_atmega3250p_UART0_38400_8000000L_B7.hex { 512, 0, 0xdaa198fa, 0x70fcc8e9 }, // optiboot_flash_atmega3250p_UART0_9600_1000000L_B7.hex { 512, 0, 0x9e762fa8, 0xca6c9014 }, // optiboot_flash_atmega3250p_UART0_115200_20000000L_B7.hex { 512, 0, 0x9e762fa8, 0x680e4729 }, // optiboot_flash_atmega3250p_UART0_115200_16000000L_B7.hex { 1024, 1, 0xae42ebb8, 0xe11ad957 }, // optiboot_flash_atmega644a_UART1_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xdc558cfc }, // optiboot_flash_atmega644a_UART1_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xc4b9120d }, // optiboot_flash_atmega644a_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x1327cc64 }, // optiboot_flash_atmega644a_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x93195537 }, // optiboot_flash_atmega644a_UART0_57600_8000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x1224da19 }, // optiboot_flash_atmega644a_UART0_38400_8000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x1ec7bc40 }, // optiboot_flash_atmega644a_UART1_38400_8000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xe9d90a4f }, // optiboot_flash_atmega644a_UART1_57600_8000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x9d361c4e }, // optiboot_flash_atmega644a_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x1e9a5d21 }, // optiboot_flash_atmega644a_UART1_9600_1000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x3b651e15 }, // optiboot_flash_atmega644a_UART1_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xea8fe774 }, // optiboot_flash_atmega644a_UART0_9600_1000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xb49eaa1f }, // optiboot_flash_atmega644a_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xbdbcaa5b }, // optiboot_flash_atmega644a_UART1_115200_20000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x8298e287 }, // optiboot_flash_atmega644a_UART1_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x50418be4 }, // optiboot_flash_atmega644a_UART0_115200_20000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xf9f61eb2 }, // optiboot_flash_atmega644a_UART0_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x7b6e9bb9 }, // optiboot_flash_atmega644a_UART1_115200_16000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xe27428c7 }, // optiboot_flash_atmega644a_UART1_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xdab405bd }, // optiboot_flash_atmega644a_UART0_115200_16000000L_B0_BIGBOOT.hex { 512, 0, 0x281edc46, 0xf013cd1b }, // optiboot_flash_atmega8_UART0_38400_8000000L_B5.hex { 512, 0, 0x281edc46, 0x8cc6362a }, // optiboot_flash_atmega8_UART0_57600_8000000L_B5.hex { 512, 0, 0x281edc46, 0x1d7084ea }, // optiboot_flash_atmega8_UART0_9600_1000000L_B5.hex { 512, 0, 0x281edc46, 0xe35b8b8e }, // optiboot_flash_atmega8_UART0_115200_20000000L_B5.hex { 512, 0, 0x281edc46, 0xa6eeec00 }, // optiboot_flash_atmega8_UART0_115200_20000000L_B5 { 512, 0, 0x281edc46, 0x3f821234 }, // optiboot_flash_atmega8_UART0_115200_16000000L_B5.hex { 512, 0, 0x281edc46, 0x8f39129c }, // optiboot_flash_atmega8_UART0_115200_16000000L_B5 { 512, 0, 0x6e02926f, 0x95dee889 }, // optiboot_flash_atmega168_UART0_38400_8000000L_B5.hex { 512, 0, 0x6e02926f, 0x35af7f90 }, // optiboot_flash_atmega168_UART0_57600_8000000L_B5.hex { 512, 0, 0x6d0b2063, 0x275726b6 }, // optiboot_flash_atmega168_UART0_9600_1000000L_B5.hex { 512, 0, 0x6e02926f, 0xd5185017 }, // optiboot_flash_atmega168_UART0_115200_20000000L_B5.hex { 512, 0, 0x6e02926f, 0x7cc1e494 }, // optiboot_flash_atmega168_UART0_115200_16000000L_B5.hex { 512, 0, 0x5e0e0dd4, 0x35d5431e }, // optiboot_flash_atmega165p_UART0_38400_8000000L_B5.hex { 512, 0, 0x5e0e0dd4, 0xe668d759 }, // optiboot_flash_atmega165p_UART0_57600_8000000L_B5.hex { 512, 0, 0x43900a31, 0xd9660e09 }, // optiboot_flash_atmega165p_UART0_9600_1000000L_B5.hex { 512, 0, 0x5e0e0dd4, 0xdce1048b }, // optiboot_flash_atmega165p_UART0_115200_20000000L_B5.hex { 512, 0, 0x5e0e0dd4, 0xa53600f9 }, // optiboot_flash_atmega165p_UART0_115200_16000000L_B5.hex { 512, 0, 0x7b09aae5, 0x69bf5c8e }, // optiboot_flash_atmega324p_UART0_57600_8000000L_B0.hex { 512, 0, 0x6b6a18c2, 0xf5a5eb3c }, // optiboot_flash_atmega324p_UART1_38400_8000000L_B7.hex { 512, 0, 0x7b09aae5, 0xb615bceb }, // optiboot_flash_atmega324p_UART0_57600_8000000L_B7.hex { 512, 0, 0x6b6a18c2, 0x0289d638 }, // optiboot_flash_atmega324p_UART1_38400_8000000L_B0.hex { 512, 0, 0x7b09aae5, 0x8a733497 }, // optiboot_flash_atmega324p_UART0_38400_8000000L_B7.hex { 512, 0, 0x6b6a18c2, 0x6eeef491 }, // optiboot_flash_atmega324p_UART1_57600_8000000L_B0.hex { 512, 0, 0x7b09aae5, 0x9a762e7d }, // optiboot_flash_atmega324p_UART0_38400_8000000L_B0.hex { 512, 0, 0x6b6a18c2, 0x80502860 }, // optiboot_flash_atmega324p_UART1_57600_8000000L_B7.hex { 512, 0, 0xc0548728, 0xbace9eb0 }, // optiboot_flash_atmega324p_UART0_9600_1000000L_B0.hex { 512, 0, 0xc0548728, 0xcaee2c76 }, // optiboot_flash_atmega324p_UART0_9600_1000000L_B7.hex { 512, 0, 0xd93615c8, 0x43a30b2c }, // optiboot_flash_atmega324p_UART1_9600_1000000L_B0.hex { 512, 0, 0xd93615c8, 0x97447ea4 }, // optiboot_flash_atmega324p_UART1_9600_1000000L_B7.hex { 512, 0, 0x6b6a18c2, 0x38bfc4ae }, // optiboot_flash_atmega324p_UART1_115200_20000000L_B0.hex { 512, 0, 0x6b6a18c2, 0x9b8dfb02 }, // optiboot_flash_atmega324p_UART1_115200_20000000L_B7.hex { 512, 0, 0x7b09aae5, 0x6abeaf7f }, // optiboot_flash_atmega324p_UART0_115200_20000000L_B7.hex { 512, 0, 0x7b09aae5, 0x3cf239db }, // optiboot_flash_atmega324p_UART0_115200_20000000L_B0.hex { 512, 0, 0x7b09aae5, 0x4b40506a }, // optiboot_flash_atmega324p_UART0_115200_16000000L_B7.hex { 512, 0, 0x7b09aae5, 0xe75b8b91 }, // optiboot_flash_atmega324p_UART0_115200_16000000L_B0.hex { 512, 0, 0x6b6a18c2, 0xba7b95c0 }, // optiboot_flash_atmega324p_UART1_115200_16000000L_B0.hex { 512, 0, 0x6b6a18c2, 0x35013504 }, // optiboot_flash_atmega324p_UART1_115200_16000000L_B7.hex { 1024, 1, 0xae42ebb8, 0x72e304c8 }, // optiboot_flash_atmega645_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xfbb2c79a }, // optiboot_flash_atmega645_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x6a60f73b }, // optiboot_flash_atmega645_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x84ab943f }, // optiboot_flash_atmega645_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x7c2c24f9 }, // optiboot_flash_atmega645_UART0_115200_16000000L_B5_BIGBOOT.hex { 512, 0, 0x3efcbf6f, 0xae9b86b1 }, // optiboot_flash_atmega88pb_UART0_38400_8000000L_B5.hex { 512, 0, 0x3efcbf6f, 0xa82da96e }, // optiboot_flash_atmega88pb_UART0_57600_8000000L_B5.hex { 512, 0, 0xc65332c3, 0x74825a27 }, // optiboot_flash_atmega88pb_UART0_9600_1000000L_B5.hex { 512, 0, 0x3efcbf6f, 0x58548b06 }, // optiboot_flash_atmega88pb_UART0_115200_20000000L_B5.hex { 512, 0, 0x3efcbf6f, 0x44f778e5 }, // optiboot_flash_atmega88pb_UART0_115200_16000000L_B5.hex { 1024, 1, 0x60bc143e, 0x20e29e43 }, // optiboot_flash_atmega2561_UART1_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x955eba65 }, // optiboot_flash_atmega2561_UART1_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x765d7928 }, // optiboot_flash_atmega2561_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x4080ee21 }, // optiboot_flash_atmega2561_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x679ba32b, 0x490d324b }, // optiboot_flash_atmega2561_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x679ba32b, 0x79f90273 }, // optiboot_flash_atmega2561_UART1_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x33759a79 }, // optiboot_flash_atmega2561_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0xa920ec6f }, // optiboot_flash_atmega2561_UART1_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x50c46e8f }, // optiboot_flash_atmega2561_UART0_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x3c27b00b }, // optiboot_flash_atmega2561_UART1_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xd85f6d82 }, // optiboot_flash_atmega1284p_UART0_57600_8000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x1fbd2028 }, // optiboot_flash_atmega1284p_UART0_38400_8000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xed72231d }, // optiboot_flash_atmega1284p_UART1_38400_8000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x7f4a01a9 }, // optiboot_flash_atmega1284p_UART1_57600_8000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xb0f7a5b8 }, // optiboot_flash_atmega1284p_UART1_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xc20575ef }, // optiboot_flash_atmega1284p_UART1_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x88e15790 }, // optiboot_flash_atmega1284p_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x55370f29 }, // optiboot_flash_atmega1284p_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x96d5dbb4 }, // optiboot_flash_atmega1284p_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x658f1f52 }, // optiboot_flash_atmega1284p_UART1_9600_1000000L_B0_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0xbee18fbd }, // optiboot_flash_atmega1284p_UART1_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x1fc522fc }, // optiboot_flash_atmega1284p_UART0_9600_1000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x10b83310 }, // optiboot_flash_atmega1284p_UART1_115200_20000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x39e2135a }, // optiboot_flash_atmega1284p_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x3fc0adef }, // optiboot_flash_atmega1284p_UART0_115200_20000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xa19ba944 }, // optiboot_flash_atmega1284p_UART1_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x5bc6b3f2 }, // optiboot_flash_atmega1284p_UART1_115200_16000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x7ee4239d }, // optiboot_flash_atmega1284p_UART0_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x246eaa1b }, // optiboot_flash_atmega1284p_UART0_115200_16000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xc9469042 }, // optiboot_flash_atmega1284p_UART1_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x685e324a }, // optiboot_flash_at90can128_UART1_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x40460a3e }, // optiboot_flash_at90can128_UART1_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x31358fa6 }, // optiboot_flash_at90can128_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0xad844b43 }, // optiboot_flash_at90can128_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x74b9c238, 0x80d4a95f }, // optiboot_flash_at90can128_UART1_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x74b9c238, 0xbdb2e58f }, // optiboot_flash_at90can128_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x8f1246d8 }, // optiboot_flash_at90can128_UART1_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x45af5fee }, // optiboot_flash_at90can128_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0xd9678677 }, // optiboot_flash_at90can128_UART1_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x9aa1fd94 }, // optiboot_flash_at90can128_UART0_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x9bcc1a0e }, // optiboot_flash_atmega2560_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x629de678 }, // optiboot_flash_atmega2560_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x30007b05 }, // optiboot_flash_atmega2560_UART1_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x90b8b8bc }, // optiboot_flash_atmega2560_UART1_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0xd2c7eafc }, // optiboot_flash_atmega2560_UART2_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x08f9d27e }, // optiboot_flash_atmega2560_UART2_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0xefb8f92a }, // optiboot_flash_atmega2560_UART3_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0xe386a2c9 }, // optiboot_flash_atmega2560_UART3_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x679ba32b, 0x4b945002 }, // optiboot_flash_atmega2560_UART2_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x679ba32b, 0x3c39f01e }, // optiboot_flash_atmega2560_UART1_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x679ba32b, 0xd4735023 }, // optiboot_flash_atmega2560_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x679ba32b, 0x0efd4181 }, // optiboot_flash_atmega2560_UART3_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x91c04fe3 }, // optiboot_flash_atmega2560_UART2_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0xbefc45da }, // optiboot_flash_atmega2560_UART1_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x3dd17c66 }, // optiboot_flash_atmega2560_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x08806ff2 }, // optiboot_flash_atmega2560_UART3_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x9846ce79 }, // optiboot_flash_atmega2560_UART1_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0xfb06ea82 }, // optiboot_flash_atmega2560_UART2_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x2c48547d }, // optiboot_flash_atmega2560_UART3_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x60bc143e, 0x332b8fbd }, // optiboot_flash_atmega2560_UART0_115200_16000000L_B7_BIGBOOT.hex { 512, 0, 0xf9a539c1, 0x1eb31a77 }, // optiboot_flash_atmega168pb_UART0_57600_8000000L_B5.hex { 512, 0, 0xf9a539c1, 0xc8abf849 }, // optiboot_flash_atmega168pb_UART0_38400_8000000L_B5.hex { 512, 0, 0x41fc44ac, 0xfa99a078 }, // optiboot_flash_atmega168pb_UART0_9600_1000000L_B5.hex { 512, 0, 0xf9a539c1, 0x39b85e77 }, // optiboot_flash_atmega168pb_UART0_115200_20000000L_B5.hex { 512, 0, 0xf9a539c1, 0x671dbf66 }, // optiboot_flash_atmega168pb_UART0_115200_16000000L_B5.hex { 512, 0, 0xd2abed82, 0xb7ca9aa0 }, // optiboot_flash_atmega329p_UART0_57600_8000000L_B5.hex { 512, 0, 0xd2abed82, 0x591c05db }, // optiboot_flash_atmega329p_UART0_38400_8000000L_B5.hex { 512, 0, 0x0367a176, 0x8379176b }, // optiboot_flash_atmega329p_UART0_9600_1000000L_B5.hex { 512, 0, 0xd2abed82, 0xe9039cee }, // optiboot_flash_atmega329p_UART0_115200_20000000L_B5.hex { 512, 0, 0xd2abed82, 0xa42a31ae }, // optiboot_flash_atmega329p_UART0_115200_16000000L_B5.hex { 512, 0, 0x109d28fd, 0x944d7982 }, // optiboot_flash_atmega328pb_UART1_38400_8000000L_B5.hex { 512, 0, 0xaaca6333, 0x7527e2c3 }, // optiboot_flash_atmega328pb_UART0_57600_8000000L_B5.hex { 512, 0, 0xaaca6333, 0xe99f2951 }, // optiboot_flash_atmega328pb_UART0_38400_8000000L_B5.hex { 512, 0, 0x109d28fd, 0xbcd6db5f }, // optiboot_flash_atmega328pb_UART1_57600_8000000L_B5.hex { 512, 0, 0x43d06d19, 0xec3eecdc }, // optiboot_flash_atmega328pb_UART0_9600_1000000L_B5.hex { 512, 0, 0x04f203a3, 0xb005f0fa }, // optiboot_flash_atmega328pb_UART1_9600_1000000L_B5.hex { 512, 0, 0xaaca6333, 0xeb9f0236 }, // optiboot_flash_atmega328pb_UART0_115200_20000000L_B5.hex { 512, 0, 0x109d28fd, 0x7ef5c1ec }, // optiboot_flash_atmega328pb_UART1_115200_20000000L_B5.hex { 512, 0, 0x109d28fd, 0x06c4c2ee }, // optiboot_flash_atmega328pb_UART1_115200_16000000L_B5.hex { 512, 0, 0xaaca6333, 0xfcb4d5b7 }, // optiboot_flash_atmega328pb_UART0_115200_16000000L_B5.hex { 512, 0, 0x9e762fa8, 0xb21ddc89 }, // optiboot_flash_atmega3250_UART0_38400_8000000L_B7.hex { 512, 0, 0x9e762fa8, 0xe2724ea2 }, // optiboot_flash_atmega3250_UART0_57600_8000000L_B7.hex { 512, 0, 0xdaa198fa, 0x70fcc8e9 }, // optiboot_flash_atmega3250_UART0_9600_1000000L_B7.hex { 512, 0, 0x9e762fa8, 0xca6c9014 }, // optiboot_flash_atmega3250_UART0_115200_20000000L_B7.hex { 512, 0, 0x9e762fa8, 0x680e4729 }, // optiboot_flash_atmega3250_UART0_115200_16000000L_B7.hex { 512, 0, 0x3145df66, 0xc272ddc7 }, // optiboot_flash_atmega324pa_UART0_57600_8000000L_B0.hex { 512, 0, 0x071af385, 0x46471318 }, // optiboot_flash_atmega324pa_UART1_38400_8000000L_B7.hex { 512, 0, 0x3145df66, 0xe5b50fbd }, // optiboot_flash_atmega324pa_UART0_57600_8000000L_B7.hex { 512, 0, 0x071af385, 0x85b4a0de }, // optiboot_flash_atmega324pa_UART1_38400_8000000L_B0.hex { 512, 0, 0x3145df66, 0x72ff2709 }, // optiboot_flash_atmega324pa_UART0_38400_8000000L_B7.hex { 512, 0, 0x071af385, 0x60508357 }, // optiboot_flash_atmega324pa_UART1_57600_8000000L_B0.hex { 512, 0, 0x3145df66, 0xcbaa0339 }, // optiboot_flash_atmega324pa_UART0_38400_8000000L_B0.hex { 512, 0, 0x071af385, 0x8ef6048f }, // optiboot_flash_atmega324pa_UART1_57600_8000000L_B7.hex { 512, 0, 0x81d8a7ee, 0xcd519875 }, // optiboot_flash_atmega324pa_UART1_9600_1000000L_B7.hex { 512, 0, 0x81d8a7ee, 0x111d249a }, // optiboot_flash_atmega324pa_UART1_9600_1000000L_B0.hex { 512, 0, 0x06a9ef74, 0x6b5d6b2a }, // optiboot_flash_atmega324pa_UART0_9600_1000000L_B7.hex { 512, 0, 0x06a9ef74, 0x34087c9f }, // optiboot_flash_atmega324pa_UART0_9600_1000000L_B0.hex { 512, 0, 0x3145df66, 0xd5787c2f }, // optiboot_flash_atmega324pa_UART0_115200_20000000L_B0.hex { 512, 0, 0x3145df66, 0xc4f81beb }, // optiboot_flash_atmega324pa_UART0_115200_20000000L_B7.hex { 512, 0, 0x071af385, 0xdb04426f }, // optiboot_flash_atmega324pa_UART1_115200_20000000L_B7.hex { 512, 0, 0x071af385, 0xd4a6a12d }, // optiboot_flash_atmega324pa_UART1_115200_20000000L_B0.hex { 512, 0, 0x071af385, 0x2823c21c }, // optiboot_flash_atmega324pa_UART1_115200_16000000L_B7.hex { 512, 0, 0x071af385, 0x1c41a6ff }, // optiboot_flash_atmega324pa_UART1_115200_16000000L_B0.hex { 512, 0, 0x3145df66, 0xe7173071 }, // optiboot_flash_atmega324pa_UART0_115200_16000000L_B0.hex { 512, 0, 0x3145df66, 0xccd80acb }, // optiboot_flash_atmega324pa_UART0_115200_16000000L_B7.hex { 512, 0, 0x5f64e566, 0x21e29c66 }, // optiboot_flash_atmega8535_UART0_38400_8000000L_B0.hex { 512, 0, 0xdc6b58da, 0x559f4e01 }, // optiboot_flash_atmega8535_UART0_38400_8000000L_B7.hex { 512, 0, 0xdc6b58da, 0xf3221cb1 }, // optiboot_flash_atmega8535_UART0_57600_8000000L_B7.hex { 512, 0, 0x5f64e566, 0x308a27e4 }, // optiboot_flash_atmega8535_UART0_57600_8000000L_B0.hex { 512, 0, 0xdc6b58da, 0x36dda6dd }, // optiboot_flash_atmega8535_UART0_9600_1000000L_B7.hex { 512, 0, 0x5f64e566, 0x4168537d }, // optiboot_flash_atmega8535_UART0_9600_1000000L_B0.hex { 512, 0, 0xdc6b58da, 0x4abee68c }, // optiboot_flash_atmega8535_UART0_115200_20000000L_B7.hex { 512, 0, 0x5f64e566, 0xf520104b }, // optiboot_flash_atmega8535_UART0_115200_20000000L_B0.hex { 512, 0, 0xdc6b58da, 0x82613346 }, // optiboot_flash_atmega8535_UART0_115200_16000000L_B7.hex { 512, 0, 0x5f64e566, 0x24b5ffd9 }, // optiboot_flash_atmega8535_UART0_115200_16000000L_B0.hex { 512, 0, 0x19c64b08, 0x70ae9c0a }, // optiboot_flash_atmega88_UART0_57600_8000000L_B5.hex { 512, 0, 0x19c64b08, 0x4270dce3 }, // optiboot_flash_atmega88_UART0_38400_8000000L_B5.hex { 512, 0, 0x25ddbfca, 0x039961cd }, // optiboot_flash_atmega88_UART0_9600_1000000L_B5.hex { 512, 0, 0x19c64b08, 0x9bf7763b }, // optiboot_flash_atmega88_UART0_115200_20000000L_B5.hex { 512, 0, 0x19c64b08, 0x6159afd6 }, // optiboot_flash_atmega88_UART0_115200_16000000L_B5.hex { 1024, 1, 0xae42ebb8, 0x4ec4df61 }, // optiboot_flash_atmega6490_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x6f542d9f }, // optiboot_flash_atmega6490_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x66724b13 }, // optiboot_flash_atmega6490_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x987e5f86 }, // optiboot_flash_atmega6490_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x4b132863 }, // optiboot_flash_atmega6490_UART0_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x72e304c8 }, // optiboot_flash_atmega645p_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xfbb2c79a }, // optiboot_flash_atmega645p_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x6a60f73b }, // optiboot_flash_atmega645p_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x84ab943f }, // optiboot_flash_atmega645p_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x7c2c24f9 }, // optiboot_flash_atmega645p_UART0_115200_16000000L_B5_BIGBOOT.hex { 512, 0, 0x35e2b5b6, 0xe3f2c268 }, // optiboot_flash_atmega164a_UART0_38400_8000000L_B0.hex { 512, 0, 0x46954df9, 0xc307e815 }, // optiboot_flash_atmega164a_UART1_57600_8000000L_B7.hex { 512, 0, 0x35e2b5b6, 0xc38c7647 }, // optiboot_flash_atmega164a_UART0_38400_8000000L_B7.hex { 512, 0, 0x46954df9, 0xe5e526c7 }, // optiboot_flash_atmega164a_UART1_57600_8000000L_B0.hex { 512, 0, 0x35e2b5b6, 0x390f2ade }, // optiboot_flash_atmega164a_UART0_57600_8000000L_B7.hex { 512, 0, 0x46954df9, 0xe3a119bb }, // optiboot_flash_atmega164a_UART1_38400_8000000L_B0.hex { 512, 0, 0x35e2b5b6, 0xe5235996 }, // optiboot_flash_atmega164a_UART0_57600_8000000L_B0.hex { 512, 0, 0x46954df9, 0x54a100b1 }, // optiboot_flash_atmega164a_UART1_38400_8000000L_B7.hex { 512, 0, 0x74d076c7, 0xe8287590 }, // optiboot_flash_atmega164a_UART1_9600_1000000L_B0.hex { 512, 0, 0x74d076c7, 0xe8bed4e0 }, // optiboot_flash_atmega164a_UART1_9600_1000000L_B7.hex { 512, 0, 0x59f8865b, 0xdf955279 }, // optiboot_flash_atmega164a_UART0_9600_1000000L_B0.hex { 512, 0, 0x59f8865b, 0x0082b42c }, // optiboot_flash_atmega164a_UART0_9600_1000000L_B7.hex { 512, 0, 0x35e2b5b6, 0x404b2202 }, // optiboot_flash_atmega164a_UART0_115200_20000000L_B7.hex { 512, 0, 0x35e2b5b6, 0x65c16403 }, // optiboot_flash_atmega164a_UART0_115200_20000000L_B0.hex { 512, 0, 0x46954df9, 0xb062bbd4 }, // optiboot_flash_atmega164a_UART1_115200_20000000L_B0.hex { 512, 0, 0x46954df9, 0x8d570578 }, // optiboot_flash_atmega164a_UART1_115200_20000000L_B7.hex { 512, 0, 0x46954df9, 0xe4472d82 }, // optiboot_flash_atmega164a_UART1_115200_16000000L_B0.hex { 512, 0, 0x46954df9, 0x6660ce56 }, // optiboot_flash_atmega164a_UART1_115200_16000000L_B7.hex { 512, 0, 0x35e2b5b6, 0x3e909f95 }, // optiboot_flash_atmega164a_UART0_115200_16000000L_B7.hex { 512, 0, 0x35e2b5b6, 0x98798052 }, // optiboot_flash_atmega164a_UART0_115200_16000000L_B0.hex { 512, 0, 0xc188885a, 0xce4f7081 }, // optiboot_flash_atmega325_UART0_57600_8000000L_B5.hex { 512, 0, 0xc188885a, 0xe63cf120 }, // optiboot_flash_atmega325_UART0_38400_8000000L_B5.hex { 512, 0, 0x058e72b8, 0x284da256 }, // optiboot_flash_atmega325_UART0_9600_1000000L_B5.hex { 512, 0, 0xc188885a, 0xc4ec9a85 }, // optiboot_flash_atmega325_UART0_115200_20000000L_B5.hex { 512, 0, 0xc188885a, 0x13d2f0ef }, // optiboot_flash_atmega325_UART0_115200_16000000L_B5.hex { 1024, 1, 0xee6789c2, 0xde984e88 }, // optiboot_flash_atmega128_UART1_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xee6789c2, 0x047fffc9 }, // optiboot_flash_atmega128_UART1_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xd562886c, 0x6a2952aa }, // optiboot_flash_atmega128_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xd562886c, 0xa77e0c20 }, // optiboot_flash_atmega128_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xee6789c2, 0x09a5c098 }, // optiboot_flash_atmega128_UART1_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xd562886c, 0x604e9f9a }, // optiboot_flash_atmega128_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xee6789c2, 0xfc7070b2 }, // optiboot_flash_atmega128_UART1_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0xd562886c, 0xb11bf9e2 }, // optiboot_flash_atmega128_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0xee6789c2, 0xc9701422 }, // optiboot_flash_atmega128_UART1_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0xd562886c, 0xc2be4e0f }, // optiboot_flash_atmega128_UART0_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x4ec4df61 }, // optiboot_flash_atmega6490p_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x6f542d9f }, // optiboot_flash_atmega6490p_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x66724b13 }, // optiboot_flash_atmega6490p_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x987e5f86 }, // optiboot_flash_atmega6490p_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x4b132863 }, // optiboot_flash_atmega6490p_UART0_115200_16000000L_B7_BIGBOOT.hex { 512, 0, 0xb90059d5, 0x6e225cd3 }, // optiboot_flash_atmega168p_UART0_38400_8000000L_B5.hex { 512, 0, 0xb90059d5, 0x8a4282f1 }, // optiboot_flash_atmega168p_UART0_57600_8000000L_B5.hex { 512, 0, 0x87a200aa, 0x902a90c9 }, // optiboot_flash_atmega168p_UART0_9600_1000000L_B5.hex { 512, 0, 0xb90059d5, 0x19ff1b96 }, // optiboot_flash_atmega168p_UART0_115200_20000000L_B5.hex { 512, 0, 0xb90059d5, 0x995224d3 }, // optiboot_flash_atmega168p_UART0_115200_16000000L_B5.hex { 1024, 1, 0x70394fcf, 0x98fdf349 }, // optiboot_flash_atmega1284_UART1_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xd48d3fb8 }, // optiboot_flash_atmega1284_UART1_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xd4f39919 }, // optiboot_flash_atmega1284_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x8be783b2 }, // optiboot_flash_atmega1284_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x0c66f86d }, // optiboot_flash_atmega1284_UART0_38400_8000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xc3c1fa0a }, // optiboot_flash_atmega1284_UART0_57600_8000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x8ce72fce }, // optiboot_flash_atmega1284_UART1_57600_8000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x2607dc62 }, // optiboot_flash_atmega1284_UART1_38400_8000000L_B0_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x3163b91d }, // optiboot_flash_atmega1284_UART1_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x3ef3abf3 }, // optiboot_flash_atmega1284_UART0_9600_1000000L_B0_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x31a00898 }, // optiboot_flash_atmega1284_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x09e6912d }, // optiboot_flash_atmega1284_UART1_9600_1000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xa1de91d9 }, // optiboot_flash_atmega1284_UART1_115200_20000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x433d6e94 }, // optiboot_flash_atmega1284_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x1e70b8cf }, // optiboot_flash_atmega1284_UART0_115200_20000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xa3cd737c }, // optiboot_flash_atmega1284_UART1_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x18bb2f99 }, // optiboot_flash_atmega1284_UART1_115200_16000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xb135ab3c }, // optiboot_flash_atmega1284_UART0_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xf4675d8b }, // optiboot_flash_atmega1284_UART0_115200_16000000L_B0_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xd96949e5 }, // optiboot_flash_atmega1284_UART1_115200_16000000L_B7_BIGBOOT.hex { 512, 0, 0x8c6fdab4, 0x8e5d9c95 }, // optiboot_flash_atmega16_UART0_38400_8000000L_B0.hex { 512, 0, 0x47fd9a23, 0x5c54fb4a }, // optiboot_flash_atmega16_UART0_38400_8000000L_B7.hex { 512, 0, 0x47fd9a23, 0xf8f086f5 }, // optiboot_flash_atmega16_UART0_57600_8000000L_B7.hex { 512, 0, 0x8c6fdab4, 0x57b69579 }, // optiboot_flash_atmega16_UART0_57600_8000000L_B0.hex { 512, 0, 0x8c6fdab4, 0xf7dabebc }, // optiboot_flash_atmega16_UART0_9600_1000000L_B0.hex { 512, 0, 0x47fd9a23, 0x4d2b24be }, // optiboot_flash_atmega16_UART0_9600_1000000L_B7.hex { 512, 0, 0x8c6fdab4, 0xfb8d3b56 }, // optiboot_flash_atmega16_UART0_115200_20000000L_B0.hex { 512, 0, 0x47fd9a23, 0xf417591b }, // optiboot_flash_atmega16_UART0_115200_20000000L_B7.hex { 512, 0, 0x8c6fdab4, 0xfc0d86b5 }, // optiboot_flash_atmega16_UART0_115200_16000000L_B0.hex { 512, 0, 0x47fd9a23, 0x9bdeeb3c }, // optiboot_flash_atmega16_UART0_115200_16000000L_B7.hex { 1024, 1, 0xae42ebb8, 0x270bdd64 }, // optiboot_flash_atmega64_UART1_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x4c3d0b81 }, // optiboot_flash_atmega64_UART1_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x94b2a13c }, // optiboot_flash_atmega64_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x4cf8b9ab }, // optiboot_flash_atmega64_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x204dbfa5 }, // optiboot_flash_atmega64_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x0774388e }, // optiboot_flash_atmega64_UART1_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xbd6f5121 }, // optiboot_flash_atmega64_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x67960f85 }, // optiboot_flash_atmega64_UART1_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x583a87ca }, // optiboot_flash_atmega64_UART0_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x1462de41 }, // optiboot_flash_atmega64_UART1_115200_16000000L_B5_BIGBOOT.hex { 512, 0, 0x4abf9198, 0xda79c706 }, // optiboot_flash_atmega8515_UART0_57600_8000000L_B0.hex { 512, 0, 0x4abf9198, 0x82098a14 }, // optiboot_flash_atmega8515_UART0_38400_8000000L_B0.hex { 512, 0, 0x4abf9198, 0x3b291035 }, // optiboot_flash_atmega8515_UART0_9600_1000000L_B0.hex { 512, 0, 0x4abf9198, 0xd57f0c10 }, // optiboot_flash_atmega8515_UART0_115200_20000000L_B0.hex { 512, 0, 0x4abf9198, 0x0f838688 }, // optiboot_flash_atmega8515_UART0_115200_16000000L_B0.hex { 512, 0, 0xaa622fda, 0x4f06239c }, // optiboot_flash_atmega3290p_UART0_38400_8000000L_B7.hex { 512, 0, 0xaa622fda, 0x294107c3 }, // optiboot_flash_atmega3290p_UART0_57600_8000000L_B7.hex { 512, 0, 0x0626ce58, 0x211cae4c }, // optiboot_flash_atmega3290p_UART0_9600_1000000L_B7.hex { 512, 0, 0xaa622fda, 0x21a0acf6 }, // optiboot_flash_atmega3290p_UART0_115200_20000000L_B7.hex { 512, 0, 0xaa622fda, 0x71720261 }, // optiboot_flash_atmega3290p_UART0_115200_16000000L_B7.hex { 512, 0, 0x2afe013b, 0xd5de2de6 }, // optiboot_flash_atmega169p_UART0_57600_8000000L_B5.hex { 512, 0, 0x2afe013b, 0x5775955f }, // optiboot_flash_atmega169p_UART0_38400_8000000L_B5.hex { 512, 0, 0x7de5e119, 0xecba44da }, // optiboot_flash_atmega169p_UART0_9600_1000000L_B5.hex { 512, 0, 0x2afe013b, 0x0ebf1682 }, // optiboot_flash_atmega169p_UART0_115200_20000000L_B5.hex { 512, 0, 0x2afe013b, 0xee9f5b33 }, // optiboot_flash_atmega169p_UART0_115200_16000000L_B5.hex { 1024, 1, 0xae42ebb8, 0x97ab29d7 }, // optiboot_flash_atmega644p_UART1_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x4023218f }, // optiboot_flash_atmega644p_UART1_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x94298c9c }, // optiboot_flash_atmega644p_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x27bbf745 }, // optiboot_flash_atmega644p_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x26ced1dc }, // optiboot_flash_atmega644p_UART0_38400_8000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x1094e6b3 }, // optiboot_flash_atmega644p_UART0_57600_8000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x6d886955 }, // optiboot_flash_atmega644p_UART1_57600_8000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xc69f1084 }, // optiboot_flash_atmega644p_UART1_38400_8000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x796847db }, // optiboot_flash_atmega644p_UART1_9600_1000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x767ff663 }, // optiboot_flash_atmega644p_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x0599449e }, // optiboot_flash_atmega644p_UART0_9600_1000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x56979720 }, // optiboot_flash_atmega644p_UART1_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x83ea01e1 }, // optiboot_flash_atmega644p_UART1_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x66c88213 }, // optiboot_flash_atmega644p_UART0_115200_20000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x6897b483 }, // optiboot_flash_atmega644p_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x2eb98629 }, // optiboot_flash_atmega644p_UART1_115200_20000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x28a87902 }, // optiboot_flash_atmega644p_UART1_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x0b89845e }, // optiboot_flash_atmega644p_UART0_115200_16000000L_B0_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x4d7e38df }, // optiboot_flash_atmega644p_UART0_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xc9f335c4 }, // optiboot_flash_atmega644p_UART1_115200_16000000L_B0_BIGBOOT.hex { 512, 0, 0x2afe013b, 0xd5de2de6 }, // optiboot_flash_atmega165_UART0_57600_8000000L_B5.hex { 512, 0, 0x2afe013b, 0x5775955f }, // optiboot_flash_atmega165_UART0_38400_8000000L_B5.hex { 512, 0, 0x7de5e119, 0xecba44da }, // optiboot_flash_atmega165_UART0_9600_1000000L_B5.hex { 512, 0, 0x2afe013b, 0x0ebf1682 }, // optiboot_flash_atmega165_UART0_115200_20000000L_B5.hex { 512, 0, 0x2afe013b, 0xee9f5b33 }, // optiboot_flash_atmega165_UART0_115200_16000000L_B5.hex { 512, 0, 0x7426b344, 0x8785ab7e }, // optiboot_flash_atmega162_UART1_57600_8000000L_B0.hex { 512, 0, 0xda8d468f, 0xe903fd84 }, // optiboot_flash_atmega162_UART0_38400_8000000L_B0.hex { 512, 0, 0xda8d468f, 0x9859287c }, // optiboot_flash_atmega162_UART0_57600_8000000L_B0.hex { 512, 0, 0x7426b344, 0x7f9312a9 }, // optiboot_flash_atmega162_UART1_38400_8000000L_B0.hex { 512, 0, 0x3d2a281f, 0x1cc1dd8c }, // optiboot_flash_atmega162_UART0_9600_1000000L_B0.hex { 512, 0, 0x132fb9cf, 0xb4c6e662 }, // optiboot_flash_atmega162_UART1_9600_1000000L_B0.hex { 512, 0, 0x7426b344, 0xceb4839a }, // optiboot_flash_atmega162_UART1_115200_20000000L_B0.hex { 512, 0, 0xda8d468f, 0x747f258c }, // optiboot_flash_atmega162_UART0_115200_20000000L_B0.hex { 512, 0, 0xda8d468f, 0x9859287c }, // optiboot_flash_atmega162_UART0_115200_16000000L_B0.hex { 512, 0, 0x7426b344, 0x8785ab7e }, // optiboot_flash_atmega162_UART1_115200_16000000L_B0.hex { 1024, 1, 0x5790d602, 0x3870ca19 }, // optiboot_flash_at90can32_UART1_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x09092111 }, // optiboot_flash_at90can32_UART1_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x675f40ab }, // optiboot_flash_at90can32_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x650469af }, // optiboot_flash_at90can32_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x74b9c238, 0x20e0c28b }, // optiboot_flash_at90can32_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x74b9c238, 0x4d1375ab }, // optiboot_flash_at90can32_UART1_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x141f9dd1 }, // optiboot_flash_at90can32_UART1_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x1584a240 }, // optiboot_flash_at90can32_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0x12c681d4 }, // optiboot_flash_at90can32_UART1_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0x5790d602, 0xa23efbfe }, // optiboot_flash_at90can32_UART0_115200_16000000L_B5_BIGBOOT.hex { 512, 0, 0x2d9a8617, 0x9576f026 }, // optiboot_flash_atmega324a_UART1_57600_8000000L_B7.hex { 512, 0, 0xeebb98c4, 0x1c644fb2 }, // optiboot_flash_atmega324a_UART0_38400_8000000L_B0.hex { 512, 0, 0x2d9a8617, 0xb73769d1 }, // optiboot_flash_atmega324a_UART1_57600_8000000L_B0.hex { 512, 0, 0xeebb98c4, 0x497e8ac5 }, // optiboot_flash_atmega324a_UART0_38400_8000000L_B7.hex { 512, 0, 0x2d9a8617, 0x5e488620 }, // optiboot_flash_atmega324a_UART1_38400_8000000L_B0.hex { 512, 0, 0xeebb98c4, 0x1e7ff2f9 }, // optiboot_flash_atmega324a_UART0_57600_8000000L_B7.hex { 512, 0, 0x2d9a8617, 0xccd64c5b }, // optiboot_flash_atmega324a_UART1_38400_8000000L_B7.hex { 512, 0, 0xeebb98c4, 0x0fb6694e }, // optiboot_flash_atmega324a_UART0_57600_8000000L_B0.hex { 512, 0, 0x24de513c, 0xba0c877d }, // optiboot_flash_atmega324a_UART1_9600_1000000L_B0.hex { 512, 0, 0x24de513c, 0x14cea2eb }, // optiboot_flash_atmega324a_UART1_9600_1000000L_B7.hex { 512, 0, 0x6eb4e9a6, 0x7934547f }, // optiboot_flash_atmega324a_UART0_9600_1000000L_B0.hex { 512, 0, 0x6eb4e9a6, 0x795931d0 }, // optiboot_flash_atmega324a_UART0_9600_1000000L_B7.hex { 512, 0, 0xeebb98c4, 0xa22a39b9 }, // optiboot_flash_atmega324a_UART0_115200_20000000L_B7.hex { 512, 0, 0xeebb98c4, 0xf23c1c01 }, // optiboot_flash_atmega324a_UART0_115200_20000000L_B0.hex { 512, 0, 0x2d9a8617, 0x79726fb0 }, // optiboot_flash_atmega324a_UART1_115200_20000000L_B0.hex { 512, 0, 0x2d9a8617, 0xbab08ccb }, // optiboot_flash_atmega324a_UART1_115200_20000000L_B7.hex { 512, 0, 0x2d9a8617, 0x6f998a26 }, // optiboot_flash_atmega324a_UART1_115200_16000000L_B0.hex { 512, 0, 0x2d9a8617, 0x379b94b7 }, // optiboot_flash_atmega324a_UART1_115200_16000000L_B7.hex { 512, 0, 0xeebb98c4, 0xb7798c1d }, // optiboot_flash_atmega324a_UART0_115200_16000000L_B7.hex { 512, 0, 0xeebb98c4, 0xa3ba96e7 }, // optiboot_flash_atmega324a_UART0_115200_16000000L_B0.hex { 512, 0, 0x5ccf35cb, 0x898afdb0 }, // optiboot_flash_atmega88p_UART0_57600_8000000L_B5.hex { 512, 0, 0x5ccf35cb, 0xf0399a23 }, // optiboot_flash_atmega88p_UART0_38400_8000000L_B5.hex { 512, 0, 0x42f48861, 0x8cfdfcb8 }, // optiboot_flash_atmega88p_UART0_9600_1000000L_B5.hex { 512, 0, 0x5ccf35cb, 0x8990a68e }, // optiboot_flash_atmega88p_UART0_115200_20000000L_B5.hex { 512, 0, 0x5ccf35cb, 0xa35ca98a }, // optiboot_flash_atmega88p_UART0_115200_16000000L_B5.hex { 512, 0, 0xc0e0c9aa, 0x2fcb09d8 }, // optiboot_flash_atmega328p_UART0_38400_8000000L_B5.hex { 512, 0, 0xc0e0c9aa, 0xb15524df }, // optiboot_flash_atmega328p_UART0_57600_8000000L_B5.hex { 512, 0, 0xe15a32cd, 0x32d973ec }, // optiboot_flash_atmega328p_UART0_9600_1000000L_B5.hex { 512, 0, 0xc0e0c9aa, 0x0127527c }, // optiboot_flash_atmega328p_UART0_115200_20000000L_B5.hex { 512, 0, 0xc0e0c9aa, 0x2cbe3881 }, // optiboot_flash_atmega328p_UART0_115200_16000000L_B5.hex { 1024, 1, 0xae42ebb8, 0x0976c9ef }, // optiboot_flash_atmega649_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xa498f3ed }, // optiboot_flash_atmega649_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x064c9396 }, // optiboot_flash_atmega649_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xc42e67a3 }, // optiboot_flash_atmega649_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xb7ca22b5 }, // optiboot_flash_atmega649_UART0_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xc7d736d6 }, // optiboot_flash_atmega640_UART3_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xf1c8ea31 }, // optiboot_flash_atmega640_UART3_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x7e45b263 }, // optiboot_flash_atmega640_UART2_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xe2f5ab2b }, // optiboot_flash_atmega640_UART2_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xe279ccd5 }, // optiboot_flash_atmega640_UART1_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x7da86a27 }, // optiboot_flash_atmega640_UART1_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xa8c13596 }, // optiboot_flash_atmega640_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xcdd9bb83 }, // optiboot_flash_atmega640_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x781c56b2 }, // optiboot_flash_atmega640_UART2_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x5c86eb3f }, // optiboot_flash_atmega640_UART1_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x6abacc22 }, // optiboot_flash_atmega640_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x55c95f39 }, // optiboot_flash_atmega640_UART3_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x5df0eb9e }, // optiboot_flash_atmega640_UART1_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xa35dcc84 }, // optiboot_flash_atmega640_UART2_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x49ef04b1 }, // optiboot_flash_atmega640_UART3_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x817efbcf }, // optiboot_flash_atmega640_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x9c06346f }, // optiboot_flash_atmega640_UART2_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x507dd91e }, // optiboot_flash_atmega640_UART1_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x615a09e4 }, // optiboot_flash_atmega640_UART0_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x21b86ab9 }, // optiboot_flash_atmega640_UART3_115200_16000000L_B7_BIGBOOT.hex { 512, 0, 0xaa622fda, 0x294107c3 }, // optiboot_flash_atmega3290_UART0_57600_8000000L_B7.hex { 512, 0, 0xaa622fda, 0x4f06239c }, // optiboot_flash_atmega3290_UART0_38400_8000000L_B7.hex { 512, 0, 0x0626ce58, 0x211cae4c }, // optiboot_flash_atmega3290_UART0_9600_1000000L_B7.hex { 512, 0, 0xaa622fda, 0x21a0acf6 }, // optiboot_flash_atmega3290_UART0_115200_20000000L_B7.hex { 512, 0, 0xaa622fda, 0x71720261 }, // optiboot_flash_atmega3290_UART0_115200_16000000L_B7.hex { 512, 0, 0xc188885a, 0xe63cf120 }, // optiboot_flash_atmega325p_UART0_38400_8000000L_B5.hex { 512, 0, 0xc188885a, 0xce4f7081 }, // optiboot_flash_atmega325p_UART0_57600_8000000L_B5.hex { 512, 0, 0x058e72b8, 0x284da256 }, // optiboot_flash_atmega325p_UART0_9600_1000000L_B5.hex { 512, 0, 0xc188885a, 0xc4ec9a85 }, // optiboot_flash_atmega325p_UART0_115200_20000000L_B5.hex { 512, 0, 0xc188885a, 0x13d2f0ef }, // optiboot_flash_atmega325p_UART0_115200_16000000L_B5.hex { 512, 0, 0xe70524cd, 0x76b1e5e7 }, // optiboot_flash_atmega324pb_UART1_57600_8000000L_B7.hex { 512, 0, 0x0cf7e212, 0x02724086 }, // optiboot_flash_atmega324pb_UART0_38400_8000000L_B0.hex { 512, 0, 0x119c8746, 0xc5b68c97 }, // optiboot_flash_atmega324pb_UART2_38400_8000000L_B7.hex { 512, 0, 0xe70524cd, 0x7d44fb76 }, // optiboot_flash_atmega324pb_UART1_57600_8000000L_B0.hex { 512, 0, 0x119c8746, 0x515f6cc8 }, // optiboot_flash_atmega324pb_UART2_38400_8000000L_B0.hex { 512, 0, 0x0cf7e212, 0x9fd0954e }, // optiboot_flash_atmega324pb_UART0_38400_8000000L_B7.hex { 512, 0, 0xe70524cd, 0x7b7220cf }, // optiboot_flash_atmega324pb_UART1_38400_8000000L_B0.hex { 512, 0, 0x119c8746, 0xfa254553 }, // optiboot_flash_atmega324pb_UART2_57600_8000000L_B0.hex { 512, 0, 0x0cf7e212, 0x1cc4a79d }, // optiboot_flash_atmega324pb_UART0_57600_8000000L_B7.hex { 512, 0, 0xe70524cd, 0x73288ce3 }, // optiboot_flash_atmega324pb_UART1_38400_8000000L_B7.hex { 512, 0, 0x0cf7e212, 0x1cba5cf5 }, // optiboot_flash_atmega324pb_UART0_57600_8000000L_B0.hex { 512, 0, 0x119c8746, 0x1bc2e50d }, // optiboot_flash_atmega324pb_UART2_57600_8000000L_B7.hex { 512, 0, 0x23882f25, 0xf4e3bedc }, // optiboot_flash_atmega324pb_UART2_9600_1000000L_B7.hex { 512, 0, 0x23882f25, 0x309c6619 }, // optiboot_flash_atmega324pb_UART2_9600_1000000L_B0.hex { 512, 0, 0x4eda2f7e, 0xe23050d8 }, // optiboot_flash_atmega324pb_UART1_9600_1000000L_B0.hex { 512, 0, 0x4eda2f7e, 0xe571fa99 }, // optiboot_flash_atmega324pb_UART1_9600_1000000L_B7.hex { 512, 0, 0x25d48eb2, 0xe5bbf4cb }, // optiboot_flash_atmega324pb_UART0_9600_1000000L_B0.hex { 512, 0, 0x25d48eb2, 0x367e2797 }, // optiboot_flash_atmega324pb_UART0_9600_1000000L_B7.hex { 512, 0, 0x119c8746, 0x7a7b4a0e }, // optiboot_flash_atmega324pb_UART2_115200_20000000L_B7.hex { 512, 0, 0x119c8746, 0x46dce88c }, // optiboot_flash_atmega324pb_UART2_115200_20000000L_B0.hex { 512, 0, 0xe70524cd, 0xd64392cc }, // optiboot_flash_atmega324pb_UART1_115200_20000000L_B0.hex { 512, 0, 0xe70524cd, 0x2c53ef72 }, // optiboot_flash_atmega324pb_UART1_115200_20000000L_B7.hex { 512, 0, 0x0cf7e212, 0x151316da }, // optiboot_flash_atmega324pb_UART0_115200_20000000L_B7.hex { 512, 0, 0x0cf7e212, 0x7d599f19 }, // optiboot_flash_atmega324pb_UART0_115200_20000000L_B0.hex { 512, 0, 0x0cf7e212, 0x5d9ee2b8 }, // optiboot_flash_atmega324pb_UART0_115200_16000000L_B7.hex { 512, 0, 0x0cf7e212, 0xd67c7167 }, // optiboot_flash_atmega324pb_UART0_115200_16000000L_B0.hex { 512, 0, 0x119c8746, 0x722ccc92 }, // optiboot_flash_atmega324pb_UART2_115200_16000000L_B7.hex { 512, 0, 0x119c8746, 0x929de9d1 }, // optiboot_flash_atmega324pb_UART2_115200_16000000L_B0.hex { 512, 0, 0xe70524cd, 0x566a2f82 }, // optiboot_flash_atmega324pb_UART1_115200_16000000L_B0.hex { 512, 0, 0xe70524cd, 0x5fdf497d }, // optiboot_flash_atmega324pb_UART1_115200_16000000L_B7.hex { 512, 0, 0x76291c3d, 0xb99fa55c }, // optiboot_flash_atmega328_UART0_38400_8000000L_B5.hex { 512, 0, 0x76291c3d, 0xca16f284 }, // optiboot_flash_atmega328_UART0_57600_8000000L_B5.hex { 512, 0, 0xe6d3ec9c, 0xf39cd12f }, // optiboot_flash_atmega328_UART0_9600_1000000L_B5.hex { 512, 0, 0x76291c3d, 0xd4685bd8 }, // optiboot_flash_atmega328_UART0_115200_20000000L_B5.hex { 512, 0, 0x76291c3d, 0xf983b103 }, // optiboot_flash_atmega328_UART0_115200_16000000L_B5.hex { 1024, 1, 0x2f29a5a8, 0x7f45706b }, // optiboot_flash_atmega1281_UART1_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x2f29a5a8, 0xc5174f64 }, // optiboot_flash_atmega1281_UART1_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x2f29a5a8, 0xd272f5d9 }, // optiboot_flash_atmega1281_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0x2f29a5a8, 0xe19b2f1b }, // optiboot_flash_atmega1281_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xe9fba810, 0xc4eebbbc }, // optiboot_flash_atmega1281_UART1_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xe9fba810, 0xb9923382 }, // optiboot_flash_atmega1281_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0x2f29a5a8, 0x422c3281 }, // optiboot_flash_atmega1281_UART1_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x2f29a5a8, 0xcfee8326 }, // optiboot_flash_atmega1281_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0x2f29a5a8, 0x24ae0a4a }, // optiboot_flash_atmega1281_UART1_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0x2f29a5a8, 0xcfc68538 }, // optiboot_flash_atmega1281_UART0_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x82288400 }, // optiboot_flash_atmega6450p_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xe8704cb1 }, // optiboot_flash_atmega6450p_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xb80318bc }, // optiboot_flash_atmega6450p_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x31550abd }, // optiboot_flash_atmega6450p_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x28381b17 }, // optiboot_flash_atmega6450p_UART0_115200_16000000L_B7_BIGBOOT.hex { 512, 0, 0x46954df9, 0x54a100b1 }, // optiboot_flash_atmega164p_UART1_38400_8000000L_B7.hex { 512, 0, 0x35e2b5b6, 0xe5235996 }, // optiboot_flash_atmega164p_UART0_57600_8000000L_B0.hex { 512, 0, 0x46954df9, 0xe3a119bb }, // optiboot_flash_atmega164p_UART1_38400_8000000L_B0.hex { 512, 0, 0x35e2b5b6, 0x390f2ade }, // optiboot_flash_atmega164p_UART0_57600_8000000L_B7.hex { 512, 0, 0x46954df9, 0xe5e526c7 }, // optiboot_flash_atmega164p_UART1_57600_8000000L_B0.hex { 512, 0, 0x35e2b5b6, 0xc38c7647 }, // optiboot_flash_atmega164p_UART0_38400_8000000L_B7.hex { 512, 0, 0x46954df9, 0xc307e815 }, // optiboot_flash_atmega164p_UART1_57600_8000000L_B7.hex { 512, 0, 0x35e2b5b6, 0xe3f2c268 }, // optiboot_flash_atmega164p_UART0_38400_8000000L_B0.hex { 512, 0, 0x59f8865b, 0xdf955279 }, // optiboot_flash_atmega164p_UART0_9600_1000000L_B0.hex { 512, 0, 0x59f8865b, 0x0082b42c }, // optiboot_flash_atmega164p_UART0_9600_1000000L_B7.hex { 512, 0, 0x74d076c7, 0xe8287590 }, // optiboot_flash_atmega164p_UART1_9600_1000000L_B0.hex { 512, 0, 0x74d076c7, 0xe8bed4e0 }, // optiboot_flash_atmega164p_UART1_9600_1000000L_B7.hex { 512, 0, 0x46954df9, 0xb062bbd4 }, // optiboot_flash_atmega164p_UART1_115200_20000000L_B0.hex { 512, 0, 0x46954df9, 0x8d570578 }, // optiboot_flash_atmega164p_UART1_115200_20000000L_B7.hex { 512, 0, 0x35e2b5b6, 0x404b2202 }, // optiboot_flash_atmega164p_UART0_115200_20000000L_B7.hex { 512, 0, 0x35e2b5b6, 0x65c16403 }, // optiboot_flash_atmega164p_UART0_115200_20000000L_B0.hex { 512, 0, 0x35e2b5b6, 0x3e909f95 }, // optiboot_flash_atmega164p_UART0_115200_16000000L_B7.hex { 512, 0, 0x35e2b5b6, 0x98798052 }, // optiboot_flash_atmega164p_UART0_115200_16000000L_B0.hex { 512, 0, 0x46954df9, 0xe4472d82 }, // optiboot_flash_atmega164p_UART1_115200_16000000L_B0.hex { 512, 0, 0x46954df9, 0x6660ce56 }, // optiboot_flash_atmega164p_UART1_115200_16000000L_B7.hex { 1024, 1, 0x70394fcf, 0x990b0718 }, // optiboot_flash_atmega1280_UART2_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xedc43871 }, // optiboot_flash_atmega1280_UART2_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xc8c6b978 }, // optiboot_flash_atmega1280_UART3_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x46efca2b }, // optiboot_flash_atmega1280_UART3_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x48da213b }, // optiboot_flash_atmega1280_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x83e33e5a }, // optiboot_flash_atmega1280_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xe8fba5b2 }, // optiboot_flash_atmega1280_UART1_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x32c02cce }, // optiboot_flash_atmega1280_UART1_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x9fb7469b }, // optiboot_flash_atmega1280_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x72d58ca6 }, // optiboot_flash_atmega1280_UART3_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0xe8d4fd48 }, // optiboot_flash_atmega1280_UART2_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x6f4a2030, 0x7e7f2a4f }, // optiboot_flash_atmega1280_UART1_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x5a177a62 }, // optiboot_flash_atmega1280_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x9f55ef91 }, // optiboot_flash_atmega1280_UART3_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x69c6037a }, // optiboot_flash_atmega1280_UART2_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x131b5a3c }, // optiboot_flash_atmega1280_UART1_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x9c8cdeb7 }, // optiboot_flash_atmega1280_UART3_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x337c346c }, // optiboot_flash_atmega1280_UART0_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0x517bae1c }, // optiboot_flash_atmega1280_UART1_115200_16000000L_B7_BIGBOOT.hex { 1024, 1, 0x70394fcf, 0xf25fb27c }, // optiboot_flash_atmega1280_UART2_115200_16000000L_B7_BIGBOOT.hex { 512, 0, 0x58b9d0f6, 0x0ac150c9 }, // optiboot_flash_atmega329_UART0_38400_8000000L_B5.hex { 512, 0, 0x58b9d0f6, 0x27eeb558 }, // optiboot_flash_atmega329_UART0_57600_8000000L_B5.hex { 512, 0, 0x203e2338, 0x7a9110b5 }, // optiboot_flash_atmega329_UART0_9600_1000000L_B5.hex { 512, 0, 0x58b9d0f6, 0x8d2698e6 }, // optiboot_flash_atmega329_UART0_115200_20000000L_B5.hex { 512, 0, 0x58b9d0f6, 0xc77803d4 }, // optiboot_flash_atmega329_UART0_115200_16000000L_B5.hex { 1024, 1, 0xae42ebb8, 0xed657349 }, // optiboot_flash_atmega649p_UART0_38400_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xb8d02007 }, // optiboot_flash_atmega649p_UART0_57600_8000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x4f40d9a6 }, // optiboot_flash_atmega649p_UART0_9600_1000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x28f40c94 }, // optiboot_flash_atmega649p_UART0_115200_20000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xe55392cf }, // optiboot_flash_atmega649p_UART0_115200_16000000L_B5_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x82288400 }, // optiboot_flash_atmega6450_UART0_38400_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xe8704cb1 }, // optiboot_flash_atmega6450_UART0_57600_8000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0xb80318bc }, // optiboot_flash_atmega6450_UART0_9600_1000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x31550abd }, // optiboot_flash_atmega6450_UART0_115200_20000000L_B7_BIGBOOT.hex { 1024, 1, 0xae42ebb8, 0x28381b17 }, // optiboot_flash_atmega6450_UART0_115200_16000000L_B7_BIGBOOT.hex ```
stefanrueger commented 1 year ago

same hash, even though they are different parts

Hash function clashes are vvv unlikely (1/4bn). The different parts will have the same signature, and therefore the bootloaders will be identical. Here one example:

$ grep 0xee9f5b33 /tmp/hash-list
    {  512, 0, 0x2afe013b, 0xee9f5b33 }, // optiboot_flash_atmega169_UART0_115200_16000000L_B5.hex
    {  512, 0, 0x2afe013b, 0xee9f5b33 }, // optiboot_flash_atmega169p_UART0_115200_16000000L_B5.hex
    {  512, 0, 0x2afe013b, 0xee9f5b33 }, // optiboot_flash_atmega165_UART0_115200_16000000L_B5.hex

My bet is that the bootloaders for these three parts are identical, and in particular that the signatures are the same. Your list has 480 different hashes. (And I very much predict your 542-strong bootloader list has only 480 unique ones.) You get the 57 hashes that occur multiple times by

$ cut -f4 -d, /tmp/hash-list  | sort | uniq -c | grep -v " 1 " | sort -n

It makes sense to keep only one representative of bootoaders that are identical (though there is no harm in having identical hashes in the list: the algorithm copes).

stefanrueger commented 1 year ago

The more important question is: which of these bootloaders have EEPROM support and which don't. The script uses the heuristic(!) that all bootloaders that have bigboot or BIGBOOT in its names cope with EEPROM (ie, get a 1 in the second column).

MCUdude commented 1 year ago

My bet is that the bootloaders for these three parts are identical, and in particular that the signatures are the same. Your list has 480 different hashes. (And I very much predict your 542-strong bootloader list has only 480 unique ones.) You get the 57 hashes that occur multiple times by

I realize now that I should have built these bootloaders for ATmega165A and ATmega169A instead of the non-A models. There seems to be a bug in the avr-libc version I used where the non-A parts incorrectly has the same signature values in their io.h file. I should fix this, re-build the bootloader and update the hash table

The more important question is: which of these bootloaders have EEPROM support and which don't. The script uses the heuristic(!) that all bootloaders that have bigboot or BIGBOOT in its names cope with EEPROM (ie, get a 1 in the second column).

All bootloaders that have BIGBOOT in their name support EEPROM read/write, so the script is correct.

stefanrueger commented 1 year ago

| I should fix this, re-build the bootloader and update the hash table

We had the discussion before: signatures are no good indicator for the part. So, this cannot be fixed!

Unless you switch to urboot that is. :grinning:

And for good measure, signatures can be different between avr-libc and avrdude.

stefanrueger commented 1 year ago

@MCUdude I've been wondering why your (8 MHz, 57600 baud) bootloaders are different from (16 MHz, 115200 baud) bootloaders, but I now suspect that optiboot flashes the LED for a while with a certain frequency - and that therefore the code will be different for these two bootloader versions. For the comms alone the code would be identical.

mcuee commented 1 year ago

I agree with change the lable to wontfix. We can keep this issue open for a while and then close it.

We can even create a FAQ Wiki page to include information like this one.

mcuee commented 1 year ago

This is a well-known optiboot bug. It returns flash for EEPROM if optiboot has been compiled to not handle EEPROM. This bug has been around for a long time (and possibly still is today but defo was 2016 when I last looked closely at optiboot).

I can confirm the issue is still there with latest optiboot git.

PS C:\work\avr\avrdude_test\avrdude_bin> .\avrdude -c urclock -P COM4 -p m328p -xbootsize=512 -xshowall

avrdude: AVR device initialized and ready to accept instructions
0 2022-06-10 21.21 Blink.ino.standard.hex 924 store 31298 meta 34 boot 512 o8.3 -?s-?-r-- vector 0 (RESET) ATmega328P

PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c arduino -P COM4 -p m328p -qqt
avrdude> dump eeprom 0 0x10
0000  0c 94 5c 00 0c 94 6e 00  0c 94 6e 00 0c 94 6e 00  | .\. .n. .n. .n.|

avrdude>
avrdude>
PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c usbasp -p m328p -qqt
avrdude> dump eeprom 0 0x10
0000  ff ff ff ff ff ff ff ff  ff ff ff ff ff ff ff ff  |................|

avrdude>
avrdude>

I consider this as a serious bug of optiboot. The only saving grace is that writing to EEPROM will fail.

PS C:\work\avr\avrdude_test\avrdude_bin> echo "write eeprom 0 0xaa 0x55" | .\avrdude -c arduino -P COM4 -p m328p -qqt
avrdude> write eeprom 0 0xaa 0x55
avrdude>
avrdude> avrdude error: programmer is not responding
(CTRL-C to exit)

PS C:\work\avr\avrdude_test\avrdude_bin> echo "dump eeprom 0 0x10" | .\avrdude -c usbasp -p m328p -qqt
avrdude> dump eeprom 0 0x10
0000  ff ff ff ff ff ff ff ff  ff ff ff ff ff ff ff ff  |................|

avrdude>
avrdude>
mcuee commented 1 year ago

@WestfW Just wondering if you have any intentions to fix this paticular optiboot bug. Thanks.

@MCUdude and @SpenceKonde Just wondering if you know this bug or not. I consider it as a serious bug.

MCUdude commented 1 year ago

We had the discussion before: https://github.com/avrdudes/avrdude/pull/1091#issuecomment-1231678867. So, this cannot be fixed!

Signatures aren't the best, I agree. Atmel is to blame here for their inconsistency. However, in my case, uploading to an ATmega169A will fail, because the signature hardcoded into the device differs from the one in the bootloader. I'll ditch the non-A parts for now. I'm doing this because I want a last "known-good" MegaCore release before migrating everything to Urboot.

Just wondering if you know this bug or not. I consider it as a serious bug.

I wasn't aware of it, but since Arduino IDE doesn't support uploading directly to EEPROM, it has never really been an issue. If I'm going to switch to Urboot later, I don't think I'll bother fixing it and compiling all new hex files.

mcuee commented 1 year ago

I wasn't aware of it, but since Arduino IDE doesn't support uploading directly to EEPROM, it has never really been an issue.

Ah, that explains why this issue was not noticed for so long.

mcuee commented 1 year ago

https://github.com/Optiboot/optiboot/issues/357 raised against Optiboot.

mcuee commented 1 year ago

Re-open this issue so that we can continue which hash to be included in avrdude.

SpenceKonde commented 1 year ago

@MCUdude: What is this "Urboot" thing"?

mcuee commented 1 year ago

@SpenceKonde It is here. https://github.com/stefanrueger/urboot

I am thinking it may be useful for your ATTinyCore.

In paticular, it may be the ultimate fix for the issue you raised against Optiboot.

But @stefanrueger and @MCUdude may be able to give you better perspectives about switching from Optiboot to urboot.

MCUdude commented 1 year ago

@SpenceKonde It's a new bootloader written together with the Avrdude implementation of the protocol. It has all the bells and whistles you might dream of (Only for classic AVRs for now), and it occupies very little flash space. The virtual bootloaders are very interesting and are impossible to brick as long as you don't wipe or modify the flash contents with an ISP programmer.

It lets you:

More about the Urboot bootloader here: https://github.com/stefanrueger/urboot/blob/b068ad0a16ac6e11690a72172c43ef689c8b8425/src/urboot.c#L1-L709

More about the Avrdude protocol implementation (Urclock) and what it supports here: https://github.com/avrdudes/avrdude/pull/1171

The Avrdude docs (avrdude.texi and avrdude.1) also contain lots of information.

Bottom line: It's an incredibly feature-rich and packed bootloader designed around a custom protocol specifically for bootloader usage. It's an impressive piece of software, and I'm planning to migrate all my Arduino cores to use Urboot and ditch Optiboot completely. And for ATtinyCore where lots of parts use virtual bootloaders, It's a no-brainer.

MCUdude commented 1 year ago

From urboot.c:


* Feature-rich bootloader that is fast and small
 *  - Tight code: most bootloaders fit into 256 bytes
 *  - Highly modular feature set:
 *     + Dedicated protocol between programmer and bootloader (urprotocol)
 *     + EEPROM read/write support
 *     + Vector bootloader for devices without a boot section or to save space on devices with one
 *     + Software UART: no hardware UART required, but also useful when the chip's CPU frequency
 *       and the bootloader's desired baud rate are incompatible (eg, 8 MHz and 115,200 baud)
 *     + Subroutine pgm_write_page(sram, progmem) for applications so they can change themselves:
 *       on many MCUs the SPM write flash only works when called from the bootloader section
 *     + Dual programming from external SPI flash memory for over-the-air programming
 *     + Template bootloader with nops that will be replaced "on the fly" with code to manipulate
 *       the right LED/TX/RX/CS pins at bootloader-burning time (see accompanying urloader sketch)
 *     + Saves the reset flags in R2 for inspection by the application via the .init0 section
 *     + Bootloader protects itself from overwriting
 *     + Automatic host baud rate detection
 *     + Chip erase in bootloader (faster than -c urclock emulation)
 *
* How the bootloader works
 *   In common with bootloaders, it runs after every reset and tries to communicate with an
 *   external uploader program via a serial interface using a variant of the STK500v1 protocol.
 *   Hence, only the serial I/O needs to be connected from a Raspberry Pi/PC/laptop host to the
 *   board with the to-be-programmed MCU on it. After every reset the bootloader code determines
 *   its cause: if that was an external reset as opposed to power-up reset or watchdog timeout
 *   (WDT) it waits a small time for protocol initialisation bytes from an uploader program. If
 *   there was was a valid handshake, the bootloader carries out one of several possible tasks
 *   driven by the host's uploader such as receiving and burning a new sketch, downloading an
 *   existing sketch on the MCU, and, if compiled for it, reading or writing the EEPROM on the MCU.
 *   The bootloader finishes this part typically through a watchdog timeout reset that kicks in
 *   when initially no valid handshake could be detected, when a serial hardware or protocol error
 *   occurred during burning/verification or when the bootloader finished its task successfully.
 *   Watchdog timeout resets the MCU just like an external reset. When the bootloader is entered
 *   under this condition, though, it then normally jumps directly to the application. However,
 *   when the bootloader was compiled with dual-boot support, it first checks external SPI flash
 *   memory to see it contains a new sketch, in which case a copy of it is burned from external
 *   memory onto internal flash. The idea is that the application sketch could have been written to
 *   receive a new version via a radio and have placed it onto the external SPI flash memory before
 *   issuing a WDT reset. Hence, this dual-boot property is also called over the air programming,
 *   although one could conceivably also plug a new external SPI flash into a board for
 *   programming.
 *
 *
 * Assumptions, limitations and caveats of *any* bootloader
 *
 *   - Establishing communication invariably causes some small startup delay on external reset.
 *
 *   - For bootloaders on ISP MCUs there is no need for a physical programmer, though in order to
 *     burn the bootloader itself onto the MCU, an SPI header and an SPI programmer is needed at
 *     least once in the beginning. Burning the bootloader using SPI necessitates the MCU be in
 *     reset mode: all chip select lines of attached SPI hardware (external flash memory, radios
 *     etc) need therefore be pulled high through resistors to ensure all external SPI devices are
 *     inactive during SPI programming of the bootloader.
 *
 *   - In most cases the connection from the PC for uploading sketches via the bootloader will be
 *     through USB, which necessitates a USB to serial converter cable if the destination board
 *     does not have USB. Some PCs (most notably, the Raspberry Pi) have a native serial connection
 *     that also could be used for connecting to a board without USB.
 *
 *   - The bootloader sets the TX line of the UART or the designated TX pin of the software serial
 *     communication to output after every reset. If the bootloader is compiled to blink an LED, to
 *     output a square wave for debugging or to communicate via SPI with external memory for dual
 *     programming, there will be other lines that are set to output shortly after each reset. Not
 *     all projects can deal gracefully with these short flares of output activity on some of the
 *     pins. If you use a bootloader for production settings it is best to carefully consider the
 *     hardware implications on the circuit.
 *
 *   - As with all bootloaders they work best when the host has a way to reset the board, which is
 *     typically done via DTR/RTS lines of the host's serial port. Avrdude -c [arduino|urclock]
 *     does this automatically. The board needs to have hardware to facilitate the DTR/RTS
 *     connection for reset. Most boards do. If not, sometimes running a small dedicated reset
 *     program on the host just before running avrdude helps. This reset program somehow needs to
 *     pull the board's reset line low for a short time; on a Raspberry Pi external GPIO pins can
 *     be used for that. If that is not possible either, then setting the watchdog timeout to a
 *     long time (see the WDTO option below) may be helpful, so one can manually reset the board
 *     before calling avrdude. The default for the timeout is 500 ms. Only with the urclock
 *     programmer can smaller timeouts down to 128 ms be reliably utilised.
 *
 *
 * Assumptions, limitations, caveats, tips and tricks for *this* bootloader
 *
 *   - The uploading program is assumed to be avrdude with either the arduino or urclock
 *     programmer: call avrdude -c [arduino|urclock] for this. I have not tested other uploaders.
 *     The tightest bootloader code (see URPROTOCOL=1 option below) requires avrdude's urclock
 *     programmer as this forgoes some get/put parameter calls that arduino issues unnecessarily
 *     and uses its own leaner protocol.
 *
 *   - A bootloader with dual-boot support needs to know which port pin is assigned to the chip
 *     select of the SPI flash memory, which pin drives a blinking LED (if wanted), where the tx/rx
 *     lines are for serial communication, how long the watchdog timeout should be etc. This
 *     explodes the option space for this bootloader. Using the accompanying urloader sketch for
 *     burning this bootloader onto a board mitigates this somewhat by the use of "template"
 *     bootloaders (see TEMPLATE option). Urloader lets you interactively set at bootloader burn
 *     time which pins it should set/clear for LED, chip select, and RX/TX (for software serial
 *     I/O). Urloader knows some common boards and offers the right bootloaders for them.
 *
 *   - Remember that dual-boot bootloaders communicate with the SPI flash memory at all external
 *     and WDT resets. Therefore, all other attached SPI devices need their chip select pulled
 *     high. While in theory urboot.c could be changed so that it uses software pullup for these
 *     additional devices, this could cost additional code and will complicate the already too big
 *     option space. It is better practice to use hardware pullups in the board design.
 *
 *   - A dual-boot bootloader deals gracefully with a board that has no external SPI flash memory:
 *     it simply reads 0xff values and decides there is nothing interesting there. However, this
 *     causes unnecessary delay at each external reset and each WDT reset, and it toggles the SPI
 *     and chip select lines (see above); it is therefore not recommended to burn the most-feature
 *     rich urboot bootloader onto all your boards. Carefully determine what you actually need.
 *
 *   - When using external SPI memory on a board with a dual-boot bootloader, remember to reserve
 *     the first FLASHEND+1 bytes exclusively for sketches to be burned onto the MCU. These are
 *     recognised by the second byte being indicative of an rjmp or a jmp opcode. Placing  some
 *     random data in that area risks the MCU being programmed with just these random data.
 *
 *   - Vector bootloaders are great for devices with no dedicated boot section. They assume
 *       + the vector table of the MCU, and therefore the reset vector, resides at address zero
 *       + the compiler puts either a jmp or an rjmp at address zero
 *       + the compiler does not zap/shorten the vector table if no or few interrupts are used
 *       + the compiler does not utilise unused interrupt vectors to place code there
 *
 *     This should be the case with all regular sketches produced by avr-gcc. Vector bootloaders
 *     are also useful for devices with boot section support to allow them to use less space than
 *     the smallest offered hardware-supported boot section. In this case ensure that the fuses are
 *     set to make the processor jump to the reset vector as opposed to the bootloader. And ensure
 *     that the protection bits in the lock byte actually allow code be written into the bootloader
 *     section with SPM instructions. Otherwise the extra space in the boot section that is freed
 *     by smaller vector bootloaders cannot be used. The urloader sketch sets fuses and lock bits
 *     appropriately when burning a vector bootloader onto your board. More on VBLs below.
 *
 *   - The code makes several assumptions that reduce the code size (eg, no interrupts can occur,
 *     SP points to RAMEND). They are true after a hardware reset, but will not necessarily be true
 *     if the bootloader is called directly. So don't.
mcuee commented 1 year ago

Re-open this issue so that we can continue which hash to be included in avrdude.

That has been addressed in PR #1226.