在 C 中使用远指针时更改代码大小



我在一家软件公司的部门工作,主要从事汽车网络设计。我们主要用 C 语言编写网络协议栈。最近,我接到了一个需要使用飞思卡尔HC12控制器的项目。最初编写的协议栈支持使用无银行型 RAM 以及银行型和无银行型闪存。在分配给我的项目中,客户需要使用银行 RAM 而不是未银行的 RAM(原因我不知道)。当我致力于这个项目的开发时,我意识到我可以使用远指针来访问(读/写)银行RAM。

我的问题是:当我使用 far 指针访问银行 RAM 时,我的库代码大小增加了多达 10KB。这正常吗?在我正在使用的编译器(codewarrior)的参考手册中,提到远指针的大小为3个字节,而不是大小为2字节的普通指针。这 1 个额外的字节真的会导致代码大小如此大的差异吗?有没有其他方法不包括使用远指针,我仍然可以访问银行 RAM?

我的疑问的任何有用答案将不胜感激。

最初,HCS12 上的内存仅用于闪存中的程序代码,在这种情况下,您不会注意到程序大小的巨大差异。唯一的区别是子例程调用需要使用银行内存指令(CALL,RTC而不是JMP,RTS),每个函数调用需要多几个字节的程序内存。

后来,他们发布了同时具有银行闪存和银行RAM的设备(一些HCS12X等)。RAM显然是用于数据,而不是程序存储器。

问题是HCS12是16位CPU,因此它不能轻松处理24位数据指针。这意味着银行内存中的所有此类代码处理数据将变得相当低效:对于每次访问(通过"远"指针等),它必须设置表示 24 位地址的高 8 位的页面寄存器。一旦完成,它就可以用正常的指令将数据读/写到地址的16位部分,硬件会将其映射到正确的页面。完成此操作后,程序还必须恢复页面寄存器。

编译器很可能无法很好地优化对分页数据的访问 - 理论上,您可以设置页面寄存器,然后在需要还原之前访问该页面中的所有数据。但在编译时,编译器可能无法知道变量将分配到的确切位置。

你可以很容易地看到使用Codewarrior的反汇编器实际生成的代码。另请注意,Codewarrior 在优化方面一直相当功能失调:永远不清楚哪些优化必须显式启用,哪些是"内置"的。确保您确实启用了所有相关优化。

总体而言,请尽可能避免存放内存。您可以使用最多 64k 内存的非存储内存模型。只有当您超出该限制时,您才需要分页内存。也许这就是您的客户需要它的原因,他们可能用完了 RAM。

是的,不一定是指针大小在增长,而是处理"远"指针的代码(无论 hc12 上的指针是什么)

内核本身实际上只支持 16 位指针,这种分页有点附加功能,需要程序手动操作才能使其工作。

好消息是你现在正在分页,所以 10k 并不可怕。

相关内容

最新更新