Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

netfilter: xtables: avoid NFPROTO_UNSPEC where needed

syzbot managed to call xt_cluster match via ebtables:

WARNING: CPU: 0 PID: 11 at net/netfilter/xt_cluster.c:72 xt_cluster_mt+0x196/0x780
[..]
ebt_do_table+0x174b/0x2a40

Module registers to NFPROTO_UNSPEC, but it assumes ipv4/ipv6 packet
processing. As this is only useful to restrict locally terminating
TCP/UDP traffic, register this for ipv4 and ipv6 family only.

Pablo points out that this is a general issue, direct users of the
set/getsockopt interface can call into targets/matches that were only
intended for use with ip(6)tables.

Check all UNSPEC matches and targets for similar issues:

- matches and targets are fine except if they assume skb_network_header()
is valid -- this is only true when called from inet layer: ip(6) stack
pulls the ip/ipv6 header into linear data area.
- targets that return XT_CONTINUE or other xtables verdicts must be
restricted too, they are incompatbile with the ebtables traverser, e.g.
EBT_CONTINUE is a completely different value than XT_CONTINUE.

Most matches/targets are changed to register for NFPROTO_IPV4/IPV6, as
they are provided for use by ip(6)tables.

The MARK target is also used by arptables, so register for NFPROTO_ARP too.

While at it, bail out if connbytes fails to enable the corresponding
conntrack family.

This change passes the selftests in iptables.git.

Reported-by: syzbot+256c348558aa5cf611a9@syzkaller.appspotmail.com
Closes: https://lore.kernel.org/netfilter-devel/66fec2e2.050a0220.9ec68.0047.GAE@google.com/
Fixes: 0269ea493734 ("netfilter: xtables: add cluster match")
Signed-off-by: Florian Westphal <fw@strlen.de>
Co-developed-by: Pablo Neira Ayuso <pablo@netfilter.org>
Signed-off-by: Pablo Neira Ayuso <pablo@netfilter.org>

authored by

Florian Westphal and committed by
Pablo Neira Ayuso
0bfcb7b7 983e35ce

+443 -186
+23 -10
net/netfilter/xt_CHECKSUM.c
··· 63 63 return 0; 64 64 } 65 65 66 - static struct xt_target checksum_tg_reg __read_mostly = { 67 - .name = "CHECKSUM", 68 - .family = NFPROTO_UNSPEC, 69 - .target = checksum_tg, 70 - .targetsize = sizeof(struct xt_CHECKSUM_info), 71 - .table = "mangle", 72 - .checkentry = checksum_tg_check, 73 - .me = THIS_MODULE, 66 + static struct xt_target checksum_tg_reg[] __read_mostly = { 67 + { 68 + .name = "CHECKSUM", 69 + .family = NFPROTO_IPV4, 70 + .target = checksum_tg, 71 + .targetsize = sizeof(struct xt_CHECKSUM_info), 72 + .table = "mangle", 73 + .checkentry = checksum_tg_check, 74 + .me = THIS_MODULE, 75 + }, 76 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 77 + { 78 + .name = "CHECKSUM", 79 + .family = NFPROTO_IPV6, 80 + .target = checksum_tg, 81 + .targetsize = sizeof(struct xt_CHECKSUM_info), 82 + .table = "mangle", 83 + .checkentry = checksum_tg_check, 84 + .me = THIS_MODULE, 85 + }, 86 + #endif 74 87 }; 75 88 76 89 static int __init checksum_tg_init(void) 77 90 { 78 - return xt_register_target(&checksum_tg_reg); 91 + return xt_register_targets(checksum_tg_reg, ARRAY_SIZE(checksum_tg_reg)); 79 92 } 80 93 81 94 static void __exit checksum_tg_exit(void) 82 95 { 83 - xt_unregister_target(&checksum_tg_reg); 96 + xt_unregister_targets(checksum_tg_reg, ARRAY_SIZE(checksum_tg_reg)); 84 97 } 85 98 86 99 module_init(checksum_tg_init);
+14 -2
net/netfilter/xt_CLASSIFY.c
··· 38 38 { 39 39 .name = "CLASSIFY", 40 40 .revision = 0, 41 - .family = NFPROTO_UNSPEC, 41 + .family = NFPROTO_IPV4, 42 42 .hooks = (1 << NF_INET_LOCAL_OUT) | (1 << NF_INET_FORWARD) | 43 - (1 << NF_INET_POST_ROUTING), 43 + (1 << NF_INET_POST_ROUTING), 44 44 .target = classify_tg, 45 45 .targetsize = sizeof(struct xt_classify_target_info), 46 46 .me = THIS_MODULE, ··· 54 54 .targetsize = sizeof(struct xt_classify_target_info), 55 55 .me = THIS_MODULE, 56 56 }, 57 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 58 + { 59 + .name = "CLASSIFY", 60 + .revision = 0, 61 + .family = NFPROTO_IPV6, 62 + .hooks = (1 << NF_INET_LOCAL_OUT) | (1 << NF_INET_FORWARD) | 63 + (1 << NF_INET_POST_ROUTING), 64 + .target = classify_tg, 65 + .targetsize = sizeof(struct xt_classify_target_info), 66 + .me = THIS_MODULE, 67 + }, 68 + #endif 57 69 }; 58 70 59 71 static int __init classify_tg_init(void)
+25 -11
net/netfilter/xt_CONNSECMARK.c
··· 114 114 nf_ct_netns_put(par->net, par->family); 115 115 } 116 116 117 - static struct xt_target connsecmark_tg_reg __read_mostly = { 118 - .name = "CONNSECMARK", 119 - .revision = 0, 120 - .family = NFPROTO_UNSPEC, 121 - .checkentry = connsecmark_tg_check, 122 - .destroy = connsecmark_tg_destroy, 123 - .target = connsecmark_tg, 124 - .targetsize = sizeof(struct xt_connsecmark_target_info), 125 - .me = THIS_MODULE, 117 + static struct xt_target connsecmark_tg_reg[] __read_mostly = { 118 + { 119 + .name = "CONNSECMARK", 120 + .revision = 0, 121 + .family = NFPROTO_IPV4, 122 + .checkentry = connsecmark_tg_check, 123 + .destroy = connsecmark_tg_destroy, 124 + .target = connsecmark_tg, 125 + .targetsize = sizeof(struct xt_connsecmark_target_info), 126 + .me = THIS_MODULE, 127 + }, 128 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 129 + { 130 + .name = "CONNSECMARK", 131 + .revision = 0, 132 + .family = NFPROTO_IPV6, 133 + .checkentry = connsecmark_tg_check, 134 + .destroy = connsecmark_tg_destroy, 135 + .target = connsecmark_tg, 136 + .targetsize = sizeof(struct xt_connsecmark_target_info), 137 + .me = THIS_MODULE, 138 + }, 139 + #endif 126 140 }; 127 141 128 142 static int __init connsecmark_tg_init(void) 129 143 { 130 - return xt_register_target(&connsecmark_tg_reg); 144 + return xt_register_targets(connsecmark_tg_reg, ARRAY_SIZE(connsecmark_tg_reg)); 131 145 } 132 146 133 147 static void __exit connsecmark_tg_exit(void) 134 148 { 135 - xt_unregister_target(&connsecmark_tg_reg); 149 + xt_unregister_targets(connsecmark_tg_reg, ARRAY_SIZE(connsecmark_tg_reg)); 136 150 } 137 151 138 152 module_init(connsecmark_tg_init);
+90 -58
net/netfilter/xt_CT.c
··· 313 313 xt_ct_tg_destroy(par, par->targinfo); 314 314 } 315 315 316 - static struct xt_target xt_ct_tg_reg[] __read_mostly = { 317 - { 318 - .name = "CT", 319 - .family = NFPROTO_UNSPEC, 320 - .targetsize = sizeof(struct xt_ct_target_info), 321 - .usersize = offsetof(struct xt_ct_target_info, ct), 322 - .checkentry = xt_ct_tg_check_v0, 323 - .destroy = xt_ct_tg_destroy_v0, 324 - .target = xt_ct_target_v0, 325 - .table = "raw", 326 - .me = THIS_MODULE, 327 - }, 328 - { 329 - .name = "CT", 330 - .family = NFPROTO_UNSPEC, 331 - .revision = 1, 332 - .targetsize = sizeof(struct xt_ct_target_info_v1), 333 - .usersize = offsetof(struct xt_ct_target_info, ct), 334 - .checkentry = xt_ct_tg_check_v1, 335 - .destroy = xt_ct_tg_destroy_v1, 336 - .target = xt_ct_target_v1, 337 - .table = "raw", 338 - .me = THIS_MODULE, 339 - }, 340 - { 341 - .name = "CT", 342 - .family = NFPROTO_UNSPEC, 343 - .revision = 2, 344 - .targetsize = sizeof(struct xt_ct_target_info_v1), 345 - .usersize = offsetof(struct xt_ct_target_info, ct), 346 - .checkentry = xt_ct_tg_check_v2, 347 - .destroy = xt_ct_tg_destroy_v1, 348 - .target = xt_ct_target_v1, 349 - .table = "raw", 350 - .me = THIS_MODULE, 351 - }, 352 - }; 353 - 354 316 static unsigned int 355 317 notrack_tg(struct sk_buff *skb, const struct xt_action_param *par) 356 318 { ··· 325 363 return XT_CONTINUE; 326 364 } 327 365 328 - static struct xt_target notrack_tg_reg __read_mostly = { 329 - .name = "NOTRACK", 330 - .revision = 0, 331 - .family = NFPROTO_UNSPEC, 332 - .target = notrack_tg, 333 - .table = "raw", 334 - .me = THIS_MODULE, 366 + static struct xt_target xt_ct_tg_reg[] __read_mostly = { 367 + { 368 + .name = "NOTRACK", 369 + .revision = 0, 370 + .family = NFPROTO_IPV4, 371 + .target = notrack_tg, 372 + .table = "raw", 373 + .me = THIS_MODULE, 374 + }, 375 + { 376 + .name = "CT", 377 + .family = NFPROTO_IPV4, 378 + .targetsize = sizeof(struct xt_ct_target_info), 379 + .usersize = offsetof(struct xt_ct_target_info, ct), 380 + .checkentry = xt_ct_tg_check_v0, 381 + .destroy = xt_ct_tg_destroy_v0, 382 + .target = xt_ct_target_v0, 383 + .table = "raw", 384 + .me = THIS_MODULE, 385 + }, 386 + { 387 + .name = "CT", 388 + .family = NFPROTO_IPV4, 389 + .revision = 1, 390 + .targetsize = sizeof(struct xt_ct_target_info_v1), 391 + .usersize = offsetof(struct xt_ct_target_info, ct), 392 + .checkentry = xt_ct_tg_check_v1, 393 + .destroy = xt_ct_tg_destroy_v1, 394 + .target = xt_ct_target_v1, 395 + .table = "raw", 396 + .me = THIS_MODULE, 397 + }, 398 + { 399 + .name = "CT", 400 + .family = NFPROTO_IPV4, 401 + .revision = 2, 402 + .targetsize = sizeof(struct xt_ct_target_info_v1), 403 + .usersize = offsetof(struct xt_ct_target_info, ct), 404 + .checkentry = xt_ct_tg_check_v2, 405 + .destroy = xt_ct_tg_destroy_v1, 406 + .target = xt_ct_target_v1, 407 + .table = "raw", 408 + .me = THIS_MODULE, 409 + }, 410 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 411 + { 412 + .name = "NOTRACK", 413 + .revision = 0, 414 + .family = NFPROTO_IPV6, 415 + .target = notrack_tg, 416 + .table = "raw", 417 + .me = THIS_MODULE, 418 + }, 419 + { 420 + .name = "CT", 421 + .family = NFPROTO_IPV6, 422 + .targetsize = sizeof(struct xt_ct_target_info), 423 + .usersize = offsetof(struct xt_ct_target_info, ct), 424 + .checkentry = xt_ct_tg_check_v0, 425 + .destroy = xt_ct_tg_destroy_v0, 426 + .target = xt_ct_target_v0, 427 + .table = "raw", 428 + .me = THIS_MODULE, 429 + }, 430 + { 431 + .name = "CT", 432 + .family = NFPROTO_IPV6, 433 + .revision = 1, 434 + .targetsize = sizeof(struct xt_ct_target_info_v1), 435 + .usersize = offsetof(struct xt_ct_target_info, ct), 436 + .checkentry = xt_ct_tg_check_v1, 437 + .destroy = xt_ct_tg_destroy_v1, 438 + .target = xt_ct_target_v1, 439 + .table = "raw", 440 + .me = THIS_MODULE, 441 + }, 442 + { 443 + .name = "CT", 444 + .family = NFPROTO_IPV6, 445 + .revision = 2, 446 + .targetsize = sizeof(struct xt_ct_target_info_v1), 447 + .usersize = offsetof(struct xt_ct_target_info, ct), 448 + .checkentry = xt_ct_tg_check_v2, 449 + .destroy = xt_ct_tg_destroy_v1, 450 + .target = xt_ct_target_v1, 451 + .table = "raw", 452 + .me = THIS_MODULE, 453 + }, 454 + #endif 335 455 }; 336 456 337 457 static int __init xt_ct_tg_init(void) 338 458 { 339 - int ret; 340 - 341 - ret = xt_register_target(&notrack_tg_reg); 342 - if (ret < 0) 343 - return ret; 344 - 345 - ret = xt_register_targets(xt_ct_tg_reg, ARRAY_SIZE(xt_ct_tg_reg)); 346 - if (ret < 0) { 347 - xt_unregister_target(&notrack_tg_reg); 348 - return ret; 349 - } 350 - return 0; 459 + return xt_register_targets(xt_ct_tg_reg, ARRAY_SIZE(xt_ct_tg_reg)); 351 460 } 352 461 353 462 static void __exit xt_ct_tg_exit(void) 354 463 { 355 464 xt_unregister_targets(xt_ct_tg_reg, ARRAY_SIZE(xt_ct_tg_reg)); 356 - xt_unregister_target(&notrack_tg_reg); 357 465 } 358 466 359 467 module_init(xt_ct_tg_init);
+40 -19
net/netfilter/xt_IDLETIMER.c
··· 458 458 459 459 static struct xt_target idletimer_tg[] __read_mostly = { 460 460 { 461 - .name = "IDLETIMER", 462 - .family = NFPROTO_UNSPEC, 463 - .target = idletimer_tg_target, 464 - .targetsize = sizeof(struct idletimer_tg_info), 465 - .usersize = offsetof(struct idletimer_tg_info, timer), 466 - .checkentry = idletimer_tg_checkentry, 467 - .destroy = idletimer_tg_destroy, 468 - .me = THIS_MODULE, 461 + .name = "IDLETIMER", 462 + .family = NFPROTO_IPV4, 463 + .target = idletimer_tg_target, 464 + .targetsize = sizeof(struct idletimer_tg_info), 465 + .usersize = offsetof(struct idletimer_tg_info, timer), 466 + .checkentry = idletimer_tg_checkentry, 467 + .destroy = idletimer_tg_destroy, 468 + .me = THIS_MODULE, 469 469 }, 470 470 { 471 - .name = "IDLETIMER", 472 - .family = NFPROTO_UNSPEC, 473 - .revision = 1, 474 - .target = idletimer_tg_target_v1, 475 - .targetsize = sizeof(struct idletimer_tg_info_v1), 476 - .usersize = offsetof(struct idletimer_tg_info_v1, timer), 477 - .checkentry = idletimer_tg_checkentry_v1, 478 - .destroy = idletimer_tg_destroy_v1, 479 - .me = THIS_MODULE, 471 + .name = "IDLETIMER", 472 + .family = NFPROTO_IPV4, 473 + .revision = 1, 474 + .target = idletimer_tg_target_v1, 475 + .targetsize = sizeof(struct idletimer_tg_info_v1), 476 + .usersize = offsetof(struct idletimer_tg_info_v1, timer), 477 + .checkentry = idletimer_tg_checkentry_v1, 478 + .destroy = idletimer_tg_destroy_v1, 479 + .me = THIS_MODULE, 480 480 }, 481 - 482 - 481 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 482 + { 483 + .name = "IDLETIMER", 484 + .family = NFPROTO_IPV6, 485 + .target = idletimer_tg_target, 486 + .targetsize = sizeof(struct idletimer_tg_info), 487 + .usersize = offsetof(struct idletimer_tg_info, timer), 488 + .checkentry = idletimer_tg_checkentry, 489 + .destroy = idletimer_tg_destroy, 490 + .me = THIS_MODULE, 491 + }, 492 + { 493 + .name = "IDLETIMER", 494 + .family = NFPROTO_IPV6, 495 + .revision = 1, 496 + .target = idletimer_tg_target_v1, 497 + .targetsize = sizeof(struct idletimer_tg_info_v1), 498 + .usersize = offsetof(struct idletimer_tg_info_v1, timer), 499 + .checkentry = idletimer_tg_checkentry_v1, 500 + .destroy = idletimer_tg_destroy_v1, 501 + .me = THIS_MODULE, 502 + }, 503 + #endif 483 504 }; 484 505 485 506 static struct class *idletimer_tg_class;
+27 -12
net/netfilter/xt_LED.c
··· 175 175 kfree(ledinternal); 176 176 } 177 177 178 - static struct xt_target led_tg_reg __read_mostly = { 179 - .name = "LED", 180 - .revision = 0, 181 - .family = NFPROTO_UNSPEC, 182 - .target = led_tg, 183 - .targetsize = sizeof(struct xt_led_info), 184 - .usersize = offsetof(struct xt_led_info, internal_data), 185 - .checkentry = led_tg_check, 186 - .destroy = led_tg_destroy, 187 - .me = THIS_MODULE, 178 + static struct xt_target led_tg_reg[] __read_mostly = { 179 + { 180 + .name = "LED", 181 + .revision = 0, 182 + .family = NFPROTO_IPV4, 183 + .target = led_tg, 184 + .targetsize = sizeof(struct xt_led_info), 185 + .usersize = offsetof(struct xt_led_info, internal_data), 186 + .checkentry = led_tg_check, 187 + .destroy = led_tg_destroy, 188 + .me = THIS_MODULE, 189 + }, 190 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 191 + { 192 + .name = "LED", 193 + .revision = 0, 194 + .family = NFPROTO_IPV6, 195 + .target = led_tg, 196 + .targetsize = sizeof(struct xt_led_info), 197 + .usersize = offsetof(struct xt_led_info, internal_data), 198 + .checkentry = led_tg_check, 199 + .destroy = led_tg_destroy, 200 + .me = THIS_MODULE, 201 + }, 202 + #endif 188 203 }; 189 204 190 205 static int __init led_tg_init(void) 191 206 { 192 - return xt_register_target(&led_tg_reg); 207 + return xt_register_targets(led_tg_reg, ARRAY_SIZE(led_tg_reg)); 193 208 } 194 209 195 210 static void __exit led_tg_exit(void) 196 211 { 197 - xt_unregister_target(&led_tg_reg); 212 + xt_unregister_targets(led_tg_reg, ARRAY_SIZE(led_tg_reg)); 198 213 } 199 214 200 215 module_init(led_tg_init);
+25 -11
net/netfilter/xt_NFLOG.c
··· 64 64 nf_logger_put(par->family, NF_LOG_TYPE_ULOG); 65 65 } 66 66 67 - static struct xt_target nflog_tg_reg __read_mostly = { 68 - .name = "NFLOG", 69 - .revision = 0, 70 - .family = NFPROTO_UNSPEC, 71 - .checkentry = nflog_tg_check, 72 - .destroy = nflog_tg_destroy, 73 - .target = nflog_tg, 74 - .targetsize = sizeof(struct xt_nflog_info), 75 - .me = THIS_MODULE, 67 + static struct xt_target nflog_tg_reg[] __read_mostly = { 68 + { 69 + .name = "NFLOG", 70 + .revision = 0, 71 + .family = NFPROTO_IPV4, 72 + .checkentry = nflog_tg_check, 73 + .destroy = nflog_tg_destroy, 74 + .target = nflog_tg, 75 + .targetsize = sizeof(struct xt_nflog_info), 76 + .me = THIS_MODULE, 77 + }, 78 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 79 + { 80 + .name = "NFLOG", 81 + .revision = 0, 82 + .family = NFPROTO_IPV4, 83 + .checkentry = nflog_tg_check, 84 + .destroy = nflog_tg_destroy, 85 + .target = nflog_tg, 86 + .targetsize = sizeof(struct xt_nflog_info), 87 + .me = THIS_MODULE, 88 + }, 89 + #endif 76 90 }; 77 91 78 92 static int __init nflog_tg_init(void) 79 93 { 80 - return xt_register_target(&nflog_tg_reg); 94 + return xt_register_targets(nflog_tg_reg, ARRAY_SIZE(nflog_tg_reg)); 81 95 } 82 96 83 97 static void __exit nflog_tg_exit(void) 84 98 { 85 - xt_unregister_target(&nflog_tg_reg); 99 + xt_unregister_targets(nflog_tg_reg, ARRAY_SIZE(nflog_tg_reg)); 86 100 } 87 101 88 102 module_init(nflog_tg_init);
+27 -12
net/netfilter/xt_RATEEST.c
··· 179 179 xt_rateest_put(par->net, info->est); 180 180 } 181 181 182 - static struct xt_target xt_rateest_tg_reg __read_mostly = { 183 - .name = "RATEEST", 184 - .revision = 0, 185 - .family = NFPROTO_UNSPEC, 186 - .target = xt_rateest_tg, 187 - .checkentry = xt_rateest_tg_checkentry, 188 - .destroy = xt_rateest_tg_destroy, 189 - .targetsize = sizeof(struct xt_rateest_target_info), 190 - .usersize = offsetof(struct xt_rateest_target_info, est), 191 - .me = THIS_MODULE, 182 + static struct xt_target xt_rateest_tg_reg[] __read_mostly = { 183 + { 184 + .name = "RATEEST", 185 + .revision = 0, 186 + .family = NFPROTO_IPV4, 187 + .target = xt_rateest_tg, 188 + .checkentry = xt_rateest_tg_checkentry, 189 + .destroy = xt_rateest_tg_destroy, 190 + .targetsize = sizeof(struct xt_rateest_target_info), 191 + .usersize = offsetof(struct xt_rateest_target_info, est), 192 + .me = THIS_MODULE, 193 + }, 194 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 195 + { 196 + .name = "RATEEST", 197 + .revision = 0, 198 + .family = NFPROTO_IPV6, 199 + .target = xt_rateest_tg, 200 + .checkentry = xt_rateest_tg_checkentry, 201 + .destroy = xt_rateest_tg_destroy, 202 + .targetsize = sizeof(struct xt_rateest_target_info), 203 + .usersize = offsetof(struct xt_rateest_target_info, est), 204 + .me = THIS_MODULE, 205 + }, 206 + #endif 192 207 }; 193 208 194 209 static __net_init int xt_rateest_net_init(struct net *net) ··· 229 214 230 215 if (err) 231 216 return err; 232 - return xt_register_target(&xt_rateest_tg_reg); 217 + return xt_register_targets(xt_rateest_tg_reg, ARRAY_SIZE(xt_rateest_tg_reg)); 233 218 } 234 219 235 220 static void __exit xt_rateest_tg_fini(void) 236 221 { 237 - xt_unregister_target(&xt_rateest_tg_reg); 222 + xt_unregister_targets(xt_rateest_tg_reg, ARRAY_SIZE(xt_rateest_tg_reg)); 238 223 unregister_pernet_subsys(&xt_rateest_net_ops); 239 224 } 240 225
+25 -2
net/netfilter/xt_SECMARK.c
··· 157 157 { 158 158 .name = "SECMARK", 159 159 .revision = 0, 160 - .family = NFPROTO_UNSPEC, 160 + .family = NFPROTO_IPV4, 161 161 .checkentry = secmark_tg_check_v0, 162 162 .destroy = secmark_tg_destroy, 163 163 .target = secmark_tg_v0, ··· 167 167 { 168 168 .name = "SECMARK", 169 169 .revision = 1, 170 - .family = NFPROTO_UNSPEC, 170 + .family = NFPROTO_IPV4, 171 171 .checkentry = secmark_tg_check_v1, 172 172 .destroy = secmark_tg_destroy, 173 173 .target = secmark_tg_v1, ··· 175 175 .usersize = offsetof(struct xt_secmark_target_info_v1, secid), 176 176 .me = THIS_MODULE, 177 177 }, 178 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 179 + { 180 + .name = "SECMARK", 181 + .revision = 0, 182 + .family = NFPROTO_IPV6, 183 + .checkentry = secmark_tg_check_v0, 184 + .destroy = secmark_tg_destroy, 185 + .target = secmark_tg_v0, 186 + .targetsize = sizeof(struct xt_secmark_target_info), 187 + .me = THIS_MODULE, 188 + }, 189 + { 190 + .name = "SECMARK", 191 + .revision = 1, 192 + .family = NFPROTO_IPV6, 193 + .checkentry = secmark_tg_check_v1, 194 + .destroy = secmark_tg_destroy, 195 + .target = secmark_tg_v1, 196 + .targetsize = sizeof(struct xt_secmark_target_info_v1), 197 + .usersize = offsetof(struct xt_secmark_target_info_v1, secid), 198 + .me = THIS_MODULE, 199 + }, 200 + #endif 178 201 }; 179 202 180 203 static int __init secmark_tg_init(void)
+24 -11
net/netfilter/xt_TRACE.c
··· 29 29 return XT_CONTINUE; 30 30 } 31 31 32 - static struct xt_target trace_tg_reg __read_mostly = { 33 - .name = "TRACE", 34 - .revision = 0, 35 - .family = NFPROTO_UNSPEC, 36 - .table = "raw", 37 - .target = trace_tg, 38 - .checkentry = trace_tg_check, 39 - .destroy = trace_tg_destroy, 40 - .me = THIS_MODULE, 32 + static struct xt_target trace_tg_reg[] __read_mostly = { 33 + { 34 + .name = "TRACE", 35 + .revision = 0, 36 + .family = NFPROTO_IPV4, 37 + .table = "raw", 38 + .target = trace_tg, 39 + .checkentry = trace_tg_check, 40 + .destroy = trace_tg_destroy, 41 + .me = THIS_MODULE, 42 + }, 43 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 44 + { 45 + .name = "TRACE", 46 + .revision = 0, 47 + .family = NFPROTO_IPV6, 48 + .table = "raw", 49 + .target = trace_tg, 50 + .checkentry = trace_tg_check, 51 + .destroy = trace_tg_destroy, 52 + }, 53 + #endif 41 54 }; 42 55 43 56 static int __init trace_tg_init(void) 44 57 { 45 - return xt_register_target(&trace_tg_reg); 58 + return xt_register_targets(trace_tg_reg, ARRAY_SIZE(trace_tg_reg)); 46 59 } 47 60 48 61 static void __exit trace_tg_exit(void) 49 62 { 50 - xt_unregister_target(&trace_tg_reg); 63 + xt_unregister_targets(trace_tg_reg, ARRAY_SIZE(trace_tg_reg)); 51 64 } 52 65 53 66 module_init(trace_tg_init);
+13 -2
net/netfilter/xt_addrtype.c
··· 208 208 }, 209 209 { 210 210 .name = "addrtype", 211 - .family = NFPROTO_UNSPEC, 211 + .family = NFPROTO_IPV4, 212 212 .revision = 1, 213 213 .match = addrtype_mt_v1, 214 214 .checkentry = addrtype_mt_checkentry_v1, 215 215 .matchsize = sizeof(struct xt_addrtype_info_v1), 216 216 .me = THIS_MODULE 217 - } 217 + }, 218 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 219 + { 220 + .name = "addrtype", 221 + .family = NFPROTO_IPV6, 222 + .revision = 1, 223 + .match = addrtype_mt_v1, 224 + .checkentry = addrtype_mt_checkentry_v1, 225 + .matchsize = sizeof(struct xt_addrtype_info_v1), 226 + .me = THIS_MODULE 227 + }, 228 + #endif 218 229 }; 219 230 220 231 static int __init addrtype_mt_init(void)
+23 -10
net/netfilter/xt_cluster.c
··· 146 146 nf_ct_netns_put(par->net, par->family); 147 147 } 148 148 149 - static struct xt_match xt_cluster_match __read_mostly = { 150 - .name = "cluster", 151 - .family = NFPROTO_UNSPEC, 152 - .match = xt_cluster_mt, 153 - .checkentry = xt_cluster_mt_checkentry, 154 - .matchsize = sizeof(struct xt_cluster_match_info), 155 - .destroy = xt_cluster_mt_destroy, 156 - .me = THIS_MODULE, 149 + static struct xt_match xt_cluster_match[] __read_mostly = { 150 + { 151 + .name = "cluster", 152 + .family = NFPROTO_IPV4, 153 + .match = xt_cluster_mt, 154 + .checkentry = xt_cluster_mt_checkentry, 155 + .matchsize = sizeof(struct xt_cluster_match_info), 156 + .destroy = xt_cluster_mt_destroy, 157 + .me = THIS_MODULE, 158 + }, 159 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 160 + { 161 + .name = "cluster", 162 + .family = NFPROTO_IPV6, 163 + .match = xt_cluster_mt, 164 + .checkentry = xt_cluster_mt_checkentry, 165 + .matchsize = sizeof(struct xt_cluster_match_info), 166 + .destroy = xt_cluster_mt_destroy, 167 + .me = THIS_MODULE, 168 + }, 169 + #endif 157 170 }; 158 171 159 172 static int __init xt_cluster_mt_init(void) 160 173 { 161 - return xt_register_match(&xt_cluster_match); 174 + return xt_register_matches(xt_cluster_match, ARRAY_SIZE(xt_cluster_match)); 162 175 } 163 176 164 177 static void __exit xt_cluster_mt_fini(void) 165 178 { 166 - xt_unregister_match(&xt_cluster_match); 179 + xt_unregister_matches(xt_cluster_match, ARRAY_SIZE(xt_cluster_match)); 167 180 } 168 181 169 182 MODULE_AUTHOR("Pablo Neira Ayuso <pablo@netfilter.org>");
+3 -1
net/netfilter/xt_connbytes.c
··· 111 111 return -EINVAL; 112 112 113 113 ret = nf_ct_netns_get(par->net, par->family); 114 - if (ret < 0) 114 + if (ret < 0) { 115 115 pr_info_ratelimited("cannot load conntrack support for proto=%u\n", 116 116 par->family); 117 + return ret; 118 + } 117 119 118 120 /* 119 121 * This filter cannot function correctly unless connection tracking
+27 -12
net/netfilter/xt_connlimit.c
··· 117 117 nf_ct_netns_put(par->net, par->family); 118 118 } 119 119 120 - static struct xt_match connlimit_mt_reg __read_mostly = { 121 - .name = "connlimit", 122 - .revision = 1, 123 - .family = NFPROTO_UNSPEC, 124 - .checkentry = connlimit_mt_check, 125 - .match = connlimit_mt, 126 - .matchsize = sizeof(struct xt_connlimit_info), 127 - .usersize = offsetof(struct xt_connlimit_info, data), 128 - .destroy = connlimit_mt_destroy, 129 - .me = THIS_MODULE, 120 + static struct xt_match connlimit_mt_reg[] __read_mostly = { 121 + { 122 + .name = "connlimit", 123 + .revision = 1, 124 + .family = NFPROTO_IPV4, 125 + .checkentry = connlimit_mt_check, 126 + .match = connlimit_mt, 127 + .matchsize = sizeof(struct xt_connlimit_info), 128 + .usersize = offsetof(struct xt_connlimit_info, data), 129 + .destroy = connlimit_mt_destroy, 130 + .me = THIS_MODULE, 131 + }, 132 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 133 + { 134 + .name = "connlimit", 135 + .revision = 1, 136 + .family = NFPROTO_IPV6, 137 + .checkentry = connlimit_mt_check, 138 + .match = connlimit_mt, 139 + .matchsize = sizeof(struct xt_connlimit_info), 140 + .usersize = offsetof(struct xt_connlimit_info, data), 141 + .destroy = connlimit_mt_destroy, 142 + .me = THIS_MODULE, 143 + }, 144 + #endif 130 145 }; 131 146 132 147 static int __init connlimit_mt_init(void) 133 148 { 134 - return xt_register_match(&connlimit_mt_reg); 149 + return xt_register_matches(connlimit_mt_reg, ARRAY_SIZE(connlimit_mt_reg)); 135 150 } 136 151 137 152 static void __exit connlimit_mt_exit(void) 138 153 { 139 - xt_unregister_match(&connlimit_mt_reg); 154 + xt_unregister_matches(connlimit_mt_reg, ARRAY_SIZE(connlimit_mt_reg)); 140 155 } 141 156 142 157 module_init(connlimit_mt_init);
+25 -3
net/netfilter/xt_connmark.c
··· 151 151 { 152 152 .name = "CONNMARK", 153 153 .revision = 1, 154 - .family = NFPROTO_UNSPEC, 154 + .family = NFPROTO_IPV4, 155 155 .checkentry = connmark_tg_check, 156 156 .target = connmark_tg, 157 157 .targetsize = sizeof(struct xt_connmark_tginfo1), ··· 161 161 { 162 162 .name = "CONNMARK", 163 163 .revision = 2, 164 - .family = NFPROTO_UNSPEC, 164 + .family = NFPROTO_IPV4, 165 165 .checkentry = connmark_tg_check, 166 166 .target = connmark_tg_v2, 167 167 .targetsize = sizeof(struct xt_connmark_tginfo2), 168 168 .destroy = connmark_tg_destroy, 169 169 .me = THIS_MODULE, 170 - } 170 + }, 171 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 172 + { 173 + .name = "CONNMARK", 174 + .revision = 1, 175 + .family = NFPROTO_IPV6, 176 + .checkentry = connmark_tg_check, 177 + .target = connmark_tg, 178 + .targetsize = sizeof(struct xt_connmark_tginfo1), 179 + .destroy = connmark_tg_destroy, 180 + .me = THIS_MODULE, 181 + }, 182 + { 183 + .name = "CONNMARK", 184 + .revision = 2, 185 + .family = NFPROTO_IPV6, 186 + .checkentry = connmark_tg_check, 187 + .target = connmark_tg_v2, 188 + .targetsize = sizeof(struct xt_connmark_tginfo2), 189 + .destroy = connmark_tg_destroy, 190 + .me = THIS_MODULE, 191 + }, 192 + #endif 171 193 }; 172 194 173 195 static struct xt_match connmark_mt_reg __read_mostly = {
+32 -10
net/netfilter/xt_mark.c
··· 39 39 return ((skb->mark & info->mask) == info->mark) ^ info->invert; 40 40 } 41 41 42 - static struct xt_target mark_tg_reg __read_mostly = { 43 - .name = "MARK", 44 - .revision = 2, 45 - .family = NFPROTO_UNSPEC, 46 - .target = mark_tg, 47 - .targetsize = sizeof(struct xt_mark_tginfo2), 48 - .me = THIS_MODULE, 42 + static struct xt_target mark_tg_reg[] __read_mostly = { 43 + { 44 + .name = "MARK", 45 + .revision = 2, 46 + .family = NFPROTO_IPV4, 47 + .target = mark_tg, 48 + .targetsize = sizeof(struct xt_mark_tginfo2), 49 + .me = THIS_MODULE, 50 + }, 51 + #if IS_ENABLED(CONFIG_IP_NF_ARPTABLES) 52 + { 53 + .name = "MARK", 54 + .revision = 2, 55 + .family = NFPROTO_ARP, 56 + .target = mark_tg, 57 + .targetsize = sizeof(struct xt_mark_tginfo2), 58 + .me = THIS_MODULE, 59 + }, 60 + #endif 61 + #if IS_ENABLED(CONFIG_IP6_NF_IPTABLES) 62 + { 63 + .name = "MARK", 64 + .revision = 2, 65 + .family = NFPROTO_IPV4, 66 + .target = mark_tg, 67 + .targetsize = sizeof(struct xt_mark_tginfo2), 68 + .me = THIS_MODULE, 69 + }, 70 + #endif 49 71 }; 50 72 51 73 static struct xt_match mark_mt_reg __read_mostly = { ··· 83 61 { 84 62 int ret; 85 63 86 - ret = xt_register_target(&mark_tg_reg); 64 + ret = xt_register_targets(mark_tg_reg, ARRAY_SIZE(mark_tg_reg)); 87 65 if (ret < 0) 88 66 return ret; 89 67 ret = xt_register_match(&mark_mt_reg); 90 68 if (ret < 0) { 91 - xt_unregister_target(&mark_tg_reg); 69 + xt_unregister_targets(mark_tg_reg, ARRAY_SIZE(mark_tg_reg)); 92 70 return ret; 93 71 } 94 72 return 0; ··· 97 75 static void __exit mark_mt_exit(void) 98 76 { 99 77 xt_unregister_match(&mark_mt_reg); 100 - xt_unregister_target(&mark_tg_reg); 78 + xt_unregister_targets(mark_tg_reg, ARRAY_SIZE(mark_tg_reg)); 101 79 } 102 80 103 81 module_init(mark_mt_init);