summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--extensions/GNUmakefile.in12
-rw-r--r--extensions/libxt_set.h7
-rw-r--r--include/ip6tables.h8
-rw-r--r--include/iptables.h10
-rw-r--r--include/xtables.h.in3
-rw-r--r--ip6tables-multi.c5
-rw-r--r--ip6tables-restore.c6
-rw-r--r--ip6tables-save.c4
-rw-r--r--ip6tables-standalone.c2
-rw-r--r--ip6tables.c30
-rw-r--r--iptables-multi.c6
-rw-r--r--iptables-restore.c10
-rw-r--r--iptables-save.c4
-rw-r--r--iptables-standalone.c4
-rw-r--r--iptables-xml.c2
-rw-r--r--iptables.c32
-rw-r--r--xtables.c66
17 files changed, 123 insertions, 88 deletions
diff --git a/extensions/GNUmakefile.in b/extensions/GNUmakefile.in
index b96bd11f..0e562fb5 100644
--- a/extensions/GNUmakefile.in
+++ b/extensions/GNUmakefile.in
@@ -127,8 +127,8 @@ initext4.c: .initext4.dd
for i in ${initext_func}; do \
echo "extern void lib$${i}_init(void);" >>$@; \
done; \
- echo "void init_extensions(void);" >>$@; \
- echo "void init_extensions(void)" >>$@; \
+ echo "void init_extensions4(void);" >>$@; \
+ echo "void init_extensions4(void)" >>$@; \
echo "{" >>$@; \
for i in ${initext_func}; do \
echo " ""lib$${i}_init();" >>$@; \
@@ -143,8 +143,8 @@ initext6.c: .initext6.dd
for i in ${initext6_func}; do \
echo "extern void lib$${i}_init(void);" >>$@; \
done; \
- echo "void init_extensions(void);" >>$@; \
- echo "void init_extensions(void)" >>$@; \
+ echo "void init_extensions6(void);" >>$@; \
+ echo "void init_extensions6(void)" >>$@; \
echo "{" >>$@; \
for i in ${initext6_func}; do \
echo " ""lib$${i}_init();" >>$@; \
@@ -155,8 +155,8 @@ initext6.c: .initext6.dd
#
# Manual pages
#
-ex_matches = $(sort $(shell echo $(1) | LC_ALL=POSIX grep -Eo '\b[[:alnum:]_]+\b'))
-ex_targets = $(sort $(shell echo $(1) | LC_ALL=POSIX grep -Eo '\b[[:alnum:]_]+\b'))
+ex_matches = $(sort $(shell echo $(1) | LC_ALL=POSIX grep -Eo '\b[[:lower:][:digit:]_]+\b'))
+ex_targets = $(sort $(shell echo $(1) | LC_ALL=POSIX grep -Eo '\b[[:upper:][:digit:]_]+\b'))
man_run = \
${AM_VERBOSE_GEN} \
for ext in $(1); do \
diff --git a/extensions/libxt_set.h b/extensions/libxt_set.h
index 6b936911..4ac84fa9 100644
--- a/extensions/libxt_set.h
+++ b/extensions/libxt_set.h
@@ -114,7 +114,7 @@ parse_dirs_v0(const char *opt_arg, struct xt_set_info_v0 *info)
if (tmp)
xtables_error(PARAMETER_PROBLEM,
"Can't be more src/dst options than %i.",
- IPSET_DIM_MAX - 1);
+ IPSET_DIM_MAX);
free(saved);
}
@@ -124,9 +124,8 @@ parse_dirs(const char *opt_arg, struct xt_set_info *info)
{
char *saved = strdup(opt_arg);
char *ptr, *tmp = saved;
- int i = 0;
- while (i < (IPSET_DIM_MAX - 1) && tmp != NULL) {
+ while (info->dim < IPSET_DIM_MAX && tmp != NULL) {
info->dim++;
ptr = strsep(&tmp, ",");
if (strncmp(ptr, "src", 3) == 0)
@@ -139,7 +138,7 @@ parse_dirs(const char *opt_arg, struct xt_set_info *info)
if (tmp)
xtables_error(PARAMETER_PROBLEM,
"Can't be more src/dst options than %i.",
- IPSET_DIM_MAX - 1);
+ IPSET_DIM_MAX);
free(saved);
}
diff --git a/include/ip6tables.h b/include/ip6tables.h
index ca0f9a05..e976361f 100644
--- a/include/ip6tables.h
+++ b/include/ip6tables.h
@@ -10,10 +10,10 @@
extern int do_command6(int argc, char *argv[], char **table,
struct ip6tc_handle **handle);
-extern int for_each_chain(int (*fn)(const ip6t_chainlabel, int, struct ip6tc_handle *), int verbose, int builtinstoo, struct ip6tc_handle *handle);
-extern int flush_entries(const ip6t_chainlabel chain, int verbose, struct ip6tc_handle *handle);
-extern int delete_chain(const ip6t_chainlabel chain, int verbose, struct ip6tc_handle *handle);
-void print_rule(const struct ip6t_entry *e, struct ip6tc_handle *h, const char *chain, int counters);
+extern int for_each_chain6(int (*fn)(const ip6t_chainlabel, int, struct ip6tc_handle *), int verbose, int builtinstoo, struct ip6tc_handle *handle);
+extern int flush_entries6(const ip6t_chainlabel chain, int verbose, struct ip6tc_handle *handle);
+extern int delete_chain6(const ip6t_chainlabel chain, int verbose, struct ip6tc_handle *handle);
+void print_rule6(const struct ip6t_entry *e, struct ip6tc_handle *h, const char *chain, int counters);
extern struct xtables_globals ip6tables_globals;
diff --git a/include/iptables.h b/include/iptables.h
index 84211c32..65b32909 100644
--- a/include/iptables.h
+++ b/include/iptables.h
@@ -7,15 +7,15 @@
#include <iptables/internal.h>
/* Your shared library should call one of these. */
-extern int do_command(int argc, char *argv[], char **table,
+extern int do_command4(int argc, char *argv[], char **table,
struct iptc_handle **handle);
-extern int delete_chain(const ipt_chainlabel chain, int verbose,
+extern int delete_chain4(const ipt_chainlabel chain, int verbose,
struct iptc_handle *handle);
-extern int flush_entries(const ipt_chainlabel chain, int verbose,
+extern int flush_entries4(const ipt_chainlabel chain, int verbose,
struct iptc_handle *handle);
-extern int for_each_chain(int (*fn)(const ipt_chainlabel, int, struct iptc_handle *),
+extern int for_each_chain4(int (*fn)(const ipt_chainlabel, int, struct iptc_handle *),
int verbose, int builtinstoo, struct iptc_handle *handle);
-extern void print_rule(const struct ipt_entry *e,
+extern void print_rule4(const struct ipt_entry *e,
struct iptc_handle *handle, const char *chain, int counters);
/* kernel revision handling */
diff --git a/include/xtables.h.in b/include/xtables.h.in
index 14d7b043..3bdf7248 100644
--- a/include/xtables.h.in
+++ b/include/xtables.h.in
@@ -379,7 +379,8 @@ extern void xtables_save_string(const char *value);
# undef _init
# define _init _INIT
# endif
- extern void init_extensions(void);
+ extern void init_extensions4(void);
+ extern void init_extensions6(void);
#else
# define _init __attribute__((constructor)) _INIT
#endif
diff --git a/ip6tables-multi.c b/ip6tables-multi.c
index 7e6603f8..40ce37bf 100644
--- a/ip6tables-multi.c
+++ b/ip6tables-multi.c
@@ -2,10 +2,7 @@
#include <stdlib.h>
#include <string.h>
#include "xshared.h"
-
-int ip6tables_main(int argc, char **argv);
-int ip6tables_save_main(int argc, char **argv);
-int ip6tables_restore_main(int argc, char **argv);
+#include "ip6tables-multi.h"
static const struct subcommand multi6_subcommands[] = {
{"ip6tables", ip6tables_main},
diff --git a/ip6tables-restore.c b/ip6tables-restore.c
index 10c3acfc..5531d6e3 100644
--- a/ip6tables-restore.c
+++ b/ip6tables-restore.c
@@ -137,7 +137,7 @@ int main(int argc, char *argv[])
exit(1);
}
#if defined(ALL_INCLUSIVE) || defined(NO_SHARED_LIBS)
- init_extensions();
+ init_extensions6();
#endif
while ((c = getopt_long(argc, argv, "bcvthnM:", options, NULL)) != -1) {
@@ -226,12 +226,12 @@ int main(int argc, char *argv[])
if (noflush == 0) {
DEBUGP("Cleaning all chains of table '%s'\n",
table);
- for_each_chain(flush_entries, verbose, 1,
+ for_each_chain6(flush_entries6, verbose, 1,
handle);
DEBUGP("Deleting all user-defined chains "
"of table '%s'\n", table);
- for_each_chain(delete_chain, verbose, 0,
+ for_each_chain6(delete_chain6, verbose, 0,
handle);
}
diff --git a/ip6tables-save.c b/ip6tables-save.c
index c3b8ec0d..d9ecc62d 100644
--- a/ip6tables-save.c
+++ b/ip6tables-save.c
@@ -109,7 +109,7 @@ static int do_output(const char *tablename)
/* Dump out rules */
e = ip6tc_first_rule(chain, h);
while(e) {
- print_rule(e, h, chain, show_counters);
+ print_rule6(e, h, chain, show_counters);
e = ip6tc_next_rule(e, h);
}
}
@@ -149,7 +149,7 @@ int main(int argc, char *argv[])
exit(1);
}
#if defined(ALL_INCLUSIVE) || defined(NO_SHARED_LIBS)
- init_extensions();
+ init_extensions6();
#endif
while ((c = getopt_long(argc, argv, "bcdt:", options, NULL)) != -1) {
diff --git a/ip6tables-standalone.c b/ip6tables-standalone.c
index 8661bd9c..7d346840 100644
--- a/ip6tables-standalone.c
+++ b/ip6tables-standalone.c
@@ -59,7 +59,7 @@ main(int argc, char *argv[])
}
#if defined(ALL_INCLUSIVE) || defined(NO_SHARED_LIBS)
- init_extensions();
+ init_extensions6();
#endif
ret = do_command6(argc, argv, &table, &handle);
diff --git a/ip6tables.c b/ip6tables.c
index 3beeddf6..f9909f13 100644
--- a/ip6tables.c
+++ b/ip6tables.c
@@ -127,12 +127,6 @@ static struct option original_opts[] = {
{NULL},
};
-/* we need this for ip6tables-restore. ip6tables-restore.c sets line to the
- * current line of the input file, in order to give a more precise error
- * message. ip6tables itself doesn't need this, so it is initialized to the
- * magic number of -1 */
-int line = -1;
-
void ip6tables_exit_error(enum xtables_exittype status, const char *msg, ...) __attribute__((noreturn, format(printf,2,3)));
struct xtables_globals ip6tables_globals = {
.option_offset = 0,
@@ -859,7 +853,7 @@ check_entry(const ip6t_chainlabel chain, struct ip6t_entry *fw,
}
int
-for_each_chain(int (*fn)(const ip6t_chainlabel, int, struct ip6tc_handle *),
+for_each_chain6(int (*fn)(const ip6t_chainlabel, int, struct ip6tc_handle *),
int verbose, int builtinstoo, struct ip6tc_handle *handle)
{
int ret = 1;
@@ -895,11 +889,11 @@ for_each_chain(int (*fn)(const ip6t_chainlabel, int, struct ip6tc_handle *),
}
int
-flush_entries(const ip6t_chainlabel chain, int verbose,
+flush_entries6(const ip6t_chainlabel chain, int verbose,
struct ip6tc_handle *handle)
{
if (!chain)
- return for_each_chain(flush_entries, verbose, 1, handle);
+ return for_each_chain6(flush_entries6, verbose, 1, handle);
if (verbose)
fprintf(stdout, "Flushing chain `%s'\n", chain);
@@ -911,7 +905,7 @@ zero_entries(const ip6t_chainlabel chain, int verbose,
struct ip6tc_handle *handle)
{
if (!chain)
- return for_each_chain(zero_entries, verbose, 1, handle);
+ return for_each_chain6(zero_entries, verbose, 1, handle);
if (verbose)
fprintf(stdout, "Zeroing chain `%s'\n", chain);
@@ -919,11 +913,11 @@ zero_entries(const ip6t_chainlabel chain, int verbose,
}
int
-delete_chain(const ip6t_chainlabel chain, int verbose,
+delete_chain6(const ip6t_chainlabel chain, int verbose,
struct ip6tc_handle *handle)
{
if (!chain)
- return for_each_chain(delete_chain, verbose, 0, handle);
+ return for_each_chain6(delete_chain6, verbose, 0, handle);
if (verbose)
fprintf(stdout, "Deleting chain `%s'\n", chain);
@@ -1083,7 +1077,7 @@ static void print_ip(const char *prefix, const struct in6_addr *ip,
/* We want this to be readable, so only print out neccessary fields.
* Because that's the kind of world I want to live in. */
-void print_rule(const struct ip6t_entry *e,
+void print_rule6(const struct ip6t_entry *e,
struct ip6tc_handle *h, const char *chain, int counters)
{
const struct ip6t_entry_target *t;
@@ -1215,7 +1209,7 @@ list_rules(const ip6t_chainlabel chain, int rulenum, int counters,
while(e) {
num++;
if (!rulenum || num == rulenum)
- print_rule(e, handle, this, counters);
+ print_rule6(e, handle, this, counters);
e = ip6tc_next_rule(e, handle);
}
found = 1;
@@ -1425,11 +1419,11 @@ int do_command6(int argc, char *argv[], char **table, struct ip6tc_handle **hand
cs.jumpto = "";
cs.argv = argv;
- /* re-set optind to 0 in case do_command gets called
+ /* re-set optind to 0 in case do_command6 gets called
* a second time */
optind = 0;
- /* clear mflags in case do_command gets called a second time
+ /* clear mflags in case do_command6 gets called a second time
* (we clear the global list of all matches for security)*/
for (m = xtables_matches; m; m = m->next)
m->mflags = 0;
@@ -1953,7 +1947,7 @@ int do_command6(int argc, char *argv[], char **table, struct ip6tc_handle **hand
*handle);
break;
case CMD_FLUSH:
- ret = flush_entries(chain, cs.options&OPT_VERBOSE, *handle);
+ ret = flush_entries6(chain, cs.options&OPT_VERBOSE, *handle);
break;
case CMD_ZERO:
ret = zero_entries(chain, cs.options&OPT_VERBOSE, *handle);
@@ -1994,7 +1988,7 @@ int do_command6(int argc, char *argv[], char **table, struct ip6tc_handle **hand
ret = ip6tc_create_chain(chain, *handle);
break;
case CMD_DELETE_CHAIN:
- ret = delete_chain(chain, cs.options&OPT_VERBOSE, *handle);
+ ret = delete_chain6(chain, cs.options&OPT_VERBOSE, *handle);
break;
case CMD_RENAME_CHAIN:
ret = ip6tc_rename_chain(chain, newname, *handle);
diff --git a/iptables-multi.c b/iptables-multi.c
index 754b5873..14579e00 100644
--- a/iptables-multi.c
+++ b/iptables-multi.c
@@ -2,11 +2,7 @@
#include <stdlib.h>
#include <string.h>
#include "xshared.h"
-
-int iptables_main(int argc, char **argv);
-int iptables_save_main(int argc, char **argv);
-int iptables_restore_main(int argc, char **argv);
-int iptables_xml_main(int argc, char **argv);
+#include "iptables-multi.h"
static const struct subcommand multi4_subcommands[] = {
{"iptables", iptables_main},
diff --git a/iptables-restore.c b/iptables-restore.c
index c2cc58c8..e4f0604f 100644
--- a/iptables-restore.c
+++ b/iptables-restore.c
@@ -140,7 +140,7 @@ main(int argc, char *argv[])
exit(1);
}
#if defined(ALL_INCLUSIVE) || defined(NO_SHARED_LIBS)
- init_extensions();
+ init_extensions4();
#endif
while ((c = getopt_long(argc, argv, "bcvthnM:T:", options, NULL)) != -1) {
@@ -233,12 +233,12 @@ main(int argc, char *argv[])
if (noflush == 0) {
DEBUGP("Cleaning all chains of table '%s'\n",
table);
- for_each_chain(flush_entries, verbose, 1,
+ for_each_chain4(flush_entries4, verbose, 1,
handle);
DEBUGP("Deleting all user-defined chains "
"of table '%s'\n", table);
- for_each_chain(delete_chain, verbose, 0,
+ for_each_chain4(delete_chain4, verbose, 0,
handle);
}
@@ -438,13 +438,13 @@ main(int argc, char *argv[])
}
}
- DEBUGP("calling do_command(%u, argv, &%s, handle):\n",
+ DEBUGP("calling do_command4(%u, argv, &%s, handle):\n",
newargc, curtable);
for (a = 0; a < newargc; a++)
DEBUGP("argv[%u]: %s\n", a, newargv[a]);
- ret = do_command(newargc, newargv,
+ ret = do_command4(newargc, newargv,
&newargv[2], &handle);
free_argv();
diff --git a/iptables-save.c b/iptables-save.c
index 3e3ec43c..dee17528 100644
--- a/iptables-save.c
+++ b/iptables-save.c
@@ -107,7 +107,7 @@ static int do_output(const char *tablename)
/* Dump out rules */
e = iptc_first_rule(chain, h);
while(e) {
- print_rule(e, h, chain, show_counters);
+ print_rule4(e, h, chain, show_counters);
e = iptc_next_rule(e, h);
}
}
@@ -149,7 +149,7 @@ main(int argc, char *argv[])
exit(1);
}
#if defined(ALL_INCLUSIVE) || defined(NO_SHARED_LIBS)
- init_extensions();
+ init_extensions4();
#endif
while ((c = getopt_long(argc, argv, "bcdt:", options, NULL)) != -1) {
diff --git a/iptables-standalone.c b/iptables-standalone.c
index 1f60e314..b0859464 100644
--- a/iptables-standalone.c
+++ b/iptables-standalone.c
@@ -59,10 +59,10 @@ main(int argc, char *argv[])
exit(1);
}
#if defined(ALL_INCLUSIVE) || defined(NO_SHARED_LIBS)
- init_extensions();
+ init_extensions4();
#endif
- ret = do_command(argc, argv, &table, &handle);
+ ret = do_command4(argc, argv, &table, &handle);
if (ret) {
ret = iptc_commit(handle);
iptc_free(handle);
diff --git a/iptables-xml.c b/iptables-xml.c
index 57c7486d..dc3cd4f2 100644
--- a/iptables-xml.c
+++ b/iptables-xml.c
@@ -844,7 +844,7 @@ main(int argc, char *argv[])
}
}
- DEBUGP("calling do_command(%u, argv, &%s, handle):\n",
+ DEBUGP("calling do_command4(%u, argv, &%s, handle):\n",
newargc, curTable);
for (a = 0; a < newargc; a++)
diff --git a/iptables.c b/iptables.c
index 2c1528ea..0441dce3 100644
--- a/iptables.c
+++ b/iptables.c
@@ -126,12 +126,6 @@ static struct option original_opts[] = {
{NULL},
};
-/* we need this for iptables-restore. iptables-restore.c sets line to the
- * current line of the input file, in order to give a more precise error
- * message. iptables itself doesn't need this, so it is initialized to the
- * magic number of -1 */
-int line = -1;
-
void iptables_exit_error(enum xtables_exittype status, const char *msg, ...) __attribute__((noreturn, format(printf,2,3)));
struct xtables_globals iptables_globals = {
@@ -862,7 +856,7 @@ check_entry(const ipt_chainlabel chain, struct ipt_entry *fw,
}
int
-for_each_chain(int (*fn)(const ipt_chainlabel, int, struct iptc_handle *),
+for_each_chain4(int (*fn)(const ipt_chainlabel, int, struct iptc_handle *),
int verbose, int builtinstoo, struct iptc_handle *handle)
{
int ret = 1;
@@ -898,11 +892,11 @@ for_each_chain(int (*fn)(const ipt_chainlabel, int, struct iptc_handle *),
}
int
-flush_entries(const ipt_chainlabel chain, int verbose,
+flush_entries4(const ipt_chainlabel chain, int verbose,
struct iptc_handle *handle)
{
if (!chain)
- return for_each_chain(flush_entries, verbose, 1, handle);
+ return for_each_chain4(flush_entries4, verbose, 1, handle);
if (verbose)
fprintf(stdout, "Flushing chain `%s'\n", chain);
@@ -914,7 +908,7 @@ zero_entries(const ipt_chainlabel chain, int verbose,
struct iptc_handle *handle)
{
if (!chain)
- return for_each_chain(zero_entries, verbose, 1, handle);
+ return for_each_chain4(zero_entries, verbose, 1, handle);
if (verbose)
fprintf(stdout, "Zeroing chain `%s'\n", chain);
@@ -922,11 +916,11 @@ zero_entries(const ipt_chainlabel chain, int verbose,
}
int
-delete_chain(const ipt_chainlabel chain, int verbose,
+delete_chain4(const ipt_chainlabel chain, int verbose,
struct iptc_handle *handle)
{
if (!chain)
- return for_each_chain(delete_chain, verbose, 0, handle);
+ return for_each_chain4(delete_chain4, verbose, 0, handle);
if (verbose)
fprintf(stdout, "Deleting chain `%s'\n", chain);
@@ -1101,7 +1095,7 @@ static void print_ip(const char *prefix, uint32_t ip,
/* We want this to be readable, so only print out neccessary fields.
* Because that's the kind of world I want to live in. */
-void print_rule(const struct ipt_entry *e,
+void print_rule4(const struct ipt_entry *e,
struct iptc_handle *h, const char *chain, int counters)
{
const struct ipt_entry_target *t;
@@ -1224,7 +1218,7 @@ list_rules(const ipt_chainlabel chain, int rulenum, int counters,
while(e) {
num++;
if (!rulenum || num == rulenum)
- print_rule(e, handle, this, counters);
+ print_rule4(e, handle, this, counters);
e = iptc_next_rule(e, handle);
}
found = 1;
@@ -1429,7 +1423,7 @@ static void command_match(struct iptables_command_state *cs)
xtables_error(OTHER_PROBLEM, "can't alloc memory!");
}
-int do_command(int argc, char *argv[], char **table, struct iptc_handle **handle)
+int do_command4(int argc, char *argv[], char **table, struct iptc_handle **handle)
{
struct iptables_command_state cs;
struct ipt_entry *e = NULL;
@@ -1453,11 +1447,11 @@ int do_command(int argc, char *argv[], char **table, struct iptc_handle **handle
cs.jumpto = "";
cs.argv = argv;
- /* re-set optind to 0 in case do_command gets called
+ /* re-set optind to 0 in case do_command4 gets called
* a second time */
optind = 0;
- /* clear mflags in case do_command gets called a second time
+ /* clear mflags in case do_command4 gets called a second time
* (we clear the global list of all matches for security)*/
for (m = xtables_matches; m; m = m->next)
m->mflags = 0;
@@ -1989,7 +1983,7 @@ int do_command(int argc, char *argv[], char **table, struct iptc_handle **handle
*handle);
break;
case CMD_FLUSH:
- ret = flush_entries(chain, cs.options&OPT_VERBOSE, *handle);
+ ret = flush_entries4(chain, cs.options&OPT_VERBOSE, *handle);
break;
case CMD_ZERO:
ret = zero_entries(chain, cs.options&OPT_VERBOSE, *handle);
@@ -2030,7 +2024,7 @@ int do_command(int argc, char *argv[], char **table, struct iptc_handle **handle
ret = iptc_create_chain(chain, *handle);
break;
case CMD_DELETE_CHAIN:
- ret = delete_chain(chain, cs.options&OPT_VERBOSE, *handle);
+ ret = delete_chain4(chain, cs.options&OPT_VERBOSE, *handle);
break;
case CMD_RENAME_CHAIN:
ret = iptc_rename_chain(chain, newname, *handle);
diff --git a/xtables.c b/xtables.c
index 235e2b27..a260c7bb 100644
--- a/xtables.c
+++ b/xtables.c
@@ -58,6 +58,12 @@
#define PROC_SYS_MODPROBE "/proc/sys/kernel/modprobe"
#endif
+/* we need this for ip6?tables-restore. ip6?tables-restore.c sets line to the
+ * current line of the input file, in order to give a more precise error
+ * message. ip6?tables itself doesn't need this, so it is initialized to the
+ * magic number of -1 */
+int line = -1;
+
void basic_exit_err(enum xtables_exittype status, const char *msg, ...) __attribute__((noreturn, format(printf,2,3)));
struct xtables_globals *xt_params = NULL;
@@ -157,10 +163,18 @@ static const char *xtables_libdir;
/* the path to command to load kernel module */
const char *xtables_modprobe_program;
-/* Keeping track of external matches and targets: linked lists. */
+/* Keep track of matches/targets pending full registration: linked lists. */
+struct xtables_match *xtables_pending_matches;
+struct xtables_target *xtables_pending_targets;
+
+/* Keep track of fully registered external matches/targets: linked lists. */
struct xtables_match *xtables_matches;
struct xtables_target *xtables_targets;
+/* Fully register a match/target which was previously partially registered. */
+static void xtables_fully_register_pending_match(struct xtables_match *me);
+static void xtables_fully_register_pending_target(struct xtables_target *me);
+
void xtables_init(void)
{
xtables_libdir = getenv("XTABLES_LIBDIR");
@@ -539,6 +553,7 @@ struct xtables_match *
xtables_find_match(const char *name, enum xtables_tryload tryload,
struct xtables_rule_match **matches)
{
+ struct xtables_match **dptr;
struct xtables_match *ptr;
const char *icmp6 = "icmp6";
@@ -554,6 +569,18 @@ xtables_find_match(const char *name, enum xtables_tryload tryload,
(strcmp(name,"icmp6") == 0) )
name = icmp6;
+ /* Trigger delayed initialization */
+ for (dptr = &xtables_pending_matches; *dptr; ) {
+ if (strcmp(name, (*dptr)->name) == 0) {
+ ptr = *dptr;
+ *dptr = (*dptr)->next;
+ ptr->next = NULL;
+ xtables_fully_register_pending_match(ptr);
+ } else {
+ dptr = &((*dptr)->next);
+ }
+ }
+
for (ptr = xtables_matches; ptr; ptr = ptr->next) {
if (strcmp(name, ptr->name) == 0) {
struct xtables_match *clone;
@@ -619,6 +646,7 @@ xtables_find_match(const char *name, enum xtables_tryload tryload,
struct xtables_target *
xtables_find_target(const char *name, enum xtables_tryload tryload)
{
+ struct xtables_target **dptr;
struct xtables_target *ptr;
/* Standard target? */
@@ -629,6 +657,18 @@ xtables_find_target(const char *name, enum xtables_tryload tryload)
|| strcmp(name, XTC_LABEL_RETURN) == 0)
name = "standard";
+ /* Trigger delayed initialization */
+ for (dptr = &xtables_pending_targets; *dptr; ) {
+ if (strcmp(name, (*dptr)->name) == 0) {
+ ptr = *dptr;
+ *dptr = (*dptr)->next;
+ ptr->next = NULL;
+ xtables_fully_register_pending_target(ptr);
+ } else {
+ dptr = &((*dptr)->next);
+ }
+ }
+
for (ptr = xtables_targets; ptr; ptr = ptr->next) {
if (strcmp(name, ptr->name) == 0)
break;
@@ -740,8 +780,6 @@ static void xtables_check_options(const char *name, const struct option *opt)
void xtables_register_match(struct xtables_match *me)
{
- struct xtables_match **i, *old;
-
if (me->version == NULL) {
fprintf(stderr, "%s: match %s<%u> is missing a version\n",
xt_params->program_name, me->name, me->revision);
@@ -777,6 +815,15 @@ void xtables_register_match(struct xtables_match *me)
if (me->family != afinfo->family && me->family != AF_UNSPEC)
return;
+ /* place on linked list of matches pending full registration */
+ me->next = xtables_pending_matches;
+ xtables_pending_matches = me;
+}
+
+static void xtables_fully_register_pending_match(struct xtables_match *me)
+{
+ struct xtables_match **i, *old;
+
old = xtables_find_match(me->name, XTF_DURING_LOAD, NULL);
if (old) {
if (old->revision == me->revision &&
@@ -830,8 +877,6 @@ void xtables_register_matches(struct xtables_match *match, unsigned int n)
void xtables_register_target(struct xtables_target *me)
{
- struct xtables_target *old;
-
if (me->version == NULL) {
fprintf(stderr, "%s: target %s<%u> is missing a version\n",
xt_params->program_name, me->name, me->revision);
@@ -867,6 +912,15 @@ void xtables_register_target(struct xtables_target *me)
if (me->family != afinfo->family && me->family != AF_UNSPEC)
return;
+ /* place on linked list of targets pending full registration */
+ me->next = xtables_pending_targets;
+ xtables_pending_targets = me;
+}
+
+static void xtables_fully_register_pending_target(struct xtables_target *me)
+{
+ struct xtables_target *old;
+
old = xtables_find_target(me->name, XTF_DURING_LOAD);
if (old) {
struct xtables_target **i;
@@ -1323,7 +1377,7 @@ void xtables_ipparse_any(const char *name, struct in_addr **addrpp,
const char *xtables_ip6addr_to_numeric(const struct in6_addr *addrp)
{
- /* 0000:0000:0000:0000:0000:000.000.000.000
+ /* 0000:0000:0000:0000:0000:0000:000.000.000.000
* 0000:0000:0000:0000:0000:0000:0000:0000 */
static char buf[50+1];
return inet_ntop(AF_INET6, addrp, buf, sizeof(buf));