当我使用Optiboot引导加载程序将新草图上传到Arduino Uno时,真正发生了什么?
- 什么被发送到Arduino?
- 它如何反应?
- “不同步”是什么意思?
- 什么是“同步”?
注意:这旨在作为“参考问题”。
当我使用Optiboot引导加载程序将新草图上传到Arduino Uno时,真正发生了什么?
注意:这旨在作为“参考问题”。
Answers:
当您重置运行Optiboot加载程序的Uno时,引导加载程序首先将13针闪烁3次。
顶线(灰色)发送到 Arduino,中线(橙色)发送到 Arduino。
发生这种情况时,avrdude计算机上运行的程序正在向设备发送查询:
STK_GET_SYNC / CRC_EOP  (0x30/0x20)Arduino没有注意到第一个“获取同步”,因为它正在忙于闪烁引脚13。完成后,它会注意到“获取同步”(它将由串行硬件缓冲)并回复:
STK_INSYNC / STK_OK (0x14/0x10)似乎avrdude有点急躁,并已超时,因为它再次尝试使用“获取同步”查询。这次Optiboot立即响应。
下图描述了其余的上传。示例产生了上传股票“ Blink”程序。
(单击上面的图像查看大图)
这些步骤是:
设置设备参数。以下设备参数发送到芯片:
0x42  // STK_SET_DEVICE
0x86  // device code
0x00  // revision
0x00  // progtype: “0” – Both Parallel/High-voltage and Serial mode
0x01  // parmode: “1” – Full parallel interface
0x01  // polling: “1” – Polling may be used
0x01  // selftimed: “1” – Self timed
0x01  // lockbytes: Number of Lock bytes.
0x03  // fusebytes: Number of Fuse bytes
0xFF  // flashpollval1
0xFF  // flashpollval2
0xFF  // eeprompollval1
0xFF  // eeprompollval2
0x00  // pagesizehigh
0x80  // pagesizelow
0x04  // eepromsizehigh
0x00  // eepromsizelow
0x00  // flashsize4
0x00  // flashsize3
0x80  // flashsize2
0x00  // flashsize1
0x20  // Sync_CRC_EOPOptiboot将忽略所有这些内容,并通过“同步中/确定”进行答复。:)
设置扩展设备参数:
0x45  // STK_SET_DEVICE_EXT
0x05  // commandsize: how many bytes follow
0x04  // eeprompagesize: EEPROM page size in bytes.
0xD7  // signalpagel: 
0xC2  // signalbs2: 
0x00  // ResetDisable: Defines whether a part has RSTDSBL Fuse 
0x20  // Sync_CRC_EOPOptiboot也将忽略所有这些内容,并通过“同步中/确定”进行答复。
进入程序模式。回复:在同步/确定中。
阅读签名。Optiboot答复时0x1E 0x95 0x0F 并未实际读取签名。
写保险丝(四次)。Optiboot 不写保险丝,而只是在同步/正常情况下回复。
加载地址(最初为0x0000)。地址以字为单位(即,一个字是两个字节)。这设置了下一页数据将写入的地址。
程序页(最多发送128个字节)。Optiboot立即回复“同步中”。然后在实际编程页面时会有大约4 ms的暂停。然后它回答“确定”。
加载地址(现在为0x0040)。这是十进制的地址64,即。从程序存储器的开始起128个字节。
写入另一页。此顺序一直持续到写入所有页面为止。
加载地址(返回0x0000)。这是为了验证写入。
读取页(最多读取128个字节)。这是用于验证。请注意,即使验证失败,不良数据也已经被写入芯片。
退出编程模式。
从上面可以看到,在编程过程的每一步中,Arduino都将以“同步中”(0x14)进行响应,可能还会跟一些数据,然后是“ OK”(0x10)。
如果不是“同步”,则表示avrdude没有得到“同步”响应。可能的原因可能是:
如上所述,响应“同步”表示Arduino(引导加载程序)与上传程序同步。
该协议是Atmel记录的STK500协议。请参阅下面的参考。
注意:Optiboot中未使用STK500第2版,但如果您使用的是Mega2560之类的板卡,则包含在STK500版本2中以供参考。
/* STK500 constants list, from AVRDUDE */
#define STK_OK              0x10
#define STK_FAILED          0x11  // Not used
#define STK_UNKNOWN         0x12  // Not used
#define STK_NODEVICE        0x13  // Not used
#define STK_INSYNC          0x14  // ' '
#define STK_NOSYNC          0x15  // Not used
#define ADC_CHANNEL_ERROR   0x16  // Not used
#define ADC_MEASURE_OK      0x17  // Not used
#define PWM_CHANNEL_ERROR   0x18  // Not used
#define PWM_ADJUST_OK       0x19  // Not used
#define CRC_EOP             0x20  // 'SPACE'
#define STK_GET_SYNC        0x30  // '0'
#define STK_GET_SIGN_ON     0x31  // '1'
#define STK_SET_PARAMETER   0x40  // '@'
#define STK_GET_PARAMETER   0x41  // 'A'
#define STK_SET_DEVICE      0x42  // 'B'
#define STK_SET_DEVICE_EXT  0x45  // 'E'
#define STK_ENTER_PROGMODE  0x50  // 'P'
#define STK_LEAVE_PROGMODE  0x51  // 'Q'
#define STK_CHIP_ERASE      0x52  // 'R'
#define STK_CHECK_AUTOINC   0x53  // 'S'
#define STK_LOAD_ADDRESS    0x55  // 'U'
#define STK_UNIVERSAL       0x56  // 'V'
#define STK_PROG_FLASH      0x60  // '`'
#define STK_PROG_DATA       0x61  // 'a'
#define STK_PROG_FUSE       0x62  // 'b'
#define STK_PROG_LOCK       0x63  // 'c'
#define STK_PROG_PAGE       0x64  // 'd'
#define STK_PROG_FUSE_EXT   0x65  // 'e'
#define STK_READ_FLASH      0x70  // 'p'
#define STK_READ_DATA       0x71  // 'q'
#define STK_READ_FUSE       0x72  // 'r'
#define STK_READ_LOCK       0x73  // 's'
#define STK_READ_PAGE       0x74  // 't'
#define STK_READ_SIGN       0x75  // 'u'
#define STK_READ_OSCCAL     0x76  // 'v'
#define STK_READ_FUSE_EXT   0x77  // 'w'
#define STK_READ_OSCCAL_EXT 0x78  // 'x'avrdude的默认验证行为的引导程序都是支持读取闪存内容的引导程序。