[BusyBox] Patch to network/ifupdown.c

Lars Kellogg-Stedman lars at larsshack.org
Thu Jun 5 19:30:49 UTC 2003


[A previous copy of this didn't make it to the list because I was no 
longer subscribed -- sorry for the dupe, Erik!]

I've run into what appears to be a problem with the mapping implementation 
(in run_mapping()) in network/ifupdown.c.  I've attached a patch the 
resolves my problem, but I wanted to run it by you to make sure it makes 
sense.

Here's the problem:

Let's a assume we've got the following /etc/network/interfaces file:

  auto lo eth0

  mapping eth0
    script /sbin/choose_my_name

  iface eth0-name1 inet static
    address 192.168.1.1
    netmask 255.255.255.0

  iface eth0-name2 inet static
    address 192.168.1.2
    netmask 255.255.255.0

In theory, we have a script (/sbin/choose_my_name) that will return on 
stdout either "eth0-name1" or "eth0-name2".  ifupdown should then use this 
name to find the correct interface definition.  Unfortunately, this won't 
ever work.  When we start run_mapping():

  static char * run_mapping(char *physical, char *logical, int len, struct mapping_defn_t * map)
  {

Both 'physical' and 'logical' will contain the string "eth0", and len == 4.
Later on, we retrieve the output of the script:

    if (fgets(logical, len, out)) {

Unfortunately, the length of our return value is limited by the length of
the 'logical' variable, so we can't ever return anything longer than
len - 1.  This means, of course, that our example would fail with something
along the lines of:

  ifup: Ignoring unknown interface eth.

This same problem actually appears in the Debian version of ifupdown (at
least in 0.6.4)...which leads me to wonder if (a) I've just grossly
misinterpreted something, or (b) nobody is actually using the mapping code.

In any case, my patch has run_mapping() return a string -- either the 
value of 'logical', or a malloc()'d string to hold the return value of the 
mapping script.

-- Lars

-- 
Lars Kellogg-Stedman <lars at larsshack.org>

-------------- next part --------------
Index: networking/ifupdown.c
===================================================================
RCS file: /var/cvs/busybox/networking/ifupdown.c,v
retrieving revision 1.23
diff -u -r1.23 ifupdown.c
--- networking/ifupdown.c	19 Apr 2003 23:15:06 -0000	1.23
+++ networking/ifupdown.c	5 Jun 2003 02:43:56 -0000
@@ -49,6 +49,9 @@
 #define EUNDEFVAR   10002
 #define EUNBALPER   10000
 
+#ifdef CONFIG_FEATURE_IFUPDOWN_MAPPING
+#define MAX_INTERFACE_LENGTH 10
+#endif
 
 #if 0
 #define debug_noise(fmt, args...) printf(fmt, ## args)
@@ -1106,12 +1109,13 @@
 	/* unreached */
 }
 
-static int run_mapping(char *physical, char *logical, int len, struct mapping_defn_t * map)
+static char * run_mapping(char *physical, char *logical, int len, struct mapping_defn_t * map)
 {
 	FILE *in, *out;
 	int i, status;
 	pid_t pid;
 
+	char *new_logical = NULL;
 
 	pid = popen2(&in, &out, map->script, physical, NULL);
 	if (pid == 0) {
@@ -1123,16 +1127,18 @@
 	fclose(in);
 	waitpid(pid, &status, 0);
 	if (WIFEXITED(status) && WEXITSTATUS(status) == 0) {
-		if (fgets(logical, len, out)) {
-			char *pch = logical + bb_strlen(logical) - 1;
+		new_logical = (char *)xmalloc(MAX_INTERFACE_LENGTH);
+
+		if (fgets(new_logical, MAX_INTERFACE_LENGTH, out)) {
+			char *pch = new_logical + bb_strlen(new_logical) - 1;
 
-			while (pch >= logical && isspace(*pch))
+			while (pch >= new_logical && isspace(*pch))
 				*(pch--) = '\0';
 		}
 	}
 	fclose(out);
 
-	return 1;
+	return new_logical ? new_logical : logical;
 }
 #endif /* CONFIG_FEATURE_IFUPDOWN_IPV6 */
 
@@ -1318,7 +1324,7 @@
 					if (verbose) {
 						printf("Running mapping script %s on %s\n", currmap->script, liface);
 					}
-					run_mapping(iface, liface, sizeof(liface), currmap);
+					liface = run_mapping(iface, liface, sizeof(liface), currmap);
 					break;
 				}
 			}


More information about the busybox mailing list