about summary refs log tree commit diff
path: root/src/dhcp-manager/nm-dhcp-dhclient-utils.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/dhcp-manager/nm-dhcp-dhclient-utils.c')
-rw-r--r--src/dhcp-manager/nm-dhcp-dhclient-utils.c167
1 files changed, 98 insertions, 69 deletions
diff --git a/src/dhcp-manager/nm-dhcp-dhclient-utils.c b/src/dhcp-manager/nm-dhcp-dhclient-utils.c
index ab49a765..f3d3b1b6 100644
--- a/src/dhcp-manager/nm-dhcp-dhclient-utils.c
+++ b/src/dhcp-manager/nm-dhcp-dhclient-utils.c
@@ -22,7 +22,6 @@
 #include <glib.h>
 #include <glib/gi18n.h>
 #include <string.h>
-#include <ctype.h>
 
 #include "nm-dhcp-dhclient-utils.h"
 
@@ -30,8 +29,11 @@
 #define CLIENTID_FORMAT         CLIENTID_TAG " \"%s\"; # added by NetworkManager"
 #define CLIENTID_FORMAT_OCTETS  CLIENTID_TAG " %s; # added by NetworkManager"
 
-#define HOSTNAME_TAG     "send host-name"
-#define HOSTNAME_FORMAT  HOSTNAME_TAG " \"%s\"; # added by NetworkManager"
+#define HOSTNAME4_TAG    "send host-name"
+#define HOSTNAME4_FORMAT HOSTNAME4_TAG " \"%s\"; # added by NetworkManager"
+
+#define HOSTNAME6_TAG    "send fqdn.fqdn"
+#define HOSTNAME6_FORMAT HOSTNAME6_TAG " \"%s\"; # added by NetworkManager"
 
 #define ALSOREQ_TAG "also request "
 
@@ -47,9 +49,83 @@ add_also_request (GPtrArray *array, const char *item)
 	g_ptr_array_add (array, g_strdup (item));
 }
 
+static void
+add_hostname (GString *str, const char *format, const char *hostname)
+{
+	char *plain_hostname, *dot;
+
+	if (hostname) {
+		plain_hostname = g_strdup (hostname);
+		dot = strchr (plain_hostname, '.');
+		/* get rid of the domain */
+		if (dot)
+			*dot = '\0';
+
+		g_string_append_printf (str, format, plain_hostname);
+		g_free (plain_hostname);
+	}
+}
+
+static void
+add_ip4_config (GString *str, NMSettingIP4Config *s_ip4, const char *hostname)
+{
+	if (s_ip4) {
+		const char *tmp;
+
+		tmp = nm_setting_ip4_config_get_dhcp_client_id (s_ip4);
+		if (tmp) {
+			gboolean is_octets = TRUE;
+			const char *p = tmp;
+
+			while (*p) {
+				if (!g_ascii_isxdigit (*p) && (*p != ':')) {
+					is_octets = FALSE;
+					break;
+				}
+				p++;
+			}
+
+			/* If the client ID is just hex digits and : then don't use quotes,
+			 * because dhclient expects either a quoted ASCII string, or a byte
+			 * array formated as hex octets separated by :
+			 */
+			if (is_octets)
+				g_string_append_printf (str, CLIENTID_FORMAT_OCTETS "\n", tmp);
+			else
+				g_string_append_printf (str, CLIENTID_FORMAT "\n", tmp);
+		}
+	}
+
+	add_hostname (str, HOSTNAME4_FORMAT "\n", hostname);
+
+	g_string_append_c (str, '\n');
+
+	/* Define options for classless static routes */
+	g_string_append (str,
+	                 "option rfc3442-classless-static-routes code 121 = array of unsigned integer 8;\n");
+	g_string_append (str,
+	                 "option ms-classless-static-routes code 249 = array of unsigned integer 8;\n");
+	/* Web Proxy Auto-Discovery option (bgo #368423) */
+	g_string_append (str, "option wpad code 252 = string;\n");
+
+	g_string_append_c (str, '\n');
+}
+
+static void
+add_ip6_config (GString *str, NMSettingIP6Config *s_ip6, const char *hostname)
+{
+	add_hostname (str, HOSTNAME6_FORMAT "\n", hostname);
+	g_string_append (str,
+	                 "send fqdn.encoded on;\n"
+	                 "send fqdn.no-client-update on;\n"
+	                 "send fqdn.server-update on;\n");
+}
+
 char *
 nm_dhcp_dhclient_create_config (const char *interface,
+                                gboolean is_ip6,
                                 NMSettingIP4Config *s_ip4,
+                                NMSettingIP6Config *s_ip6,
                                 guint8 *anycast_addr,
                                 const char *hostname,
                                 const char *orig_path,
@@ -84,8 +160,12 @@ nm_dhcp_dhclient_create_config (const char *interface,
 				continue;
 
 			/* Override config file hostname and use one from the connection */
-			if (hostname && !strncmp (p, HOSTNAME_TAG, strlen (HOSTNAME_TAG)))
-				continue;
+			if (hostname) {
+				if (strncmp (p, HOSTNAME4_TAG, strlen (HOSTNAME4_TAG)) == 0)
+					continue;
+				if (strncmp (p, HOSTNAME6_TAG, strlen (HOSTNAME6_TAG)) == 0)
+					continue;
+			}
 
 			/* Check for "also require" */
 			if (!strncmp (p, ALSOREQ_TAG, strlen (ALSOREQ_TAG))) {
@@ -108,7 +188,7 @@ nm_dhcp_dhclient_create_config (const char *interface,
 						break;
 					}
 
-					if (!isalnum ((*aiter)[0]))
+					if (!g_ascii_isalnum ((*aiter)[0]))
 						continue;
 
 					if ((*aiter)[strlen (*aiter) - 1] == ';') {
@@ -136,71 +216,20 @@ nm_dhcp_dhclient_create_config (const char *interface,
 	} else
 		g_string_append_c (new_contents, '\n');
 
-	/* Add NM options from connection */
-	if (s_ip4) {
-		const char *tmp;
-		gboolean added = FALSE;
-
-		tmp = nm_setting_ip4_config_get_dhcp_client_id (s_ip4);
-		if (tmp) {
-			gboolean is_octets = TRUE;
-			const char *p = tmp;
-
-			while (*p) {
-				if (!isxdigit (*p) && (*p != ':')) {
-					is_octets = FALSE;
-					break;
-				}
-				p++;
-			}
-
-			/* If the client ID is just hex digits and : then don't use quotes,
-			 * because dhclient expects either a quoted ASCII string, or a byte
-			 * array formated as hex octets separated by :
-			 */
-			if (is_octets)
-				g_string_append_printf (new_contents, CLIENTID_FORMAT_OCTETS "\n", tmp);
-			else
-				g_string_append_printf (new_contents, CLIENTID_FORMAT "\n", tmp);
-			added = TRUE;
-		}
-
-		if (hostname) {
-			char *plain_hostname, *dot;
-
-			plain_hostname = g_strdup (hostname);
-			dot = strchr (plain_hostname, '.');
-
-			/* get rid of the domain */
-			if (dot)
-				*dot = '\0';
-
-			g_string_append_printf (new_contents, HOSTNAME_FORMAT "\n", plain_hostname);
-			added = TRUE;
-
-			g_free (plain_hostname);
-		}
-
-		if (added)
-			g_string_append_c (new_contents, '\n');
+	if (is_ip6) {
+		add_ip6_config (new_contents, s_ip6, hostname);
+		add_also_request (alsoreq, "dhcp6.name-servers");
+		add_also_request (alsoreq, "dhcp6.domain-search");
+		add_also_request (alsoreq, "dhcp6.client-id");
+		add_also_request (alsoreq, "dhcp6.server-id");
+	} else {
+		add_ip4_config (new_contents, s_ip4, hostname);
+		add_also_request (alsoreq, "rfc3442-classless-static-routes");
+		add_also_request (alsoreq, "ms-classless-static-routes");
+		add_also_request (alsoreq, "wpad");
+		add_also_request (alsoreq, "ntp-servers");
 	}
 
-	/* Define options for classless static routes */
-	g_string_append (new_contents,
-	                 "option rfc3442-classless-static-routes code 121 = array of unsigned integer 8;\n");
-	g_string_append (new_contents,
-	                 "option ms-classless-static-routes code 249 = array of unsigned integer 8;\n");
-	/* Web Proxy Auto-Discovery option (bgo #368423) */
-	g_string_append (new_contents, "option wpad code 252 = string;\n");
-
-	g_string_append_c (new_contents, '\n');
-
-	/* Everything we want to request from the DHCP server */
-	add_also_request (alsoreq, "rfc3442-classless-static-routes");
-	add_also_request (alsoreq, "ms-classless-static-routes");
-	add_also_request (alsoreq, "wpad");
-	add_also_request (alsoreq, "ntp-servers");
-
 	/* And add it to the dhclient configuration */
 	for (i = 0; i < alsoreq->len; i++) {
 		char *t = g_ptr_array_index (alsoreq, i);