我有以下代码:

long int compute_data_length(unsigned char* buf, int data_offset) {

long int len;

if(!buf)
    return -1;

switch(data_offset) {
    case 2: {
                len = (buf[2] << 8) | buf[3];
            }
            break;
    case 8: {
                len = (buf[2] << 56) |
                      (buf[3] << 48) |
                      (buf[4] << 40) |
                      (buf[5] << 32) |
                      (buf[6] << 24) |
                      (buf[7] << 16) |
                      (buf[8] <<  8) |
                      (buf[9]      );
            }
            break;
    default: len = -1; break;
}
return len;
}
编译时,会收到以下警告:math_fun.c:240:21:警告:左移计数>=类型的宽度[默认启用]长度=(buf[2]<|^math_fun.c:241:27:警告:左移计数>=类型的宽度[默认启用](buf[3]<|^math_fun.c:242:27:警告:左移计数>=类型的宽度[默认启用](buf[4]<|^math_fun.c:243:27:警告:左移计数>=类型的宽度[默认启用](buf[5]<|如何修复警告?

最佳答案

整数提升将buf[2] << 56转换为(int)buf[2] << 56[注1],但是int只有32位是完全可能的,您需要它是无符号的64位类型,这样移位才有意义。您期望unsigned long为64位,但可能不是最好包含<stdint.h>并使用uint64_t在任何情况下,都需要显式转换左移位的左操作数:

((uint64_t)buf[2] << 56) | ...
[注1]:从理论上讲,unsigned char可能与int一样宽,在这种情况下,整数升迁为unsigned int但这只发生在不寻常的架构上。

10-08 16:21