This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
受朋友之托,今天第一次给大家发帖子, 把珍藏的成年老窖, 让大家尝尝, 下面是我珍藏多年的代码,我自认为有价值, 如果对你有点点帮助,请个我回个帖子.
我们用的MSP430时, 内部有几十个字节information memory 可以当EEPROM来用, 无需再外扩EEPROM芯片, 用量保存一下系数的掉电保存的数据. 我一直用这个, 很好用.
特别说明:
1.说明我用的是IAR编译器, 在IAR上一定能通过
2. 利用information memory 作为EEPROM 掉电保存数据,这是这段程序第一个亮点;
3. 写information memory 必须在RAM中运行程序. 将程序从flash 跑到RAM中运行, 很有意思. 这是第二个亮点.
#include "MSP430x16x.h"
#include "string.h"
#include"stdlib.h"
#include"flash.h"
/************************************************************************************
** 函数名称: flashWrite
** 功能描述: 在MSP430flash中写数据
**
** 输 入: td:写入地址, sd:源数据指针, size:写入字节数
** 输 出: 无
** 返 回 值: 返回需要发送给其他任务处理的数据块的指针。
** 全局变量:
** 调用模块:
** 作 者: 陈文浩
** 日 期: 2010年07月12日
************************************************************************************/
void flashWrite(unsigned char * td, unsigned char *sd, unsigned char size)
{
typedef void(*funp)(unsigned char*,unsigned char *, unsigned char); //定义函数指针类型
funp FLASHBLK;
char ramcode[100]; //ram内程序及数组地址指针
_DINT();
//ramcode=(char *)malloc(sizeof(char)*100); //为放入内存的子程分配空间(需先将heap值设为180)
FLASHBLK = flashWriteBlock; //函数指针赋值
memcpy(ramcode,(char *)FLASHBLK,100); //将块写子程放入ram中已分配空间
FLASHBLK=*(funp)ramcode; //将函数指针指向ram中的块写子程
flashErase(td); //段擦
(FLASHBLK)(td,sd, size); //块写(调用的是ram中的块写子程)
//free(ramcode); //释放空间
_EINT(); //开放中断
}
void flashWriteBlock(unsigned char * td,unsigned char *sd, unsigned char size)
{
int i;
while((FCTL3&BUSY)!=0x00); //检测busy位
FCTL2=FWKEY+FSSEL_1+20; //flash模块时钟源为MCLK 分频2
FCTL3=FWKEY; //解锁
FCTL1=FWKEY+BLKWRT+WRT; //块写
for(i=0;i<size;i++) //写64字节数据
{
*td++=*sd++; //写入
while((FCTL3&WAIT)==0); //检测wait位 是否写入该字
}
FCTL1=FWKEY; //BLKWRT WRT位复位
while((FCTL3&BUSY)!=0x00); //检测BUSY位
FCTL3=FWKEY+LOCK; //锁定
}
/*******************************************************************************/
/* 段擦除子程序 */
/*******************************************************************************/
void flashErase(unsigned char *td)
{
FCTL2=FWKEY+FSSEL_1+10; //flash模块时钟源位MCLK 分频2
FCTL3=FWKEY; //解锁
FCTL1=FWKEY+ERASE; //段擦除
*td=0; //在欲进行操作的段中空写,启动擦除操作
FCTL3=FWKEY+LOCK; //锁定
}
//功能:FLASH操作 BYTE数据写入
//编程时钟:257KHZ~476KHZ
void flashWriteByte(unsigned char * pdata, unsigned char data)
{
//WDTCTL = WDTPW + WDTHOLD; //关闭看门狗
_DINT(); //关闭总中断
FCTL2 = FWKEY+FSSEL1+12; //3686400/300K=12
FCTL3 = FWKEY; //LOCK=0;
FCTL1=FWKEY+WRT; //WRT=1;
*pdata = data;
FCTL3 = FWKEY+LOCK; //
//开通看门狗
_EINT(); //开放中断
}
void flashWriteWord(unsigned short * pdata, unsigned short data)
{
//WDTCTL = WDTPW + WDTHOLD; //关闭看门狗
_DINT(); //关闭总中断
FCTL2 = FWKEY+FSSEL1+12;
FCTL3 = FWKEY; //LOCK=0;
FCTL1=FWKEY+WRT; //WRT=1;
*pdata = data;
FCTL3 = FWKEY+LOCK; //
//开通看门狗
_EINT(); //开放中断
}
受朋友之托,今天第一次给大家发帖子, 把珍藏的成年老窖, 让大家尝尝, 下面是我珍藏多年的代码,我自认为有价值, 如果对你有点点帮助,请个我回个帖子.
我们用的MSP430时, 内部有几十个字节information memory 可以当EEPROM来用, 无需再外扩EEPROM芯片, 用量保存一下系数的掉电保存的数据. 我一直用这个, 很好用.
特别说明:
1.说明我用的是IAR编译器, 在IAR上一定能通过
2. 利用information memory 作为EEPROM 掉电保存数据,这是这段程序第一个亮点;
3. 写information memory 必须在RAM中运行程序. 将程序从flash 跑到RAM中运行, 很有意思. 这是第二个亮点.
#include "MSP430x16x.h"
#include "string.h"
#include"stdlib.h"
#include"flash.h"
/************************************************************************************
** 函数名称: flashWrite
** 功能描述: 在MSP430flash中写数据
**
** 输 入: td:写入地址, sd:源数据指针, size:写入字节数
** 输 出: 无
** 返 回 值: 返回需要发送给其他任务处理的数据块的指针。
** 全局变量:
** 调用模块:
** 作 者: 陈文浩
** 日 期: 2010年07月12日
************************************************************************************/
void flashWrite(unsigned char * td, unsigned char *sd, unsigned char size)
{
typedef void(*funp)(unsigned char*,unsigned char *, unsigned char); //定义函数指针类型
funp FLASHBLK;
char ramcode[100]; //ram内程序及数组地址指针
_DINT();
//ramcode=(char *)malloc(sizeof(char)*100); //为放入内存的子程分配空间(需先将heap值设为180)
FLASHBLK = flashWriteBlock; //函数指针赋值
memcpy(ramcode,(char *)FLASHBLK,100); //将块写子程放入ram中已分配空间
FLASHBLK=*(funp)ramcode; //将函数指针指向ram中的块写子程
flashErase(td); //段擦
(FLASHBLK)(td,sd, size); //块写(调用的是ram中的块写子程)
//free(ramcode); //释放空间
_EINT(); //开放中断
}
void flashWriteBlock(unsigned char * td,unsigned char *sd, unsigned char size)
{
int i;
while((FCTL3&BUSY)!=0x00); //检测busy位
FCTL2=FWKEY+FSSEL_1+20; //flash模块时钟源为MCLK 分频2
FCTL3=FWKEY; //解锁
FCTL1=FWKEY+BLKWRT+WRT; //块写
for(i=0;i<size;i++) //写64字节数据
{
*td++=*sd++; //写入
while((FCTL3&WAIT)==0); //检测wait位 是否写入该字
}
FCTL1=FWKEY; //BLKWRT WRT位复位
while((FCTL3&BUSY)!=0x00); //检测BUSY位
FCTL3=FWKEY+LOCK; //锁定
}
/*******************************************************************************/
/* 段擦除子程序 */
/*******************************************************************************/
void flashErase(unsigned char *td)
{
FCTL2=FWKEY+FSSEL_1+10; //flash模块时钟源位MCLK 分频2
FCTL3=FWKEY; //解锁
FCTL1=FWKEY+ERASE; //段擦除
*td=0; //在欲进行操作的段中空写,启动擦除操作
FCTL3=FWKEY+LOCK; //锁定
}
//功能:FLASH操作 BYTE数据写入
//编程时钟:257KHZ~476KHZ
void flashWriteByte(unsigned char * pdata, unsigned char data)
{
//WDTCTL = WDTPW + WDTHOLD; //关闭看门狗
_DINT(); //关闭总中断
FCTL2 = FWKEY+FSSEL1+12; //3686400/300K=12
FCTL3 = FWKEY; //LOCK=0;
FCTL1=FWKEY+WRT; //WRT=1;
*pdata = data;
FCTL3 = FWKEY+LOCK; //
//开通看门狗
_EINT(); //开放中断
}
void flashWriteWord(unsigned short * pdata, unsigned short data)
{
//WDTCTL = WDTPW + WDTHOLD; //关闭看门狗
_DINT(); //关闭总中断
FCTL2 = FWKEY+FSSEL1+12;
FCTL3 = FWKEY; //LOCK=0;
FCTL1=FWKEY+WRT; //WRT=1;
*pdata = data;
FCTL3 = FWKEY+LOCK; //
//开通看门狗
_EINT(); //开放中断
}
请问,这种方案在MSP430F425里面可以通用吗???arm999 说:受朋友之托,今天第一次给大家发帖子, 把珍藏的成年老窖, 让大家尝尝, 下面是我珍藏多年的代码,我自认为有价值, 如果对你有点点帮助,请个我回个帖子.
我们用的MSP430时, 内部有几十个字节information memory 可以当EEPROM来用, 无需再外扩EEPROM芯片, 用量保存一下系数的掉电保存的数据. 我一直用这个, 很好用.
特别说明:
1.说明我用的是IAR编译器, 在IAR上一定能通过
2. 利用information memory 作为EEPROM 掉电保存数据,这是这段程序第一个亮点;
3. 写information memory 必须在RAM中运行程序. 将程序从flash 跑到RAM中运行, 很有意思. 这是第二个亮点.
#include "MSP430x16x.h"
#include "string.h"
#include"stdlib.h"
#include"flash.h"
/************************************************************************************
** 函数名称: flashWrite
** 功能描述: 在MSP430flash中写数据
**
** 输 入: td:写入地址, sd:源数据指针, size:写入字节数
** 输 出: 无
** 返 回 值: 返回需要发送给其他任务处理的数据块的指针。
** 全局变量:
** 调用模块:
** 作 者: 陈文浩
** 日 期: 2010年07月12日
************************************************************************************/
void flashWrite(unsigned char * td, unsigned char *sd, unsigned char size)
{
typedef void(*funp)(unsigned char*,unsigned char *, unsigned char); //定义函数指针类型
funp FLASHBLK;
char ramcode[100]; //ram内程序及数组地址指针
_DINT();
//ramcode=(char *)malloc(sizeof(char)*100); //为放入内存的子程分配空间(需先将heap值设为180)
FLASHBLK = flashWriteBlock; //函数指针赋值
memcpy(ramcode,(char *)FLASHBLK,100); //将块写子程放入ram中已分配空间
FLASHBLK=*(funp)ramcode; //将函数指针指向ram中的块写子程
flashErase(td); //段擦
(FLASHBLK)(td,sd, size); //块写(调用的是ram中的块写子程)
//free(ramcode); //释放空间
_EINT(); //开放中断
}
void flashWriteBlock(unsigned char * td,unsigned char *sd, unsigned char size)
{
int i;
while((FCTL3&BUSY)!=0x00); //检测busy位
FCTL2=FWKEY+FSSEL_1+20; //flash模块时钟源为MCLK 分频2
FCTL3=FWKEY; //解锁
FCTL1=FWKEY+BLKWRT+WRT; //块写
for(i=0;i<size;i++) //写64字节数据
{
*td++=*sd++; //写入
while((FCTL3&WAIT)==0); //检测wait位 是否写入该字
}
FCTL1=FWKEY; //BLKWRT WRT位复位
while((FCTL3&BUSY)!=0x00); //检测BUSY位
FCTL3=FWKEY+LOCK; //锁定
}
/*******************************************************************************/
/* 段擦除子程序 */
/*******************************************************************************/
void flashErase(unsigned char *td)
{
FCTL2=FWKEY+FSSEL_1+10; //flash模块时钟源位MCLK 分频2
FCTL3=FWKEY; //解锁
FCTL1=FWKEY+ERASE; //段擦除
*td=0; //在欲进行操作的段中空写,启动擦除操作
FCTL3=FWKEY+LOCK; //锁定
}//功能:FLASH操作 BYTE数据写入
//编程时钟:257KHZ~476KHZ
void flashWriteByte(unsigned char * pdata, unsigned char data)
{
//WDTCTL = WDTPW + WDTHOLD; //关闭看门狗
_DINT(); //关闭总中断
FCTL2 = FWKEY+FSSEL1+12; //3686400/300K=12
FCTL3 = FWKEY; //LOCK=0;
FCTL1=FWKEY+WRT; //WRT=1;
*pdata = data;
FCTL3 = FWKEY+LOCK; //
//开通看门狗
_EINT(); //开放中断
}void flashWriteWord(unsigned short * pdata, unsigned short data)
{
//WDTCTL = WDTPW + WDTHOLD; //关闭看门狗
_DINT(); //关闭总中断
FCTL2 = FWKEY+FSSEL1+12;
FCTL3 = FWKEY; //LOCK=0;
FCTL1=FWKEY+WRT; //WRT=1;
*pdata = data;
FCTL3 = FWKEY+LOCK; //
//开通看门狗
_EINT(); //开放中断
}
谢谢分享,MSP430铁电系列 MSP430FRxxxx片上存储全部为非易失性FRAM铁电存储,轻松解决掉电保护的问题。
请在TI.COM上搜索Compute Through Power Loss。这是一个很好的解决方案把FRAM作为EEPROM甚至SRAM使用
你好,我现在调试的是MSP430i2041,编译器是IAR,现在需要用info memory保存掉电数据,上电后读出来。IAR只提供了写进info memory的接口,没有提供读出来的接口,根据我在网上找的资料,读info memory的数据是直接操作就可以了。请问有读info memory的例程吗?
//下面是代码,代码是在FLASHCTL这个demo的基础上小改
#include "driverlib.h"
// Address of the beginning of the Flash Information Segment
#define SEGSTART 0x1060
// Number of bytes within segment to write
#define SEG_LEN 16
// Value to write to segment
const uint32_t Value = 0xBEEFDEAD;
uint8_t r_value[4]={0};
uint8_t r_value1=0;
void write_InfoSeg(uint32_t value);
void FlashRead(uint8_t *pc_byte,uint8_t *Dataout,uint8_t count);
void main(void) {
// Pointer to beginning of Flash segment
uint32_t *flashPtr = (uint32_t *)SEGSTART;
// Stop WDT
WDT_hold(WDT_BASE);
// Setting the DCO to use the internal resistor. DCO will be at 16.384MHz
CS_setupDCO(CS_INTERNAL_RESISTOR);
// Setting MCLK to DCO / 1. MCLK = 16.384MHz.
CS_initClockSignal(CS_MCLK, CS_CLOCK_DIVIDER_1);
// MCLK for Flash Timing Generator
// Flash clock will run at ~390kHz. Datasheet recommends 257kHz - 476kHz
FlashCtl_setupClock(390095, 16384000, FLASHCTL_MCLK);
FlashCtl_unlockInfo();
FlashCtl_fillMemory32(Value, flashPtr, SEG_LEN / 4);
FlashCtl_lockInfo();
while(1)
{
// Set breakpoint to view memory
//__no_operation();
FlashRead((uint8_t *)SEGSTART,r_value,SEG_LEN / 4);
r_value1=r_value[0]; //r_value1仿真一直是0
}
}
//从 info memory读一个byte接口
void FlashRead(uint8_t *pc_byte,uint8_t *Dataout,uint8_t count)
{
while(count--)
{
*Dataout = *pc_byte;
Dataout++;
pc_byte++;
}
}