在C中编译套接字连接代码时出现问题

时间:2011-05-29 20:23:48

标签: c sockets

struct hostent *lh               = gethostbyname(hostname);

int socketDescriptor             = socket(AF_INET,SOCK_STREAM, 0);

sockaddr_in socketInfo;

memset(&socketInfo, 0, sizeof(socketInfo));
socketInfo.sin_family            = AF_INET;
socketInfo.sin_addr.s_addr       = ((in_addr *)(lh->h_addr))->s_addr;
socketInfo.sin_port              = htons(portNumber);

connect(socketDescriptor,&socketInfo,sizeof(socketInfo));

尝试编译时,出现以下错误:

error: cannot convert ‘sockaddr_in*’ to ‘const sockaddr*’ for argument ‘2’ to ‘int connect(int, const sockaddr*, socklen_t)’

事情看起来“按书”,但我遗漏了一些东西(显然)。它是什么?

4 个答案:

答案 0 :(得分:12)

我认为你struct上遗失了sockaddr_in socketInfo。所以它应该是struct sockaddr_in socketInfo

同时将socketInfo投射到struct sockaddr *也不错。

connect(socketDescriptor,&socketInfo,sizeof(socketInfo));

应该是

connect(socketDescriptor,(struct sockaddr *) &socketInfo,sizeof(socketInfo));

答案 1 :(得分:3)

  struct addrinfo *server;
  struct addrinfo hints; 

    memset(&hints, 0, sizeof(struct addrinfo));/*set hints*/
    hints.ai_family = AF_UNSPEC;    /* Allow IPv4 or IPv6 */
    hints.ai_socktype = SOCK_STREAM; 
    hints.ai_flags = 0;
    hints.ai_protocol = 0;          /* Any protocol */

 getaddrinfo(srvname,port,&hints,&server); /*get server ip fit args*/

 sid = socket(server->ai_family, server->ai_socktype,server->ai_protocol)
 connect(sid,server->ai_addr, server->ai_addrlen)

这些是一些可行的代码管理,您可以从中开始。

这里发生的是我设置了一个包含所有英特尔的结构,而不是将它与一些更多的信息结合起来,以获得一个不错的所有指针适合结构也传递给连接。 希望有所帮助

答案 2 :(得分:1)

如果它只是const它会起作用,但显然sockaddrsockaddr_in是不同的类型。

答案 3 :(得分:1)

套接口除了非常陈旧外,还会以这种方式故意破坏。 sockaddr_*结构隐式地以sockaddr的相同成员开头,因此将它们转换为“基础”类型是安全的。 struct sockaddr也有一个sa_family成员,所以你也可以在运行时决定给出一个struct sockaddr*哪个“派生”(虽然不是真的)类型来投射它。

因此,您可以做的最小的改变就是将struct sockaddr_in*强制转换为struct sockaddr*。通常这会非常令人反感。但别担心;在这种情况下,每个人都在这样做。我甚至可能倾向于转换为void*,因为它的字符数较少,您可以将隐含转换为struct sockaddr*

然而......其他一些不相关的观点:

  1. gethostbyname可能会失败。实际上它经常发生,例如当用户键入虚假地址时。发生这种情况时,你的程序会崩溃。检查它是否返回NULL以避免这种情况。

  2. 实际上,gethostbyname已被getaddrinfo取代。用那个。它将使您获得协议独立性,这样您就不会受到IPv4的束缚。它还会返回struct sockaddr*,因此您不必进行丑陋的演员表。