X-Git-Url: https://git.strongswan.org/?p=strongswan.git;a=blobdiff_plain;f=Source%2Fcharon%2Fnetwork%2Fhost.c;h=e09bfac751d7998fb5f910c161ef1269560f0ee6;hp=7313aedcec9036f3733eb8f3490788a80156255e;hb=3ebebc5e963afed1242192f4fa440c177daee4bc;hpb=c7314095e7141891d9cba2b48e15f1d683c7630b diff --git a/Source/charon/network/host.c b/Source/charon/network/host.c index 7313aed..e09bfac 100644 --- a/Source/charon/network/host.c +++ b/Source/charon/network/host.c @@ -49,8 +49,10 @@ struct private_host_t { /** * low-lewel structure, wich stores the address */ - sockaddr_t address; - + union { + struct sockaddr address; + struct sockaddr_in address4; + }; /** * length of address structure */ @@ -84,9 +86,8 @@ static bool is_default_route (private_host_t *this) case AF_INET: { static u_int8_t default_route[4] = {0x00,0x00,0x00,0x00}; - struct sockaddr_in *sin = (struct sockaddr_in*)&(this->address); - if (memcmp(default_route,&(sin->sin_addr.s_addr),4) == 0) + if (memcmp(default_route,&(this->address4.sin_addr.s_addr),4) == 0) { return TRUE; } @@ -110,9 +111,11 @@ static char *get_address(private_host_t *this) case AF_INET: { char *string; - struct sockaddr_in *sin = (struct sockaddr_in*)&(this->address); + /* we need to clone it, since inet_ntoa overwrites + * internal buffer on subsequent calls + */ allocator_free(this->string); - string = inet_ntoa(sin->sin_addr); + string = inet_ntoa(this->address4.sin_addr); this->string = allocator_alloc(strlen(string)+1); strcpy(this->string, string); return this->string; @@ -138,8 +141,7 @@ static chunk_t get_address_as_chunk(private_host_t *this) /* allocate 4 bytes for IPV4 address*/ address.ptr = allocator_alloc(4); address.len = 4; - struct sockaddr_in *sin = (struct sockaddr_in*)&(this->address); - memcpy(address.ptr,&(sin->sin_addr.s_addr),4); + memcpy(address.ptr,&(this->address4.sin_addr.s_addr),4); } default: { @@ -147,7 +149,27 @@ static chunk_t get_address_as_chunk(private_host_t *this) return address; } } - +} + +static xfrm_address_t get_xfrm_addr(private_host_t *this) +{ + switch (this->family) + { + case AF_INET: + { + return (xfrm_address_t)(this->address4.sin_addr.s_addr); + } + default: + { + /* todo */ + return (xfrm_address_t)(this->address4.sin_addr.s_addr); + } + } +} + +static int get_family(private_host_t *this) +{ + return this->family; } /** @@ -159,8 +181,7 @@ static u_int16_t get_port(private_host_t *this) { case AF_INET: { - struct sockaddr_in *sin = (struct sockaddr_in*)&(this->address); - return ntohs(sin->sin_port); + return ntohs(this->address4.sin_port); } default: { @@ -198,10 +219,8 @@ static bool ip_is_equal(private_host_t *this, private_host_t *other) /* IPv4 */ case AF_INET: { - struct sockaddr_in *sin1 = (struct sockaddr_in*)&(this->address); - struct sockaddr_in *sin2 = (struct sockaddr_in*)&(other->address); - if ((sin1->sin_family == sin2->sin_family) && - (sin1->sin_addr.s_addr == sin2->sin_addr.s_addr)) + if ((this->address4.sin_family == other->address4.sin_family) && + (this->address4.sin_addr.s_addr == other->address4.sin_addr.s_addr)) { return TRUE; } @@ -229,6 +248,8 @@ static private_host_t *host_create_empty() this->public.get_sockaddr = (sockaddr_t* (*) (host_t*))get_sockaddr; this->public.get_sockaddr_len = (socklen_t*(*) (host_t*))get_sockaddr_len; this->public.clone = (host_t* (*) (host_t*))clone; + this->public.get_family = (int (*) (host_t*))get_family; + this->public.get_xfrm_addr = (xfrm_address_t (*) (host_t *))get_xfrm_addr; this->public.get_address = (char* (*) (host_t *))get_address; this->public.get_address_as_chunk = (chunk_t (*) (host_t *)) get_address_as_chunk; this->public.get_port = (u_int16_t (*) (host_t *))get_port; @@ -255,10 +276,9 @@ host_t *host_create(int family, char *address, u_int16_t port) /* IPv4 */ case AF_INET: { - struct sockaddr_in *sin = (struct sockaddr_in*)&(this->address); - sin->sin_family = AF_INET; - sin->sin_addr.s_addr = inet_addr(address); - sin->sin_port = htons(port); + this->address4.sin_family = AF_INET; + this->address4.sin_addr.s_addr = inet_addr(address); + this->address4.sin_port = htons(port); this->socklen = sizeof(struct sockaddr_in); return &(this->public); } @@ -280,22 +300,20 @@ host_t *host_create_from_chunk(int family, chunk_t address, u_int16_t port) private_host_t *this = host_create_empty(); this->family = family; - - if (address.len == 4) + switch (family) { - switch (family) + /* IPv4 */ + case AF_INET: { - /* IPv4 */ - case AF_INET: + if (address.len != 4) { - struct sockaddr_in *sin = (struct sockaddr_in*)&(this->address); - sin->sin_family = AF_INET; - memcpy(&(sin->sin_addr.s_addr),address.ptr,4); - sin->sin_port = htons(port); - this->socklen = sizeof(struct sockaddr_in); - return &(this->public); + break; } - + this->address4.sin_family = AF_INET; + memcpy(&(this->address4.sin_addr.s_addr),address.ptr,4); + this->address4.sin_port = htons(port); + this->socklen = sizeof(struct sockaddr_in); + return &(this->public); } } allocator_free(this);