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

[libvirt] [PATCH V1 4/6] Use scripting for cleaning and renaming of chains



Use scripts for the renaming and cleaning up of chains. This allows us to get
rid of some of the code that is only capable of renaming and removing chains
whose names are hardcoded.

A shell function 'collect_chains' is introduced that is given the name
of an ebtables chain and then recursively determines the names of all
chanins that are accessed from this chain and its sub-chains using 'jumps'.

This resulting list of chain names is then used to delete all the found
chains by first flushing and then deleting them.

The same function is also used for renaming temporary filters to their final
names.

I tested this with the bash and dash as script interpreters.

---
 src/nwfilter/nwfilter_ebiptables_driver.c |  189 ++++++++++++++++--------------
 1 file changed, 102 insertions(+), 87 deletions(-)

Index: libvirt-acl/src/nwfilter/nwfilter_ebiptables_driver.c
===================================================================
--- libvirt-acl.orig/src/nwfilter/nwfilter_ebiptables_driver.c
+++ libvirt-acl/src/nwfilter/nwfilter_ebiptables_driver.c
@@ -91,6 +91,37 @@ static char *gawk_cmd_path;
 #define PRINT_CHAIN(buf, prefix, ifname, suffix) \
     snprintf(buf, sizeof(buf), "%c-%s-%s", prefix, ifname, suffix)
 
+#define FUNC_COLLECT_CHAINS \
+    "collect_chains()\n" \
+    "{\n" \
+    "  local sc\n" \
+    "  sc=$(%s -t %s -L $1 | \\\n" \
+    "       sed -n \"/Bridge chain*/,$ s/.*\\-j \\([%s]-.*\\)/\\1/p\")\n" \
+    "  for tmp in `echo \"$sc\"`; do\n" \
+    "    sc=\"$sc $(collect_chains $tmp)\"\n" \
+    "  done\n" \
+    "  echo \"$sc\"\n" \
+    "}\n"
+
+#define FUNC_DELETE_CHAINS \
+    "rm_chains()\n" \
+    "{\n" \
+    "  for tmp in `echo \"$1\"`; do %s -t %s -F $tmp; done\n" \
+    "  for tmp in `echo \"$1\"`; do %s -t %s -X $tmp; done\n" \
+    "}\n"
+
+#define FUNC_RENAME_CHAINS \
+    "rename_chains()\n" \
+    "{\n" \
+    "  for tmp in `echo \"$1\"`; do\n" \
+    "    tmp2=`expr substr \"$tmp\" 1 1`\n" \
+    "    if [ $tmp2 = \"%c\" ]; then\n" \
+    "        %s -t %s -E \"$tmp\" \"%c\"`expr substr \"$tmp\" 2 33`\n" \
+    "    elif [ $tmp2 = \"%c\" ]; then\n" \
+    "        %s -t %s -E \"$tmp\" \"%c\"`expr substr \"$tmp\" 2 33`\n" \
+    "    fi\n" \
+    "  done\n" \
+    "}\n"
 
 #define VIRT_IN_CHAIN      "libvirt-in"
 #define VIRT_OUT_CHAIN     "libvirt-out"
@@ -2805,95 +2836,64 @@ ebtablesCreateTmpSubChain(virBufferPtr b
     return 0;
 }
 
-
-static int
-_ebtablesRemoveSubChain(virBufferPtr buf,
-                        int incoming,
-                        const char *ifname,
-                        enum l3_proto_idx protoidx,
-                        int isTempChain)
+static int _ebtablesRemoveSubChains(virBufferPtr buf,
+                                    const char *ifname,
+                                    const char *chains)
 {
-    char rootchain[MAX_CHAINNAME_LENGTH], chain[MAX_CHAINNAME_LENGTH];
-    char chainPrefix;
-
-    if (isTempChain) {
-        chainPrefix =(incoming) ? CHAINPREFIX_HOST_IN_TEMP
-                                : CHAINPREFIX_HOST_OUT_TEMP;
-    } else {
-        chainPrefix =(incoming) ? CHAINPREFIX_HOST_IN
-                                : CHAINPREFIX_HOST_OUT;
-    }
+    char rootchain[MAX_CHAINNAME_LENGTH];
+    unsigned i;
 
-    PRINT_ROOT_CHAIN(rootchain, chainPrefix, ifname);
-    PRINT_CHAIN(chain, chainPrefix, ifname, l3_protocols[protoidx].val);
-
-    virBufferAsprintf(buf,
-                      "%s -t %s -D %s -p 0x%x -j %s" CMD_SEPARATOR
-                      "%s -t %s -F %s" CMD_SEPARATOR
-                      "%s -t %s -X %s" CMD_SEPARATOR,
+    virBufferAsprintf(buf, FUNC_COLLECT_CHAINS,
+                      ebtables_cmd_path, EBTABLES_DEFAULT_TABLE, chains);
+    virBufferAsprintf(buf, FUNC_DELETE_CHAINS,
                       ebtables_cmd_path, EBTABLES_DEFAULT_TABLE,
-                      rootchain, l3_protocols[protoidx].attr, chain,
+                      ebtables_cmd_path, EBTABLES_DEFAULT_TABLE);
 
-                      ebtables_cmd_path, EBTABLES_DEFAULT_TABLE, chain,
+    virBufferAddLit(buf, "a=\"");
+    for (i = 0; chains[i] != 0; i++) {
+        PRINT_ROOT_CHAIN(rootchain, chains[i], ifname);
+        virBufferAsprintf(buf, "$(collect_chains %s) ", rootchain);
+    }
+    virBufferAddLit(buf, "\"\n");
 
-                      ebtables_cmd_path, EBTABLES_DEFAULT_TABLE, chain);
+    for (i = 0; chains[i] != 0; i++) {
+        PRINT_ROOT_CHAIN(rootchain, chains[i], ifname);
+        virBufferAsprintf(buf,
+                          "%s -t %s -F %s\n",
+                          ebtables_cmd_path, EBTABLES_DEFAULT_TABLE,
+                          rootchain);
+    }
+    virBufferAddLit(buf, "rm_chains \"$a\"\n");
 
     return 0;
 }
 
-
-static int
-ebtablesRemoveSubChain(virBufferPtr buf,
-                       int incoming,
-                       const char *ifname,
-                       enum l3_proto_idx protoidx)
-{
-    return _ebtablesRemoveSubChain(buf,
-                                   incoming, ifname, protoidx, 0);
-}
-
-
 static int
 ebtablesRemoveSubChains(virBufferPtr buf,
                         const char *ifname)
 {
-    enum l3_proto_idx i;
-
-    for (i = 0; i < L3_PROTO_LAST_IDX; i++) {
-        ebtablesRemoveSubChain(buf, 1, ifname, i);
-        ebtablesRemoveSubChain(buf, 0, ifname, i);
-    }
-
-    return 0;
-}
-
+    char chains[3] = {
+        CHAINPREFIX_HOST_IN,
+        CHAINPREFIX_HOST_OUT,
+        0
+    };
 
-static int
-ebtablesRemoveTmpSubChain(virBufferPtr buf,
-                          int incoming,
-                          const char *ifname,
-                          enum l3_proto_idx protoidx)
-{
-    return _ebtablesRemoveSubChain(buf,
-                                   incoming, ifname, protoidx, 1);
+    return _ebtablesRemoveSubChains(buf, ifname, chains);
 }
 
-
 static int
 ebtablesRemoveTmpSubChains(virBufferPtr buf,
                            const char *ifname)
 {
-    enum l3_proto_idx i;
-
-    for (i = 0; i < L3_PROTO_LAST_IDX; i++) {
-        ebtablesRemoveTmpSubChain(buf, 1, ifname, i);
-        ebtablesRemoveTmpSubChain(buf, 0, ifname, i);
-    }
+    char chains[3] = {
+        CHAINPREFIX_HOST_IN_TEMP,
+        CHAINPREFIX_HOST_OUT_TEMP,
+        0
+    };
 
-    return 0;
+    return _ebtablesRemoveSubChains(buf, ifname, chains);
 }
 
-
 static int
 ebtablesRenameTmpSubChain(virBufferPtr buf,
                           int incoming,
@@ -2920,31 +2920,49 @@ ebtablesRenameTmpSubChain(virBufferPtr b
     return 0;
 }
 
-
 static int
-ebtablesRenameTmpSubChains(virBufferPtr buf,
+ebtablesRenameTmpRootChain(virBufferPtr buf,
+                           int incoming,
                            const char *ifname)
 {
-    enum l3_proto_idx i;
+    return ebtablesRenameTmpSubChain(buf, incoming, ifname, NULL);
+}
 
-    for (i = 0; i < L3_PROTO_LAST_IDX; i++) {
-        ebtablesRenameTmpSubChain (buf, 1, ifname, l3_protocols[i].val);
-        ebtablesRenameTmpSubChain (buf, 0, ifname, l3_protocols[i].val);
+static int
+ebtablesRenameTmpSubAndRootChains(virBufferPtr buf,
+                                  const char *ifname)
+{
+    char rootchain[MAX_CHAINNAME_LENGTH];
+    unsigned i;
+    char chains[3] = {
+        CHAINPREFIX_HOST_IN_TEMP,
+        CHAINPREFIX_HOST_OUT_TEMP,
+        0};
+
+    virBufferAsprintf(buf, FUNC_COLLECT_CHAINS,
+                      ebtables_cmd_path, EBTABLES_DEFAULT_TABLE, chains);
+    virBufferAsprintf(buf, FUNC_RENAME_CHAINS,
+                      CHAINPREFIX_HOST_IN_TEMP,
+                      ebtables_cmd_path, EBTABLES_DEFAULT_TABLE,
+                      CHAINPREFIX_HOST_IN,
+                      CHAINPREFIX_HOST_OUT_TEMP,
+                      ebtables_cmd_path, EBTABLES_DEFAULT_TABLE,
+                      CHAINPREFIX_HOST_OUT);
+    virBufferAddLit(buf, "a=\"");
+    for (i = 0; chains[i] != 0; i++) {
+        PRINT_ROOT_CHAIN(rootchain, chains[i], ifname);
+        virBufferAsprintf(buf, "$(collect_chains %s) ", rootchain);
     }
+    virBufferAddLit(buf, "\"\n");
 
-    return 0;
-}
+    virBufferAddLit(buf, "rename_chains \"$a\"\n");
 
+    ebtablesRenameTmpRootChain(buf, 1, ifname);
+    ebtablesRenameTmpRootChain(buf, 0, ifname);
 
-static int
-ebtablesRenameTmpRootChain(virBufferPtr buf,
-                           int incoming,
-                           const char *ifname)
-{
-    return ebtablesRenameTmpSubChain(buf, incoming, ifname, NULL);
+    return 0;
 }
 
-
 static void
 ebiptablesInstCommand(virBufferPtr buf,
                       const char *templ, char cmd, int pos,
@@ -3654,9 +3672,7 @@ ebiptablesTearOldRules(virConnectPtr con
         ebtablesRemoveRootChain(&buf, 1, ifname);
         ebtablesRemoveRootChain(&buf, 0, ifname);
 
-        ebtablesRenameTmpSubChains(&buf, ifname);
-        ebtablesRenameTmpRootChain(&buf, 1, ifname);
-        ebtablesRenameTmpRootChain(&buf, 0, ifname);
+        ebtablesRenameTmpSubAndRootChains(&buf, ifname);
 
         ebiptablesExecCLI(&buf, &cli_status);
     }
@@ -3741,12 +3757,11 @@ ebiptablesAllTeardown(const char *ifname
         ebtablesUnlinkRootChain(&buf, 1, ifname);
         ebtablesUnlinkRootChain(&buf, 0, ifname);
 
+        ebtablesRemoveSubChains(&buf, ifname);
+
         ebtablesRemoveRootChain(&buf, 1, ifname);
         ebtablesRemoveRootChain(&buf, 0, ifname);
-
-        ebtablesRemoveSubChains(&buf, ifname);
     }
-
     ebiptablesExecCLI(&buf, &cli_status);
 
     return 0;


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