esp32-S3专题二:内存1之RAM使用

2023-11-18

esp32-S3模块内部的存储分为ROM,RAM,SPRAM,RTC内存,FLASH,种类很多,几乎可以不使用外接存储器的情况下,可以进行很多业务场景,十分有用。现在我们逐一讲解一下他们的作用和使用方法。

一、ROM

384 KB 内部 ROM,
作用:ESP32技术手册明确说明:Internal ROM 是只读存储器,不可编程。Internal ROM 中存放有一些系统底层软件的 ROM 代码(程序指令和一些只读数据)。程序无法修改,暂不讨论。
关于ROM注意的是,全局的const变量和字符串常量通常会存放在只读数据区(.rodata),有一些硬件芯片会将这个数据区放在ROM里面,但是ESP32将数据区放置在RAM,区分清楚就好。

二、RAM

种类:片内SRAM +片外PSRAM

(一)片内SRAM:

大小:512 KB
关系:片内SRAM = IRAM (192KB ) + DRAM( 328KB )

IRAM :

作用:存储关键代码。
1.中断处理程序。注册中断处理程序时使用了 ESP_INTR_FLAG_IRAM,则中断处理程序必须要放入 IRAM。
2.可将一些时序关键代码放入 IRAM,以减少从 flash 中加载代码造成的相关损失。
3.以上两点为链接器自主操作,官方也提供接口,可以通过程序来声明函数,可以将 IRAM_ATTR 宏用作属性,直接将程序存储在这部分空间。(非芯片核心开发人员不推荐使用,容易触发芯片系统安全机制)

void IRAM_ATTR gpio_isr_handler(void* arg)
{
   const static DRAM_ATTR uint8_t INDEX_DATA[] = { 45, 33, 12, 0 };
   const static char *MSG = DRAM_STR("I am a string stored in RAM");
}

函数中的字符串或常量可能没有自动放入 RAM 中,这时可以使用 DRAM_ATTR 属性进行标记,或者也可以使用链接器脚本方法将它们自动放入 RAM 中。

DRAM:

作用两个:

  1. 非常量静态数据(.data 段)和零初始化数据(.bss 段)由链接器放入内部 SRAM 作为数据存储。
    这部分空间的使用是由链接器在对项目代码编译链接时,根据程序内容自动使用。空间大小随程序内部使用情况扩张。
  2. 官方也提供接口,可以通过程序声明变量,直接使用这部分空间。可以将 __NOINIT_ATTR 宏用作属性,从而将数据放入 .noinit 部分。放入该部分的值在启动时不会被初始化,在软件重启后也会保持值不变。
__NOINIT_ATTR uint32_t noinit_data;
  1. 此区域中的剩余空间可在程序运行时用作堆,也就是内部堆
    查看内部堆大小的函数:
printf("sp_get_free_internal_heap_size = %ld\n\r", esp_get_free_internal_heap_size());

一般打印完,发现内部堆大小只有200多KB,因为实际的内部堆大小只有RAM中的DRAM中的一部分,其最主要的作用是负责程序的运行空间,例如一般创建线程时声明的任务栈大小所需的空间就是直接从内部堆里面分配出去的。创建20k大小的线程,对应的内部堆就减少20k空间。

xTaskCreate((TaskFunction_t )task,"task", 20*1024, (void* )NULL,20,  (TaskHandle_t* )&ITask_Handler);

(二)片外PSRAM:

具体大小可根据使用业务进行配置,通常:2-8M
作用:提供更多空间,方便数据的存储和使用。

配置使用:

1.开启:使能Support for external,SPI-connected RAM
2.根据实际外置的PSRAM类型来选择:Quad 或者Octal
3.选择程序申请堆的API接口:可以选择2或者3。

在这里插入图片描述
(上图为2.9.1版ESP-IDE,部分旧版编辑器将此项类型ESPS3特殊设置或者ESP系统设置里面)

选型2:使用heap_caps_malloc()申请堆,灵活配置申请。

char *data=(char *) heap_caps_malloc(1024*sizeof(char), MALLOC_CAP_DEFAULT | MALLOC_CAP_SPIRAM);

配置项的意义:

/**
 * @brief Flags to indicate the capabilities of the various memory systems
 */
#define MALLOC_CAP_EXEC             (1<<0)  ///< Memory must be able to run executable code
#define MALLOC_CAP_32BIT            (1<<1)  ///< Memory must allow for aligned 32-bit data accesses
#define MALLOC_CAP_8BIT             (1<<2)  ///< Memory must allow for 8/16/...-bit data accesses
#define MALLOC_CAP_DMA              (1<<3)  ///< Memory must be able to accessed by DMA
#define MALLOC_CAP_PID2             (1<<4)  ///< Memory must be mapped to PID2 memory space (PIDs are not currently used)
#define MALLOC_CAP_PID3             (1<<5)  ///< Memory must be mapped to PID3 memory space (PIDs are not currently used)
#define MALLOC_CAP_PID4             (1<<6)  ///< Memory must be mapped to PID4 memory space (PIDs are not currently used)
#define MALLOC_CAP_PID5             (1<<7)  ///< Memory must be mapped to PID5 memory space (PIDs are not currently used)
#define MALLOC_CAP_PID6             (1<<8)  ///< Memory must be mapped to PID6 memory space (PIDs are not currently used)
#define MALLOC_CAP_PID7             (1<<9)  ///< Memory must be mapped to PID7 memory space (PIDs are not currently used)
#define MALLOC_CAP_SPIRAM           (1<<10) ///< Memory must be in SPI RAM
#define MALLOC_CAP_INTERNAL         (1<<11) ///< Memory must be internal; specifically it should not disappear when flash/spiram cache is switched off
#define MALLOC_CAP_DEFAULT          (1<<12) ///< Memory can be returned in a non-capability-specific memory allocation (e.g. malloc(), calloc()) call
#define MALLOC_CAP_IRAM_8BIT        (1<<13) ///< Memory must be in IRAM and allow unaligned access
#define MALLOC_CAP_RETENTION        (1<<14) ///< Memory must be able to accessed by retention DMA
#define MALLOC_CAP_RTCRAM           (1<<15) ///< Memory must be in RTC fast memory

#define MALLOC_CAP_INVALID          (1<<31) ///< Memory can't be used / list end marker

选型3:使用malloc方式申请最直接,默认使用malloc时向外部推申请空间。

 char *data=(char *)malloc(1024*sizeof(char));

另外,也可以通过API接口查看外部堆的剩余大小:

printf(".esp_get_free_heap_size = %d\n\r", esp_get_free_heap_size());

这次分享到处结束,下次分享给大家讲讲Cache、片上的flash和RTC存储器用法,觉得有帮助可以点个赞,谢谢大家。

参考:

https://docs.espressif.com/projects/esp-idf/zh_CN/latest/esp32s3/api-guides/memory-types.html#iram-ram
https://www.espressif.com.cn/sites/default/files/documentation/esp32-s3_technical_reference_manual_cn.pdf
https://blog.csdn.net/qq_41741344/article/details/116380816

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

esp32-S3专题二:内存1之RAM使用 的相关文章

随机推荐

  • Tensorflow2.0 tf.keras.Model.load_weights() 报错处理

    错误描述 保存模型 model save weights model h5 脚本重启 加载模型 model load weights model h5 模型报错 ValueError You are trying to load a wei
  • PySide2 QTableWidget常用方法

    QTableWidget 设置列宽模式 设置列宽模式为自动调整 自动拉伸列宽填充窗口 无法手动调整 self tableWidget horizontalHeader setSectionResizeMode QHeaderView Str
  • 个人sublime配色方案

    文章目录 1 效果图 2 描述文件 1 效果图 2 描述文件 color scheme Packages Color Scheme Default Monokai tmTheme font face Consolas font size 1
  • 顺序查找

    顺序查找 基本思想 1 顺序查找 线性查找 从线性表的一端向另一端逐个将记录与给定值进行比较 若相等 则查找成功 给出该记录在表中的位置 若整个表检测完仍未找到与给定值相等的记录 则查找失败 给出失败信息 例子 int SeqSearch1
  • ad10怎么挖铺的铜_跟我学丨覆铜这样操作快!准!狠

    所谓覆铜 就是将PCB上闲置的空间作为基准面 然后用固体铜填充 这些铜区又称为灌铜 覆铜的意义在于 减小地线阻抗 提高抗干扰能力 降低压降 提高电源效率 与地线相连 减小环路面积 那么如何使用立创EDA覆铜呢 一 在PCB工具对话框里面 选
  • 2021-湖湘杯final-Web

    2021 湖湘杯final Web 前言 今年湖湘报的社企组的结果就是最后只能摆烂 然后决赛那段时间正好在复习期末 然后考完了想好好的休息一段时间 打游戏打累了再来复现一下湖湘杯final的题目放松放松 vote 今年HTB的基本上算是原题
  • javax.validation.UnexpectedTypeException: HV000030: No validator could be found for constraint

    java 验证出现如下错误 javax validation UnexpectedTypeException HV000030 No validator could be found for constraint 错误原因 Java实体类中
  • 区块链的运行流程梳理记录

    目录 0 比特币交易流程 1 生成交易 2 网络传播与验证 3 交易池管理 4 交易优先级排序 5 交易手续费定价 6 共识竞争与构建区块 7 难度调整机制 8 分叉处理与主链判断 0 比特币交易流程 从交易的生命周期来看 比特币系统的交易
  • Is Usb Drive () ? DeviceIoControl, IOCTL_STORAGE_QUERY_PROPERTY

    http banderlogi blogspot com 2011 06 enum drive letters attached for usb html typedef enum STORAGE BUS TYPE BusTypeUnkno
  • Elasticsearch 相关度评分TF&IDF算法揭秘

    1 算法介绍 relevance score算法 简单来说 就是计算出 一个索引中的文本 与搜索的文本 他们之间的关联匹配程序 ElasticSearch使用的是term frequency inverse document frequen
  • 关于C++中cout.precision()的使用以及控制输出的小数位数.

    在C 中可以使用cout precison val 来控制浮点数的输出精度 但并不是意味着仅使用cout precison val 可以控制输出结果的小数点位数 在此记录一下 就当做学习笔记 下面先做一下简单的验证 include
  • NLP学习02_最大匹配算法、UniGram LM、Spell Correction

    如果没有数据的时候 那只能通过正则或者规则来解决问题 但是有些基于概率的方法 必须有一定的数据 首先我们要对句子进行切分 使用分词 接着进行预处理 拼写纠错 stemming 将不同的单词转换到原型 停用词过滤 a an 单词顾虑 同义词等
  • win7本地服务器如何添加网站,win7 添加本地服务器地址

    win7 添加本地服务器地址 内容精选 换一换 OBS Browser 是一款用于访问和管理对象存储服务的图形化工具 支持通过配置内网DNS服务器地址的方式 使在华为云上的Windows ECS通过内网直接访问OBS 下面将介绍具体其操作流
  • java写企业员工信息管理系统

    java写企业员工信息管理系统 这一篇文章主要介绍java写的企业员工信息管理系统 功能介绍 员工登录 首页 工资信息 出差记录 请假 签到 留言 修改密码 退出登录 管理员登录 员工管理 新增员工 工资信息 出差信息 请假信息 签到信息
  • RoboMaster机甲大师:裁判系统服务器搭建助手(RMServer Aid)

    RoboMaster机甲大师 裁判系统服务器搭建助手 RMServer Aid 更新 2022 03 28 写在前面 使用教程 软件简介 软件下载 软件安装 软件使用 打开软件 首次使用 1 组建局域网 2 配置RM环境 3 启动RM服务
  • vmware 磁盘扩容

    文章目录 参考 https blog csdn net zmzdmx article details 112299741 fdisk dev sda root localhost fdisk dev sda Welcome to fdisk
  • 二. SpringCloud Alibaba Sentinel 流控

    目录 一 简单介绍 二 流控模式 直接 快速失败 关联 快速失败 三 流控效果 快速失败 WarmUp 预热 排队等待 一 简单介绍 假设当前 Sentinel 监控的服务中有两个接口 针对整个服务 或针对服务中的指定接口添加流量控制设置
  • nodejs http模块

    客户端 在网络节点中 负责消费资源的电脑 叫做客户端 服务器 负责对外提供网络资源的电脑 叫做服务器 http 模块 是node js 官方提供的 用来创建web 服务器的模块 通过http 模块提供懂得 http caeateServer
  • 自删除技术详解

    基础知识 这里首先说一下程序自删除实现的思路 程序创建一个批处理文件 并创建进程执行 然后程序结束进程 批处理所做的功能便是延时5秒后 删除指定程序然后再自删除 这样 程序自删除功能便实现了 常用的有三种 自删除 技术 1 利用window
  • esp32-S3专题二:内存1之RAM使用

    esp32 S3模块内部的存储分为ROM RAM SPRAM RTC内存 FLASH 种类很多 几乎可以不使用外接存储器的情况下 可以进行很多业务场景 十分有用 现在我们逐一讲解一下他们的作用和使用方法 一 ROM 384 KB 内部 RO