打印
[PIC®/AVR®/dsPIC®产品]

合理使用AVR D系列芯片的USERROW、BOOTROW

[复制链接]
1893|15
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
lcczg|  楼主 | 2024-10-12 09:37 | 只看该作者 |只看大图 回帖奖励 |倒序浏览 |阅读模式
本帖最后由 lcczg 于 2024-10-12 09:39 编辑

在AVR D系列芯片中有一个非易失存储区是USERROW,BOOTROW, 可以用来存放终端产品的一些信息,例如校准数据,密钥串码之类的。芯片擦除(erase)时它不受影响,不会被擦。
在调试的时候耗费了一些时间,所以这里和大家分享一下,用到的话可以做一个参考。

我用的硬件是AVR64DU32 Cnano板(https://www.microchip.com/en-us/development-tool/ev59f82a),

IDE是MPLABX 6.20, 编译器XC8 v2.50.

程序里对USERROW操作,先擦再写,再读出来,调试时可以看到写入读出的数据是一致的。
USERROW大小512字节,测试时写入了32字节做验证。工程在附件里,这里直接贴一下代码

#include <xc.h>
#include <avr/io.h>
#include <avr/interrupt.h>
#include <avr/pgmspace.h>

#define USER_ROW_START_ADDRESS 0x1200
#define USER_ROW_SIZE 32

uint8_t read_buf[USER_ROW_SIZE];

uint8_t read_user_row(uint16_t address)
{
    return *(uint8_t *) address;
}

void erase_user_row(void) {
    while (NVMCTRL.STATUS & (NVMCTRL_EEBUSY_bm | NVMCTRL_FLBUSY_bm));
    _PROTECTED_WRITE_SPM(NVMCTRL.CTRLA, NVMCTRL_CMD_FLPER_gc);  // Enter erase mode
    USERROW_USERROW = 0;                                       // trigger page(512byte) Erase
    while (NVMCTRL.STATUS & NVMCTRL_FLBUSY_bm);
    _PROTECTED_WRITE_SPM(NVMCTRL.CTRLA, NVMCTRL_CMD_NONE_gc);   // Leave erase mode
}

void write_user_row(uint8_t *data, uint8_t length) {

    // Set up the NVMCTRL to write to the user row
    NVMCTRL.ADDR = USER_ROW_START_ADDRESS;

    // Write data to the user row
    for (uint8_t i = 0; i < length; i++) {
        while (NVMCTRL.STATUS & (NVMCTRL_EEBUSY_bm | NVMCTRL_FLBUSY_bm));
        CCP = CCP_SPM_gc ;
        NVMCTRL.CTRLA = 0x02;
        *((uint8_t *)(USER_ROW_START_ADDRESS + i)) = data;
    }

}

int main(void) {
    uint8_t user_data[USER_ROW_SIZE] = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08,
    0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F, 0x10,
    0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18,
    0x19, 0x1A, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F, 0x20};

    // Erase USERROW
    erase_user_row();
   
    // Write the user data to the user row
    write_user_row(user_data, USER_ROW_SIZE);

    // Read data from the user row
    for (uint8_t i = 0; i < USER_ROW_SIZE; i++) {
        read_buf = read_user_row(USER_ROW_START_ADDRESS + i);
    }

    while (1) {
    // Main loop
        NOP();
    }

    return 0;
}


烧录运行后,可以读出memory 内容到一个文件,

读出后打开文件,可以看到写入的数据



AVR64DU32-USERROW.X.zip

129.36 KB

使用特权

评论回复
沙发
micoccd| | 2024-10-12 16:39 | 只看该作者
这个是不是像FLASH一样啊

使用特权

评论回复
板凳
lcczg|  楼主 | 2024-10-16 10:53 | 只看该作者
micoccd 发表于 2024-10-12 16:39
这个是不是像FLASH一样啊

是的,本质上是FLASH。

使用特权

评论回复
地板
yellow555| | 2024-10-31 13:33 | 只看该作者
基本都要先擦再写,再读出来,调试时可以看到写入读出的数据是一致的。

使用特权

评论回复
5
yangjiaxu| | 2024-11-5 08:46 | 只看该作者
就是一个存储呗,然后就是它可以写一写配置数据在里面呗

使用特权

评论回复
6
yuliangren| | 2024-11-18 20:44 | 只看该作者
AVR D系列芯片的USERROW和BOOTROW是两个特殊的存储区域,它们在芯片的非易失性存储器中扮演着不同的角色。

使用特权

评论回复
7
canfeil| | 2024-11-21 09:39 | 只看该作者
USERROW(用户行)是一个可读写的非易失性存储区域,通常用于存储用户自定义的数据。这个区域在芯片复位后仍然保持数据,因此非常适合存储配置参数、校准数据或其他需要在系统启动时使用的信息。

使用特权

评论回复
8
eleg34ance| | 2024-11-21 11:21 | 只看该作者
其特性是非易失性,数据在断电后不会丢失。

使用特权

评论回复
9
gra22ce| | 2024-11-21 13:33 | 只看该作者
用户可以在运行时读取和写入数据。

使用特权

评论回复
10
hight1light| | 2024-11-21 14:48 | 只看该作者
通常为32字节或64字节,具体取决于芯片型号。

使用特权

评论回复
11
miltk| | 2024-11-21 15:31 | 只看该作者
USERROW的写入操作通常需要先擦除整个USERROW区域,然后再写入数据。具体操作可以参考芯片的数据手册。

使用特权

评论回复
12
nqty| | 2024-11-21 18:18 | 只看该作者
BOOTROW(引导行)是一个用于存储引导加载程序(Bootloader)的区域。这个区域通常位于芯片的Flash存储器的末尾,用于在系统启动时加载和执行引导程序。

使用特权

评论回复
13
suiziq| | 2024-11-21 20:08 | 只看该作者
配置引导程序: 在编程时,可以将引导程序代码写入BOOTROW区域。通常,芯片的编程工具(如AVR Studio或Atmel Studio)提供了配置引导程序的功能。

使用特权

评论回复
14
twinkhahale| | 2024-11-21 21:21 | 只看该作者
当芯片复位时,它会自动从BOOTROW区域加载并执行引导程序。引导程序通常负责初始化系统、加载应用程序代码等任务。

使用特权

评论回复
15
tiakon| | 2024-11-22 06:04 | 只看该作者
应用程序和引导程序的分离: 通常,应用程序代码和引导程序代码是分开存储的。应用程序代码存储在Flash存储器的前面部分,而引导程序代码存储在BOOTROW区域。

使用特权

评论回复
16
huahuagg| | 2024-11-28 16:28 | 只看该作者
提供了库函数操作?学一下。

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

个人签名:滴水可穿石,众志更成城 http://my.21ic.com/static/image/smiley/comcom/2.gif

31

主题

887

帖子

4

粉丝