嵌入式系统 ---> 程序存储器和数据存储器

任何嵌入式系统都将包括一个存储单元来存储和检索数字信息。这包括构成微控制器的关键元素之一的程序存储器和数据存储器。

程序存储器(程序内存)用于永久保存正在执行的程序,而数据存储器(数据内存)用于临时存储和保存中间结果和变量。

        程序存储器 

程序内存:程序内存用于执行永久保存程序或更常称为“程序代码”,它分为两个部分,启动程序和应用程序。

一些微控制器保持可配置部分的大小。
这两个部分可以具有不同级别的保护属性
根据编译器中的设置,程序存储器也可用于存储常量变量。
一些微控制器会将引导部分保存在物理上独立的只读存储器中,通常是 ROM,而将程序存储器的其余部分保存在片上闪存中。

数据内存:数据存储器是在程序执行期间用于存储变量的易失性存储器,一旦微控制器的电源丢失,就会被删除。数据内存通常会包括以下内容:

通用寄存器

        数据存储器包括几个通用的寄存器,证明了最短(最快)的访问时间,通常允许单周期算术逻辑单元(ALU)操作。

I/O内存

        I/O内存空间包含CPU外围功能的地址,如控制寄存器、SPI和其他I/O函数。

扩展I/O内存(MCU依赖)

        由于复杂性,一些具有更多外设的微控制器包括扩展的I/O内存,它占据了内部SRAM的一部分。扩展的I/O内存依赖于MCU。在存储I/O和扩展I/O内存中存储数据通常只由编译器处理。用户不能使用此内存空间来存储其数据。

内部RAM

        内部SRAM(数据内存)用于临时存储和保存中间结果和变量。

因此,程序内存和数据内存在构建程序中都有不同的作用。程序内存必须是一个非易失性内存(通常是芯片上或芯片外闪存),即使关闭电源也能存储信息。相反,数据存储器并不保存信息,因为它需要电源来保持存储在芯片中的信息。

        个人计算机中的程序存储器正是以这种方式实现的。 它具有包含基本输入/输出系统 (BIOS) 的程序存储器的固定部分。 这些程序永久保存在安装在主处理器板上的只读存储设备中。 以这种方式保存在 ROM 中的程序因其永久性质而被称为固件

         当今 PC 中使用的 BIOS ROM 的典型大小为 2 兆位 (MB),即 256 KB。  PC 中程序存储的大部分是由动态随机存取读/写存储设备 (DRAM) 构建的。 它们可以安装在主处理器板上,也可以安装在附加内存模块或板上。 使用 DRAM 可以读取或写入这部分程序存储内存。 它的目的再次是存储要执行的程序,但在这种情况下,它们仅在需要时才加载到内存中。 程序通常从二级存储设备(HDD或Flash)中读入,存储在内存的程序存储部分,然后运行。 当程序终止时,它所在的程序内存部分将返回给操作系统以供重用。

        此外,如果关闭电源,基于程序存储内存部分的内容就会丢失。由于这些程序的临时性性质,它们被称为软件。

        在PC领域,由于BIOS的小尺寸,主存储的主要部分是DRAM,将用于程序存储。相比之下,在一个嵌入式系统中,如电子游戏或咖啡机,完整的程序存储存储器是通过ROM或闪存设备来实现的。

        如前所述,频繁更改的信息存储在内存子系统的数据存储部分中。 例如,要由微型计算机或微控制器处理的数据保存在主存储器的数据存储部分中。 当程序运行时,数据的值可以反复变化。 出于这个原因,数据存储存储器必须使用 RAM 来实现 在 PC 中,数据不会自动驻留在内存的数据存储部分。 就像软件一样,它是从辅助存储设备(例如硬盘)中读入内存的。 然后可以将 PC DRAM 的任何部分分配给数据存储。这一切都由操作系统软件管理。 当程序运行时,数据在 DRAM 中被修改并将它们写入磁盘以保存新值。 数据形式不必是数字; 它们也可以是字母数字字符、代码和图形模式。 例如,在运行文字处理器应用程序时,数据是字母数字和图形信息。

<think>好的,用户遇到了一个编译错误:error: implicit declaration of function 'ip_fragment',并且使用的是2.6.36内核版本。我需要帮他找到原因解决办法。 首先,根据之前的引用资料,像这样的隐式声明错误通常是因为函数没有在头文件中声明,或者相关头文件没有被正确包含。例如,引用5中提到copy_from_user的问题是因为缺少头文件,引用3中的esp_blufi_close错误同样是因为头文件缺失。所以,首先应该检查是否包含了正确的头文件。 接下来,我需要确认ip_fragment函数在2.6.36内核中的情况。可能需要查阅内核源码或文档。记得用户提到的是2.6.36版本,这个版本相对较旧,可能存在函数变动的情况。例如,引用1中的dma_alloc_writecombine在内核新版本中被移除,导致错误。因此,可能ip_fragment在2.6.36中已经被移除或改名了。 搜索一下内核源码,看看ip_fragment是否存在于2.6.36版本中。如果不存在,那么可能该函数已经被其他函数替代,或者需要特定的配置选项开启。例如,某些函数可能需要启用特定的内核配置,如CONFIG_NETFILTER等。 另外,检查用户代码中是否包含了正确的头文件。ip_fragment可能在linux/ip.h或相关的网络头文件中声明。如果用户没有包含这些头文件,就会导致隐式声明错误。 还有一种可能性是,该函数在内核版本升级后变成了静态函数,无法被外部模块调用。如果是这样,用户可能需要寻找替代的函数,或者修改代码以适应新版本的内核API。 总结可能的原因:1. 缺少头文件;2. 函数在内核版本中被移除或改名;3. 需要启用特定的内核配置;4. 函数作用域变化。 解决方案方面,首先建议用户检查并添加必要的头文件,如#include <linux/ip.h>。如果头文件存在但函数不存在,可能需要查看内核变更日志,确认ip_fragment在2.6.36中的状态。此外,查找替代函数,如ip_local_out或其他分片相关函数,并调整代码实现。 另外,参考引用25中的解决方法,添加正确的头文件通常能解决隐式声明的问题。如果函数确实被移除,可能需要修改代码逻辑,使用新的API。 最后,提醒用户注意内核版本兼容性问题,建议更新代码以适应新版本的内核API,或者确认使用的内核版本与代码兼容。</think>关于Linux内核2.6.36版本中`error: implicit declaration of function 'ip_fragment'`错误的分析及解决方案如下: ### 一、错误原因分析 1. **函数声明缺失** `ip_fragment()`是内核网络协议栈中处理IP分片的函数。该错误表明编译器未找到函数的显式声明,通常由以下原因引起: - 未包含正确的头文件(例如缺少`#include <net/ip.h>`)[^1][^5] - 内核版本差异导致函数被重构或移除[^1] 2. **内核版本兼容性问题** 在2.6.36内核中,`ip_fragment()`函数已不再作为公共API导出,其实现被封装在`ip_output.c`中且未提供外部头文件声明[^1] ### 二、解决方案 #### 方案1:添加头文件引用 ```c #include <net/ip.h> #include <linux/ip.h> ``` *注意:此方法仅适用于早期内核版本,在2.6.36内核中可能无效*[^5] #### 方案2:使用替代API ```c // 替代分片实现 int err = ip_local_out(skb); if (err == NET_XMIT_DROP) { kfree_skb(skb); } ``` *说明:使用更高级别的IP输出函数代替直接分片操作* #### 方案3:内核配置检查 确保内核配置包含: ```makefile CONFIG_NET=y CONFIG_INET=y CONFIG_IP_MULTICAST=y ``` 通过`make menuconfig`检查网络协议栈配置是否完整[^1] ### 三、版本适配建议 对于2.6.36及以上内核,推荐采用以下模式: ```c struct net *net = dev_net(skb->dev); int ret = ip_do_fragment(net, skb->sk, skb, ip_finish_output); ``` *该API需要Linux 3.0+支持,需结合内核版本进行条件编译*[^1] ### 四、验证步骤 1. 使用`grep -rn ip_fragment /usr/src/linux-headers-$(uname -r)/`查找函数声明位置 2. 检查驱动代码是否包含`MODULE_LICENSE("GPL")`声明 3. 通过`make C=1`进行额外代码检查
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值