2012-05-11 3 views
2

Обучение программированию сокетов, а ниже - вырезание/вставка частей ошибки.Ошибка программирования сокета TCP-соединения

FYI, я следил за this tutorial.

Undrestood gethostbyname() возвращает struct hostent

struct hostent *gethostbyname(const char *name); 

со следующим кодом.

1 #include <stdio.h> 
    2 #include <sys/types.h> 
    3 #include <sys/socket.h> 
    4 #include <netinet/in.h> 
    5 #include <stdlib.h> 
    6 #include <strings.h> 
    7 
    8 int main(int argc, char *argv[]) 
    9 { 
10  int sockfd, portno, n; 
11  struct sockaddr_in serv_addr; 
12  struct hostent *server; 
13 
14  server = gethostbyname(argv[1]); 
15 
16  /* compose serv_addr */ 
17  bzero((char *)&serv_addr, sizeof(serv_addr)); 
18  serv_addr.sin_family = AF_INET; 
19  bcopy((char *)server->h_addr, (char *)&serv_addr.sin_addr.s_addr, server->h_length); 
20  serv_addr.sin_port = htons(portno); 
21 
22  return 0; 
23 } 

У меня есть следующие НКУ ошибки/предупреждения

$gcc client2.c 
client2.c: In function ‘main’: 
client2.c:14: warning: assignment makes pointer from integer without a cast 
client2.c:19: error: dereferencing pointer to incomplete type 
client2.c:19: error: dereferencing pointer to incomplete type 

Пожалуйста, укажите мне, что я делаю не так?

+0

Превращение всех предупреждений компилятора при использовании '-Wall' помогает ... – alk

+0

Также:' gethostbyame() 'и' gethostbyaddr() 'как-то устарели. Вы можете лучше использовать 'getnameinfo()' и 'getaddrinfo()'. – alk

ответ

9

Попробуйте добавить это к вершине:

#include <netdb.h> 

Это требуется включить для gethostbyname. Если вы наберете man gethostbyname в командной строке, вы получите страницу человека, который открывается:

Screenie of "gethostbyname(3)" manpage.

страница Справочник деталь, заголовки вам необходимо включить (под СИНТАКСИСОМ).

(Хит д для выхода man.)

+0

+1.Хотя было бы неплохо разработать C, включить файлы и как вы пришли к этому 'netdb.h'. Возможно, хотя бы упомянуть «man gethostbyname» было бы хорошо ... –

+0

@ VladLazarenko: спасибо за отзыв! Добавили некоторую информацию о поиске manpage :) – Ashe

5

Примечание в bzero(3) страницы руководства:

4.3BSD. This function is deprecated (marked as LEGACY in 
    POSIX.1-2001): use memset(3) in new programs. POSIX.1-2008 
    removes the specification of bzero(). 

Вы определенно должны использовать memset(3) вместо bzero(3) - АНИ лишь немного более многословным, но это не совсем ужасно. Такая же история для bcopy(3) и memcpy(3).

memset(3) и memcpy(3) находятся в <string.h>, а не <strings.h>, поэтому измените это тоже.

Вы используете слишком много бросков в своем коде; когда прототип функции включает void *, он будет принимать любой тип указателя в качестве параметра, и компилятор будет правильно отслеживать типы. Добавление роли подскажет компилятору, что вы знаете лучше - и будет довольно часто маски действительных ошибок и предупреждений.

Также обратите внимание, что gethostbyname(3) также требует заголовок <netdb.h>.

С учетом этих изменений в месте, ваш код компилируется с меньшим количеством предупреждений:

$ CFLAGS="-Wall -Wextra" make client2 
cc -Wall -Wextra client2.c -o client2 
client2.c: In function ‘main’: 
client2.c:11:25: warning: unused variable ‘n’ [-Wunused-variable] 
client2.c:11:9: warning: unused variable ‘sockfd’ [-Wunused-variable] 
client2.c:9:14: warning: unused parameter ‘argc’ [-Wunused-parameter] 
client2.c:21:31: warning: ‘portno’ is used uninitialized in this function [-Wuninitialized] 

(Ни один из них не должно быть сюрпризом, это код выполняется хорошо на вас за то, чтобы построить код медленно ... .)

+0

+1 не используя ужасно старые функции! – Ashe

Смежные вопросы