resolv.conf: Add support for OpenBSD style resolv.conf syntax where a non-standard DNS server port can be specified using a backet syntax.
This commit is contained in:
parent
8a3033643e
commit
2a5c7e9a92
2
configs
2
configs
@ -1 +1 @@
|
||||
Subproject commit 5eb7ce16316971813ced45e4869167ec55a72b45
|
||||
Subproject commit a4a4be4004173c67c8ed160cc48fcea1cf57308a
|
33
libc/Kconfig
33
libc/Kconfig
@ -606,23 +606,54 @@ config NETDB_RESOLVCONF_PATH
|
||||
string "Path to host configuration file"
|
||||
default "/etc/resolv.conf"
|
||||
|
||||
config NETDB_RESOLVCONF_NONSTDPORT
|
||||
bool "Non-standard port support"
|
||||
default n
|
||||
---help---
|
||||
By default, the resolv.conf file will hold only records like:
|
||||
|
||||
nameserver xx.xx.xx.xx
|
||||
nameserver xxxx:::::::xxxx
|
||||
|
||||
The default port of 53 is always assumed.
|
||||
|
||||
If this option is selected, then OpenBSD style resolv.conf files
|
||||
will be supported. This adds logic for a bracket port notation
|
||||
like:
|
||||
|
||||
nameserver [xx.xx.xx.xx]:ppppp
|
||||
nameserver [xxxx:::::::xxxx]:ppppp
|
||||
|
||||
endif # NETDB_RESOLVCONF
|
||||
|
||||
choice
|
||||
prompt "DNS server address type"
|
||||
default NETDB_DNSSERVER_NOADDR
|
||||
default NETDB_DNSSERVER_IPv4 if NET_IPv4
|
||||
default NETDB_DNSSERVER_IPv6 if !NET_IPv4 && NET_IPv6
|
||||
default NETDB_DNSSERVER_NOADDR if !NET_IPv4 && !NET_IPv6
|
||||
depends on !NETDB_RESOLVCONF
|
||||
|
||||
config NETDB_DNSSERVER_NOADDR
|
||||
bool "No default DNS server address"
|
||||
---help---
|
||||
There is not default DNS nameserver address. Application must call
|
||||
dns_add_server() at runtime to add the DNS server address.
|
||||
|
||||
config NETDB_DNSSERVER_IPv4
|
||||
bool "IPv4 DNS server address"
|
||||
depends on NET_IPv4
|
||||
---help---
|
||||
An IPv4 default DNS nameserver address will be provided. Application
|
||||
may overwrite this start default server address by calling
|
||||
dns_add_server() at runtime.
|
||||
|
||||
config NETDB_DNSSERVER_IPv6
|
||||
bool "IPv6 DNS server address"
|
||||
depends on NET_IPv6
|
||||
---help---
|
||||
An IPv6 default DNS nameserver address will be provided. Application
|
||||
may overwrite this start default server address by calling
|
||||
dns_add_server() at runtime.
|
||||
|
||||
endchoice # DNS server address type
|
||||
|
||||
|
@ -80,7 +80,8 @@
|
||||
# define CONFIG_NETDB_RESOLVCONF_PATH "/etc/resolv.conf"
|
||||
#endif
|
||||
|
||||
#define DNS_MAX_LINE 80
|
||||
#define DNS_MAX_ADDRSTR 48
|
||||
#define DNS_MAX_LINE 64
|
||||
#define NETDB_DNS_KEYWORD "nameserver"
|
||||
|
||||
/****************************************************************************
|
||||
|
@ -80,7 +80,11 @@ bool g_dns_address; /* true: We have the address of the DNS server */
|
||||
int dns_add_nameserver(FAR const struct sockaddr *addr, socklen_t addrlen)
|
||||
{
|
||||
FAR FILE *stream;
|
||||
char line[DNS_MAX_LINE];
|
||||
char addrstr[DNS_MAX_ADDRSTR];
|
||||
#ifdef CONFIG_NETDB_RESOLVCONF_NONSTDPORT
|
||||
uint16_t port;
|
||||
#endif
|
||||
int status;
|
||||
int ret;
|
||||
|
||||
stream = fopen(CONFIG_NETDB_RESOLVCONF_PATH, "at");
|
||||
@ -107,20 +111,26 @@ int dns_add_nameserver(FAR const struct sockaddr *addr, socklen_t addrlen)
|
||||
{
|
||||
FAR struct sockaddr_in *in4 = (FAR struct sockaddr_in *)addr;
|
||||
|
||||
if (inet_ntop(AF_INET, &in4->sin_addr, line, DNS_MAX_LINE) == NULL)
|
||||
if (inet_ntop(AF_INET, &in4->sin_addr, addrstr, DNS_MAX_ADDRSTR) == NULL)
|
||||
{
|
||||
ret = -errno;
|
||||
ndbg("ERROR: inet_ntop failed: %d\n", errcode);
|
||||
DEBUGASSERT(errcode < 0);
|
||||
goto errout;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_NETDB_RESOLVCONF_NONSTDPORT
|
||||
/* Get the port number */
|
||||
|
||||
port = ntohs(in4->sin_port);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
else
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_NET_IPv6
|
||||
/* Check for an IPv4 address */
|
||||
/* Check for an IPv6 address */
|
||||
|
||||
if (addr->sa_family == AF_INET6)
|
||||
{
|
||||
@ -133,13 +143,19 @@ int dns_add_nameserver(FAR const struct sockaddr *addr, socklen_t addrlen)
|
||||
{
|
||||
FAR struct sockaddr_in6 *in6 = (FAR struct sockaddr_in6 *)addr;
|
||||
|
||||
if (inet_ntop(AF_INET6, &in6->sin6_addr, line, DNS_MAX_LINE) == NULL)
|
||||
if (inet_ntop(AF_INET6, &in6->sin6_addr, addrstr, DNS_MAX_ADDRSTR) == NULL)
|
||||
{
|
||||
ret = -errno;
|
||||
ndbg("ERROR: inet_ntop failed: %d\n", errcode);
|
||||
DEBUGASSERT(errcode < 0);
|
||||
goto errout;
|
||||
}
|
||||
|
||||
#ifdef CONFIG_NETDB_RESOLVCONF_NONSTDPORT
|
||||
/* Get the port number */
|
||||
|
||||
port = ntohs(in6->sin6_port);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
else
|
||||
@ -151,9 +167,30 @@ int dns_add_nameserver(FAR const struct sockaddr *addr, socklen_t addrlen)
|
||||
goto errout;
|
||||
}
|
||||
|
||||
/* Write the new record to the end of the resolv.conf file */
|
||||
/* Write the new record to the end of the resolv.conf file. */
|
||||
|
||||
if (fprintf(stream, "%s %s\n", NETDB_DNS_KEYWORD, line) < 0)
|
||||
#ifdef CONFIG_NETDB_RESOLVCONF_NONSTDPORT
|
||||
/* The OpenBSD version supports a [host]:port syntax. When a non-standard
|
||||
* port is specified the host address must be enclosed in square brackets.
|
||||
* For example:
|
||||
*
|
||||
* nameserver [10.0.0.1]:5353
|
||||
* nameserver [::1]:5353
|
||||
*/
|
||||
|
||||
if (port != 0 && port != DNS_DEFAULT_PORT)
|
||||
{
|
||||
status = fprintf(stream, "%s [%s]:%u\n",
|
||||
NETDB_DNS_KEYWORD, addrstr, port);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
status = fprintf(stream, "%s %s\n",
|
||||
NETDB_DNS_KEYWORD, addrstr);
|
||||
}
|
||||
|
||||
if (status < 0)
|
||||
{
|
||||
ret = -errno;
|
||||
ndbg("ERROR: fprintf failed: %d\n", errcode);
|
||||
|
@ -40,6 +40,7 @@
|
||||
#include <nuttx/config.h>
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
#include <errno.h>
|
||||
@ -94,6 +95,7 @@ int dns_foreach_nameserver(dns_callback_t callback, FAR void *arg)
|
||||
char line[DNS_MAX_LINE];
|
||||
FAR char *addrstr;
|
||||
FAR char *ptr;
|
||||
uint16_t port;
|
||||
int keylen;
|
||||
int ret;
|
||||
|
||||
@ -133,9 +135,12 @@ int dns_foreach_nameserver(dns_callback_t callback, FAR void *arg)
|
||||
ptr = find_spaces(addrstr);
|
||||
*ptr = '\0';
|
||||
|
||||
/* Convert the address string to a binary representation */
|
||||
/* REVISIT: We really need a customizable port number. The
|
||||
* OpenBSD version supports a [host]:port syntax. When a
|
||||
/* Convert the address string to a binary representation. */
|
||||
|
||||
port = HTONS(DNS_DEFAULT_PORT);
|
||||
|
||||
#ifdef CONFIG_NETDB_RESOLVCONF_NONSTDPORT
|
||||
/* The OpenBSD version supports a [host]:port syntax. When a
|
||||
* non-standard port is specified the host address must be
|
||||
* enclosed in square brackets. For example:
|
||||
*
|
||||
@ -143,6 +148,46 @@ int dns_foreach_nameserver(dns_callback_t callback, FAR void *arg)
|
||||
* nameserver [::1]:5353
|
||||
*/
|
||||
|
||||
if (*addrstr == '[')
|
||||
{
|
||||
/* Make sure that ther is a right bracket */
|
||||
|
||||
ptr = strchr(addrstr, ']');
|
||||
if (ptr == NULL)
|
||||
{
|
||||
ndbg("ERROR: Missing right bracket after %s\n", line);
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Replace the right bracket with a NULL terminator */
|
||||
|
||||
addrstr++;
|
||||
*ptr++ = '\0';
|
||||
|
||||
/* Get the port number following the right bracket */
|
||||
|
||||
if (*ptr == ':')
|
||||
{
|
||||
FAR char *portstr;
|
||||
int tmp;
|
||||
|
||||
/* Isolate the port string */
|
||||
|
||||
portstr = ptr;
|
||||
ptr = find_spaces(addrstr);
|
||||
*ptr = '\0';
|
||||
|
||||
/* Get the port number */
|
||||
|
||||
tmp = atoi(portstr);
|
||||
if (tmp != 0)
|
||||
{
|
||||
port = htons(tmp);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif /* CONFIG_NETDB_RESOLVCONF_NONSTDPORT */
|
||||
|
||||
#ifdef CONFIG_NET_IPv4
|
||||
/* Try to convert the IPv4 address */
|
||||
|
||||
@ -152,10 +197,8 @@ int dns_foreach_nameserver(dns_callback_t callback, FAR void *arg)
|
||||
|
||||
if (ret == 1)
|
||||
{
|
||||
/* REVISIT: We really need a customizable port number */
|
||||
|
||||
u.ipv4.sin_family = AF_INET;
|
||||
u.ipv4.sin_port = HTONS(DNS_DEFAULT_PORT);
|
||||
u.ipv4.sin_port = port;
|
||||
ret = callback(arg, (FAR struct sockaddr *)&u.ipv4,
|
||||
sizeof(struct sockaddr_in));
|
||||
}
|
||||
@ -173,10 +216,8 @@ int dns_foreach_nameserver(dns_callback_t callback, FAR void *arg)
|
||||
|
||||
if (ret == 1)
|
||||
{
|
||||
/* REVISIT: We really need a customizable port number */
|
||||
|
||||
u.ipv6.sin6_family = AF_INET6;
|
||||
u.ipv6.sin6_port = HTONS(DNS_DEFAULT_PORT);
|
||||
u.ipv6.sin6_port = port;
|
||||
ret = callback(arg, (FAR struct sockaddr *)&u.ipv6,
|
||||
sizeof(struct sockaddr_in6));
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user