你的浏览器版本过低,可能导致网站不能正常访问!
为了你能正常使用网站功能,请使用这些浏览器。

大侠给个F767的片上FLASH写入的例子吧

[复制链接]
kylongmu 提问时间:2017-7-4 20:10 /
#define FLASH_USER (FLASH_BASE+0x00100000U)
void StartDefaultTask(void const * argument)
{

  /* USER CODE BEGIN 5 */
  uint32_t i = 0;
  uint32_t * pFlash_Data = (uint32_t *)FLASH_USER;
  /* Infinite loop */
  for(;;)
  {
        osDelay(5000);
        HAL_FLASH_Unlock();
        HAL_FLASH_Program(FLASH_PSIZE_WORD,FLASH_USER, (uint64_t)i++);
        HAL_FLASH_Lock();
        FLASH_WaitForLastOperation(100);
          
        printf("Hello world%d\n\r",*pFlash_Data);
        HAL_GPIO_WritePin(GPIOB, LD1_GREEN_Pin, i&0x00000001);
        //HAL_UART_Transmit(&huart3, "a", 1, 0xFFFF);
  }
  /* USER CODE END 5 */
}
以上代码写入后读出测试失败,大侠给个例子吧。
收藏 评论14 发布时间:2017-7-4 20:10

举报

14个回答
kylongmu 回答时间:2017-7-4 20:42:39
stm32f7_s1.jpg
调试状态下地址与数值
kylongmu 回答时间:2017-7-4 21:49:15
stm32f7_s2.jpg
12个sector,看来不好操作啊。
MrJiu 回答时间:2017-7-5 09:25:00
我觉得,还是使用串口打印数据比较好,在线调试,很多数据都不同步的!!!!而且经常出现这个问题。。。至于操作FLASH,没搞过!!!
队长shiwo 回答时间:2017-7-5 09:45:46
flash用来存数据,选越小的扇区越好,擦除速度是问题,好像都是扇区擦除的
斜阳 回答时间:2017-7-5 10:55:23
官方例程里有flash操作。另外建议写flash操作测试代码时加上计数标志,防止持续写flash
mon51 回答时间:2017-7-5 11:00:50
/* Includes ------------------------------------------------------------------*/
#include "IAP_IN_MCU.h"
#include <string.h>
/* -------------------------------------------------------------*/

//const unsigned char Flash_Var[1024*16*2] __attribute__ ((at(FLASH_USER_START_ADDR)));
//******************************************************************************************

const unsigned int PHY_SECTOR_ADDR[]={
        ADDR_FLASH_SECTOR_7,ADDR_FLASH_SECTOR_8,ADDR_FLASH_SECTOR_9,ADDR_FLASH_SECTOR_10,
};
const unsigned int ERASE_PHY_SECTOR_ADDR[]={
        FLASH_Sector_7,FLASH_Sector_8,FLASH_Sector_9,FLASH_Sector_10,
};
//计算扇区的物理地址
unsigned int MCU_Get_LB_Sector(unsigned int LB_sector,unsigned int *blk,unsigned int *page,unsigned int *EraseBlk){
        unsigned int sectorNo,offset;
       
        offset                 =LB_sector / MAX_BLOCK_CNT;
        sectorNo        =LB_sector % MAX_BLOCK_CNT;
        *blk=        sectorNo;//PHY_SECTOR_ADDR[sectorNo];
        *page= offset;
        *EraseBlk=ERASE_PHY_SECTOR_ADDR[sectorNo];
        if(offset >=MAX_BLOCK_SECTOR) return 1;
        return 0;
}
/* Private function prototypes -----------------------------------------------*/
//删除扇区 SECTOR=8,9,10,11#
unsigned char MCU_Flash_Earse(unsigned int PHYsector){

  FLASH_ClearFlag(FLASH_FLAG_EOP                 | FLASH_FLAG_OPERR         | FLASH_FLAG_WRPERR         |
                  FLASH_FLAG_PGAERR | FLASH_FLAG_PGPERR        |        FLASH_FLAG_PGSERR);

  /* Device voltage range supposed to be [2.7V to 3.6V], the operation will  be done by word */
  if(FLASH_EraseSector(PHYsector, VoltageRange_3) != FLASH_COMPLETE) return 1;
        return 0;
}
//*************************************************************************************************
//MCU 读取一个页 cnt=字节数
unsigned int MCU_Flash_Read(unsigned int page,unsigned int block,unsigned char *buf,unsigned int cnt){
        unsigned int adr;
        adr=block*MAX_BLOCK_SIZES+page*MAX_SECTOR_SZIES+START_FLASH_SECTOR;
        memcpy(buf,(unsigned char *)adr,cnt);
        return 0;
}
//*************************************************************************************************
//MCU 读取一个页 cnt=字节数
unsigned int MCU_Flash_Read_to_BufCmp(unsigned int page,unsigned int block,unsigned char *buf,unsigned int cnt){
       
        volatile unsigned char *adr;
        adr=(volatile unsigned char *)(block*MAX_BLOCK_SIZES+page*MAX_SECTOR_SZIES+START_FLASH_SECTOR);
        while(cnt--){
                if(*adr++ != *buf++ ) return 1;
        }
        return 0;
}
//*************************************************************************************************
//MCU 读取一个页 cnt=字节数
unsigned int MCU_Flash_Read_to_ByteCmp(unsigned int page,unsigned int block,unsigned char Byte,unsigned int cnt){
        volatile unsigned char *adr;
       
        adr=(volatile unsigned char *)(block*MAX_BLOCK_SIZES+page*MAX_SECTOR_SZIES+START_FLASH_SECTOR);
        while(cnt--){
                if(*adr++ != Byte ) return 1;
        }
        return 0;
}
//*************************************************************************************************
//写入字节 cnt=字节数
//*************************************************************************************************
unsigned int MCU_Flash_Program(unsigned int page,unsigned int block,unsigned char *buf,unsigned int cnt){
        unsigned int adr;
       
       
        FLASH_ClearFlag(FLASH_FLAG_EOP                 | FLASH_FLAG_OPERR         | FLASH_FLAG_WRPERR         |
                  FLASH_FLAG_PGAERR | FLASH_FLAG_PGPERR        |        FLASH_FLAG_PGSERR);

        #ifdef FLASH_WORD_BYTE
                unsigned int *p;
                p=(unsigned int *)buf;
                cnt >>=2;
               
                adr=block*MAX_BLOCK_SIZES+page*MAX_SECTOR_SZIES+START_FLASH_SECTOR;
                while(cnt--){
                        if(FLASH_ProgramWord (adr,*p++) != FLASH_COMPLETE) break;
                        adr +=4;
                }
        #else
                adr=block*MAX_BLOCK_SIZES+page*MAX_SECTOR_SZIES+START_FLASH_SECTOR;
                while(cnt--){
                        if(FLASH_ProgramByte (adr++,*buf++) != FLASH_COMPLETE) break;
                }       
        #endif
        return 0;
}
//*******************************************************************************************
//优化处理 cnt=扇区数!
unsigned int MCU_Optimized( unsigned int sector, unsigned char *buf ,unsigned int cnt){
        unsigned int block,page,eraseBlk;

        cnt *=MAX_SECTOR_SZIES;
        if(MCU_Get_LB_Sector(sector,&block,&page,&eraseBlk))                         return 1;
        if(MCU_Flash_Read_to_BufCmp(page,block,buf,cnt)==0)                         return 0;
        if(MCU_Flash_Read_to_ByteCmp(page,block,0xff,cnt))                                 return 1;
        FLASH_Unlock();
        //FLASH_PrefetchBufferCmd(DISABLE);
       
        MCU_Flash_Program(page,block,buf,cnt);
       
        //FLASH_PrefetchBufferCmd(ENABLE);
        FLASH_Lock();
        return 0;
}
//#define USE_SDRAM
//***************************************************************************************
//COPY 数据到任意位置 未先删除处理的扇区亦可,不跨块写!! cnt=要写入的页数!
//***************************************************************************************
unsigned int  MCU_SWAP_Wirte(unsigned int sector, unsigned char *buf ,unsigned int cnt){

        unsigned int block,page,eraseBlk,n;
        unsigned char *p;
        //***********************************************************
        //处理交换块
        //***********************************************************
        if(MCU_Get_LB_Sector(sector,&block,&page,&eraseBlk)) return 1;
        FLASH_Unlock();
        //FLASH_PrefetchBufferCmd(DISABLE);
        //-----------------------------------------------------------
        #ifndef USE_SDRAM
                MCU_Flash_Earse(SWAP_FLASH_SECTOR);                        //删除了交换快
                MCU_Flash_Program(0,LB_SWAP_FLASH_ADDR,(unsigned char *)PHY_SECTOR_ADDR[block],MAX_BLOCK_SIZES);
                p=(unsigned char *)SWAP_FLASH_ADDR;
        #else
                p=(unsigned char *)0xd0000000;
                memcpy(p,(unsigned char *)PHY_SECTOR_ADDR[block], MAX_BLOCK_SIZES);
        #endif
        MCU_Flash_Earse(eraseBlk);                                                        //删除了原数据块
        //***********************************************************
        //如何写回一个块数据  从0扇区开始到要插入的页前!
        //***********************************************************
        //如何写回一个块数据
                //***********************************************************
        //如何写回一个块数据  从0扇区开始到要插入的页前!
        n=page * MAX_SECTOR_SZIES;
        MCU_Flash_Program(0,block,p,n );
        //------------------- 写入新数据 --------------------------------------
        MCU_Flash_Program(page,block,buf, cnt * MAX_SECTOR_SZIES);
        n +=cnt * MAX_SECTOR_SZIES;
        MCU_Flash_Program(page+cnt,block,p+n, MAX_BLOCK_SIZES-n);

        //FLASH_PrefetchBufferCmd(ENABLE);
        FLASH_Lock();
        return 0;
}
//**************************************************************************************************
//写数据  4K一个扇区读取! sector=0,...n 逻辑地址!
//***********************************************************************************************
unsigned char MCU_Flash_Sector_write(unsigned int sector,unsigned char *buf,unsigned int cnt){

        while(cnt--){
                //********************************************************************
                //优化处理
                if(MCU_Optimized(sector,buf,1)) MCU_SWAP_Wirte(sector,buf,1);
                buf +=MAX_SECTOR_SZIES;
                sector++;
        }
        return 0;
}
//***********************************************************************************************
//读取数据  一个扇区读取! sector=0,...n 逻辑地址!
//***********************************************************************************************
unsigned char MCU_Flash_Sector_Read(unsigned int sector,unsigned char *buf,unsigned int cnt){
        unsigned int block,page,eraseBlk;

        while(cnt--){
                if(MCU_Get_LB_Sector(sector++,&block,&page,&eraseBlk)) return 1;
                MCU_Flash_Read(page,block,buf,MAX_SECTOR_SZIES);                                                                  //最多读取一个页的数据!
                buf +=MAX_SECTOR_SZIES;
        }
        return 0;
}
moyanming2013 回答时间:2017-7-5 11:53:05
赶紧走正道,下个STM32CubeF7,解压后在如下典型目录中即可找到你想要的:
\Projects\STM32F769I_EVAL\Examples\FLASH
QQ截图20170705115034.jpg
kylongmu 回答时间:2017-7-5 18:05:45
mon51 发表于 2017-7-5 11:00
/* Includes ------------------------------------------------------------------*/
#include "IAP_IN_MC ...

谢谢答复。
IAP_IN_MCU.h是那个环境的?
我是用CUBEMX生成的工程。
kylongmu 回答时间:2017-7-5 18:06:30
斜阳__ 发表于 2017-7-5 10:55
官方例程里有flash操作。另外建议写flash操作测试代码时加上计数标志,防止持续写flash ...

给个下载地址吧,F1的我能搞定。F7的完全不同啊。
kylongmu 回答时间:2017-7-5 18:07:10
队长shiwo 发表于 2017-7-5 09:45
flash用来存数据,选越小的扇区越好,擦除速度是问题,好像都是扇区擦除的 ...

是这个理啊,可惜程序烧写占了前面的小块。
kylongmu 回答时间:2017-7-6 00:57:59
moyanming2013 发表于 2017-7-5 11:53
赶紧走正道,下个STM32CubeF7,解压后在如下典型目录中即可找到你想要的:
\Projects\STM32F769I_EVAL\Exam ...

谢谢大侠提醒,看过说明后我死了用片山Flash存数据的心,还是外部加个QSPI的EEPROM吧,擦除一个bank才能写,看来只有IAP适合用。
斜阳 回答时间:2017-7-6 08:34:36
CubeMX中下载的hal库文件里。或者去st.com下载
队长shiwo 回答时间:2017-7-6 08:54:18
kylongmu 发表于 2017-7-5 18:07
是这个理啊,可惜程序烧写占了前面的小块。

编译的时候地址偏移啊,第一个扇区用来跳转,跳过第二个扇区,第二个存数据呗
kylongmu 回答时间:2017-7-7 22:50:03
队长shiwo 发表于 2017-7-6 08:54
编译的时候地址偏移啊,第一个扇区用来跳转,跳过第二个扇区,第二个存数据呗 ...

是个办法,不过我还是准备用QSPI 的flash了,片上flash擦除时间长,寿命次数太少。

所属标签

相似问题

关于
我们是谁
投资者关系
意法半导体可持续发展举措
创新与技术
意法半导体官网
联系我们
联系ST分支机构
寻找销售人员和分销渠道
社区
媒体中心
活动与培训
隐私策略
隐私策略
Cookies管理
行使您的权利
官方最新发布
STM32N6 AI生态系统
STM32MCU,MPU高性能GUI
ST ACEPACK电源模块
意法半导体生物传感器
STM32Cube扩展软件包
关注我们
st-img 微信公众号
st-img 手机版