我试图读取 atmega32 的签名行,boot_signature_byte_get(0);
但出现此错误:'SIGRD' undeclared (first use in this function)
这似乎是因为我们只能使用 SPMCR 中具有 SIGRD 位的 AVR 读取签名(我想!)。
这是正确的吗?那么我该如何以另一种方式阅读签名行?
4 回答
早在 2007 年,任何头部都没有读取签名字节的功能,然后在同年推出。但看起来,它仍然存在一些问题。
数据表说:
All Atmel microcontrollers have a three-byte signature code which identifies the device.
This code can be read in both serial and parallel mode, also when the device is locked.
The three bytes reside in a separate address space.
这意味着 ATMEGA32 可以读取该字节。同样在数据表中,它指定了如何读取该字节。在他们的大多数 MCU 中,它的读取方式相同,但由于某种原因,SIGRD
一些头文件中缺少定义号,包括 ATMEGA32 之一。
但是,作为一种解决方法,我们可以SIGRD
手动定义。我们只需要知道它的价值。当我在头文件中做一些findstr
(或grep
)搜索这个定义时,一致认为它的值为 5。
因此,解决方法是:
#define SIGRD 5
#include <avr/boot.h>
我编译成功了,但我只是尝试在模拟软件上测试程序,因为我现在没有 ATMEGA32。它返回一个字节,所以现在由您决定这是否是正确的字节......
关于你说的SPMCR这件事,好像签名行是在另外一个地址空间(据我了解,不知道对不对我无法确认),获取方式是使用一些指令, 同样当我们将一些程序上传到 MCU 时。
当我今晚面临同样的问题时,我想加强一点并说明弗拉维奥的答案。
那么我该如何以另一种方式阅读签名行?
Flavio 的解决方法做得很好:
#define SIGRD 5
#include <avr/boot.h>
void read_signature_row(uint8_t sr[3])
{
sr[0] = boot_signature_byte_get(0x0000);
sr[1] = boot_signature_byte_get(0x0002);
sr[2] = boot_signature_byte_get(0x0004);
}
void setup()
{
Serial.begin(9600);
delay(100);
uint8_t sr[3] = {0xcc, 0xcc, 0xcc};
read_signature_row(sr);
char buff[100];
snprintf(buff, sizeof buff, "Device signature: %02X %02X %02X", sr[0], sr[1], sr[2]);
Serial.println(buff);
}
void loop()
{}
我没有 ATmega32,尽管此方法为我的 ATmega328P (1E 95 0F) 和 ATmega168PA (1E 94 0B) 检索正确的签名。
似乎这是因为我们只能使用 SPMCR 中具有 SIGRD 位的 AVR 读取签名(我想!)。这是正确的吗?
不,它实际上在调用 LPM 之前将 SIGRD 设置为 SPMCR,如下所示avr/boot.h
:
#define __BOOT_SIGROW_READ (_BV(__SPM_ENABLE) | _BV(SIGRD))
#define boot_signature_byte_get(addr) \
(__extension__({ \
uint8_t __result; \
__asm__ __volatile__ \
( \
"sts %1, %2\n\t" \
"lpm %0, Z" "\n\t" \
: "=r" (__result) \
: "i" (_SFR_MEM_ADDR(__SPM_REG)), \
"r" ((uint8_t)(__BOOT_SIGROW_READ)), \
"z" ((uint16_t)(addr)) \
); \
__result; \
}))
我相信 atmega32 不支持读取用户程序中的签名字节。
atmega32 Datasheet 显示该器件在其寄存器 SPMCR 中没有称为 SIGRD的位,该寄存器的第五位保留并标记为只读。
atmega640 /1280/2560处理器有一个类似的寄存器,称为spmcSr,它有这个位 SIGRD (Bit 5)。但数据表说明不应使用此位,因为此操作保留供将来使用(尽管如此,此处解释了读取签名的过程)。
您的编译器可以正常工作,因为 atmega32 没有此 SIGRD 位。
SIGRD 存在并可用于ATmega164A/164PA/324A/324PA/644A/644PA/1284/1284P处理器。“保留供将来使用”备注仅适用于除 SPMCSR 的五个最低位之外的任何 SPM 指令,请参见第 285 页,第 26.9.1 节。