我想在unix中的tcp套接字上发送一个字符数组。
我的第一个想法是使用普通的char数组作为将通过套接字发送的结构:
typedef struct __attribute__((packed))
{
uint8_t type;
uint8_t id_index;
char char_value[STR_MSG_MAX];
} a_msg;
只是因为C char总是8位长。然而,在一些谷歌搜索后,我发现即使一个字符串总是8位长,底层表示实际上可能是一个32位整数。所以我的印象是char可能不是在消息中表示字符串的最佳方式,该消息将通过套接字从FreeBSd发送到Linux(或者如果你想要输入其他一些unix)...)。
stdint.h出现在所有现代的unix上(我希望),我的想法是,也许uint8_t或int8_t的数组可以做到这一点。
typedef struct __attribute__((packed))
{
uint8_t type;
uint8_t id_index;
uint8_t char_value[STR_MSG_MAX];
} a_msg;
或
typedef struct __attribute__((packed))
{
uint8_t type;
uint8_t id_index;
int8_t char_value[STR_MSG_MAX];
} a_msg;
但是,uint8_t是unsigned char,int8_t是signed char。标准C char既不是那个,因为我理解它的实现是未定义的。
我的问题是: 在C中表示将通过tix / ip以* nix(Linux,FreeBSD等)平台独立方式发送的字符数组(字符串)的最佳方法是什么。
答案 0 :(得分:4)
虽然char
可能超过8位宽,但它必须始终是(相等)最窄的类型。 (由于其他原因,sizeof(char)
被定义为1)。
因此,如果平台提供int8_t
,那么char
也必须恰好是8位(因为char
被单独限制为至少8位)。这意味着您也可以使用char
。
答案 1 :(得分:1)
我个人会这样做:
typedef struct __attribute__((packed))
{
uint8_t type;
uint8_t id_index;
uint8_t padding[2]; //this is to align to 32bit boundary
uint8_t char_value[STR_MSG_MAX];
} a_msg;
但它没有填充就可以工作。
在C中,char
总是8位长。所以char数组总是一个字节数组。但是字符文字'x'
是32位。这可以使用字符文字上的sizeof
运算符进行验证。您还会看到返回单个字符(例如getch
)的所有函数都返回int
。原因是我们需要一种指示文件结束EOF的方法。这只能使用8位范围之外的值来完成。
答案 2 :(得分:0)
你不能说你用c发送了什么。此信息不会传输。
您所要做的就是:
char* buffer = (char*)(&a_msg);
最安全的方法是尽可能使用无符号字符。
答案 3 :(得分:0)
我认为打包结构的想法是要走的路。我会写一些测试代码以确保它正常工作。做一个sizeof(a_msg)来查看它的大小。您应该能够判断包装是否有效而无需通过套接字发送消息。