1*a71a9546SAutomerger Merge Worker #include <stdbool.h> 2*a71a9546SAutomerger Merge Worker #include <stdio.h> 3*a71a9546SAutomerger Merge Worker #include <xtables.h> 4*a71a9546SAutomerger Merge Worker #include <linux/netfilter/xt_mark.h> 5*a71a9546SAutomerger Merge Worker 6*a71a9546SAutomerger Merge Worker struct xt_mark_info { 7*a71a9546SAutomerger Merge Worker unsigned long mark, mask; 8*a71a9546SAutomerger Merge Worker uint8_t invert; 9*a71a9546SAutomerger Merge Worker }; 10*a71a9546SAutomerger Merge Worker 11*a71a9546SAutomerger Merge Worker enum { 12*a71a9546SAutomerger Merge Worker O_MARK = 0, 13*a71a9546SAutomerger Merge Worker }; 14*a71a9546SAutomerger Merge Worker 15*a71a9546SAutomerger Merge Worker static void mark_mt_help(void) 16*a71a9546SAutomerger Merge Worker { 17*a71a9546SAutomerger Merge Worker printf( 18*a71a9546SAutomerger Merge Worker "mark match options:\n" 19*a71a9546SAutomerger Merge Worker "[!] --mark value[/mask] Match nfmark value with optional mask\n"); 20*a71a9546SAutomerger Merge Worker } 21*a71a9546SAutomerger Merge Worker 22*a71a9546SAutomerger Merge Worker static const struct xt_option_entry mark_mt_opts[] = { 23*a71a9546SAutomerger Merge Worker {.name = "mark", .id = O_MARK, .type = XTTYPE_MARKMASK32, 24*a71a9546SAutomerger Merge Worker .flags = XTOPT_MAND | XTOPT_INVERT}, 25*a71a9546SAutomerger Merge Worker XTOPT_TABLEEND, 26*a71a9546SAutomerger Merge Worker }; 27*a71a9546SAutomerger Merge Worker 28*a71a9546SAutomerger Merge Worker static void mark_mt_parse(struct xt_option_call *cb) 29*a71a9546SAutomerger Merge Worker { 30*a71a9546SAutomerger Merge Worker struct xt_mark_mtinfo1 *info = cb->data; 31*a71a9546SAutomerger Merge Worker 32*a71a9546SAutomerger Merge Worker xtables_option_parse(cb); 33*a71a9546SAutomerger Merge Worker if (cb->invert) 34*a71a9546SAutomerger Merge Worker info->invert = true; 35*a71a9546SAutomerger Merge Worker info->mark = cb->val.mark; 36*a71a9546SAutomerger Merge Worker info->mask = cb->val.mask; 37*a71a9546SAutomerger Merge Worker } 38*a71a9546SAutomerger Merge Worker 39*a71a9546SAutomerger Merge Worker static void mark_parse(struct xt_option_call *cb) 40*a71a9546SAutomerger Merge Worker { 41*a71a9546SAutomerger Merge Worker struct xt_mark_info *markinfo = cb->data; 42*a71a9546SAutomerger Merge Worker 43*a71a9546SAutomerger Merge Worker xtables_option_parse(cb); 44*a71a9546SAutomerger Merge Worker if (cb->invert) 45*a71a9546SAutomerger Merge Worker markinfo->invert = 1; 46*a71a9546SAutomerger Merge Worker markinfo->mark = cb->val.mark; 47*a71a9546SAutomerger Merge Worker markinfo->mask = cb->val.mask; 48*a71a9546SAutomerger Merge Worker } 49*a71a9546SAutomerger Merge Worker 50*a71a9546SAutomerger Merge Worker static void 51*a71a9546SAutomerger Merge Worker mark_mt_print(const void *ip, const struct xt_entry_match *match, int numeric) 52*a71a9546SAutomerger Merge Worker { 53*a71a9546SAutomerger Merge Worker const struct xt_mark_mtinfo1 *info = (const void *)match->data; 54*a71a9546SAutomerger Merge Worker 55*a71a9546SAutomerger Merge Worker printf(" mark match"); 56*a71a9546SAutomerger Merge Worker if (info->invert) 57*a71a9546SAutomerger Merge Worker printf(" !"); 58*a71a9546SAutomerger Merge Worker 59*a71a9546SAutomerger Merge Worker xtables_print_mark_mask(info->mark, info->mask); 60*a71a9546SAutomerger Merge Worker } 61*a71a9546SAutomerger Merge Worker 62*a71a9546SAutomerger Merge Worker static void 63*a71a9546SAutomerger Merge Worker mark_print(const void *ip, const struct xt_entry_match *match, int numeric) 64*a71a9546SAutomerger Merge Worker { 65*a71a9546SAutomerger Merge Worker const struct xt_mark_info *info = (const void *)match->data; 66*a71a9546SAutomerger Merge Worker 67*a71a9546SAutomerger Merge Worker printf(" MARK match"); 68*a71a9546SAutomerger Merge Worker 69*a71a9546SAutomerger Merge Worker if (info->invert) 70*a71a9546SAutomerger Merge Worker printf(" !"); 71*a71a9546SAutomerger Merge Worker 72*a71a9546SAutomerger Merge Worker xtables_print_mark_mask(info->mark, info->mask); 73*a71a9546SAutomerger Merge Worker } 74*a71a9546SAutomerger Merge Worker 75*a71a9546SAutomerger Merge Worker static void mark_mt_save(const void *ip, const struct xt_entry_match *match) 76*a71a9546SAutomerger Merge Worker { 77*a71a9546SAutomerger Merge Worker const struct xt_mark_mtinfo1 *info = (const void *)match->data; 78*a71a9546SAutomerger Merge Worker 79*a71a9546SAutomerger Merge Worker if (info->invert) 80*a71a9546SAutomerger Merge Worker printf(" !"); 81*a71a9546SAutomerger Merge Worker 82*a71a9546SAutomerger Merge Worker printf(" --mark"); 83*a71a9546SAutomerger Merge Worker xtables_print_mark_mask(info->mark, info->mask); 84*a71a9546SAutomerger Merge Worker } 85*a71a9546SAutomerger Merge Worker 86*a71a9546SAutomerger Merge Worker static void 87*a71a9546SAutomerger Merge Worker mark_save(const void *ip, const struct xt_entry_match *match) 88*a71a9546SAutomerger Merge Worker { 89*a71a9546SAutomerger Merge Worker const struct xt_mark_info *info = (const void *)match->data; 90*a71a9546SAutomerger Merge Worker 91*a71a9546SAutomerger Merge Worker if (info->invert) 92*a71a9546SAutomerger Merge Worker printf(" !"); 93*a71a9546SAutomerger Merge Worker 94*a71a9546SAutomerger Merge Worker printf(" --mark"); 95*a71a9546SAutomerger Merge Worker xtables_print_mark_mask(info->mark, info->mask); 96*a71a9546SAutomerger Merge Worker } 97*a71a9546SAutomerger Merge Worker 98*a71a9546SAutomerger Merge Worker static void 99*a71a9546SAutomerger Merge Worker print_mark_xlate(struct xt_xlate *xl, unsigned int mark, 100*a71a9546SAutomerger Merge Worker unsigned int mask, uint32_t op) 101*a71a9546SAutomerger Merge Worker { 102*a71a9546SAutomerger Merge Worker if (mask != 0xffffffffU) 103*a71a9546SAutomerger Merge Worker xt_xlate_add(xl, " and 0x%x %s 0x%x", mask, 104*a71a9546SAutomerger Merge Worker op == XT_OP_EQ ? "==" : "!=", mark); 105*a71a9546SAutomerger Merge Worker else 106*a71a9546SAutomerger Merge Worker xt_xlate_add(xl, " %s0x%x", 107*a71a9546SAutomerger Merge Worker op == XT_OP_EQ ? "" : "!= ", mark); 108*a71a9546SAutomerger Merge Worker } 109*a71a9546SAutomerger Merge Worker 110*a71a9546SAutomerger Merge Worker static int mark_mt_xlate(struct xt_xlate *xl, 111*a71a9546SAutomerger Merge Worker const struct xt_xlate_mt_params *params) 112*a71a9546SAutomerger Merge Worker { 113*a71a9546SAutomerger Merge Worker const struct xt_mark_mtinfo1 *info = (const void *)params->match->data; 114*a71a9546SAutomerger Merge Worker enum xt_op op = XT_OP_EQ; 115*a71a9546SAutomerger Merge Worker 116*a71a9546SAutomerger Merge Worker if (info->invert) 117*a71a9546SAutomerger Merge Worker op = XT_OP_NEQ; 118*a71a9546SAutomerger Merge Worker 119*a71a9546SAutomerger Merge Worker xt_xlate_add(xl, "mark"); 120*a71a9546SAutomerger Merge Worker print_mark_xlate(xl, info->mark, info->mask, op); 121*a71a9546SAutomerger Merge Worker 122*a71a9546SAutomerger Merge Worker return 1; 123*a71a9546SAutomerger Merge Worker } 124*a71a9546SAutomerger Merge Worker 125*a71a9546SAutomerger Merge Worker static int mark_xlate(struct xt_xlate *xl, 126*a71a9546SAutomerger Merge Worker const struct xt_xlate_mt_params *params) 127*a71a9546SAutomerger Merge Worker { 128*a71a9546SAutomerger Merge Worker const struct xt_mark_info *info = (const void *)params->match->data; 129*a71a9546SAutomerger Merge Worker enum xt_op op = XT_OP_EQ; 130*a71a9546SAutomerger Merge Worker 131*a71a9546SAutomerger Merge Worker if (info->invert) 132*a71a9546SAutomerger Merge Worker op = XT_OP_NEQ; 133*a71a9546SAutomerger Merge Worker 134*a71a9546SAutomerger Merge Worker xt_xlate_add(xl, "mark"); 135*a71a9546SAutomerger Merge Worker print_mark_xlate(xl, info->mark, info->mask, op); 136*a71a9546SAutomerger Merge Worker 137*a71a9546SAutomerger Merge Worker return 1; 138*a71a9546SAutomerger Merge Worker } 139*a71a9546SAutomerger Merge Worker 140*a71a9546SAutomerger Merge Worker static struct xtables_match mark_mt_reg[] = { 141*a71a9546SAutomerger Merge Worker { 142*a71a9546SAutomerger Merge Worker .family = NFPROTO_UNSPEC, 143*a71a9546SAutomerger Merge Worker .name = "mark", 144*a71a9546SAutomerger Merge Worker .revision = 0, 145*a71a9546SAutomerger Merge Worker .version = XTABLES_VERSION, 146*a71a9546SAutomerger Merge Worker .size = XT_ALIGN(sizeof(struct xt_mark_info)), 147*a71a9546SAutomerger Merge Worker .userspacesize = XT_ALIGN(sizeof(struct xt_mark_info)), 148*a71a9546SAutomerger Merge Worker .help = mark_mt_help, 149*a71a9546SAutomerger Merge Worker .print = mark_print, 150*a71a9546SAutomerger Merge Worker .save = mark_save, 151*a71a9546SAutomerger Merge Worker .x6_parse = mark_parse, 152*a71a9546SAutomerger Merge Worker .x6_options = mark_mt_opts, 153*a71a9546SAutomerger Merge Worker .xlate = mark_xlate, 154*a71a9546SAutomerger Merge Worker }, 155*a71a9546SAutomerger Merge Worker { 156*a71a9546SAutomerger Merge Worker .version = XTABLES_VERSION, 157*a71a9546SAutomerger Merge Worker .name = "mark", 158*a71a9546SAutomerger Merge Worker .revision = 1, 159*a71a9546SAutomerger Merge Worker .family = NFPROTO_UNSPEC, 160*a71a9546SAutomerger Merge Worker .size = XT_ALIGN(sizeof(struct xt_mark_mtinfo1)), 161*a71a9546SAutomerger Merge Worker .userspacesize = XT_ALIGN(sizeof(struct xt_mark_mtinfo1)), 162*a71a9546SAutomerger Merge Worker .help = mark_mt_help, 163*a71a9546SAutomerger Merge Worker .print = mark_mt_print, 164*a71a9546SAutomerger Merge Worker .save = mark_mt_save, 165*a71a9546SAutomerger Merge Worker .x6_parse = mark_mt_parse, 166*a71a9546SAutomerger Merge Worker .x6_options = mark_mt_opts, 167*a71a9546SAutomerger Merge Worker .xlate = mark_mt_xlate, 168*a71a9546SAutomerger Merge Worker }, 169*a71a9546SAutomerger Merge Worker }; 170*a71a9546SAutomerger Merge Worker 171*a71a9546SAutomerger Merge Worker void _init(void) 172*a71a9546SAutomerger Merge Worker { 173*a71a9546SAutomerger Merge Worker xtables_register_matches(mark_mt_reg, ARRAY_SIZE(mark_mt_reg)); 174*a71a9546SAutomerger Merge Worker } 175