在许多嵌入式系统中,它们具有 RAM 和某种类型的只读存储器,通常称为闪存(它可以多次编程而无需从印刷电路板上移除)。
简单的嵌入式应用程序将可执行和只读数据部分放在 Flash 中并在 Flash 外执行。读/写变量被放入 RAM。让我们为您的示例代码片段考虑这个模型:
char * c = "Hello World!";
在上面的语句中,变量c 存在于 RAM 中,因为变量的默认设置是读写访问。如果您指定变量是常量,它将存在于 ROM 中 {实际上,它代表 ROM 中的一个位置。}:在此处输入代码
char * const c = "Hello World!"; // A constant pointer that lives in ROM.
编译器将文字文本"Hello World!" 处理得稍微复杂一些。实际的文本存在于 ROM 中,要么在可执行区,要么在数据区;取决于译者。许多编译器会在 RAM 中分配内存并将文字复制到 RAM 中,并使变量 c 指向 RAM 中的副本。这是因为没有将文字指定为常量。
为避免将文字复制到 RAM 中,请声明指向常量数据的变量:
const char * c = "Hello World"; // A pointer to constant data.
上面的定义仍然允许指针在执行过程中指向不同的东西。如果您想在整个程序中引用文本文字的一个实例,请声明一个指向常量数据的常量指针:
const * char * const c = "Hello World!"; // A constant pointer to constant data
此技术允许可执行文件加载到 RAM(以加快执行速度)并仍然从 ROM 访问只读数据(这为真正的读/写变量释放 SRAM)。
在大多数 PC 上,所有内容都存在于非易失性内存(硬盘驱动器、BIOS 等)或 RAM 中。常用的方法是从 ROM(包括硬盘)加载程序并在 RAM 中执行。将可执行文件加载到 RAM 时,操作系统通常也会将只读数据加载到 RAM 中。只读数据可能会受到操作系统的保护,因此当应用程序写入该区域时会产生异常。