2012-11-11 16 views
6

jestem zdezorientowany tego argumentu do funkcji, która jest zdefiniowana jakoargument do funkcji

int bind(int s, const struct sockaddr *name, int namelen) 

i nazywany jako

bind(sd, (struct sockaddr_in *) &addr, length); 

jestem w stanie zinterpretować co struct sockaddr_in * oznacza tutaj.

Czy ta praca: bind (sd, &addr, length);?

+0

Połączenie wywołałoby ostrzeżenie. – alk

+0

ok, w jaki sposób unika się go 'struct sockaddr_in *'? Nigdy wcześniej nie słyszałem takich argumentów, więc nie mam pojęcia, co dokładnie robi. – pushgr8

+1

'struct sockaddr_in *' wywołuje ostrzeżenie. Powinien to być "struct sockaddr *". – alk

Odpowiedz

3

To powinien być nazywany tak:

bind (sd, (struct sockaddr *) &addr, length); 

Jak, dlaczego, to jest droga C robi polymorphism, jeśli spojrzeć na definicjach tych struktur:

struct sockaddr { 
    unsigned short sa_family; // address family, AF_xxx 
    char    sa_data[14]; // 14 bytes of protocol address 
}; 

// IPv4 AF_INET sockets: 
struct sockaddr_in { 
    short   sin_family; // e.g. AF_INET, AF_INET6 
    unsigned short sin_port;  // e.g. htons(3490) 
    struct in_addr sin_addr;  // see struct in_addr, below 
    char    sin_zero[8]; // zero this if you want to 
}; 

// IPv6 AF_INET6 sockets: 
struct sockaddr_in6 { 
    u_int16_t  sin6_family; // address family, AF_INET6 
    u_int16_t  sin6_port;  // port number, Network Byte Order 
    u_int32_t  sin6_flowinfo; // IPv6 flow information 
    struct in6_addr sin6_addr;  // IPv6 address 
    u_int32_t  sin6_scope_id; // Scope ID 
}; 

Wszyscy dziel się tym samym pierwszym członkiem, sa_family po przekazaniu wskaźnika do jednej z tych struktur do bind() po raz pierwszy oddałeś go do struct sockaddr *, a wewnątrz funkcji sa_family jest używany do określenia którą strukturę przekazałeś i odrzuciłeś do prawej, zamiast jednej funkcji dla każdej struktury masz jedną funkcję, która akceptuje sockaddr*.

Innym sposobem, aby spojrzeć na to z perspektywy OOP, wyobrazić sobie, że sockaddr jest klasą bazową dla sockaddr_in i i przechodzącą wskaźnik do sockaddr jest podobna do odlewania do rodzaju podłoża i wywołanie funkcji rodzajowe. mam nadzieję, że to wyjaśni.

+0

to było opisowe, rozumiałem potrzebę rozdawania odmian tutaj, dziękuję. 'bind człowiek' przedstawiony tylko przykład, ale nie mogłem znaleźć definicji struktury. – pushgr8

+0

@ pushgr8 nie ma za co :) – iabdalkader

2

Z wyjątkiem wskaźników void, konwersja ze wskaźnika na T na wskaźnik na U powinna być jawna.

bind (sd, (struct sockaddr *) &addr, length); 
1

To zależy od tego, co jest addr.

Jeśli nie jest to adres z tej samej struktury to trzeba go typecast, Inne mądry otrzymasz ostrzeżenie, że niejawny typecast z <type of addr> do const struct sockaddr*

Aby zobaczyć wszystkie komunikaty ostrzegawcze podane przez kompilator w kompilacji dowolnego programu . zażyciem (dla kompilatora gcc ostrzeżenia):

gcc -Wall <test.c> -o <test>

To najlepsza praktyka dla programistów.

Powiązane problemy