Benjamin Lindqvist
Benjamin Lindqvist

Reputation: 4610

Typecasting sockaddr structures

I'm trying to learn network programming, and C in the process. I'm confused about the structures sockaddr which is a generic adress and sockaddr_in. My book has this to say:

Thus, we can fill in the fields of a sockaddr_in and then cast (a pointer to) it to a (pointer to a) sockaddr and pass it to the socket functions, which look at the sa_family field to learn the actual type, then cast back to the appropriate type.

But it doesn't seem to me that the two structs should be compatible? One has two fields,

struct sockaddr {
    sa_family_t sa_family;
    char sa_data[14];
};

The other has plenty

struct in_addr {
    uint32_t s_addr;
};

struct sockaddr_in {
    sa_family_t sin_family;
    in_port_t sin_port;
    struct in_addr sin_addr;
    char sin_zero[8];
};

They both have size 16 in memory. I guess this is why they zero-pad the sockaddr_in structure, to enable casting? I'm still confused - can casting ever be meaningful if you don't immidiately cast back? Is it always just a temporary cast, utilizing the fact that the sa_family_t field resides in the first N bits?

Upvotes: 3

Views: 630

Answers (1)

alk
alk

Reputation: 70883

You are not requested to cast the struct but a pointer to it.

The relevant info for the underlying call, that is which struct is referenced, can be pulled from the sin_family member, which is available in any case.

So in essence the cast is just around to silence the compiler, as the function called expects a pointer to struct sockaddr but in fact gets passed a pointer to a different type.

Upvotes: 1

Related Questions