10

如果我理解正确,0x10c 的DCPU - 16 规范描述了一个 16 位地址空间,其中每个偏移量寻址一个 16 位字,而不是大多数其他内存架构中的一个字节。这会产生一些奇怪的后果,例如,我想,并且都会返回。sizeof(char)sizeof(short)1

在这些不同的内存寻址方案之间保持 C 代码可移植性是否可行?要记住什么问题?

编辑:也许我应该举一个更具体的例子。假设您有一些处理字节流的网络代码。您是否通过在每个地址仅放置一个字节来丢弃一半的内存以便代码可以保持不变,或者您是否使用位移来概括所有内容以处理每个偏移量的 N 个字节?

edit2:答案似乎集中在数据类型大小的问题上,这不是重点——我什至不应该提到它。问题是如何应对失去使用指针寻址内存中任何字节的能力。期望代码对此不可知是否合理?

4

4 回答 4

9

这是完全可行的。粗略地说,C 的基本整数数据类型具有支持的大小:

sizeof (char) <= sizeof (short) <= sizeof (int) <= sizeof (long)

The above is not exactly what the spec says, but it's close.

As pointed out by awoodland in a comment, you'd also expect a C compiler for the DCPU-16 to have CHAR_BIT == 16.

Bonus for not assuming that the DCPU-16 would have sizeof (char) == 2, that's a common fallacy.

于 2012-04-11T14:43:20.400 回答
6

当您说“失去寻址字节的能力”时,我假设您的意思是“位八位字节”,而不是“字符”。可移植代码应该只假设CHAR_BIT >= 8. 在实践中,没有字节寻址的架构通常会定义CHAR_BIT == 8,并让编译器生成访问字节的指令。

我实际上不同意答案建议:CHAR_BIT == 16作为一个不错的选择。我更喜欢:CHAR_BIT == 8,与sizeof(short) == 2. 编译器可以处理移位/屏蔽,就像它对许多 RISC 架构所做的那样,在这种情况下进行字节访问。

我想 Notch 会进一步修改和澄清 DCPU-16 规范;已经有中断机制的请求和进一步的说明。这是游戏的美学背景,所以我怀疑很快就会有官方的 ABI 规范。也就是说,有人会努力的!

编辑:

考虑一个 C 中的数组char。编译器在每个本机 16 位wordDCPU 内存中打包 2 个字节。因此,如果我们访问第 10 个元素(索引9),则获取单词 # [9 / 2] = 4,并提取字节 # [9 % 2] = 1。

设“X”为数组的起始地址,“I”为索引:

SET J, I
SHR J, 1    ; J = I / 2
ADD J, X    ; J holds word address
SET A, [J]  ; A holds word
AND I, 0x1  ; I = I % 2 {0 or 1}
MUL I, 8    ; I = {0 or 8} ; could use: SHL I, 3
SHR A, I    ; right shift by I bits for hi or lo byte.

寄存器A保存“字节” - 它是一个 16 位寄存器,因此可以忽略上半部分。或者,上半部分可以归零:

AND A, 0xff ; mask lo byte.

这不是优化的,但它传达了这个想法。

于 2012-04-11T19:58:20.547 回答
0

平等是这样的:

1 == sizeof(char) <= sizeof(short) <= sizeof(int) <= sizeof(long)

short类型可以是,1事实上,您甚至可能希望int类型1太实际(我没有阅读规范,但我假设普通数据类型是 16 位)。这些东西是由编译器定义的。

为了实用,编译器可能希望设置long为大于int即使它需要编译器做一些额外的工作(比如在软件中实现加法/乘法等)。

这不是内存寻址问题,而是粒度问题。

于 2012-04-11T18:00:43.757 回答
0

是的,完全可以移植 C 代码

在数据传输方面,建议将位打包(或使用压缩)或以 16 位字节发送

因为 CPU 几乎完全只与(游戏)内部设备进行通信,这些设备也可能都是 16 位的,这应该不是真正的问题

顺便说一句,我同意CHAR_BIT应该是 16,因为(IIRC)每个字符都必须是可寻址的,因此制作CHAR_BIT ==8sizeof(char*) ==2需要这将使其他一切变得过于复杂

于 2012-04-11T20:08:44.407 回答