patches for openrc



Hi, Dan

The old baselayout-1 has been removed from Gentoo and openrc has been
stabilized for months. Some configuration style has been changed since
then. These patches add support for the new style. To be compatible,
the code for the old style is kept. But we will remove it in future.

Thanks
-- 
Best wishes,
Mu Qiao
GnuPG fingerprint: 92B1 B0C4 8D14 F8C4 EFA5  3ACC 30B3 0DE4 17B1 57E9
From c5f080923f0c52084a929b4125e8fbe19f6e7279 Mon Sep 17 00:00:00 2001
From: Mu Qiao <qiaomuf gentoo org>
Date: Tue, 6 Dec 2011 14:55:03 +0800
Subject: [PATCH 1/2] ifnet: support reading openrc style

IP configuration like 192.168.1.{2..4} is not supported anymore.
---
 src/settings/plugins/ifnet/connection_parser.c |   14 +-
 src/settings/plugins/ifnet/net_parser.c        |   84 ++++++++++----
 src/settings/plugins/ifnet/net_utils.c         |  144 ++++++++++--------------
 src/settings/plugins/ifnet/tests/net           |   11 ++-
 src/settings/plugins/ifnet/tests/test_all.c    |   30 ++++-
 5 files changed, 163 insertions(+), 120 deletions(-)

diff --git a/src/settings/plugins/ifnet/connection_parser.c b/src/settings/plugins/ifnet/connection_parser.c
index b4aaa8d..66ce318 100644
--- a/src/settings/plugins/ifnet/connection_parser.c
+++ b/src/settings/plugins/ifnet/connection_parser.c
@@ -567,7 +567,7 @@ make_wired_connection_setting (NMConnection *connection,
 		nm_connection_add_setting (connection, NM_SETTING (s_wired));
 }
 
-/* add NM_SETTING_IP4_CONFIG_DHCP_HOSTNAME, 
+/* add NM_SETTING_IP4_CONFIG_DHCP_HOSTNAME,
  * NM_SETTING_IP4_CONFIG_DHCP_CLIENT_ID in future*/
 static void
 make_ip4_setting (NMConnection *connection,
@@ -596,19 +596,19 @@ make_ip4_setting (NMConnection *connection,
 			g_object_unref (ip4_setting);
 			return;
 		}
-		if (!strcmp (method, "dhcp"))
+		if (strstr (method, "dhcp"))
 			g_object_set (ip4_setting,
 						  NM_SETTING_IP4_CONFIG_METHOD,
 						  NM_SETTING_IP4_CONFIG_METHOD_AUTO,
 						  NM_SETTING_IP4_CONFIG_NEVER_DEFAULT, FALSE, NULL);
-		else if (!strcmp (method, "autoip")){
+		else if (strstr (method, "autoip")){
 			g_object_set (ip4_setting,
 						  NM_SETTING_IP4_CONFIG_METHOD,
 						  NM_SETTING_IP4_CONFIG_METHOD_LINK_LOCAL,
 						  NM_SETTING_IP4_CONFIG_NEVER_DEFAULT, FALSE, NULL);
 			nm_connection_add_setting (connection, NM_SETTING (ip4_setting));
 			return;
-		} else if (!strcmp (method, "shared")){
+		} else if (strstr (method, "shared")){
 			g_object_set (ip4_setting,
 						  NM_SETTING_IP4_CONFIG_METHOD,
 						  NM_SETTING_IP4_CONFIG_METHOD_SHARED,
@@ -663,7 +663,7 @@ make_ip4_setting (NMConnection *connection,
 	}
 
 	/* add dhcp hostname and client id */
-	if (!is_static_block && !strcmp (method, "dhcp")) {
+	if (!is_static_block && strstr (method, "dhcp")) {
 		gchar *dhcp_hostname, *client_id;
 
 		get_dhcp_hostname_and_client_id (&dhcp_hostname, &client_id);
@@ -868,7 +868,7 @@ make_ip6_setting (NMConnection *connection,
 		nm_ip6_route_set_dest (route, iblock->ip);
 		nm_ip6_route_set_next_hop (route, iblock->next_hop);
 		nm_ip6_route_set_prefix (route, iblock->prefix);
-		/* metric is not per routes configuration right now 
+		/* metric is not per routes configuration right now
 		 * global metric is also supported (metric="x") */
 		if ((metric_str = ifnet_get_data (conn_name, "metric")) != NULL) {
 			metric = strtol (metric_str, NULL, 10);
@@ -995,7 +995,7 @@ make_wireless_connection_setting (const char *conn_name,
 		goto error;
 	}
 
-	/* mode=0: infrastructure 
+	/* mode=0: infrastructure
 	 * mode=1: adhoc */
 	value = wpa_get_value (conn_name, "mode");
 	if (value)
diff --git a/src/settings/plugins/ifnet/net_parser.c b/src/settings/plugins/ifnet/net_parser.c
index a48103d..4befc37 100644
--- a/src/settings/plugins/ifnet/net_parser.c
+++ b/src/settings/plugins/ifnet/net_parser.c
@@ -169,12 +169,10 @@ init_block_by_line (gchar * buf)
 			conn = add_new_connection_config ("wireless", pos);
 	}
 	data = g_strdup (key_value[1]);
-	tmp = strip_string (data, '(');
-	tmp = strip_string (tmp, ')');
-	strip_string (tmp, '"');
+	tmp = strip_string (data, '"');
 	strip_string (tmp, '\'');
 	if (conn)
-		g_hash_table_insert (conn, g_strdup (key_value[0]),
+		g_hash_table_insert (conn, strip_string (g_strdup (key_value[0]), ' '),
 				     g_strdup (tmp));
 	g_free (data);
 	g_strfreev (key_value);
@@ -283,6 +281,22 @@ is_function (gchar * line)
 	return FALSE;
 }
 
+static void
+append_line (GString *buf, gchar* line)
+{
+	gchar *pos = NULL;
+
+	if ((pos = strchr (line, '#')) != NULL)
+		*pos = '\0';
+	g_strstrip (line);
+
+	if (line[0] != '\0') {
+		g_string_append_printf (buf,
+					" %s", line);
+	}
+	g_free (line);
+}
+
 gboolean
 ifnet_init (gchar * config_file)
 {
@@ -292,6 +306,8 @@ ifnet_init (gchar * config_file)
 	/* Handle multiple lines with brackets */
 	gboolean complete = TRUE;
 
+	gboolean openrc_style = TRUE;
+
 	/* line buffer */
 	GString *buf;
 
@@ -319,36 +335,60 @@ ifnet_init (gchar * config_file)
 			strip_function (channel, line);
 			continue;
 		}
-		if (line[0] != '#' && line[0] != '\0') {
-			gchar *pos = NULL;
 
+		// New openrc style, bash arrays are not allowed. We only care about '"'
+		if (openrc_style && line[0] != '#' && line[0] != '\0'
+				&& !strchr (line, '(') && !strchr (line, ')')) {
+			gchar *tmp = line;
+
+			while ((tmp = strchr (tmp, '"')) != NULL) {
+				complete = !complete;
+				++tmp;
+			}
+
+			append_line (buf, line);
+			// Add "(separator) for routes. It will be easier for later parsing
+			if (strstr (buf->str, "via"))
+				g_string_append_printf (buf, "\"");
+
+			if (!complete)
+				continue;
+
+			strip_string (buf->str, '"');
+
+			init_block_by_line (buf->str);
+			g_string_free (buf, TRUE);
+			buf = g_string_new (NULL);
+		}
+		// Old bash arrays for baselayout-1, to be deleted
+		else if (line[0] != '#' && line[0] != '\0') {
 			if (!complete) {
 				complete =
 				    g_strrstr (line,
 					       ")") == NULL ? FALSE : TRUE;
-				if ((pos = strchr (line, '#')) != NULL)
-					*pos = '\0';
-				g_strstrip (line);
-				if (line[0] != '\0') {
-					g_string_append_printf (buf,
-								" %s", line);
-				}
-				g_free (line);
-				if (!complete)
+
+				append_line (buf, line);
+				if (!complete) {
+					openrc_style = FALSE;
 					continue;
+				}
+				else {
+					openrc_style = TRUE;
+				}
 			} else {
 				complete =
 				    (g_strrstr (line, "(") != NULL
 				     && g_strrstr (line, ")") != NULL)
 				    || g_strrstr (line, "(") == NULL;
-				if ((pos = strchr (line, '#')) != NULL)
-					*pos = '\0';
-				g_strstrip (line);
-				if (line[0] != '\0')
-					g_string_append (buf, line);
-				g_free (line);
+
+				append_line (buf, line);
 				if (!complete)
+				{
+					openrc_style = FALSE;
 					continue;
+				} else {
+					openrc_style = TRUE;
+				}
 			}
 			init_block_by_line (buf->str);
 			g_string_free (buf, TRUE);
@@ -391,7 +431,7 @@ ifnet_set_data (const char *conn_name, const char *key, const char *value)
 	}
 	/* Remove existing key value pair */
 	if (g_hash_table_lookup_extended (conn, key, &old_key, &old_value)) {
-		if (stripped && !strcmp(old_value, stripped)){
+		if (stripped && !strcmp (old_value, stripped)){
 			g_free (stripped);
 			return;
 		}
diff --git a/src/settings/plugins/ifnet/net_utils.c b/src/settings/plugins/ifnet/net_utils.c
index b533ae3..fc7e283 100644
--- a/src/settings/plugins/ifnet/net_utils.c
+++ b/src/settings/plugins/ifnet/net_utils.c
@@ -352,6 +352,49 @@ is_ip6_address (const char *in_address)
 
 }
 
+// 'c' is only used for openrc style
+static gchar **
+split_addresses_by_char (const gchar *addresses, const gchar *c)
+{
+	gchar **ipset;
+
+	if (addresses == NULL)
+		return NULL;
+
+	if (strchr (addresses, '(') != NULL) { // old baselayout style
+		gchar *tmp = g_strdup (addresses);
+		strip_string (tmp, '(');
+		strip_string (tmp, ')');
+		strip_string (tmp, '"');
+		strip_string (tmp, '\'');
+		ipset = g_strsplit (tmp, "\" \"", 0);
+		g_free(tmp);
+	} else { // openrc style
+		if (strstr (addresses, "netmask"))
+			// There is only one ip address if "netmask" is specified.
+			// '\n' is not used in config so there will be only one split.
+			ipset = g_strsplit (addresses, "\n", 0);
+		else
+			ipset = g_strsplit (addresses, c, 0);
+	}
+
+	return ipset;
+}
+
+static gchar **
+split_addresses (const gchar* addresses)
+{
+	// " " is only used by openrc style
+	return split_addresses_by_char (addresses, " ");
+}
+
+static gchar **
+split_routes (const gchar* routes)
+{
+	// "\"" is only used by openrc style
+	return split_addresses_by_char (routes, "\"");
+}
+
 gboolean
 has_ip6_address (const char *conn_name)
 {
@@ -360,7 +403,7 @@ has_ip6_address (const char *conn_name)
 	guint i;
 
 	g_return_val_if_fail (conn_name != NULL, FALSE);
-	ipset = g_strsplit (ifnet_get_data (conn_name, "config"), "\" \"", 0);
+	ipset = split_addresses (ifnet_get_data (conn_name, "config"));
 	length = g_strv_length (ipset);
 	for (i = 0; i < length; i++) {
 		if (!is_ip6_address (ipset[i]))
@@ -512,8 +555,11 @@ get_ip4_gateway (gchar * gateway)
 	tmp = g_strdup (tmp);
 	strip_string (tmp, ' ');
 	strip_string (tmp, '"');
+
+	// Only one gateway is selected
 	if ((split = strstr (tmp, "\"")) != NULL)
 		*split = '\0';
+
 	if (!inet_pton (AF_INET, tmp, &tmp_ip4_addr))
 		goto error;
 	g_free (tmp);
@@ -567,14 +613,11 @@ convert_ip4_config_block (const char *conn_name)
 	gchar *ip;
 	guint32 def_gateway = 0;
 	const char *routes;
-	gchar *pos;
 	ip_block *start = NULL, *current = NULL, *iblock = NULL;
-	const char *pattern =
-	    "((\\d{1,3}\\.\\d{1,3}\\.\\d{1,3}\\.)\\{(\\d{1,3})\\.\\.(\\d{1,3})\\}(/\\d{1,2}))";
 
 	g_return_val_if_fail (conn_name != NULL, NULL);
 
-	ipset = g_strsplit (ifnet_get_data (conn_name, "config"), "\" \"", 0);
+	ipset = split_addresses (ifnet_get_data (conn_name, "config"));
 	length = g_strv_length (ipset);
 
 	routes = ifnet_get_data (conn_name, "routes");
@@ -584,73 +627,16 @@ convert_ip4_config_block (const char *conn_name)
 	for (i = 0; i < length; i++) {
 		ip = ipset[i];
 		ip = strip_string (ip, '"');
-		//Handle ip like 192.168.4.{1..3}
-		if ((pos = strchr (ip, '{')) != NULL) {
-			gchar *ip_start, *ip_prefix;
-			gchar *begin_str, *end_str;
-			int begin, end, j;
-			GRegex *regex;
-			GMatchInfo *match_info;
-
-			regex = g_regex_new (pattern, 0, 0, NULL);
-			g_regex_match (regex, ip, 0, &match_info);
-			g_regex_unref (regex);
-
-			if (!g_match_info_matches (match_info)) {
-				g_match_info_free (match_info);
-				continue;
-			}
-			begin_str = g_match_info_fetch (match_info, 3);
-			end_str = g_match_info_fetch (match_info, 4);
-			begin = atoi (begin_str);
-			end = atoi (end_str);
-			ip_start = g_match_info_fetch (match_info, 2);
-			ip_prefix = g_match_info_fetch (match_info, 5);
-			if (end < begin || begin < 1 || end > 254) {
-				g_match_info_free (match_info);
-				continue;
-			}
-
-			for (j = begin; j <= end; j++) {
-				char suf[4];
-				gchar *newip;
-
-				sprintf (suf, "%d", j);
-				newip =
-				    g_strconcat (ip_start, suf, ip_prefix,
-						 NULL);
-				iblock = create_ip4_block (newip);
-				if (iblock == NULL) {
-					g_free (newip);
-					continue;
-				}
-				if (!iblock->gateway && def_gateway != 0)
-					iblock->gateway = def_gateway;
-				if (start == NULL)
-					start = current = iblock;
-				else {
-					current->next = iblock;
-					current = iblock;
-				}
-				g_free (newip);
-			}
-			g_free (begin_str);
-			g_free (end_str);
-			g_free (ip_start);
-			g_free (ip_prefix);
-			g_match_info_free (match_info);
-		} else {
-			iblock = create_ip4_block (ip);
-			if (iblock == NULL)
-				continue;
-			if (!iblock->gateway && def_gateway != 0)
-				iblock->gateway = def_gateway;
-			if (start == NULL)
-				start = current = iblock;
-			else {
-				current->next = iblock;
-				current = iblock;
-			}
+		iblock = create_ip4_block (ip);
+		if (iblock == NULL)
+			continue;
+		if (!iblock->gateway && def_gateway != 0)
+			iblock->gateway = def_gateway;
+		if (start == NULL)
+			start = current = iblock;
+		else {
+			current->next = iblock;
+			current = iblock;
 		}
 	}
 	g_strfreev (ipset);
@@ -667,7 +653,7 @@ convert_ip6_config_block (const char *conn_name)
 	ip6_block *start = NULL, *current = NULL, *iblock = NULL;
 
 	g_return_val_if_fail (conn_name != NULL, NULL);
-	ipset = g_strsplit (ifnet_get_data (conn_name, "config"), "\" \"", 0);
+	ipset = split_addresses (ifnet_get_data (conn_name, "config"));
 	length = g_strv_length (ipset);
 	for (i = 0; i < length; i++) {
 		ip = ipset[i];
@@ -693,15 +679,11 @@ convert_ip4_routes_block (const char *conn_name)
 	guint length;
 	guint i;
 	gchar *ip;
-	const char *routes;
 	ip_block *start = NULL, *current = NULL, *iblock = NULL;
 
 	g_return_val_if_fail (conn_name != NULL, NULL);
 
-	routes = ifnet_get_data (conn_name, "routes");
-	if (!routes)
-		return NULL;
-	ipset = g_strsplit (routes, "\" \"", 0);
+	ipset = split_routes (ifnet_get_data (conn_name, "routes"));
 	length = g_strv_length (ipset);
 	for (i = 0; i < length; i++) {
 		ip = ipset[i];
@@ -731,15 +713,11 @@ convert_ip6_routes_block (const char *conn_name)
 	guint length;
 	guint i;
 	gchar *ip, *tmp_addr;
-	const char *routes;
 	ip6_block *start = NULL, *current = NULL, *iblock = NULL;
 	struct in6_addr *tmp_ip6_addr;
 
 	g_return_val_if_fail (conn_name != NULL, NULL);
-	routes = ifnet_get_data (conn_name, "routes");
-	if (!routes)
-		return NULL;
-	ipset = g_strsplit (routes, "\" \"", 0);
+	ipset = split_routes (ifnet_get_data (conn_name, "routes"));
 	length = g_strv_length (ipset);
 	for (i = 0; i < length; i++) {
 		ip = ipset[i];
diff --git a/src/settings/plugins/ifnet/tests/net b/src/settings/plugins/ifnet/tests/net
index 0eef399..27d39f4 100644
--- a/src/settings/plugins/ifnet/tests/net
+++ b/src/settings/plugins/ifnet/tests/net
@@ -27,10 +27,9 @@ config_eth2=(
 routes_eth2=("default via  4321:0:1:2:3:4:567:89ab")
 enable_ipv6_eth2="true"
 config_eth3=("nufjlsjlll")
-managed_eth4=("false")
+managed_eth4="false"
 routes_eth4=("default via 4321:0:1:2:3:4:567:89ab")
 config_eth5=("dhcp")
-config_eth6=("192.168.4.{1..101}/24")
 
 config_eth7=( "dhcp" )
 auto_eth7="true"
@@ -38,6 +37,14 @@ auto_eth7="true"
 # missing config_eth8
 auto_eth8="true"
 
+#new openrc style
+config_eth9="202.117.16.10/24 202.117.17.10/24"
+routes_eth9="default via 202.117.16.1
+10.0.0.0/8 via 192.168.0.1
+"
+config_eth10="202.117.16.2 netmask 255.255.255.0"
+routes_eth10="10.0.0.0/8 via 192.168.0.1"
+
 config_myxjtu2=("202.117.16.121/24 brd 202.117.16.255")
 routes_myxjtu2=("default via 202.117.16.1")
 dns_servers_myxjtu2="202.117.0.20 202.117.0.21"
diff --git a/src/settings/plugins/ifnet/tests/test_all.c b/src/settings/plugins/ifnet/tests/test_all.c
index 52d9ce2..9ca5f65 100644
--- a/src/settings/plugins/ifnet/tests/test_all.c
+++ b/src/settings/plugins/ifnet/tests/test_all.c
@@ -37,7 +37,7 @@ static void
 test_getdata ()
 {
 	ASSERT (ifnet_get_data ("eth1", "config")
-		&& strcmp (ifnet_get_data ("eth1", "config"), "dhcp") == 0,
+		&& strcmp (ifnet_get_data ("eth1", "config"), "( \"dhcp\" )") == 0,
 		"get data", "config_eth1 is not correct");
 	ASSERT (ifnet_get_data ("ppp0", "username")
 		&& strcmp (ifnet_get_data ("ppp0", "username"), "user") == 0,
@@ -84,7 +84,7 @@ test_is_static ()
 	ASSERT (is_static_ip4 ("eth0") == TRUE, "is static",
 		"a static interface is recognized as dhcp");
 	ASSERT (!is_static_ip6 ("eth0") == TRUE, "is static",
-		"a static interface is recognized as dhcp");
+		"a dhcp interface is recognized as static");
 }
 
 static void
@@ -182,10 +182,6 @@ test_convert_ipv4_config_block ()
 	ASSERT (iblock == NULL, "convert config_block",
 		"convert error configuration");
 	destroy_ip_block (iblock);
-	iblock = convert_ip4_config_block ("eth6");
-	ASSERT (iblock != NULL, "convert config_block",
-		"convert error configuration");
-	destroy_ip_block (iblock);
 }
 
 static void
@@ -200,6 +196,16 @@ test_convert_ipv4_routes_block ()
 	destroy_ip_block (tmp);
 	ASSERT (iblock == NULL, "convert ip4 routes",
 		"should only get one route");
+
+	iblock = convert_ip4_routes_block ("eth9");
+	tmp = iblock;
+
+	ASSERT (iblock != NULL, "convert ip4 routes", "should get one route");
+	check_ip_block (iblock, "10.0.0.0", "255.0.0.0", "192.168.0.1");
+	iblock = iblock->next;
+	destroy_ip_block (tmp);
+	ASSERT (iblock == NULL, "convert ip4 routes",
+		"should only get one route");
 }
 
 static void
@@ -272,6 +278,18 @@ test_new_connection ()
 		"new connection failed: %s",
 		error ? error->message : "NONE");
 	g_object_unref (connection);
+
+	connection = ifnet_update_connection_from_config_block ("eth9", &error);
+	ASSERT (connection != NULL, "new connection",
+		"new connection(eth9) failed: %s",
+		error ? error->message : "NONE");
+	g_object_unref (connection);
+
+	connection = ifnet_update_connection_from_config_block ("eth10", &error);
+	ASSERT (connection != NULL, "new connection",
+		"new connection(eth10) failed: %s",
+		error ? error->message : "NONE");
+	g_object_unref (connection);
 }
 
 #define NET_GEN_NAME "net.generate"
-- 
1.7.3.4

From e895b3c71cf2c1e3bee09f16d6492664e8de2446 Mon Sep 17 00:00:00 2001
From: Mu Qiao <qiaomuf gentoo org>
Date: Wed, 7 Dec 2011 10:39:26 +0800
Subject: [PATCH 2/2] ifnet: support writing openrc style

---
 src/settings/plugins/ifnet/net_parser.c |   20 +++++++++++++-------
 1 files changed, 13 insertions(+), 7 deletions(-)

diff --git a/src/settings/plugins/ifnet/net_parser.c b/src/settings/plugins/ifnet/net_parser.c
index 4befc37..abca89c 100644
--- a/src/settings/plugins/ifnet/net_parser.c
+++ b/src/settings/plugins/ifnet/net_parser.c
@@ -476,22 +476,28 @@ format_ips (gchar * value, gchar ** out_line, gchar * key, gchar * name)
 	guint length, i;
 	GString *formated_string = g_string_new (NULL);
 
+	strip_string (value, '(');
+	strip_string (value, ')');
 	strip_string (value, '"');
-	ipset = g_strsplit (value, "\" \"", 0);
+	ipset = g_strsplit (value, "\"", 0);
 	length = g_strv_length (ipset);
 
 	//only one line
 	if (length < 2) {
 		*out_line =
-		    g_strdup_printf ("%s_%s=( \"%s\" )\n", key, name, value);
+		    g_strdup_printf ("%s_%s=\"%s\"\n", key, name, value);
 		goto done;
 	}
 	// Multiple lines
-	g_string_append_printf (formated_string, "%s_%s=(\n", key, name);
+	g_string_append_printf (formated_string, "%s_%s=\"\n", key, name);
 	for (i = 0; i < length; i++)
-		g_string_append_printf (formated_string,
-					"\t\"%s\"\n", ipset[i]);
-	g_string_append (formated_string, ")\n");
+	{
+		strip_string (ipset[i], ' ');
+		if (ipset[i][0] != '\0')
+			g_string_append_printf (formated_string,
+						"%s\n", ipset[i]);
+	}
+	g_string_append (formated_string, "\"\n");
 	*out_line = g_strdup (formated_string->str);
 done:
 	g_string_free (formated_string, TRUE);
@@ -506,7 +512,7 @@ ifnet_flush_to_file (const char *config_file)
 	gpointer key, value, name, network;
 	GHashTableIter iter, iter_network;
 	GList *list_iter;
-	gchar *out_line;
+	gchar *out_line = NULL;
 	gsize bytes_written;
 	gboolean result = FALSE;
 
-- 
1.7.3.4



[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]