C中uint8和char的转换

Conversion between uint8 and char in C

我有一个API实现对EEPROM的写操作。这是它的声明:

CYBLE_API_RESULT_T CyBle_StoreAppData (uint8 * srcBuff, const uint8 destAddr[], uint32 buffLen, uint8 isForceWrite);

当我调用此函数并将数组参数发送到已声明为 uint8 类型的 srcBuff 时,它运行良好。

问题是,我需要向它发送 char 数组指针。我在想 char 已经是一个 uint8,但是如果我发送一个 char 数组指针而不是 uint8 到那个函数,我会得到一个编译器警告。为什么我不能使用 char 而不是 uint8 ?以下是调用该函数的 2 个示例:

static const uint8      datastack_ROM[dedicatedRomSize] = {0};
uint8                   Container_ID[10];
char                    Prefix[10];

//Call the function with Container_ID which has been declared as uint8. This is working.
CyBle_StoreAppData(Container_ID,datastack_ROM,10,0);

//Call the function with Prefix which has been declared as char. This is NOT working.
CyBle_StoreAppData(Prefix,datastack_ROM,10,0);

这是第二次调用的警告:

passing char[10] to parameter of type 'uint8 *' converts between pointers to integer types with different sign.

charuint8不一样吗?

uint8_t 很可能定义为无符号字符。

char 是它自己的类型,其行为与 signed char 或 unsigned char 完全一样(注意,它们是三种不同的类型)。

在这种情况下,它的行为类似于 signed char,并且您会收到转换警告。

两种类型都是8位长。不同之处在于签名。

  • uint8 类型是无符号的。
  • char 类型应在您的案例中签名。实际上,它依赖于编译器,但大多数编译器默认将 char 类型视为有符号类型,并且可以选择在需要时将 char 类型强制为无符号类型。请参阅 C99 standard document reference §6.2.5p15:

The implementation shall define char to have the same range, representation, and behavior as either signed char or unsigned char.

CHAR_MIN, defined in limits.h, will have one of the values 0 or SCHAR_MIN, and this can be used to distinguish the two options.

uint8                   Container_ID[10];

这是一个无符号的 8 位整数,可能的值从 0255

char                    Prefix[10];

在你的例子中,一个带符号的 8 位字符,整数值从 -127+128

因为它们不是相同的符号类型,您会收到转换警告,这是您应该看到的。

charuint8 有一些共同点,这很重要:它们都是 8 位整数。现在两个问题

  • is/are this/these 8 位整数有符号还是无符号?

更重要的是

  • 这对你来说重要吗?

即你想向函数发送一个由整数组成的数组吗?对它们来说,让它们被认为是有符号的很重要吗?例如,如果函数会做类似的事情,

if (charvalue < 0) { ... 

或者如果希望函数注意字节的符号(如果可能的话);如果函数会这样做,并且符号很重要:发送 255 是肯定的,但考虑到带符号的字节,这将被解释为 -1...

但这没有意义,因为函数采用 uint8 *(实际上在函数内部,开发人员可能使用 char 来单独处理字节,并使用它们的符号,但在这种情况下拥有这样的函数签名会产生很大的误导!)

因此 E2PROM 正在处理无符号字节,您可以安全地转换给函数的指针以删除警告,

CyBle_StoreAppData((uint8 *)Prefix,datastack_ROM,10,0);

或者干脆

uint8  Prefix[10];

如果这不会导致其他 problems/warning 与您的其余代码。