lokkit --custom-rules expects the passed file to include the iptables command and chain name (e.g. "--inset INPUT") rather than just the rest of the arguments. Add both of those to what will be saved to the rules file and simplify the resulting code by splitting out a argvToString() helper function. The one complication is that when we're removing a rule we need to make sure we don't search for it using "--delete" rather than "--insert". For that reason, only change the argument to "--delete" once we've constructed the string we use to search through the existing rules. Signed-off-by: Mark McLoughlin Index: libvirt/src/iptables.c =================================================================== --- libvirt.orig/src/iptables.c 2008-01-04 12:09:05.000000000 +0000 +++ libvirt.orig/src/iptables.c 2008-01-04 12:09:05.000000000 +0000 @@ -380,37 +380,55 @@ iptablesAddRemoveChain(iptRules *rules, return retval; } +static char * +argvToString(char **argv) +{ + int len, i; + char *ret, *p; + + for (len = 1, i = 0; argv[i]; i++) + len += strlen(argv[i]) + 1; + + if (!(p = ret = (char *)malloc(len))) + return NULL; + + for (i = 0; argv[i]; i++) { + if (i != 0) + *(p++) = ' '; + + strcpy(p, argv[i]); + p += strlen(argv[i]); + } + + *p = '\0'; + + return ret; +} + static int iptablesAddRemoveRule(iptRules *rules, int action, const char *arg, ...) { va_list args; int retval = ENOMEM; char **argv; - char *rule = NULL, *p; + char *rule = NULL; const char *s; - int n, rulelen, command_idx; + int n, command_idx; n = 1 + /* /sbin/iptables */ 2 + /* --table foo */ 2 + /* --insert bar */ 1; /* arg */ - rulelen = strlen(arg) + 1; - va_start(args, arg); - while ((s = va_arg(args, const char *))) { + while ((s = va_arg(args, const char *))) n++; - rulelen += strlen(s) + 1; - } va_end(args); if (!(argv = calloc(n + 1, sizeof(*argv)))) goto error; - if (!(rule = (char *)malloc(rulelen))) - goto error; - n = 0; if (!(argv[n++] = strdup(IPTABLES_PATH))) @@ -424,7 +442,7 @@ iptablesAddRemoveRule(iptRules *rules, i command_idx = n; - if (!(argv[n++] = strdup(action == ADD ? "--insert" : "--delete"))) + if (!(argv[n++] = strdup("--insert"))) goto error; if (!(argv[n++] = strdup(rules->chain))) @@ -433,23 +451,22 @@ iptablesAddRemoveRule(iptRules *rules, i if (!(argv[n++] = strdup(arg))) goto error; - p = strcpy(rule, arg); - p += strlen(arg); - va_start(args, arg); - while ((s = va_arg(args, const char *))) { + while ((s = va_arg(args, const char *))) if (!(argv[n++] = strdup(s))) goto error; - *(p++) = ' '; - strcpy(p, s); - p += strlen(s); - } - va_end(args); - *p = '\0'; + if (!(rule = argvToString(&argv[command_idx]))) + goto error; + + if (action == REMOVE) { + free(argv[command_idx]); + if (!(argv[command_idx] = strdup("--delete"))) + goto error; + } if (action == ADD && (retval = iptablesAddRemoveChain(rules, action))) --