getnameinfo指定socklen\u t

getnameinfo指定socklen\u t,c,linux,networking,posix,socklen-t,C,Linux,Networking,Posix,Socklen T,getnameinfo原型的第二个参数要求使用socklen\u t类型,但sizeof使用size\u t。那我怎么才能拿到袜子呢 原型: int getnameinfo(const struct sockaddr *restrict sa, socklen_t salen, char *restrict node, socklen_t nodelen, char *restrict service, socklen_t servicelen, int flags)

getnameinfo原型的第二个参数要求使用socklen\u t类型,但sizeof使用size\u t。那我怎么才能拿到袜子呢

原型:

int getnameinfo(const struct sockaddr *restrict sa, socklen_t salen,
       char *restrict node, socklen_t nodelen, char *restrict service,
       socklen_t servicelen, int flags);
例如:

struct sockaddr_in SIN;
memset(&SIN, 0, sizeof(SIN)); // This should also be socklen_t ?
SIN.sin_family      = AF_INET;
SIN.sin_addr.s_addr = inet_addr(IP);
SIN.sin_port        = 0;

getnameinfo((struct sockaddr *)&SIN, sizeof(SIN) /* socklen_t */, BUFFER, NI_MAXHOST, NULL, 0, 0);
这将导致编译器错误:

socklen_t VAR;
getnameinfo((struct sockaddr *)&SIN, &VAR, BUFFER, NI_MAXHOST, NULL, 0, 0);
size\u t
作为无符号整数类型;C99保证它至少是16位

socklen\u t
作为至少32位的整数类型。(编辑:它不一定是无符号的,尽管在实践中,负长度是没有意义的。)

因此,传递
size\u t
参数并让编译器隐式地将其强制转换为
socklen\u t
是没有问题的,我认为让隐式转换发生而不是添加迂腐的强制转换会使代码更清晰

最后一个例子

socklen_t VAR;
getnameinfo((struct sockaddr *)&SIN, &VAR, BUFFER, NI_MAXHOST, NULL, 0, 0);

给出一个编译器错误,因为您传递的是指向socken\u t而不是socklen\u t的指针。

您的信息已过期,socklen\u t是至少32位的整数类型(不一定是无符号的)()

(这是一个试图弄清
socklen\t
存在的根本原因的答案。)

正如其他人所指出的,它可以被认为是posixsocketsapi的
size\t
等价物,它以字节表示各种数据结构的长度。最值得注意的是
bind()
listen()
connect()
函数,其中它表示
struct sockaddr
的各种实现的长度,但并不限于此

这本书实际上解释了它是如何形成的,并且对IMHO很有启发性:

socklen\u t类型的发明是为了涵盖该领域中的各种实现。
socklen\u t
的目的是成为所有长度的类型,这些长度在尺寸上自然有界;也就是说,它们是一个缓冲区的长度,而缓冲区的大小不能明显地变大:例如网络地址、主机名、它们的字符串表示、辅助数据、控制消息和套接字选项。真正无限的大小由
size\t
表示,如
read()
write()

所有
socklen\u t
类型最初(在BSD UNIX中)都是
int
类型。在POSIX.1-2008的开发过程中,决定将所有缓冲区长度更改为
size\u t
,这从表面上看是合理的。当出现双模式32/64位系统时,这种选择不必要地使系统接口复杂化,因为在ILP32和LP64型号下,
size\u t
(带long)的大小不同。恢复到
int
可能会发生,除非某些实现已经提供了仅64位的接口。折衷是一种可以通过实现定义为任意大小的类型:
socklen\u t


sizeof
本身是否会导致问题?您是否遇到编译错误?没有问题或编译器错误,但我想如果getnameinfo要求socklen\t,我不应该通过size\t…生活中还有更糟糕的事情需要担心。我从来没有见过套接字代码会为此烦恼。我总是提供原型要求的东西。最佳实践。更重要的是,对于任何
sockaddr
类型结构,
sizeof
返回的值将始终适合
socklen\t
类型,因此转换是安全的。