首页 > 解决方案 > RISC-V 是否更喜欢对 8 位操作数进行符号扩展?

问题描述

在 64 位 RISC-V 上,当将 32 位操作数加载到寄存器中时,需要决定是符号扩展还是零扩展到 64 位,而架构决定是更喜欢前者,大概因为 C 系列语言中最常见的int类型是有符号的 32 位整数。所以符号扩展比零扩展略快。

8位操作数也一样吗?换句话说,signed char比 更有效unsigned char吗?

标签: riscv

解决方案


如果您要将大量 8 位值扩大到wchar_t,unsigned char是您想要的,因为这是一个无操作而不是位掩码。如果您的char格式是 UTF-8,您还希望能够在班次中使用无符号数学。如果您正在使用库函数,那么使用您的库期望的类型是最方便的。

RISC-V 架构既有LB将符号扩展的 8 位值加载到寄存器中的LBU指令,也有零扩展的指令。两者都同样有效。在 C 中,signed char算术运算中使用的任何值都扩展为int,并且 C 标准库函数指定扩展charint,因此这会将变量置于正确的格式中以供使用。

存储是一个截断问题,从任何整数类型转换为unsigned char都是微不足道的(位掩码为0xff)。从 an 转换unsigned char为有符号值可以在不超过两条指令中完成,无需条件或寄存器压力(SLLI将 的符号位char放入机器寄存器的符号位,然后SRLI对高位进行符号扩展)。

因此,在此架构中使用任何一种都不会产生额外的开销。API 指定有符号数量的符号扩展而不是零扩展。

顺便说一句,RV64I 在架构上并不喜欢符号扩展。那是ABI 约定,但是指令集添加了一条LWU指令,用于从内存中加载一个零扩展的 32 位值,以及一个ADDIW可以对零扩展的 32 位结果进行符号扩展的指令。ADDIB( 8 位或ADDIH16 位数量没有对应关系。)


推荐阅读