Add a host_t constructor from string, but with a specific family
This commit is contained in:
@@ -358,57 +358,59 @@ static host_t *host_create_any_port(int family, u_int16_t port)
|
|||||||
/*
|
/*
|
||||||
* Described in header.
|
* Described in header.
|
||||||
*/
|
*/
|
||||||
host_t *host_create_from_string(char *string, u_int16_t port)
|
host_t *host_create_from_string_and_family(char *string, int family,
|
||||||
|
u_int16_t port)
|
||||||
{
|
{
|
||||||
private_host_t *this;
|
union {
|
||||||
|
sockaddr_t sockaddr;
|
||||||
|
struct sockaddr_in v4;
|
||||||
|
struct sockaddr_in6 v6;
|
||||||
|
} addr;
|
||||||
|
|
||||||
if (streq(string, "%any"))
|
if ((family == AF_UNSPEC || family == AF_INET) && streq(string, "%any"))
|
||||||
{
|
{
|
||||||
return host_create_any_port(AF_INET, port);
|
return host_create_any_port(AF_INET, port);
|
||||||
}
|
}
|
||||||
if (streq(string, "%any6"))
|
if ((family == AF_UNSPEC || family == AF_INET6) && streq(string, "%any6"))
|
||||||
{
|
{
|
||||||
return host_create_any_port(AF_INET6, port);
|
return host_create_any_port(AF_INET6, port);
|
||||||
}
|
}
|
||||||
|
switch (family)
|
||||||
this = host_create_empty();
|
|
||||||
if (strchr(string, '.'))
|
|
||||||
{
|
{
|
||||||
this->address.sa_family = AF_INET;
|
case AF_UNSPEC:
|
||||||
}
|
if (strchr(string, '.'))
|
||||||
else
|
|
||||||
{
|
|
||||||
this->address.sa_family = AF_INET6;
|
|
||||||
}
|
|
||||||
switch (this->address.sa_family)
|
|
||||||
{
|
|
||||||
case AF_INET:
|
|
||||||
{
|
|
||||||
if (inet_pton(AF_INET, string, &this->address4.sin_addr) <=0)
|
|
||||||
{
|
{
|
||||||
break;
|
goto af_inet;
|
||||||
}
|
}
|
||||||
this->address4.sin_port = htons(port);
|
/* FALL */
|
||||||
this->socklen = sizeof(struct sockaddr_in);
|
|
||||||
return &this->public;
|
|
||||||
}
|
|
||||||
case AF_INET6:
|
case AF_INET6:
|
||||||
{
|
if (inet_pton(AF_INET6, string, &addr.v6.sin6_addr) != 1)
|
||||||
if (inet_pton(AF_INET6, string, &this->address6.sin6_addr) <=0)
|
|
||||||
{
|
{
|
||||||
break;
|
return NULL;
|
||||||
}
|
}
|
||||||
this->address6.sin6_port = htons(port);
|
addr.v6.sin6_port = htons(port);
|
||||||
this->socklen = sizeof(struct sockaddr_in6);
|
addr.sockaddr.sa_family = AF_INET6;
|
||||||
return &this->public;
|
return host_create_from_sockaddr(&addr.sockaddr);
|
||||||
}
|
case AF_INET:
|
||||||
|
af_inet:
|
||||||
|
if (inet_pton(AF_INET, string, &addr.v4.sin_addr) != 1)
|
||||||
|
{
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
addr.v4.sin_port = htons(port);
|
||||||
|
addr.sockaddr.sa_family = AF_INET;
|
||||||
|
return host_create_from_sockaddr(&addr.sockaddr);
|
||||||
default:
|
default:
|
||||||
{
|
return NULL;
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
free(this);
|
}
|
||||||
return NULL;
|
|
||||||
|
/*
|
||||||
|
* Described in header.
|
||||||
|
*/
|
||||||
|
host_t *host_create_from_string(char *string, u_int16_t port)
|
||||||
|
{
|
||||||
|
return host_create_from_string_and_family(string, AF_UNSPEC, port);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|||||||
@@ -159,6 +159,17 @@ struct host_t {
|
|||||||
*/
|
*/
|
||||||
host_t *host_create_from_string(char *string, u_int16_t port);
|
host_t *host_create_from_string(char *string, u_int16_t port);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Same as host_create_from_string(), but with the option to enforce a family.
|
||||||
|
*
|
||||||
|
* @param string string of an address
|
||||||
|
* @param family address family, or AF_UNSPEC
|
||||||
|
* @param port port number
|
||||||
|
* @return host_t, NULL if string not an address.
|
||||||
|
*/
|
||||||
|
host_t *host_create_from_string_and_family(char *string, int family,
|
||||||
|
u_int16_t port);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Constructor to create a host_t from a DNS name.
|
* Constructor to create a host_t from a DNS name.
|
||||||
*
|
*
|
||||||
|
|||||||
Reference in New Issue
Block a user