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

Merge git://git.kernel.org/pub/scm/linux/kernel/git/pablo/nf-next

Pablo Neira Ayuso says:

====================
Netfilter updates for net-next

The following patchset contains Netfilter updates for net-next:

1) Rewrite inner header IPv6 in ICMPv6 messages in ip6t_NPT,
from Michael Zhou.

2) do_ip_vs_set_ctl() dereferences uninitialized value,
from Peilin Ye.

3) Support for userdata in tables, from Jose M. Guisado.

4) Do not increment ct error and invalid stats at the same time,
from Florian Westphal.

5) Remove ct ignore stats, also from Florian.

6) Add ct stats for clash resolution, from Florian Westphal.

7) Bump reference counter bump on ct clash resolution only,
this is safe because bucket lock is held, again from Florian.

8) Use ip_is_fragment() in xt_HMARK, from YueHaibing.

9) Add wildcard support for nft_socket, from Balazs Scheidler.

10) Remove superfluous IPVS dependency on iptables, from
Yaroslav Bolyukin.

11) Remove unused definition in ebt_stp, from Wang Hai.

12) Replace CONFIG_NFT_CHAIN_NAT_{IPV4,IPV6} by CONFIG_NFT_NAT
in selftests/net, from Fabian Frederick.

13) Add userdata support for nft_object, from Jose M. Guisado.
====================

Signed-off-by: David S. Miller <davem@davemloft.net>

+148 -41
+1 -1
include/linux/netfilter/nf_conntrack_common.h
··· 8 8 struct ip_conntrack_stat { 9 9 unsigned int found; 10 10 unsigned int invalid; 11 - unsigned int ignore; 12 11 unsigned int insert; 13 12 unsigned int insert_failed; 13 + unsigned int clash_resolve; 14 14 unsigned int drop; 15 15 unsigned int early_drop; 16 16 unsigned int error;
-3
include/net/ip_vs.h
··· 25 25 #include <linux/ip.h> 26 26 #include <linux/ipv6.h> /* for struct ipv6hdr */ 27 27 #include <net/ipv6.h> 28 - #if IS_ENABLED(CONFIG_IP_VS_IPV6) 29 - #include <linux/netfilter_ipv6/ip6_tables.h> 30 - #endif 31 28 #if IS_ENABLED(CONFIG_NF_CONNTRACK) 32 29 #include <net/netfilter/nf_conntrack.h> 33 30 #endif
+4
include/net/netfilter/nf_tables.h
··· 1082 1082 flags:8, 1083 1083 genmask:2; 1084 1084 char *name; 1085 + u16 udlen; 1086 + u8 *udata; 1085 1087 }; 1086 1088 1087 1089 void nft_register_chain_type(const struct nft_chain_type *); ··· 1125 1123 u32 genmask:2, 1126 1124 use:30; 1127 1125 u64 handle; 1126 + u16 udlen; 1127 + u8 *udata; 1128 1128 /* runtime data below here */ 1129 1129 const struct nft_object_ops *ops ____cacheline_aligned; 1130 1130 unsigned char data[]
+6
include/uapi/linux/netfilter/nf_tables.h
··· 172 172 * @NFTA_TABLE_NAME: name of the table (NLA_STRING) 173 173 * @NFTA_TABLE_FLAGS: bitmask of enum nft_table_flags (NLA_U32) 174 174 * @NFTA_TABLE_USE: number of chains in this table (NLA_U32) 175 + * @NFTA_TABLE_USERDATA: user data (NLA_BINARY) 175 176 */ 176 177 enum nft_table_attributes { 177 178 NFTA_TABLE_UNSPEC, ··· 181 180 NFTA_TABLE_USE, 182 181 NFTA_TABLE_HANDLE, 183 182 NFTA_TABLE_PAD, 183 + NFTA_TABLE_USERDATA, 184 184 __NFTA_TABLE_MAX 185 185 }; 186 186 #define NFTA_TABLE_MAX (__NFTA_TABLE_MAX - 1) ··· 1010 1008 * 1011 1009 * @NFT_SOCKET_TRANSPARENT: Value of the IP(V6)_TRANSPARENT socket option 1012 1010 * @NFT_SOCKET_MARK: Value of the socket mark 1011 + * @NFT_SOCKET_WILDCARD: Whether the socket is zero-bound (e.g. 0.0.0.0 or ::0) 1013 1012 */ 1014 1013 enum nft_socket_keys { 1015 1014 NFT_SOCKET_TRANSPARENT, 1016 1015 NFT_SOCKET_MARK, 1016 + NFT_SOCKET_WILDCARD, 1017 1017 __NFT_SOCKET_MAX 1018 1018 }; 1019 1019 #define NFT_SOCKET_MAX (__NFT_SOCKET_MAX - 1) ··· 1559 1555 * @NFTA_OBJ_DATA: stateful object data (NLA_NESTED) 1560 1556 * @NFTA_OBJ_USE: number of references to this expression (NLA_U32) 1561 1557 * @NFTA_OBJ_HANDLE: object handle (NLA_U64) 1558 + * @NFTA_OBJ_USERDATA: user data (NLA_BINARY) 1562 1559 */ 1563 1560 enum nft_object_attributes { 1564 1561 NFTA_OBJ_UNSPEC, ··· 1570 1565 NFTA_OBJ_USE, 1571 1566 NFTA_OBJ_HANDLE, 1572 1567 NFTA_OBJ_PAD, 1568 + NFTA_OBJ_USERDATA, 1573 1569 __NFTA_OBJ_MAX 1574 1570 }; 1575 1571 #define NFTA_OBJ_MAX (__NFTA_OBJ_MAX - 1)
-1
net/bridge/netfilter/ebt_stp.c
··· 15 15 #include <linux/netfilter_bridge/ebt_stp.h> 16 16 17 17 #define BPDU_TYPE_CONFIG 0 18 - #define BPDU_TYPE_TCN 0x80 19 18 20 19 struct stp_header { 21 20 u8 dsap;
+39
net/ipv6/netfilter/ip6t_NPT.c
··· 77 77 return true; 78 78 } 79 79 80 + static struct ipv6hdr *icmpv6_bounced_ipv6hdr(struct sk_buff *skb, 81 + struct ipv6hdr *_bounced_hdr) 82 + { 83 + if (ipv6_hdr(skb)->nexthdr != IPPROTO_ICMPV6) 84 + return NULL; 85 + 86 + if (!icmpv6_is_err(icmp6_hdr(skb)->icmp6_type)) 87 + return NULL; 88 + 89 + return skb_header_pointer(skb, 90 + skb_transport_offset(skb) + sizeof(struct icmp6hdr), 91 + sizeof(struct ipv6hdr), 92 + _bounced_hdr); 93 + } 94 + 80 95 static unsigned int 81 96 ip6t_snpt_tg(struct sk_buff *skb, const struct xt_action_param *par) 82 97 { 83 98 const struct ip6t_npt_tginfo *npt = par->targinfo; 99 + struct ipv6hdr _bounced_hdr; 100 + struct ipv6hdr *bounced_hdr; 101 + struct in6_addr bounced_pfx; 84 102 85 103 if (!ip6t_npt_map_pfx(npt, &ipv6_hdr(skb)->saddr)) { 86 104 icmpv6_send(skb, ICMPV6_PARAMPROB, ICMPV6_HDR_FIELD, 87 105 offsetof(struct ipv6hdr, saddr)); 88 106 return NF_DROP; 89 107 } 108 + 109 + /* rewrite dst addr of bounced packet which was sent to dst range */ 110 + bounced_hdr = icmpv6_bounced_ipv6hdr(skb, &_bounced_hdr); 111 + if (bounced_hdr) { 112 + ipv6_addr_prefix(&bounced_pfx, &bounced_hdr->daddr, npt->src_pfx_len); 113 + if (ipv6_addr_cmp(&bounced_pfx, &npt->src_pfx.in6) == 0) 114 + ip6t_npt_map_pfx(npt, &bounced_hdr->daddr); 115 + } 116 + 90 117 return XT_CONTINUE; 91 118 } 92 119 ··· 121 94 ip6t_dnpt_tg(struct sk_buff *skb, const struct xt_action_param *par) 122 95 { 123 96 const struct ip6t_npt_tginfo *npt = par->targinfo; 97 + struct ipv6hdr _bounced_hdr; 98 + struct ipv6hdr *bounced_hdr; 99 + struct in6_addr bounced_pfx; 124 100 125 101 if (!ip6t_npt_map_pfx(npt, &ipv6_hdr(skb)->daddr)) { 126 102 icmpv6_send(skb, ICMPV6_PARAMPROB, ICMPV6_HDR_FIELD, 127 103 offsetof(struct ipv6hdr, daddr)); 128 104 return NF_DROP; 129 105 } 106 + 107 + /* rewrite src addr of bounced packet which was sent from dst range */ 108 + bounced_hdr = icmpv6_bounced_ipv6hdr(skb, &_bounced_hdr); 109 + if (bounced_hdr) { 110 + ipv6_addr_prefix(&bounced_pfx, &bounced_hdr->saddr, npt->src_pfx_len); 111 + if (ipv6_addr_cmp(&bounced_pfx, &npt->src_pfx.in6) == 0) 112 + ip6t_npt_map_pfx(npt, &bounced_hdr->saddr); 113 + } 114 + 130 115 return XT_CONTINUE; 131 116 } 132 117
-1
net/netfilter/ipvs/Kconfig
··· 29 29 config IP_VS_IPV6 30 30 bool "IPv6 support for IPVS" 31 31 depends on IPV6 = y || IP_VS = IPV6 32 - select IP6_NF_IPTABLES 33 32 select NF_DEFRAG_IPV6 34 33 help 35 34 Add IPv6 support to IPVS.
+4 -3
net/netfilter/ipvs/ip_vs_ctl.c
··· 2508 2508 /* Set timeout values for (tcp tcpfin udp) */ 2509 2509 ret = ip_vs_set_timeout(ipvs, (struct ip_vs_timeout_user *)arg); 2510 2510 goto out_unlock; 2511 + } else if (!len) { 2512 + /* No more commands with len == 0 below */ 2513 + ret = -EINVAL; 2514 + goto out_unlock; 2511 2515 } 2512 2516 2513 2517 usvc_compat = (struct ip_vs_service_user *)arg; ··· 2588 2584 break; 2589 2585 case IP_VS_SO_SET_DELDEST: 2590 2586 ret = ip_vs_del_dest(svc, &udest); 2591 - break; 2592 - default: 2593 - ret = -EINVAL; 2594 2587 } 2595 2588 2596 2589 out_unlock:
+10 -15
net/netfilter/nf_conntrack_core.c
··· 859 859 860 860 out: 861 861 nf_conntrack_double_unlock(hash, reply_hash); 862 - NF_CT_STAT_INC(net, insert_failed); 863 862 local_bh_enable(); 864 863 return -EEXIST; 865 864 } ··· 908 909 tstamp->start = ktime_get_real_ns(); 909 910 } 910 911 912 + /* caller must hold locks to prevent concurrent changes */ 911 913 static int __nf_ct_resolve_clash(struct sk_buff *skb, 912 914 struct nf_conntrack_tuple_hash *h) 913 915 { ··· 922 922 if (nf_ct_is_dying(ct)) 923 923 return NF_DROP; 924 924 925 - if (!atomic_inc_not_zero(&ct->ct_general.use)) 926 - return NF_DROP; 927 - 928 925 if (((ct->status & IPS_NAT_DONE_MASK) == 0) || 929 926 nf_ct_match(ct, loser_ct)) { 930 927 struct net *net = nf_ct_net(ct); 928 + 929 + nf_conntrack_get(&ct->ct_general); 931 930 932 931 nf_ct_acct_merge(ct, ctinfo, loser_ct); 933 932 nf_ct_add_to_dying_list(loser_ct); 934 933 nf_conntrack_put(&loser_ct->ct_general); 935 934 nf_ct_set(skb, ct, ctinfo); 936 935 937 - NF_CT_STAT_INC(net, insert_failed); 936 + NF_CT_STAT_INC(net, clash_resolve); 938 937 return NF_ACCEPT; 939 938 } 940 939 941 - nf_ct_put(ct); 942 940 return NF_DROP; 943 941 } 944 942 ··· 996 998 997 999 hlist_nulls_add_head_rcu(&loser_ct->tuplehash[IP_CT_DIR_REPLY].hnnode, 998 1000 &nf_conntrack_hash[repl_idx]); 1001 + 1002 + NF_CT_STAT_INC(net, clash_resolve); 999 1003 return NF_ACCEPT; 1000 1004 } 1001 1005 ··· 1027 1027 * 1028 1028 * Failing that, the new, unconfirmed conntrack is still added to the table 1029 1029 * provided that the collision only occurs in the ORIGINAL direction. 1030 - * The new entry will be added after the existing one in the hash list, 1030 + * The new entry will be added only in the non-clashing REPLY direction, 1031 1031 * so packets in the ORIGINAL direction will continue to match the existing 1032 1032 * entry. The new entry will also have a fixed timeout so it expires -- 1033 - * due to the collision, it will not see bidirectional traffic. 1033 + * due to the collision, it will only see reply traffic. 1034 1034 * 1035 1035 * Returns NF_DROP if the clash could not be resolved. 1036 1036 */ ··· 1725 1725 else 1726 1726 return NF_ACCEPT; 1727 1727 1728 - if (ret <= 0) { 1728 + if (ret <= 0) 1729 1729 NF_CT_STAT_INC_ATOMIC(state->net, error); 1730 - NF_CT_STAT_INC_ATOMIC(state->net, invalid); 1731 - } 1732 1730 1733 1731 return ret; 1734 1732 } ··· 1800 1802 if (tmpl || ctinfo == IP_CT_UNTRACKED) { 1801 1803 /* Previously seen (loopback or untracked)? Ignore. */ 1802 1804 if ((tmpl && !nf_ct_is_template(tmpl)) || 1803 - ctinfo == IP_CT_UNTRACKED) { 1804 - NF_CT_STAT_INC_ATOMIC(state->net, ignore); 1805 + ctinfo == IP_CT_UNTRACKED) 1805 1806 return NF_ACCEPT; 1806 - } 1807 1807 skb->_nfct = 0; 1808 1808 } 1809 1809 ··· 1809 1813 dataoff = get_l4proto(skb, skb_network_offset(skb), state->pf, &protonum); 1810 1814 if (dataoff <= 0) { 1811 1815 pr_debug("not prepared to track yet or error occurred\n"); 1812 - NF_CT_STAT_INC_ATOMIC(state->net, error); 1813 1816 NF_CT_STAT_INC_ATOMIC(state->net, invalid); 1814 1817 ret = NF_ACCEPT; 1815 1818 goto out;
+3 -2
net/netfilter/nf_conntrack_netlink.c
··· 2509 2509 2510 2510 if (nla_put_be32(skb, CTA_STATS_FOUND, htonl(st->found)) || 2511 2511 nla_put_be32(skb, CTA_STATS_INVALID, htonl(st->invalid)) || 2512 - nla_put_be32(skb, CTA_STATS_IGNORE, htonl(st->ignore)) || 2513 2512 nla_put_be32(skb, CTA_STATS_INSERT, htonl(st->insert)) || 2514 2513 nla_put_be32(skb, CTA_STATS_INSERT_FAILED, 2515 2514 htonl(st->insert_failed)) || ··· 2516 2517 nla_put_be32(skb, CTA_STATS_EARLY_DROP, htonl(st->early_drop)) || 2517 2518 nla_put_be32(skb, CTA_STATS_ERROR, htonl(st->error)) || 2518 2519 nla_put_be32(skb, CTA_STATS_SEARCH_RESTART, 2519 - htonl(st->search_restart))) 2520 + htonl(st->search_restart)) || 2521 + nla_put_be32(skb, CTA_STATS_CLASH_RESOLVE, 2522 + htonl(st->clash_resolve))) 2520 2523 goto nla_put_failure; 2521 2524 2522 2525 nlmsg_end(skb, nlh);
+2 -2
net/netfilter/nf_conntrack_standalone.c
··· 435 435 seq_printf(seq, "%08x %08x %08x %08x %08x %08x %08x %08x " 436 436 "%08x %08x %08x %08x %08x %08x %08x %08x %08x\n", 437 437 nr_conntracks, 438 - 0, 438 + st->clash_resolve, /* was: searched */ 439 439 st->found, 440 440 0, 441 441 st->invalid, 442 - st->ignore, 442 + 0, 443 443 0, 444 444 0, 445 445 st->insert,
+48 -9
net/netfilter/nf_tables_api.c
··· 650 650 .len = NFT_TABLE_MAXNAMELEN - 1 }, 651 651 [NFTA_TABLE_FLAGS] = { .type = NLA_U32 }, 652 652 [NFTA_TABLE_HANDLE] = { .type = NLA_U64 }, 653 + [NFTA_TABLE_USERDATA] = { .type = NLA_BINARY, 654 + .len = NFT_USERDATA_MAXLEN } 653 655 }; 654 656 655 657 static int nf_tables_fill_table_info(struct sk_buff *skb, struct net *net, ··· 677 675 nla_put_be64(skb, NFTA_TABLE_HANDLE, cpu_to_be64(table->handle), 678 676 NFTA_TABLE_PAD)) 679 677 goto nla_put_failure; 678 + 679 + if (table->udata) { 680 + if (nla_put(skb, NFTA_TABLE_USERDATA, table->udlen, table->udata)) 681 + goto nla_put_failure; 682 + } 680 683 681 684 nlmsg_end(skb, nlh); 682 685 return 0; ··· 984 977 int family = nfmsg->nfgen_family; 985 978 const struct nlattr *attr; 986 979 struct nft_table *table; 987 - u32 flags = 0; 988 980 struct nft_ctx ctx; 981 + u32 flags = 0; 982 + u16 udlen = 0; 989 983 int err; 990 984 991 985 lockdep_assert_held(&net->nft.commit_mutex); ··· 1022 1014 if (table->name == NULL) 1023 1015 goto err_strdup; 1024 1016 1017 + if (nla[NFTA_TABLE_USERDATA]) { 1018 + udlen = nla_len(nla[NFTA_TABLE_USERDATA]); 1019 + table->udata = kzalloc(udlen, GFP_KERNEL); 1020 + if (table->udata == NULL) 1021 + goto err_table_udata; 1022 + 1023 + nla_memcpy(table->udata, nla[NFTA_TABLE_USERDATA], udlen); 1024 + table->udlen = udlen; 1025 + } 1026 + 1025 1027 err = rhltable_init(&table->chains_ht, &nft_chain_ht_params); 1026 1028 if (err) 1027 1029 goto err_chain_ht; ··· 1054 1036 err_trans: 1055 1037 rhltable_destroy(&table->chains_ht); 1056 1038 err_chain_ht: 1039 + kfree(table->udata); 1040 + err_table_udata: 1057 1041 kfree(table->name); 1058 1042 err_strdup: 1059 1043 kfree(table); ··· 5750 5730 [NFTA_OBJ_TYPE] = { .type = NLA_U32 }, 5751 5731 [NFTA_OBJ_DATA] = { .type = NLA_NESTED }, 5752 5732 [NFTA_OBJ_HANDLE] = { .type = NLA_U64}, 5733 + [NFTA_OBJ_USERDATA] = { .type = NLA_BINARY, 5734 + .len = NFT_USERDATA_MAXLEN }, 5753 5735 }; 5754 5736 5755 5737 static struct nft_object *nft_obj_init(const struct nft_ctx *ctx, ··· 5899 5877 struct nft_object *obj; 5900 5878 struct nft_ctx ctx; 5901 5879 u32 objtype; 5880 + u16 udlen; 5902 5881 int err; 5903 5882 5904 5883 if (!nla[NFTA_OBJ_TYPE] || ··· 5944 5921 obj = nft_obj_init(&ctx, type, nla[NFTA_OBJ_DATA]); 5945 5922 if (IS_ERR(obj)) { 5946 5923 err = PTR_ERR(obj); 5947 - goto err1; 5924 + goto err_init; 5948 5925 } 5949 5926 obj->key.table = table; 5950 5927 obj->handle = nf_tables_alloc_handle(table); ··· 5952 5929 obj->key.name = nla_strdup(nla[NFTA_OBJ_NAME], GFP_KERNEL); 5953 5930 if (!obj->key.name) { 5954 5931 err = -ENOMEM; 5955 - goto err2; 5932 + goto err_strdup; 5933 + } 5934 + 5935 + if (nla[NFTA_OBJ_USERDATA]) { 5936 + udlen = nla_len(nla[NFTA_OBJ_USERDATA]); 5937 + obj->udata = kzalloc(udlen, GFP_KERNEL); 5938 + if (obj->udata == NULL) 5939 + goto err_userdata; 5940 + 5941 + nla_memcpy(obj->udata, nla[NFTA_OBJ_USERDATA], udlen); 5942 + obj->udlen = udlen; 5956 5943 } 5957 5944 5958 5945 err = nft_trans_obj_add(&ctx, NFT_MSG_NEWOBJ, obj); 5959 5946 if (err < 0) 5960 - goto err3; 5947 + goto err_trans; 5961 5948 5962 5949 err = rhltable_insert(&nft_objname_ht, &obj->rhlhead, 5963 5950 nft_objname_ht_params); 5964 5951 if (err < 0) 5965 - goto err4; 5952 + goto err_obj_ht; 5966 5953 5967 5954 list_add_tail_rcu(&obj->list, &table->objects); 5968 5955 table->use++; 5969 5956 return 0; 5970 - err4: 5957 + err_obj_ht: 5971 5958 /* queued in transaction log */ 5972 5959 INIT_LIST_HEAD(&obj->list); 5973 5960 return err; 5974 - err3: 5961 + err_trans: 5975 5962 kfree(obj->key.name); 5976 - err2: 5963 + err_userdata: 5964 + kfree(obj->udata); 5965 + err_strdup: 5977 5966 if (obj->ops->destroy) 5978 5967 obj->ops->destroy(&ctx, obj); 5979 5968 kfree(obj); 5980 - err1: 5969 + err_init: 5981 5970 module_put(type->owner); 5982 5971 return err; 5983 5972 } ··· 6019 5984 nft_object_dump(skb, NFTA_OBJ_DATA, obj, reset) || 6020 5985 nla_put_be64(skb, NFTA_OBJ_HANDLE, cpu_to_be64(obj->handle), 6021 5986 NFTA_OBJ_PAD)) 5987 + goto nla_put_failure; 5988 + 5989 + if (obj->udata && 5990 + nla_put(skb, NFTA_OBJ_USERDATA, obj->udlen, obj->udata)) 6022 5991 goto nla_put_failure; 6023 5992 6024 5993 nlmsg_end(skb, nlh);
+27
net/netfilter/nft_socket.c
··· 14 14 }; 15 15 }; 16 16 17 + static void nft_socket_wildcard(const struct nft_pktinfo *pkt, 18 + struct nft_regs *regs, struct sock *sk, 19 + u32 *dest) 20 + { 21 + switch (nft_pf(pkt)) { 22 + case NFPROTO_IPV4: 23 + nft_reg_store8(dest, inet_sk(sk)->inet_rcv_saddr == 0); 24 + break; 25 + #if IS_ENABLED(CONFIG_NF_TABLES_IPV6) 26 + case NFPROTO_IPV6: 27 + nft_reg_store8(dest, ipv6_addr_any(&sk->sk_v6_rcv_saddr)); 28 + break; 29 + #endif 30 + default: 31 + regs->verdict.code = NFT_BREAK; 32 + return; 33 + } 34 + } 35 + 17 36 static void nft_socket_eval(const struct nft_expr *expr, 18 37 struct nft_regs *regs, 19 38 const struct nft_pktinfo *pkt) ··· 78 59 return; 79 60 } 80 61 break; 62 + case NFT_SOCKET_WILDCARD: 63 + if (!sk_fullsock(sk)) { 64 + regs->verdict.code = NFT_BREAK; 65 + return; 66 + } 67 + nft_socket_wildcard(pkt, regs, sk, dest); 68 + break; 81 69 default: 82 70 WARN_ON(1); 83 71 regs->verdict.code = NFT_BREAK; ··· 123 97 priv->key = ntohl(nla_get_u32(tb[NFTA_SOCKET_KEY])); 124 98 switch(priv->key) { 125 99 case NFT_SOCKET_TRANSPARENT: 100 + case NFT_SOCKET_WILDCARD: 126 101 len = sizeof(u8); 127 102 break; 128 103 case NFT_SOCKET_MARK:
+1 -1
net/netfilter/xt_HMARK.c
··· 276 276 return 0; 277 277 278 278 /* follow-up fragments don't contain ports, skip all fragments */ 279 - if (ip->frag_off & htons(IP_MF | IP_OFFSET)) 279 + if (ip_is_fragment(ip)) 280 280 return 0; 281 281 282 282 hmark_set_tuple_ports(skb, (ip->ihl * 4) + nhoff, t, info);
+1 -2
tools/testing/selftests/net/config
··· 24 24 CONFIG_NF_TABLES=m 25 25 CONFIG_NF_TABLES_IPV6=y 26 26 CONFIG_NF_TABLES_IPV4=y 27 - CONFIG_NFT_CHAIN_NAT_IPV6=m 28 - CONFIG_NFT_CHAIN_NAT_IPV4=m 27 + CONFIG_NFT_NAT=m 29 28 CONFIG_NET_SCH_FQ=m 30 29 CONFIG_NET_SCH_ETF=m 31 30 CONFIG_NET_SCH_NETEM=y