43_读写内部Flash实验

news2024/12/24 2:13:34

目录

STM32的内部FLASH简介

内部FLASH的构成

主存储器

系统存储区

对内部FLASH的写入过程

解锁

擦除扇区

写入数据

操作内部FLASH的库函数

FLASH解锁、上锁函数

设置操作位数及擦除扇区

写入数据

实验源码


STM32的内部FLASH简介

在STM32芯片内部有一个FLASH(nor Flash)存储器,它主要用于存储代码,我们在电脑上编写好应用程序后,使用下载器把编译后的代码文件烧录到该内部FLASH中,由于FLASH存储器的内容在掉电后不会丢失,芯片重新上电复位后,内核可从内部FLASH中加载代码并运行:

除了使用外部的工具(如下载器)读写内部FLASH外, STM32芯片在运行的时候,也能对自身的内部FLASH进行读写,因此,若内部FLASH存储了应用程序后还有剩余的空间,我们可以把它像外部SPI-FLASH那样利用起来,存储一些程序运行时产生的需要掉电保存的数据。由于访问内部FLASH的速度要比外部的SPI-FLASH快得多,所以在紧急状态下常常会使用内部FLASH存储关键记录;为了防止应用程序被抄袭,有的应用会禁止读写内部FLASH中的内容,或者在第一次运行时计算加密信息并记录到某些区域,然后删除自身的部分加密代码,这些应用都涉及到内部FLASH的操作。

STM32的内部FLASH包含主存储器、系统存储器以及选项字节区域,它们的地址分布及大小如下: 

内部FLASH的构成

主存储器

般我们说STM32内部FLASH的时候,都是指这个主存储器区域,它是存储用户应用程序的空间,芯片型号说明中的256K FLASH、512K FLASH都是指这个区域的大小。

主存储器分为256页,每页大小为2KB,共512KB。这个分页的概念,实质就是FLASH存储器的扇区,与其它FLASH一样,在写入数据前,要先按页(扇区)擦除。

注意上表中的主存储器是本实验板使用的STM32ZET6型号芯片的参数,即STM32F1大容量产品。若使用超大容量、中容量或小容量产品,它们主存储器的页数量、页大小均有不同,使用的时候要注意区分。

系统存储区

系统存储区是用户不能访问的区域,它在芯片出厂时已经固化了启动代码,它负责实现串口、USB以及CAN等ISP烧录功能。

选项字节

选项字节用于配置FLASH的读写保护、待机/停机复位、软件/硬件看门狗等功能,这部分共16字节。可以通过修改FLASH的选项控制寄存器修改。

对内部FLASH的写入过程

解锁

由于内部FLASH空间主要存储的是应用程序,是非常关键的数据,为了防止误操作修改了这些内容,芯片复位后默认会结FLASH上锁,这个时候不允许设置FLASH的控制寄存器,并且不能对修改FLASH中的内容。

所以对FLASH写入数据前,需要先给它解锁。解锁的操作步骤如下:

往Flash密钥寄存器 FLASH_KEYR中写入KEY1 = 0x45670123

再往Flash密钥寄存器FLASH KEYR中写入KEY2 = 0xCDEF89AB

擦除扇区

在写入新的数据前,需要先擦除存储区域,STM32提供了扇区擦除指令和整个FLASH擦除(批量擦除)的指令,批量擦除指令仅针对主存储区。扇区擦除的过程如下:

检查FLASH_SR寄存器中的“忙碌寄存器位BSY”,以确认当前未执行任何Flash操作;

在FLASH_CR寄存器中,将“激活页擦除寄存器位PER”置1,

用FLASH_AR寄存器选择要擦除的页;

将FLASH_CR寄存器中的“开始擦除寄存器位STRT”置1,开始擦除;

等待BSY位被清零时,表示擦除完成

写入数据

擦除完毕后即可写入数据,写入数据的过程并不是仅仅使用指针向地址赋值,赋值前还还需要配置一系列的寄存器,步骤如下:

检查FLASH_SR 中的BSY位,以确认当前未执行任何其它的内部Flash操作;

将FLASH_CR寄存器中的“激活编程寄存器位PG”置1;

向指定的FLASH存储器地址执行数据写入操作,每次只能以16位的方式写入;

等待BSY位被清零时,表示写入完成

操作内部FLASH的库函数

为简化编程, STM32标准库提供了一些库函数,它们封装了对内部FLASH写入数据操作寄存器的过程。

FLASH解锁、上锁函数

#define FLASH KEY1  ((uint32_t) 0x45670123)
#define FLASH KEY2  ((uint32 t) 0xCDEF89AB)

/** @brief Unlocks the FLASH control register access
* @param None
*@retval Nonevoid 
*/
Void FLASH_Unlock (void)
{
if ((FLASH->CR & FLASH_CR_LOCK) != RESET)
{
 /* Authorize the FLASH Registers access */ 
FLASH->KEYR = FLASH KEY1;
FLASH->KEYR 	= FLASH KEY2;
} 
}

/** @brief Locks the FLASH control register access
*@param None
*@retval Nonevoid 
*/
Void FLASH_Lock (void)
{
/* Set the LOCK Bit to lock the FLASH Registers access */
 	FLASH->CR |= FLASH CR LOCK;

}

解锁的时候,它对FLASH KEYR寄存器写入两个解锁参数,上锁的时候,对FLASH_CR寄存器的FLASH_CR_LOCK。位置1。

设置操作位数及擦除扇区

解锁后擦除扇区时可调用FLASH_EraseSector完成:

/**@brief 擦除指定的页
*@param Page_Address:要擦除的页地址,
*@retval FLASH Status:
*可能的返回值: FLASH_BUSY, FLASH_ERROR_PG,
*FLASH_ERROR_WRP, FLASH_COMPLETE or FLASH TIMEOUT.
*/
FLASH_Status FLASH_ErasePage
{
(uint32_t Page_Address)FLASH_Status status FLASH_COMPLETE;
/*检查参数*/
assert param (IS FLASH ADDRESS (Page Address));
/*...此处省略XL超大容量花片的控制部分*/
/*等待上一次操作完成*/
status = FLASH_waitForLastOperation (EraseTimeout)

if (status == FLASH_COMPLETE) 
{
/*若上次操作完成,则开始页擦除*/
FLASH->CR |= CR PER_Set;
FLASH->AR = Page_Address;
FLASH->CRI= CR_STRT_Set;
/*等待操作完成*/
status = FLASH_WaitForLastOperation (EraseTimeout);

/*复位PER位*/
FLASH->CR 6= CR PER Reset;
}
/*返回擦除结果*/
return status;

} 

写入数据

对内部FLASH写入数据不像对SDRAM操作那样直接指针操作就完成了,还要设置一系列的寄存器,利用FLASH_ProgramWord和FLASH_ProgramHalfWord函数可按字、半字节单位写入数据:

/**@brief 向指定的地址写入一个字的数据(32位)
*eparam Address:要写入的地址
*@param Data:要写入的数据
*@retval FLASH Status:
可能的返回值: FLASH_ERROR_PG,
FLASH_ERROR_WRP, FLASH_COMPLETE or FLASH_TIMEOUT.
*/
FLASH_Status FLASH_ProgramWord (uint32_t Address, uint32_t Data)
{
FLASH_Status status = FLASH_COMPLETE;
IO uint32_t tmp = 0;
/*检查参数*/
Assert_param (IS FLASH ADDRESS (Address));

/*此处省略XL超大容量芯片的控制部分*/
/* Wait for last operation to be completed */
status = FLASH_WaitForLastOperation (ProgramTimeout);
if (status FLASH COMPLETE)
{
/*若上次操作完成,则开始页入低16位的数据(输入参数的第1部分) */
FLASH->CR | CR_PG_Set;
*(IO uint16_t*) Address = (uint16_t) Data;
/*等待上一次操作完成*/
status = FLASH WaitForLastOperation (ProgramTimeout);
if (status == FLASH_COMPLETE) 
{
/*若上次操作完成,则开始页入高16位的数据(输入参数的第2部分) */
tmp = Address + 2;
*(IO uint16_t*) tmp Data >> 16;
/*等待操作完成*/
status = FLASH_waitForLastOperation (ProgramTimeout);
/*复位PG位*/
FLASH->CR & CR PG Reset;
}else
{
/*复位PG位*/
 FLASH->CR &= CR_PG Reset;
}

}
/*返回写入结果*/
return status;

}

从函数代码可了解到,使用指针进行赋值操作前设置了PG寄存器位,在赋值操作后,调用了FLASH_WaitForLastOperation数等待写操作完毕。HalfWord和Byte操作宽度的函数执行过程类似。

实验源码

/**
  ******************************************************************************
  * @file           : user_mian.h
  * @brief          : V1.00
  ******************************************************************************
  * @attention
  *
  ******************************************************************************
  */

/* Include 包含---------------------------------------------------------------*/
#include "stm32f10x.h"
#include <stdbool.h>
#include "user_gpio.h"
#include "user_delay.h"
#include "user_rcc_config.h"
#include "user_uart.h"


/* Typedef 类型----------------------------------------------------------------*/
/* Define  定义----------------------------------------------------------------*/
/* Macro   宏------------------------------------------------------------------*/
/* Variables 变量--------------------------------------------------------------*/	 
/* Constants 常量--------------------------------------------------------------*/
/* Function  函数--------------------------------------------------------------*/


 int main(void)
 {	

	 uint32_t *p;
	/*配置系统中断分组为2位抢占2位响应*/
	 NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
	 /*延时函数初始化*/
	 delay_init();
	/*RCC配置*/
	 Rcc_config();
	/*GPIO初始化*/ 
	 Gpio_Init();
	/*USART1初始化*/
	 Uart1_Init(9600);
	 /*解锁Flash*/
	 FLASH_Unlock();
	 /*擦除指定的页 第10页*/
	 /*0x8000000是基地址1k等于1024一页是2k*/
	 FLASH_ErasePage(0x8000000+2*1024*10);
	 /*写入数据*/
	 FLASH_ProgramWord(0x8000000+2*1024*10,0x1234567);
	 /*提示语句*/
	 printf("写入完成\r\n");
	 /*上锁Flash*/
	 FLASH_Lock();	 
	 /*指向写入的数据地址*/
	 p = (uint32_t *)(0x8000000+2*1024*10);
	 /*读出数据*/
	 printf("读取的内容为:0x%x\r\n",*p);

	/*死循环*/ 
	 while(1){

	}
		

}
 
 /************************************************************** END OF FILE ****/

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/99807.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

vTESTstudio入门到精通 - vTESTstudio工具栏介绍_ Traceability Documentation Environment

由于Traceability & Documentation和Environment的两块内容较少&#xff0c;所以就合并起来介绍&#xff0c;单独的功能介绍略少&#xff0c;就不分开了&#xff0c;vTESTstudio工具栏介绍这块内容主要也是给大家做个普及&#xff0c;大家也是主要做个了解&#xff0c;方便…

可信启动、安全启动:SGX、TrustZone、SecureEnclave

最近在公众号上看到了一篇文章&#xff0c;算是又丰富了自己的安全方面的眼界。 最近看公众号取代了小视频、知乎这些东西。以前是真的不喜欢碎片化的东西&#xff0c;看什么学什么总是要找到书籍。但是这样的做法太过的极端&#xff0c;因为有时候有些事是两面性的。比如像安全…

SD nand与SD卡 SPI模式驱动

SD nand 与 SD卡的SPI模式驱动 文章目录SD nand 与 SD卡的SPI模式驱动1. 概述2. SPI接口模式与SD接口模式区别2.1 接口模式区别2.2 硬件引脚2.3 注意事项3. SD接口协议3.1 命令3.1.1 命令格式3.1.2 命令类型3.2 响应3.2.1 响应格式4. SD nand&#xff08;SD卡&#xff09;结构描…

小程序01/ 小程序 模板语法—条件渲染方式、小程序 模板语法-列表循环渲染方式

模板语法—条件渲染方式 1.wx:if 语法: 单分支: wx:if" 条件 " 双分支: wx:else 多分支: wx:elif" 条件 " 作用: 根据条件渲染 如果条件不满足 则该元素不会添加到DOM数 注意: wx:else前面必须要有 wx:if 或 wx:elif 2.hidden 语法: hidden&qu…

Vue Router安装与基本使用

Vue Router安装与基本使用(入门使用) 一、安装 npm install vue-router4在package.json 会配置一行 “vue-router”: “^4.1.6” 二、基本使用 2.1、新建路由器 新建 router文件夹 1个index.js文件 //1.定义路由组件 import Home from ../views/Home.vue import About from ..…

[附源码]Python计算机毕业设计Django学生社团信息管理系统

项目运行 环境配置&#xff1a; Pychram社区版 python3.7.7 Mysql5.7 HBuilderXlist pipNavicat11Djangonodejs。 项目技术&#xff1a; django python Vue 等等组成&#xff0c;B/S模式 pychram管理等等。 环境需要 1.运行环境&#xff1a;最好是python3.7.7&#xff0c;…

QtCreator同时运行多个程序

更多精彩内容&#x1f449;个人内容分类汇总 &#x1f448;&#x1f449;Qt开发经验 &#x1f448; QtCreator同时运行多个程序 在Windows下QtCreator默认只能运行一个程序&#xff0c;再次编译运行就会自动关闭之前运行的程序&#xff1b; 有时候我们想运行多个程序时&#x…

【电力系统】考虑储能优化的微网能量管理双层模型附matlab代码

​✅作者简介&#xff1a;热爱科研的Matlab仿真开发者&#xff0c;修心和技术同步精进&#xff0c;matlab项目合作可私信。 &#x1f34e;个人主页&#xff1a;Matlab科研工作室 &#x1f34a;个人信条&#xff1a;格物致知。 更多Matlab仿真内容点击&#x1f447; 智能优化算法…

一篇文章带你了解HBase、Zookeeper的安装部署

第 2 章 HBase 快速入门2.1 HBase 安装部署2.1.1 Zookeeper 正常部署2.1.2 Hadoop 正常部署2.1.3 HBase 的解压2.1.4 HBase 的配置文件2.1.5 HBase 远程发送到其他集群2.1.6 HBase 服务的启动2.1.7 查看 HBase 页面2.1.8 高可用&#xff08;可选&#xff09;2.2 HBase Shell 操…

「地表最强」C++核心编程(四)类和对象—对象初始化和清理

环境&#xff1a; 编译器&#xff1a;CLion2021.3&#xff1b;操作系统&#xff1a;macOS Ventura 13.0.1 文章目录一、构造函数和析构函数1.1 构造函数1.2 析构函数1.3 示例二、构造函数的分类及调用1.1 构造函数的分类1.2 构造函数的调用三、拷贝构造函数调用时机3.1 调用时机…

黑*头条_第1章_环境搭建、SpringCloud微服务(注册发现、服务调用、网关)(新版)

黑*头条_第1章_环境搭建、SpringCloud微服务(注册发现、服务调用、网关)&#xff08;新版&#xff09; 文章目录黑*头条_第1章_环境搭建、SpringCloud微服务(注册发现、服务调用、网关)&#xff08;新版&#xff09;1)课程对比2)项目概述2.1)能让你收获什么2.2)项目课程大纲2.3…

计算机毕业设计——基于HTML仿淘宝电商项目的设计与实现管理系统论文源码(21页)

常见网页设计作业题材有 个人、 美食、 公司、 学校、 旅游、 电商、 宠物、 电器、 茶叶、 家居、 酒店、 舞蹈、 动漫、 服装、 体育、 化妆品、 物流、 环保、 书籍、 婚纱、 游戏、 节日、 戒烟、 电影、 摄影、 文化、 家乡、 鲜花、 礼品、 汽车、 其他等网页设计题目, A…

毕业设计 stm32便携用电功率统计系统 -物联网 嵌入式 单片机

文章目录0 前言1 简介2 主要器件3 实现效果4 设计原理4.1 降压电路4.2 接口部分4.3 主控4.4 OLED模块5 部分核心代码5 最后0 前言 &#x1f525; 这两年开始毕业设计和毕业答辩的要求和难度不断提升&#xff0c;传统的毕设题目缺少创新和亮点&#xff0c;往往达不到毕业答辩的…

小黑被劝退了,生活学习依然继续的leetcode之旅:572. 另一棵树的子树

小黑代码 # Definition for a binary tree node. # class TreeNode: # def __init__(self, val0, leftNone, rightNone): # self.val val # self.left left # self.right right class Solution:def isSubtree(self, root: Optional[TreeNode],…

PyTorch~cpp_extension

还是pytorch哈~~ 结合 Python 与 C 各自的优点&#xff0c;在 PyTorch 中加入 C / CUDA的扩展&#xff0c;详细解释C/CUDA 算子实现和调用全流程 代码来源&#xff1a;MMCV, PyTorch。 https://github.com/open-mmlab/mmcv https://github.com/pytorch/pytorch 注&#xff1a…

python 编程 函数的返回值

作者简介&#xff1a;一名在校计算机学生、每天分享Python的学习经验、和学习笔记。 座右铭&#xff1a;低头赶路&#xff0c;敬事如仪 个人主页&#xff1a;网络豆的主页​​​​​​ 目录 前言 一.函数 1.函数的返回值介绍 2.函数的返回值定义 例子&#xff1a; 3.函…

【图像去噪】均值+中值滤波图像去噪(含PNSR)【含GUI Matlab源码 372期】

⛄一、图像去噪及滤波简介 1 图像去噪 1.1 图像噪声定义 噪声是干扰图像视觉效果的重要因素&#xff0c;图像去噪是指减少图像中噪声的过程。噪声分类有三种&#xff1a;加性噪声&#xff0c;乘性噪声和量化噪声。我们用f(x,y&#xff09;表示图像&#xff0c;g(x,y&#xff0…

面试题:进程 线程 协程

进程&#xff08;Process&#xff09;是计算机中的程序关于某数据集合上的一次运行活动&#xff0c;是系统进行资源分配和调度的基本单位 通俗的讲&#xff1a;进程可以理解为我们在电脑上正在运行的一个个应用&#xff0c;例如&#xff1a;QQ&#xff0c;微信&#xff0c;LOL…

数据结构---寻找一个整数所有数字全排列的下一个数

寻找一个整数所有数字全排列的下一个数储备知识第一步第二步第三步JAVA实现给出一个正整数&#xff0c;找出这个正整数所有数字全排列的下一个数。说通俗点就是在一个整数所包含数字的全部组合中&#xff0c;找到一个大于且仅大于原数的新整数。 例子&#xff1a; 如果输入123…

【翻译】GPT-3是如何工作的

前排提示 这是我补充的内容&#xff0c;仅代表个人观点&#xff0c;和作者本人无关。 主要是意译我的补充&#xff0c;想看原文表达的拖到最底下有链接。 原文翻译 在科技界我们可以看到很多关于GPT-3的新闻。大型语言模型&#xff08;比如GPT-3&#xff09;已经展示出让我们惊…