summaryrefslogtreecommitdiffstats
path: root/libip6t_MAP66.c
diff options
context:
space:
mode:
Diffstat (limited to 'libip6t_MAP66.c')
-rw-r--r--libip6t_MAP66.c33
1 files changed, 30 insertions, 3 deletions
diff --git a/libip6t_MAP66.c b/libip6t_MAP66.c
index a5502c3..9fab6a6 100644
--- a/libip6t_MAP66.c
+++ b/libip6t_MAP66.c
@@ -61,6 +61,7 @@ static void MAP66_help(void)
"MAP66 target options\n"
" --" IP6T_MAP66_DST_TO " ipv6addr/prefixlength (Prefix to map IPv6 destination address to)\n"
" --" IP6T_MAP66_SRC_TO " ipv6addr/prefixlength (Prefix to map IPv6 source address to)\n"
+" --offset number (Use another part of addrs to balance csum)\n"
" --nocheck (Disables the do-not-map-to-my-addr check)\n"
"\n"
"Note: you need two ip6tables rules to map an internal network\n"
@@ -140,14 +141,36 @@ static int MAP66_parse(
xtables_error(PARAMETER_PROBLEM, "Invalid IPv6 address in --" IP6T_MAP66_SRC_TO ": \"%s\"", optarg);
}
i = atoi(p + 1);
- if (0 >= i || 128 <= i || 0 != i % 16) {
- xtables_error(PARAMETER_PROBLEM, "Invalid prefix length in --" IP6T_MAP66_SRC_TO ": \"%s\" (use /112, /96 .. /16)", p + 1);
+ if (0 > i || 128 <= i || 0 != i % 16) {
+ xtables_error(PARAMETER_PROBLEM, "Invalid prefix length in --" IP6T_MAP66_SRC_TO ": \"%s\" (use /112, /96 .. /0)", p + 1);
}
info->pfix_src_len = i / 16;
info->pfix_src_csum = ~csum16((const u_int16_t *)&info->pfix_src_to, info->pfix_src_len);
return 1;
break;
case '3':
+ if (!optarg) {
+ xtables_error(PARAMETER_PROBLEM, "--offset: You must specify a value");
+ }
+ if (xtables_check_inverse(optarg, &invert, NULL, 0
+#if IPTABLES_VERSION_CODE >= IPTABLES_VERSION_CMP(1,4,6)
+ ,argv
+#endif
+ )) {
+ xtables_error(PARAMETER_PROBLEM, "Unexpected `!' after --offset");
+ }
+ if (0 != (IP6T_MAP66_OPT_OFFSET & *flags)) {
+ xtables_error(PARAMETER_PROBLEM, "Multiple --offset not supported");
+ }
+ *flags |= IP6T_MAP66_OPT_OFFSET;
+ i = atoi(p + 1);
+ if (0 > i || 14 <= i) {
+ xtables_error(PARAMETER_PROBLEM, "Invalid value in --offset: \"%s\" (use 0-14)", p + 1);
+ }
+ info->mapoffset = i;
+ return 0;
+ break;
+ case '4':
if (0 != (IP6T_MAP66_OPT_NOCHECK & *flags)) {
xtables_error(PARAMETER_PROBLEM, "Multiple --nocheck not supported");
}
@@ -178,6 +201,9 @@ static void MAP66_save(
if (0 != (IP6T_MAP66_OPT_SRC_TO & info->mapflags)) {
printf("--" IP6T_MAP66_SRC_TO " %s/%d ", inet_ntop(AF_INET6, &info->pfix_src_to, s, sizeof(s)), 16 * info->pfix_src_len);
}
+ if (0 != info->mapoffset)) {
+ printf("--offset %d ", info->mapoffset);
+ }
if (0 != (IP6T_MAP66_OPT_NOCHECK & info->mapflags)) {
printf("--nocheck ");
}
@@ -186,7 +212,8 @@ static void MAP66_save(
static struct option MAP66_opts[] = {
{ .name = IP6T_MAP66_DST_TO, .has_arg = 1, .flag = NULL, .val = '1' },
{ .name = IP6T_MAP66_SRC_TO, .has_arg = 1, .flag = NULL, .val = '2' },
- { .name = "nocheck", .has_arg = 0, .flag = NULL, .val = '3' },
+ { .name = "offset", .has_arg = 1, .flag = NULL, .val = '3' },
+ { .name = "nocheck", .has_arg = 0, .flag = NULL, .val = '4' },
{ .name = NULL }
};