summaryrefslogtreecommitdiffstats
path: root/extensions/libxt_tos.c
diff options
context:
space:
mode:
authorJan Engelhardt <jengelh@medozas.de>2008-01-20 13:22:42 +0000
committerPatrick McHardy <kaber@trash.net>2008-01-20 13:22:42 +0000
commit0720c1226381f5c71748673c43c12499f1f254c7 (patch)
tree868b1d0be14c82b12b8162429acda4baf9826927 /extensions/libxt_tos.c
parent5c5cd885daf43256f7bd24a3a698306764438145 (diff)
libxt_tos
Move libipt_tos revision 0 to libxt_tos revision 0 and add support for xt_tos match revision 1. Signed-off-by: Jan Engelhardt <jengelh@computergmbh.de>
Diffstat (limited to 'extensions/libxt_tos.c')
-rw-r--r--extensions/libxt_tos.c190
1 files changed, 190 insertions, 0 deletions
diff --git a/extensions/libxt_tos.c b/extensions/libxt_tos.c
new file mode 100644
index 00000000..e437f470
--- /dev/null
+++ b/extensions/libxt_tos.c
@@ -0,0 +1,190 @@
+/*
+ * Shared library add-on to iptables to add tos match support
+ *
+ * Copyright © CC Computer Consultants GmbH, 2007
+ * Contact: Jan Engelhardt <jengelh@computergmbh.de>
+ */
+#include <getopt.h>
+#include <netdb.h>
+#include <stdbool.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include <xtables.h>
+#include <linux/netfilter/xt_dscp.h>
+#include <linux/netfilter_ipv4/ipt_tos.h>
+#include "tos_values.c"
+
+enum {
+ FLAG_TOS = 1 << 0,
+};
+
+static const struct option tos_mt_opts[] = {
+ {.name = "tos", .has_arg = true, .val = 't'},
+ {},
+};
+
+static void tos_mt_help(void)
+{
+ const struct tos_symbol_info *symbol;
+
+ printf(
+"tos match options:\n"
+"[!] --tos value[/mask] Match Type of Service/Priority field value\n"
+"[!] --tos symbol Match TOS field (IPv4 only) by symbol\n"
+" Accepted symbolic names for value are:\n");
+
+ for (symbol = tos_symbol_names; symbol->name != NULL; ++symbol)
+ printf(" (0x%02x) %2u %s\n",
+ symbol->value, symbol->value, symbol->name);
+
+ printf("\n");
+}
+
+static int tos_mt_parse_v0(int c, char **argv, int invert, unsigned int *flags,
+ const void *entry, struct xt_entry_match **match)
+{
+ struct ipt_tos_info *info = (void *)(*match)->data;
+ struct tos_value_mask tvm;
+
+ switch (c) {
+ case 't':
+ param_act(P_ONLY_ONCE, "tos", "--tos", *flags & FLAG_TOS);
+ if (!tos_parse_symbolic(optarg, &tvm, 0xFF))
+ param_act(P_BAD_VALUE, "tos", "--tos", optarg);
+ if (tvm.mask != 0xFF)
+ exit_error(PARAMETER_PROBLEM, "tos: Your kernel is "
+ "too old to support anything besides /0xFF "
+ "as a mask.");
+ info->tos = tvm.value;
+ if (invert)
+ info->invert = true;
+ *flags |= FLAG_TOS;
+ return true;
+ }
+ return false;
+}
+
+static int tos_mt_parse(int c, char **argv, int invert, unsigned int *flags,
+ const void *entry, struct xt_entry_match **match)
+{
+ struct xt_tos_match_info *info = (void *)(*match)->data;
+ struct tos_value_mask tvm = {.mask = 0xFF};
+
+ switch (c) {
+ case 't':
+ param_act(P_ONLY_ONCE, "tos", "--tos", *flags & FLAG_TOS);
+ if (!tos_parse_symbolic(optarg, &tvm, 0x3F))
+ param_act(P_BAD_VALUE, "tos", "--tos", optarg);
+ info->tos_value = tvm.value;
+ info->tos_mask = tvm.mask;
+ if (invert)
+ info->invert = true;
+ *flags |= FLAG_TOS;
+ return true;
+ }
+ return false;
+}
+
+static void tos_mt_check(unsigned int flags)
+{
+ if (flags == 0)
+ exit_error(PARAMETER_PROBLEM,
+ "tos: --tos parameter required");
+}
+
+static void tos_mt_print_v0(const void *ip, const struct xt_entry_match *match,
+ int numeric)
+{
+ const struct ipt_tos_info *info = (const void *)match->data;
+
+ printf("tos match ");
+ if (info->invert)
+ printf("!");
+ if (numeric || !tos_try_print_symbolic("", info->tos, 0x3F))
+ printf("0x%02x ", info->tos);
+}
+
+static void tos_mt_print(const void *ip, const struct xt_entry_match *match,
+ int numeric)
+{
+ const struct xt_tos_match_info *info = (const void *)match->data;
+
+ printf("tos match ");
+ if (info->invert)
+ printf("!");
+ if (numeric ||
+ !tos_try_print_symbolic("", info->tos_value, info->tos_mask))
+ printf("0x%02x/0x%02x ", info->tos_value, info->tos_mask);
+}
+
+static void tos_mt_save_v0(const void *ip, const struct xt_entry_match *match)
+{
+ const struct ipt_tos_info *info = (const void *)match->data;
+
+ if (info->invert)
+ printf("! ");
+ printf("--tos 0x%02x ", info->tos);
+}
+
+static void tos_mt_save(const void *ip, const struct xt_entry_match *match)
+{
+ const struct xt_tos_match_info *info = (const void *)match->data;
+
+ if (info->invert)
+ printf("! ");
+ printf("--tos 0x%02x/0x%02x ", info->tos_value, info->tos_mask);
+}
+
+static struct xtables_match tos_mt_reg_v0 = {
+ .version = IPTABLES_VERSION,
+ .name = "tos",
+ .family = AF_INET,
+ .revision = 0,
+ .size = XT_ALIGN(sizeof(struct ipt_tos_info)),
+ .userspacesize = XT_ALIGN(sizeof(struct ipt_tos_info)),
+ .help = tos_mt_help,
+ .parse = tos_mt_parse_v0,
+ .final_check = tos_mt_check,
+ .print = tos_mt_print_v0,
+ .save = tos_mt_save_v0,
+ .extra_opts = tos_mt_opts,
+};
+
+static struct xtables_match tos_mt_reg = {
+ .version = IPTABLES_VERSION,
+ .name = "tos",
+ .family = AF_INET,
+ .revision = 1,
+ .size = XT_ALIGN(sizeof(struct xt_tos_match_info)),
+ .userspacesize = XT_ALIGN(sizeof(struct xt_tos_match_info)),
+ .help = tos_mt_help,
+ .parse = tos_mt_parse,
+ .final_check = tos_mt_check,
+ .print = tos_mt_print,
+ .save = tos_mt_save,
+ .extra_opts = tos_mt_opts,
+};
+
+static struct xtables_match tos_mt6_reg = {
+ .version = IPTABLES_VERSION,
+ .name = "tos",
+ .family = AF_INET6,
+ .revision = 1,
+ .size = XT_ALIGN(sizeof(struct xt_tos_match_info)),
+ .userspacesize = XT_ALIGN(sizeof(struct xt_tos_match_info)),
+ .help = tos_mt_help,
+ .parse = tos_mt_parse,
+ .final_check = tos_mt_check,
+ .print = tos_mt_print,
+ .save = tos_mt_save,
+ .extra_opts = tos_mt_opts,
+};
+
+void _init(void)
+{
+ xtables_register_match(&tos_mt_reg_v0);
+ xtables_register_match(&tos_mt_reg);
+ xtables_register_match(&tos_mt6_reg);
+}