This is an automated email from the ASF dual-hosted git repository.
acassis pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git
The following commit(s) were added to refs/heads/master by this push:
new 65e318421d9 netdb/lib_dnsdelserver.c: support delete the DNS server
address by index or address
65e318421d9 is described below
commit 65e318421d94b8b05ee0dc6c435e1bfc0b628b7e
Author: nuttxs <[email protected]>
AuthorDate: Wed Nov 5 17:59:11 2025 +0800
netdb/lib_dnsdelserver.c: support delete the DNS server address
by index or address
- dns_del_nameserver()
- dns_del_nameserver_by_index()
Update the "DNS function" section in 11_network.rst, and create
the netlib API documentation in netlib/index.rst
Signed-off-by: nuttxs <[email protected]>
---
.../applications/netutils/netlib/index.rst | 650 +++++++++++++++++++++
Documentation/reference/user/11_network.rst | 111 ++++
include/nuttx/net/dns.h | 25 +-
libs/libc/netdb/CMakeLists.txt | 3 +-
libs/libc/netdb/Make.defs | 2 +-
libs/libc/netdb/lib_dnsdelserver.c | 227 +++++++
6 files changed, 1015 insertions(+), 3 deletions(-)
diff --git a/Documentation/applications/netutils/netlib/index.rst
b/Documentation/applications/netutils/netlib/index.rst
index 6099b31da45..ee12c5b6fbf 100644
--- a/Documentation/applications/netutils/netlib/index.rst
+++ b/Documentation/applications/netutils/netlib/index.rst
@@ -1,3 +1,653 @@
==================================
``netlib`` Network support library
==================================
+
+The ``netlib`` library provides a collection of network utility functions
+for managing network interfaces, IP addresses, routing tables, and other
+network-related operations. These functions are defined in
+``netutils/netlib.h`` and are intended for internal use by NuttX applications.
+
+Device Management
+==================
+
+ - :c:func:`netlib_get_devices`
+
+.. c:function:: ssize_t netlib_get_devices(struct netlib_device_s *devlist,
unsigned int nentries, sa_family_t family)
+
+ Get a list of all network devices.
+
+ :param devlist: Pointer to an array of ``netlib_device_s`` structures to
+ receive the device list.
+ :param nentries: Maximum number of entries in the array.
+ :param family: Address family filter (``AF_INET``, ``AF_INET6``, or
+ ``AF_UNSPEC`` for all).
+
+ :return: Number of devices returned on success; -1 on error with ``errno``
+ set appropriately.
+
+Address Conversion Functions
+=============================
+
+ - :c:func:`netlib_ipv4addrconv`
+ - :c:func:`netlib_ethaddrconv`
+
+.. c:function:: bool netlib_ipv4addrconv(const char *addrstr, uint8_t *addr)
+
+ Convert a textual representation of an IPv4 address to a numerical
+ representation. This function takes an IP address in the form ``a.b.c.d``
+ and converts it into a 4-byte array.
+
+ :param addrstr: A pointer to a string containing the IP address in textual
form.
+ :param addr: A pointer to a 4-byte array that will be filled with the
+ numerical representation of the address.
+
+ :return: ``true`` if the IP address was parsed successfully; ``false``
otherwise.
+
+.. c:function:: bool netlib_ethaddrconv(const char *hwstr, uint8_t *hw)
+
+ Convert a textual representation of an Ethernet MAC address to a numerical
+ representation.
+
+ :param hwstr: A pointer to a string containing the MAC address in textual
form
+ (e.g., ``"00:11:22:33:44:55"``).
+ :param hw: A pointer to a byte array that will be filled with the numerical
+ representation of the MAC address.
+
+ :return: ``true`` if the MAC address was parsed successfully; ``false``
otherwise.
+
+MAC Address Management
+=======================
+
+ - :c:func:`netlib_setmacaddr`
+ - :c:func:`netlib_getmacaddr`
+
+.. c:function:: int netlib_setmacaddr(const char *ifname, const uint8_t
*macaddr)
+
+ Set the MAC address for an Ethernet network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param macaddr: Pointer to a 6-byte array containing the MAC address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_getmacaddr(const char *ifname, uint8_t *macaddr)
+
+ Get the MAC address of an Ethernet network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param macaddr: Pointer to a 6-byte array to receive the MAC address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+IPv4 Address Management
+========================
+
+ - :c:func:`netlib_set_ipv4addr`
+ - :c:func:`netlib_get_ipv4addr`
+ - :c:func:`netlib_set_dripv4addr`
+ - :c:func:`netlib_get_dripv4addr`
+ - :c:func:`netlib_set_ipv4netmask`
+ - :c:func:`netlib_get_ipv4netmask`
+ - :c:func:`netlib_ipv4adaptor`
+
+.. c:function:: int netlib_set_ipv4addr(const char *ifname, const struct
in_addr *addr)
+
+ Set the IPv4 address for a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in_addr`` structure containing the IPv4 address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_get_ipv4addr(const char *ifname, struct in_addr
*addr)
+
+ Get the IPv4 address of a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in_addr`` structure to receive the IPv4 address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_set_dripv4addr(const char *ifname, const struct
in_addr *addr)
+
+ Set the default router (gateway) IPv4 address for a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in_addr`` structure containing the gateway
address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_get_dripv4addr(const char *ifname, struct in_addr
*addr)
+
+ Get the default router (gateway) IPv4 address of a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in_addr`` structure to receive the gateway
address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_set_ipv4netmask(const char *ifname, const struct
in_addr *addr)
+
+ Set the IPv4 netmask for a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in_addr`` structure containing the netmask.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_get_ipv4netmask(const char *ifname, struct in_addr
*addr)
+
+ Get the IPv4 netmask of a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in_addr`` structure to receive the netmask.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_ipv4adaptor(in_addr_t destipaddr, in_addr_t
*srcipaddr)
+
+ Find the appropriate source IPv4 address to use for communicating with a
+ destination address.
+
+ :param destipaddr: Destination IPv4 address (in network byte order).
+ :param srcipaddr: Pointer to receive the source IPv4 address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+IPv6 Address Management
+========================
+
+ - :c:func:`netlib_set_ipv6addr`
+ - :c:func:`netlib_get_ipv6addr`
+ - :c:func:`netlib_add_ipv6addr`
+ - :c:func:`netlib_del_ipv6addr`
+ - :c:func:`netlib_set_dripv6addr`
+ - :c:func:`netlib_set_ipv6netmask`
+ - :c:func:`netlib_ipv6adaptor`
+ - :c:func:`netlib_ipv6netmask2prefix`
+ - :c:func:`netlib_prefix2ipv6netmask`
+
+.. c:function:: int netlib_set_ipv6addr(const char *ifname, const struct
in6_addr *addr)
+
+ Set the IPv6 address for a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``). Can include slot
+ number for multiple addresses (e.g., ``"eth0:0"``).
+ :param addr: Pointer to an ``in6_addr`` structure containing the IPv6
address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_get_ipv6addr(const char *ifname, struct in6_addr
*addr)
+
+ Get the IPv6 address of a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``). Can include slot
+ number for multiple addresses (e.g., ``"eth0:0"``).
+ :param addr: Pointer to an ``in6_addr`` structure to receive the IPv6
address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_add_ipv6addr(const char *ifname, const struct
in6_addr *addr, uint8_t preflen)
+
+ Add an IPv6 address to a network interface. This function is recommended for
+ managing multiple IPv6 addresses on a single interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in6_addr`` structure containing the IPv6
address.
+ :param preflen: Prefix length (0-128).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_del_ipv6addr(const char *ifname, const struct
in6_addr *addr, uint8_t preflen)
+
+ Remove an IPv6 address from a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in6_addr`` structure containing the IPv6 address
+ to remove.
+ :param preflen: Prefix length (0-128).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_set_dripv6addr(const char *ifname, const struct
in6_addr *addr)
+
+ Set the default router (gateway) IPv6 address for a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in6_addr`` structure containing the gateway
address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_set_ipv6netmask(const char *ifname, const struct
in6_addr *addr)
+
+ Set the IPv6 netmask for a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param addr: Pointer to an ``in6_addr`` structure containing the netmask.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_ipv6adaptor(const struct in6_addr *destipaddr,
struct in6_addr *srcipaddr)
+
+ Find the appropriate source IPv6 address to use for communicating with a
+ destination address.
+
+ :param destipaddr: Pointer to the destination IPv6 address.
+ :param srcipaddr: Pointer to receive the source IPv6 address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: uint8_t netlib_ipv6netmask2prefix(const uint16_t *mask)
+
+ Convert an IPv6 netmask to a prefix length.
+
+ :param mask: Pointer to a 16-bit array representing the netmask.
+
+ :return: Prefix length (0-128).
+
+.. c:function:: void netlib_prefix2ipv6netmask(uint8_t preflen, struct
in6_addr *netmask)
+
+ Convert a prefix length to an IPv6 netmask.
+
+ :param preflen: Prefix length (0-128).
+ :param netmask: Pointer to an ``in6_addr`` structure to receive the netmask.
+
+Network Interface Management
+=============================
+
+ - :c:func:`netlib_getifstatus`
+ - :c:func:`netlib_ifup`
+ - :c:func:`netlib_ifdown`
+ - :c:func:`netlib_set_mtu`
+
+.. c:function:: int netlib_getifstatus(const char *ifname, uint8_t *flags)
+
+ Get the status flags of a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param flags: Pointer to receive the interface flags.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_ifup(const char *ifname)
+
+ Bring a network interface up (activate it).
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_ifdown(const char *ifname)
+
+ Bring a network interface down (deactivate it).
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_set_mtu(const char *ifname, int mtu)
+
+ Set the Maximum Transmission Unit (MTU) for a network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+ :param mtu: MTU value in bytes.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+ARP Table Support
+==================
+
+ - :c:func:`netlib_set_arpmapping`
+ - :c:func:`netlib_get_arpmapping`
+ - :c:func:`netlib_del_arpmapping`
+ - :c:func:`netlib_get_arptable`
+
+.. c:function:: int netlib_set_arpmapping(const struct sockaddr_in *inaddr,
const uint8_t *macaddr, const char *ifname)
+
+ Add or update an ARP table entry mapping an IPv4 address to a MAC address.
+
+ :param inaddr: Pointer to a ``sockaddr_in`` structure containing the IPv4
address.
+ :param macaddr: Pointer to a 6-byte array containing the MAC address.
+ :param ifname: Network interface name (e.g., ``"eth0"``), or NULL for any
interface.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_get_arpmapping(const struct sockaddr_in *inaddr,
uint8_t *macaddr, const char *ifname)
+
+ Retrieve the MAC address associated with an IPv4 address from the ARP table.
+
+ :param inaddr: Pointer to a ``sockaddr_in`` structure containing the IPv4
address.
+ :param macaddr: Pointer to a 6-byte array to receive the MAC address.
+ :param ifname: Network interface name (e.g., ``"eth0"``), or NULL for any
interface.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_del_arpmapping(const struct sockaddr_in *inaddr,
const char *ifname)
+
+ Delete an entry from the ARP table.
+
+ :param inaddr: Pointer to a ``sockaddr_in`` structure containing the IPv4
address.
+ :param ifname: Network interface name (e.g., ``"eth0"``), or NULL for any
interface.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: ssize_t netlib_get_arptable(struct arpreq *arptab, unsigned
int nentries)
+
+ Retrieve the entire ARP table.
+
+ :param arptab: Pointer to an array of ``arpreq`` structures to receive the
+ ARP table entries.
+ :param nentries: Maximum number of entries in the array.
+
+ :return: Number of entries returned on success; -1 on error with ``errno``
+ set appropriately.
+
+Routing Table Support
+======================
+
+ - :c:func:`netlib_ipv4router`
+ - :c:func:`netlib_ipv6router`
+ - :c:func:`netlib_open_ipv4route`
+ - :c:func:`netlib_close_ipv4route`
+ - :c:func:`netlib_read_ipv4route`
+ - :c:func:`netlib_open_ipv6route`
+ - :c:func:`netlib_close_ipv6route`
+ - :c:func:`netlib_read_ipv6route`
+ - :c:func:`netlib_get_route`
+
+.. c:function:: int netlib_ipv4router(const struct in_addr *destipaddr, struct
in_addr *router)
+
+ Find the router (gateway) address to use for reaching a destination IPv4
address.
+
+ :param destipaddr: Pointer to the destination IPv4 address.
+ :param router: Pointer to receive the router IPv4 address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_ipv6router(const struct in6_addr *destipaddr,
struct in6_addr *router)
+
+ Find the router (gateway) address to use for reaching a destination IPv6
address.
+
+ :param destipaddr: Pointer to the destination IPv6 address.
+ :param router: Pointer to receive the router IPv6 address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: FILE *netlib_open_ipv4route(void)
+
+ Open the IPv4 routing table for reading. This is a macro that opens
+ ``/proc/net/route/ipv4``.
+
+ :return: File pointer on success; NULL on error.
+
+.. c:function:: void netlib_close_ipv4route(FILE *stream)
+
+ Close the IPv4 routing table file. This is a macro that calls ``fclose()``.
+
+ :param stream: File pointer returned by ``netlib_open_ipv4route()``.
+
+.. c:function:: ssize_t netlib_read_ipv4route(FILE *stream, struct
netlib_ipv4_route_s *route)
+
+ Read one entry from the IPv4 routing table.
+
+ :param stream: File pointer returned by ``netlib_open_ipv4route()``.
+ :param route: Pointer to a ``netlib_ipv4_route_s`` structure to receive the
+ route entry.
+
+ :return: 1 on success; 0 on end of file; -1 on error.
+
+.. c:function:: FILE *netlib_open_ipv6route(void)
+
+ Open the IPv6 routing table for reading. This is a macro that opens
+ ``/proc/net/route/ipv6``.
+
+ :return: File pointer on success; NULL on error.
+
+.. c:function:: void netlib_close_ipv6route(FILE *stream)
+
+ Close the IPv6 routing table file. This is a macro that calls ``fclose()``.
+
+ :param stream: File pointer returned by ``netlib_open_ipv6route()``.
+
+.. c:function:: ssize_t netlib_read_ipv6route(FILE *stream, struct
netlib_ipv6_route_s *route)
+
+ Read one entry from the IPv6 routing table.
+
+ :param stream: File pointer returned by ``netlib_open_ipv6route()``.
+ :param route: Pointer to a ``netlib_ipv6_route_s`` structure to receive the
+ route entry.
+
+ :return: 1 on success; 0 on end of file; -1 on error.
+
+.. c:function:: ssize_t netlib_get_route(struct rtentry *rtelist, unsigned int
nentries, sa_family_t family)
+
+ Retrieve routing table entries using Netlink.
+
+ :param rtelist: Pointer to an array of ``rtentry`` structures to receive the
+ routing entries.
+ :param nentries: Maximum number of entries in the array.
+ :param family: Address family filter (``AF_INET``, ``AF_INET6``, or
+ ``AF_UNSPEC`` for all).
+
+ :return: Number of entries returned on success; -1 on error with ``errno``
+ set appropriately.
+
+DHCP Support
+=============
+
+ - :c:func:`netlib_obtain_ipv4addr`
+ - :c:func:`netlib_icmpv6_autoconfiguration`
+ - :c:func:`netlib_obtain_ipv6addr`
+
+.. c:function:: int netlib_obtain_ipv4addr(const char *ifname)
+
+ Obtain an IPv4 address via DHCP for the specified network interface. This
+ function blocks until an address is obtained or an error occurs.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_icmpv6_autoconfiguration(const char *ifname)
+
+ Perform IPv6 stateless address autoconfiguration (SLAAC) for the specified
+ network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_obtain_ipv6addr(const char *ifname)
+
+ Obtain an IPv6 address via DHCPv6 for the specified network interface.
+
+ :param ifname: Network interface name (e.g., ``"eth0"``).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+DNS Server Address Management
+===============================
+
+ - :c:func:`netlib_set_ipv4dnsaddr`
+ - :c:func:`netlib_del_ipv4dnsaddr`
+ - :c:func:`netlib_del_ipv4dnsaddr_by_index`
+ - :c:func:`netlib_set_ipv6dnsaddr`
+ - :c:func:`netlib_del_ipv6dnsaddr`
+ - :c:func:`netlib_del_ipv6dnsaddr_by_index`
+
+.. c:function:: int netlib_set_ipv4dnsaddr(const struct in_addr *inaddr)
+
+ Add an IPv4 DNS server address to the resolver configuration.
+
+ :param inaddr: Pointer to an ``in_addr`` structure containing the DNS server
+ address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_del_ipv4dnsaddr(const struct in_addr *inaddr)
+
+ Remove an IPv4 DNS server address from the resolver configuration.
+
+ :param inaddr: Pointer to an ``in_addr`` structure containing the DNS server
+ address to remove.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_del_ipv4dnsaddr_by_index(int index)
+
+ Remove an IPv4 DNS server from the resolver configuration by index.
+
+ :param index: Index of the DNS server to remove (0-based).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_set_ipv6dnsaddr(const struct in6_addr *inaddr)
+
+ Add an IPv6 DNS server address to the resolver configuration.
+
+ :param inaddr: Pointer to an ``in6_addr`` structure containing the DNS server
+ address.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_del_ipv6dnsaddr(const struct in6_addr *inaddr)
+
+ Remove an IPv6 DNS server address from the resolver configuration.
+
+ :param inaddr: Pointer to an ``in6_addr`` structure containing the DNS server
+ address to remove.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_del_ipv6dnsaddr_by_index(int index)
+
+ Remove an IPv6 DNS server from the resolver configuration by index.
+
+ :param index: Index of the DNS server to remove (0-based).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+Wireless Configuration
+=======================
+
+ - :c:func:`netlib_getessid`
+ - :c:func:`netlib_setessid`
+
+.. c:function:: int netlib_getessid(const char *ifname, char *essid, size_t
idlen)
+
+ Get the ESSID (network name) of a wireless network interface.
+
+ :param ifname: Wireless network interface name (e.g., ``"wlan0"``).
+ :param essid: Buffer to receive the ESSID string.
+ :param idlen: Size of the buffer.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_setessid(const char *ifname, const char *essid)
+
+ Set the ESSID (network name) for a wireless network interface.
+
+ :param ifname: Wireless network interface name (e.g., ``"wlan0"``).
+ :param essid: ESSID string to set.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+URL Parsing
+============
+
+ - :c:func:`netlib_parsehttpurl`
+ - :c:func:`netlib_parseurl`
+
+.. c:function:: int netlib_parsehttpurl(const char *url, uint16_t *port, char
*hostname, int hostlen, char *filename, int namelen)
+
+ Parse an HTTP URL into its components.
+
+ :param url: URL string to parse (e.g.,
``"http://example.com:8080/path/file"``).
+ :param port: Pointer to receive the port number (default 80 if not
specified).
+ :param hostname: Buffer to receive the hostname.
+ :param hostlen: Size of the hostname buffer.
+ :param filename: Buffer to receive the path/filename.
+ :param namelen: Size of the filename buffer.
+
+ :return: 0 on success; -1 on error.
+
+.. c:function:: int netlib_parseurl(const char *str, struct url_s *url)
+
+ Parse a generic URL into its components. This function handles various URL
+ schemes beyond HTTP.
+
+ :param str: URL string to parse.
+ :param url: Pointer to a ``url_s`` structure to receive the parsed
components.
+
+ :return: 0 on success; -1 on error.
+
+Server Support
+===============
+
+ - :c:func:`netlib_listenon`
+ - :c:func:`netlib_server`
+
+.. c:function:: int netlib_listenon(uint16_t portno)
+
+ Create a TCP socket and listen on the specified port. This is a convenience
+ function for setting up a server socket.
+
+ :param portno: Port number to listen on.
+
+ :return: Socket descriptor on success; -1 on error with ``errno`` set
+ appropriately.
+
+.. c:function:: void netlib_server(uint16_t portno, pthread_startroutine_t
handler, int stacksize)
+
+ Create a simple server that listens on the specified port and spawns a new
+ thread for each connection using the provided handler function.
+
+ :param portno: Port number to listen on.
+ :param handler: Function to call for each new connection. The handler
receives
+ the client socket descriptor as an argument.
+ :param stacksize: Stack size for handler threads.
+
+Neighbor Table (IPv6)
+======================
+
+ - :c:func:`netlib_get_nbtable`
+
+.. c:function:: ssize_t netlib_get_nbtable(struct neighbor_entry_s *nbtab,
unsigned int nentries)
+
+ Retrieve the IPv6 neighbor table (similar to ARP for IPv4).
+
+ :param nbtab: Pointer to an array of ``neighbor_entry_s`` structures to
+ receive the neighbor table entries.
+ :param nentries: Maximum number of entries in the array.
+
+ :return: Number of entries returned on success; -1 on error with ``errno``
+ set appropriately.
+
+Connection Tracking (Netfilter)
+=================================
+
+ - :c:func:`netlib_get_conntrack`
+ - :c:func:`netlib_parse_conntrack`
+
+.. c:function:: int netlib_get_conntrack(sa_family_t family,
netlib_conntrack_cb_t cb)
+
+ Retrieve connection tracking entries from the kernel's connection tracking
+ table.
+
+ :param family: Address family filter (``AF_INET``, ``AF_INET6``, or
+ ``AF_UNSPEC`` for all).
+ :param cb: Callback function to invoke for each connection. The callback
+ receives a pointer to a ``netlib_conntrack_s`` structure.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+
+.. c:function:: int netlib_parse_conntrack(const struct nlmsghdr *nlh, size_t
len, struct netlib_conntrack_s *ct)
+
+ Parse a Netlink message containing connection tracking information.
+
+ :param nlh: Pointer to the Netlink message header.
+ :param len: Length of the message.
+ :param ct: Pointer to a ``netlib_conntrack_s`` structure to receive the
+ parsed connection information.
+
+ :return: 0 on success; -1 on error.
diff --git a/Documentation/reference/user/11_network.rst
b/Documentation/reference/user/11_network.rst
index a7d3ac47dca..1d25ff39504 100644
--- a/Documentation/reference/user/11_network.rst
+++ b/Documentation/reference/user/11_network.rst
@@ -413,3 +413,114 @@ the following paragraphs.
- ``NOBUFS``. Insufficient resources are available in the system to
complete the call.
+=============
+DNS Functions
+=============
+
+NuttX provides DNS resolver functions for configuring and managing DNS
+servers. These functions are defined in ``nuttx/net/dns.h`` and allow
+applications to add, remove, and query DNS nameservers.
+
+ - :c:func:`dns_add_nameserver`
+ - :c:func:`dns_del_nameserver`
+ - :c:func:`dns_del_nameserver_by_index`
+ - :c:func:`dns_default_nameserver`
+ - :c:func:`dns_foreach_nameserver`
+ - :c:func:`dns_register_notify`
+ - :c:func:`dns_unregister_notify`
+ - :c:func:`dns_set_queryfamily`
+
+.. c:function:: int dns_add_nameserver(const struct sockaddr *addr, socklen_t
addrlen);
+
+ Configure a DNS server to use for queries. Set the port number to zero
+ to use the default DNS server port (53).
+
+ :param addr: Address of the DNS server (sockaddr_in or sockaddr_in6).
+ :param addrlen: Length of the address structure.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately:
+
+ - ``EINVAL``. Invalid argument.
+ - ``ENOMEM``. Insufficient memory to add the new DNS server.
+
+.. c:function:: int dns_del_nameserver(const struct sockaddr *addr, socklen_t
addrlen);
+
+ Remove a DNS server from the list by address.
+
+ :param addr: Address of the DNS server to remove.
+ :param addrlen: Length of the address structure.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately:
+
+ - ``EINVAL``. Invalid argument.
+ - ``ENOENT``. The specified DNS server was not found.
+
+.. c:function:: int dns_del_nameserver_by_index(int index);
+
+ Remove a DNS server from the list by index (0-based).
+
+ :param index: Index of the DNS server in the list (0-based).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately:
+
+ - ``EINVAL``. Invalid index.
+
+.. c:function:: int dns_default_nameserver(void);
+
+ Reset the resolver to use only the default DNS server, if any. This function
+ clears all added DNS servers and restores the default configuration.
+
+ :return: 0 on success; -1 on error.
+
+.. c:function:: int dns_foreach_nameserver(dns_callback_t callback, void *arg);
+
+ Traverse each nameserver entry and perform the provided callback.
+
+ :param callback: Callback function to invoke for each DNS server. The
callback
+ prototype is: ``int (*callback)(void *arg, struct sockaddr
*addr, socklen_t addrlen)``
+ :param arg: User argument to pass to the callback function.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately.
+ If the callback returns a non-zero value, traversal stops and that
value is returned.
+
+ - ``EINVAL``. Callback function pointer is NULL.
+
+.. c:function:: int dns_register_notify(dns_callback_t callback, void *arg);
+
+ Register a callback function to receive nameserver change notifications.
When the
+ DNS server list changes (servers added or removed), registered callbacks
will be invoked.
+
+ :param callback: Callback function to invoke on nameserver changes.
+ :param arg: User argument to pass to the callback function.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately:
+
+ - ``EINVAL``. Callback function pointer is NULL.
+ - ``ENOMEM``. Insufficient memory to register the notification.
+
+.. c:function:: int dns_unregister_notify(dns_callback_t callback, void *arg);
+
+ Unsubscribe from nameserver change notifications.
+
+ :param callback: Callback function to unregister.
+ :param arg: User argument provided during registration.
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately:
+
+ - ``EINVAL``. Callback function pointer is NULL.
+ - ``ENOENT``. The specified callback was not found.
+
+.. c:function:: int dns_set_queryfamily(sa_family_t family);
+
+ Configure the address family to be used for queries.
+
+ :param family: Address family, can be:
+
+ - ``AF_INET``: Use IPv4 for DNS queries.
+ - ``AF_INET6``: Use IPv6 for DNS queries.
+ - ``AF_UNSPEC``: Automatic selection (prefer IPv6, fallback to IPv4).
+
+ :return: 0 on success; -1 on error with ``errno`` set appropriately:
+
+ - ``EINVAL``. Unsupported address family.
+
diff --git a/include/nuttx/net/dns.h b/include/nuttx/net/dns.h
index a5267deedfb..08a842c8de6 100644
--- a/include/nuttx/net/dns.h
+++ b/include/nuttx/net/dns.h
@@ -2,7 +2,10 @@
* include/nuttx/net/dns.h
*
* SPDX-License-Identifier: BSD-3-Clause
- * SPDX-FileCopyrightText: 2007-2009, 2011-2012, 2014-2015, 2018 Gregory Nutt.
All rights reserved.
+ * SPDX-FileCopyrightText: 2018 Gregory Nutt. All rights reserved.
+ * SPDX-FileCopyrightText: 2014-2015 Gregory Nutt. All rights reserved.
+ * SPDX-FileCopyrightText: 2011-2012 Gregory Nutt. All rights reserved.
+ * SPDX-FileCopyrightText: 2007-2009 Gregory Nutt. All rights reserved.
* SPDX-FileCopyrightText: 2002-2003, Adam Dunkels. All rights reserved.
* SPDX-FileContributor: Gregory Nutt <[email protected]>
* SPDX-FileContributor: Adam Dunkels <[email protected]>
@@ -203,6 +206,26 @@ extern "C"
int dns_add_nameserver(FAR const struct sockaddr *addr, socklen_t addrlen);
+/****************************************************************************
+ * Name: dns_del_nameserver
+ *
+ * Description:
+ * Remove a DNS server from the list by address.
+ *
+ ****************************************************************************/
+
+int dns_del_nameserver(FAR const struct sockaddr *addr, socklen_t addrlen);
+
+/****************************************************************************
+ * Name: dns_del_nameserver_by_index
+ *
+ * Description:
+ * Remove a DNS server from the list by index (0-based).
+ *
+ ****************************************************************************/
+
+int dns_del_nameserver_by_index(int index);
+
/****************************************************************************
* Name: dns_default_nameserver
*
diff --git a/libs/libc/netdb/CMakeLists.txt b/libs/libc/netdb/CMakeLists.txt
index f522c647a92..cf063f00797 100644
--- a/libs/libc/netdb/CMakeLists.txt
+++ b/libs/libc/netdb/CMakeLists.txt
@@ -59,7 +59,8 @@ if(CONFIG_LIBC_NETDB)
if(CONFIG_NETDB_DNSCLIENT)
list(APPEND SRCS lib_dnsinit.c lib_dnsbind.c lib_dnsquery.c)
- list(APPEND SRCS lib_dnsaddserver.c lib_dnsdefaultserver.c)
+ list(APPEND SRCS lib_dnsaddserver.c lib_dnsdelserver.c
+ lib_dnsdefaultserver.c)
list(APPEND SRCS lib_dnsforeach.c lib_dnsnotify.c)
list(APPEND SRCS lib_dnsqueryfamily.c)
diff --git a/libs/libc/netdb/Make.defs b/libs/libc/netdb/Make.defs
index 39f7beef4cd..95aac44cc73 100644
--- a/libs/libc/netdb/Make.defs
+++ b/libs/libc/netdb/Make.defs
@@ -44,7 +44,7 @@ endif
ifeq ($(CONFIG_NETDB_DNSCLIENT),y)
CSRCS += lib_dnsinit.c lib_dnsbind.c lib_dnsquery.c
-CSRCS += lib_dnsaddserver.c lib_dnsdefaultserver.c
+CSRCS += lib_dnsaddserver.c lib_dnsdelserver.c lib_dnsdefaultserver.c
CSRCS += lib_dnsforeach.c lib_dnsnotify.c
CSRCS += lib_dnsqueryfamily.c
diff --git a/libs/libc/netdb/lib_dnsdelserver.c
b/libs/libc/netdb/lib_dnsdelserver.c
new file mode 100644
index 00000000000..4da5f813d07
--- /dev/null
+++ b/libs/libc/netdb/lib_dnsdelserver.c
@@ -0,0 +1,227 @@
+/****************************************************************************
+ * libs/libc/netdb/lib_dnsdelserver.c
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership. The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <stdbool.h>
+#include <stdio.h>
+#include <string.h>
+#include <errno.h>
+#include <debug.h>
+
+#include <nuttx/net/ip.h>
+#include <nuttx/net/dns.h>
+
+#include "netdb/lib_dns.h"
+
+#ifdef CONFIG_NETDB_DNSCLIENT
+
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+#ifndef CONFIG_NETDB_RESOLVCONF
+
+static int dns_find_nameserver_index(FAR const struct sockaddr *addr,
+ socklen_t addrlen)
+{
+ size_t cmplen = 0;
+ int i;
+
+#ifdef CONFIG_NET_IPv4
+ if (addr->sa_family == AF_INET)
+ {
+ cmplen = sizeof(struct sockaddr_in);
+ }
+#endif
+
+#ifdef CONFIG_NET_IPv6
+ if (addr->sa_family == AF_INET6)
+ {
+ cmplen = sizeof(struct sockaddr_in6);
+ }
+#endif
+
+ if (cmplen == 0)
+ {
+ /* Unsupported address family */
+
+ return -ENOSYS;
+ }
+
+ if (addrlen < cmplen)
+ {
+ return -EINVAL;
+ }
+
+ dns_lock();
+
+ /* Search for the matching nameserver in the array */
+
+ for (i = 0; i < g_dns_nservers; i++)
+ {
+ if (g_dns_servers[i].addr.sa_family == addr->sa_family)
+ {
+#ifdef CONFIG_NET_IPv4
+ if (addr->sa_family == AF_INET)
+ {
+ FAR struct sockaddr_in *in1 =
+ (FAR struct sockaddr_in *)&g_dns_servers[i].addr;
+ FAR struct sockaddr_in *in2 =
+ (FAR struct sockaddr_in *)addr;
+
+ /* Compare only the IP address part, ignore port and padding */
+
+ if (net_ipv4addr_cmp(in1->sin_addr.s_addr,
+ in2->sin_addr.s_addr))
+ {
+ dns_unlock();
+ return i;
+ }
+ }
+#endif
+
+#ifdef CONFIG_NET_IPv6
+ if (addr->sa_family == AF_INET6)
+ {
+ FAR struct sockaddr_in6 *in6_1 =
+ (FAR struct sockaddr_in6 *)&g_dns_servers[i].addr;
+ FAR struct sockaddr_in6 *in6_2 =
+ (FAR struct sockaddr_in6 *)addr;
+
+ /* Compare only the IPv6 address part */
+
+ if (net_ipv6addr_cmp(in6_1->sin6_addr.s6_addr,
+ in6_2->sin6_addr.s6_addr))
+ {
+ dns_unlock();
+ return i;
+ }
+ }
+#endif
+ }
+ }
+
+ dns_unlock();
+ return -ENOENT;
+}
+
+#endif /* !CONFIG_NETDB_RESOLVCONF */
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: dns_del_nameserver
+ *
+ * Description:
+ * Remove a DNS server from the list by matching the address
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_NETDB_RESOLVCONF
+
+int dns_del_nameserver(FAR const struct sockaddr *addr, socklen_t addrlen)
+{
+ /* Not implemented for CONFIG_NETDB_RESOLVCONF */
+
+ return -ENOSYS;
+}
+
+int dns_del_nameserver_by_index(int index)
+{
+ /* For resolv.conf mode, removing requires rewriting the file */
+
+ return -ENOSYS;
+}
+
+#else /* !CONFIG_NETDB_RESOLVCONF */
+
+int dns_del_nameserver(FAR const struct sockaddr *addr, socklen_t addrlen)
+{
+ int index;
+
+ if (addr == NULL)
+ {
+ return -EINVAL;
+ }
+
+ /* Find the nameserver in the array */
+
+ index = dns_find_nameserver_index(addr, addrlen);
+ if (index < 0)
+ {
+ return index; /* Return the error code */
+ }
+
+ /* Remove the server by index */
+
+ return dns_del_nameserver_by_index(index);
+}
+
+int dns_del_nameserver_by_index(int index)
+{
+ int i;
+
+ if (index < 0 || index >= CONFIG_NETDB_DNSSERVER_NAMESERVERS)
+ {
+ return -EINVAL;
+ }
+
+ dns_lock();
+
+ if (index >= g_dns_nservers)
+ {
+ dns_unlock();
+ return -ENOENT;
+ }
+
+ /* Shift all subsequent entries down by one position */
+
+ for (i = index; i < g_dns_nservers - 1; i++)
+ {
+ memcpy(&g_dns_servers[i], &g_dns_servers[i + 1],
+ sizeof(union dns_addr_u));
+ }
+
+ memset(&g_dns_servers[g_dns_nservers - 1], 0, sizeof(union dns_addr_u));
+
+ /* Decrement the server count */
+
+ g_dns_nservers--;
+
+ dns_unlock();
+
+#if CONFIG_NETDB_DNSCLIENT_ENTRIES > 0
+ /* Clear the DNS cache after removing a server */
+
+ dns_clear_answer();
+#endif
+
+ return OK;
+}
+
+#endif /* CONFIG_NETDB_RESOLVCONF */
+#endif /* CONFIG_NETDB_DNSCLIENT */