forked from mirrors/linux
		
	netfilter: avoid using skb->nf_bridge directly
This pointer is going to be removed soon, so use the existing helpers in more places to avoid noise when the removal happens. Signed-off-by: Florian Westphal <fw@strlen.de> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
		
							parent
							
								
									8239d57904
								
							
						
					
					
						commit
						c4b0e771f9
					
				
					 9 changed files with 103 additions and 66 deletions
				
			
		| 
						 | 
					@ -17,43 +17,58 @@ static inline void br_drop_fake_rtable(struct sk_buff *skb)
 | 
				
			||||||
		skb_dst_drop(skb);
 | 
							skb_dst_drop(skb);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static inline struct nf_bridge_info *
 | 
				
			||||||
 | 
					nf_bridge_info_get(const struct sk_buff *skb)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						return skb->nf_bridge;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static inline bool nf_bridge_info_exists(const struct sk_buff *skb)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						return skb->nf_bridge != NULL;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static inline int nf_bridge_get_physinif(const struct sk_buff *skb)
 | 
					static inline int nf_bridge_get_physinif(const struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct nf_bridge_info *nf_bridge;
 | 
						const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if (skb->nf_bridge == NULL)
 | 
						if (!nf_bridge)
 | 
				
			||||||
		return 0;
 | 
							return 0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	nf_bridge = skb->nf_bridge;
 | 
					 | 
				
			||||||
	return nf_bridge->physindev ? nf_bridge->physindev->ifindex : 0;
 | 
						return nf_bridge->physindev ? nf_bridge->physindev->ifindex : 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static inline int nf_bridge_get_physoutif(const struct sk_buff *skb)
 | 
					static inline int nf_bridge_get_physoutif(const struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct nf_bridge_info *nf_bridge;
 | 
						const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if (skb->nf_bridge == NULL)
 | 
						if (!nf_bridge)
 | 
				
			||||||
		return 0;
 | 
							return 0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	nf_bridge = skb->nf_bridge;
 | 
					 | 
				
			||||||
	return nf_bridge->physoutdev ? nf_bridge->physoutdev->ifindex : 0;
 | 
						return nf_bridge->physoutdev ? nf_bridge->physoutdev->ifindex : 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static inline struct net_device *
 | 
					static inline struct net_device *
 | 
				
			||||||
nf_bridge_get_physindev(const struct sk_buff *skb)
 | 
					nf_bridge_get_physindev(const struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	return skb->nf_bridge ? skb->nf_bridge->physindev : NULL;
 | 
						const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nf_bridge ? nf_bridge->physindev : NULL;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static inline struct net_device *
 | 
					static inline struct net_device *
 | 
				
			||||||
nf_bridge_get_physoutdev(const struct sk_buff *skb)
 | 
					nf_bridge_get_physoutdev(const struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	return skb->nf_bridge ? skb->nf_bridge->physoutdev : NULL;
 | 
						const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nf_bridge ? nf_bridge->physoutdev : NULL;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static inline bool nf_bridge_in_prerouting(const struct sk_buff *skb)
 | 
					static inline bool nf_bridge_in_prerouting(const struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	return skb->nf_bridge && skb->nf_bridge->in_prerouting;
 | 
						const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nf_bridge && nf_bridge->in_prerouting;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
#else
 | 
					#else
 | 
				
			||||||
#define br_drop_fake_rtable(skb)	        do { } while (0)
 | 
					#define br_drop_fake_rtable(skb)	        do { } while (0)
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -22,12 +22,6 @@ int br_nf_hook_thresh(unsigned int hook, struct net *net, struct sock *sk,
 | 
				
			||||||
		      int (*okfn)(struct net *, struct sock *,
 | 
							      int (*okfn)(struct net *, struct sock *,
 | 
				
			||||||
				  struct sk_buff *));
 | 
									  struct sk_buff *));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static inline struct nf_bridge_info *
 | 
					 | 
				
			||||||
nf_bridge_info_get(const struct sk_buff *skb)
 | 
					 | 
				
			||||||
{
 | 
					 | 
				
			||||||
	return skb->nf_bridge;
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
unsigned int nf_bridge_encap_header_len(const struct sk_buff *skb);
 | 
					unsigned int nf_bridge_encap_header_len(const struct sk_buff *skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static inline void nf_bridge_push_encap_header(struct sk_buff *skb)
 | 
					static inline void nf_bridge_push_encap_header(struct sk_buff *skb)
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -247,7 +247,9 @@ static int br_validate_ipv4(struct net *net, struct sk_buff *skb)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void nf_bridge_update_protocol(struct sk_buff *skb)
 | 
					void nf_bridge_update_protocol(struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	switch (skb->nf_bridge->orig_proto) {
 | 
						const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						switch (nf_bridge->orig_proto) {
 | 
				
			||||||
	case BRNF_PROTO_8021Q:
 | 
						case BRNF_PROTO_8021Q:
 | 
				
			||||||
		skb->protocol = htons(ETH_P_8021Q);
 | 
							skb->protocol = htons(ETH_P_8021Q);
 | 
				
			||||||
		break;
 | 
							break;
 | 
				
			||||||
| 
						 | 
					@ -569,7 +571,8 @@ static unsigned int br_nf_forward_ip(void *priv,
 | 
				
			||||||
	struct net_device *parent;
 | 
						struct net_device *parent;
 | 
				
			||||||
	u_int8_t pf;
 | 
						u_int8_t pf;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if (!skb->nf_bridge)
 | 
						nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
						if (!nf_bridge)
 | 
				
			||||||
		return NF_ACCEPT;
 | 
							return NF_ACCEPT;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	/* Need exclusive nf_bridge_info since we might have multiple
 | 
						/* Need exclusive nf_bridge_info since we might have multiple
 | 
				
			||||||
| 
						 | 
					@ -701,7 +704,9 @@ br_nf_ip_fragment(struct net *net, struct sock *sk, struct sk_buff *skb,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static unsigned int nf_bridge_mtu_reduction(const struct sk_buff *skb)
 | 
					static unsigned int nf_bridge_mtu_reduction(const struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	if (skb->nf_bridge->orig_proto == BRNF_PROTO_PPPOE)
 | 
						const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if (nf_bridge->orig_proto == BRNF_PROTO_PPPOE)
 | 
				
			||||||
		return PPPOE_SES_HLEN;
 | 
							return PPPOE_SES_HLEN;
 | 
				
			||||||
	return 0;
 | 
						return 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
| 
						 | 
					@ -839,7 +844,9 @@ static unsigned int ip_sabotage_in(void *priv,
 | 
				
			||||||
				   struct sk_buff *skb,
 | 
									   struct sk_buff *skb,
 | 
				
			||||||
				   const struct nf_hook_state *state)
 | 
									   const struct nf_hook_state *state)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	if (skb->nf_bridge && !skb->nf_bridge->in_prerouting &&
 | 
						struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if (nf_bridge && !nf_bridge->in_prerouting &&
 | 
				
			||||||
	    !netif_is_l3_master(skb->dev)) {
 | 
						    !netif_is_l3_master(skb->dev)) {
 | 
				
			||||||
		state->okfn(state->net, state->sk, skb);
 | 
							state->okfn(state->net, state->sk, skb);
 | 
				
			||||||
		return NF_STOLEN;
 | 
							return NF_STOLEN;
 | 
				
			||||||
| 
						 | 
					@ -877,7 +884,9 @@ static void br_nf_pre_routing_finish_bridge_slow(struct sk_buff *skb)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static int br_nf_dev_xmit(struct sk_buff *skb)
 | 
					static int br_nf_dev_xmit(struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	if (skb->nf_bridge && skb->nf_bridge->bridged_dnat) {
 | 
						const struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if (nf_bridge && nf_bridge->bridged_dnat) {
 | 
				
			||||||
		br_nf_pre_routing_finish_bridge_slow(skb);
 | 
							br_nf_pre_routing_finish_bridge_slow(skb);
 | 
				
			||||||
		return 1;
 | 
							return 1;
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -102,6 +102,7 @@ EXPORT_SYMBOL_GPL(nf_reject_ip_tcphdr_put);
 | 
				
			||||||
/* Send RST reply */
 | 
					/* Send RST reply */
 | 
				
			||||||
void nf_send_reset(struct net *net, struct sk_buff *oldskb, int hook)
 | 
					void nf_send_reset(struct net *net, struct sk_buff *oldskb, int hook)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
 | 
						struct net_device *br_indev __maybe_unused;
 | 
				
			||||||
	struct sk_buff *nskb;
 | 
						struct sk_buff *nskb;
 | 
				
			||||||
	struct iphdr *niph;
 | 
						struct iphdr *niph;
 | 
				
			||||||
	const struct tcphdr *oth;
 | 
						const struct tcphdr *oth;
 | 
				
			||||||
| 
						 | 
					@ -147,10 +148,11 @@ void nf_send_reset(struct net *net, struct sk_buff *oldskb, int hook)
 | 
				
			||||||
	 * build the eth header using the original destination's MAC as the
 | 
						 * build the eth header using the original destination's MAC as the
 | 
				
			||||||
	 * source, and send the RST packet directly.
 | 
						 * source, and send the RST packet directly.
 | 
				
			||||||
	 */
 | 
						 */
 | 
				
			||||||
	if (oldskb->nf_bridge) {
 | 
						br_indev = nf_bridge_get_physindev(oldskb);
 | 
				
			||||||
 | 
						if (br_indev) {
 | 
				
			||||||
		struct ethhdr *oeth = eth_hdr(oldskb);
 | 
							struct ethhdr *oeth = eth_hdr(oldskb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		nskb->dev = nf_bridge_get_physindev(oldskb);
 | 
							nskb->dev = br_indev;
 | 
				
			||||||
		niph->tot_len = htons(nskb->len);
 | 
							niph->tot_len = htons(nskb->len);
 | 
				
			||||||
		ip_send_check(niph);
 | 
							ip_send_check(niph);
 | 
				
			||||||
		if (dev_hard_header(nskb, nskb->dev, ntohs(nskb->protocol),
 | 
							if (dev_hard_header(nskb, nskb->dev, ntohs(nskb->protocol),
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -131,6 +131,7 @@ EXPORT_SYMBOL_GPL(nf_reject_ip6_tcphdr_put);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void nf_send_reset6(struct net *net, struct sk_buff *oldskb, int hook)
 | 
					void nf_send_reset6(struct net *net, struct sk_buff *oldskb, int hook)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
 | 
						struct net_device *br_indev __maybe_unused;
 | 
				
			||||||
	struct sk_buff *nskb;
 | 
						struct sk_buff *nskb;
 | 
				
			||||||
	struct tcphdr _otcph;
 | 
						struct tcphdr _otcph;
 | 
				
			||||||
	const struct tcphdr *otcph;
 | 
						const struct tcphdr *otcph;
 | 
				
			||||||
| 
						 | 
					@ -197,15 +198,18 @@ void nf_send_reset6(struct net *net, struct sk_buff *oldskb, int hook)
 | 
				
			||||||
	 * build the eth header using the original destination's MAC as the
 | 
						 * build the eth header using the original destination's MAC as the
 | 
				
			||||||
	 * source, and send the RST packet directly.
 | 
						 * source, and send the RST packet directly.
 | 
				
			||||||
	 */
 | 
						 */
 | 
				
			||||||
	if (oldskb->nf_bridge) {
 | 
						br_indev = nf_bridge_get_physindev(oldskb);
 | 
				
			||||||
 | 
						if (br_indev) {
 | 
				
			||||||
		struct ethhdr *oeth = eth_hdr(oldskb);
 | 
							struct ethhdr *oeth = eth_hdr(oldskb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		nskb->dev = nf_bridge_get_physindev(oldskb);
 | 
							nskb->dev = br_indev;
 | 
				
			||||||
		nskb->protocol = htons(ETH_P_IPV6);
 | 
							nskb->protocol = htons(ETH_P_IPV6);
 | 
				
			||||||
		ip6h->payload_len = htons(sizeof(struct tcphdr));
 | 
							ip6h->payload_len = htons(sizeof(struct tcphdr));
 | 
				
			||||||
		if (dev_hard_header(nskb, nskb->dev, ntohs(nskb->protocol),
 | 
							if (dev_hard_header(nskb, nskb->dev, ntohs(nskb->protocol),
 | 
				
			||||||
				    oeth->h_source, oeth->h_dest, nskb->len) < 0)
 | 
									    oeth->h_source, oeth->h_dest, nskb->len) < 0) {
 | 
				
			||||||
 | 
								kfree_skb(nskb);
 | 
				
			||||||
			return;
 | 
								return;
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
		dev_queue_xmit(nskb);
 | 
							dev_queue_xmit(nskb);
 | 
				
			||||||
	} else
 | 
						} else
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -156,22 +156,20 @@ nf_log_dump_packet_common(struct nf_log_buf *m, u_int8_t pf,
 | 
				
			||||||
			  const struct net_device *out,
 | 
								  const struct net_device *out,
 | 
				
			||||||
			  const struct nf_loginfo *loginfo, const char *prefix)
 | 
								  const struct nf_loginfo *loginfo, const char *prefix)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
 | 
						const struct net_device *physoutdev __maybe_unused;
 | 
				
			||||||
 | 
						const struct net_device *physindev __maybe_unused;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	nf_log_buf_add(m, KERN_SOH "%c%sIN=%s OUT=%s ",
 | 
						nf_log_buf_add(m, KERN_SOH "%c%sIN=%s OUT=%s ",
 | 
				
			||||||
	       '0' + loginfo->u.log.level, prefix,
 | 
						       '0' + loginfo->u.log.level, prefix,
 | 
				
			||||||
	       in ? in->name : "",
 | 
						       in ? in->name : "",
 | 
				
			||||||
	       out ? out->name : "");
 | 
						       out ? out->name : "");
 | 
				
			||||||
#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
 | 
					#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
 | 
				
			||||||
	if (skb->nf_bridge) {
 | 
						physindev = nf_bridge_get_physindev(skb);
 | 
				
			||||||
		const struct net_device *physindev;
 | 
						if (physindev && in != physindev)
 | 
				
			||||||
		const struct net_device *physoutdev;
 | 
							nf_log_buf_add(m, "PHYSIN=%s ", physindev->name);
 | 
				
			||||||
 | 
						physoutdev = nf_bridge_get_physoutdev(skb);
 | 
				
			||||||
		physindev = nf_bridge_get_physindev(skb);
 | 
						if (physoutdev && out != physoutdev)
 | 
				
			||||||
		if (physindev && in != physindev)
 | 
							nf_log_buf_add(m, "PHYSOUT=%s ", physoutdev->name);
 | 
				
			||||||
			nf_log_buf_add(m, "PHYSIN=%s ", physindev->name);
 | 
					 | 
				
			||||||
		physoutdev = nf_bridge_get_physoutdev(skb);
 | 
					 | 
				
			||||||
		if (physoutdev && out != physoutdev)
 | 
					 | 
				
			||||||
			nf_log_buf_add(m, "PHYSOUT=%s ", physoutdev->name);
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
EXPORT_SYMBOL_GPL(nf_log_dump_packet_common);
 | 
					EXPORT_SYMBOL_GPL(nf_log_dump_packet_common);
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -46,6 +46,24 @@ void nf_unregister_queue_handler(struct net *net)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
EXPORT_SYMBOL(nf_unregister_queue_handler);
 | 
					EXPORT_SYMBOL(nf_unregister_queue_handler);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void nf_queue_entry_release_br_nf_refs(struct sk_buff *skb)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
					#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
 | 
				
			||||||
 | 
						struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if (nf_bridge) {
 | 
				
			||||||
 | 
							struct net_device *physdev;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							physdev = nf_bridge_get_physindev(skb);
 | 
				
			||||||
 | 
							if (physdev)
 | 
				
			||||||
 | 
								dev_put(physdev);
 | 
				
			||||||
 | 
							physdev = nf_bridge_get_physoutdev(skb);
 | 
				
			||||||
 | 
							if (physdev)
 | 
				
			||||||
 | 
								dev_put(physdev);
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void nf_queue_entry_release_refs(struct nf_queue_entry *entry)
 | 
					void nf_queue_entry_release_refs(struct nf_queue_entry *entry)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	struct nf_hook_state *state = &entry->state;
 | 
						struct nf_hook_state *state = &entry->state;
 | 
				
			||||||
| 
						 | 
					@ -57,20 +75,28 @@ void nf_queue_entry_release_refs(struct nf_queue_entry *entry)
 | 
				
			||||||
		dev_put(state->out);
 | 
							dev_put(state->out);
 | 
				
			||||||
	if (state->sk)
 | 
						if (state->sk)
 | 
				
			||||||
		sock_put(state->sk);
 | 
							sock_put(state->sk);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						nf_queue_entry_release_br_nf_refs(entry->skb);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					EXPORT_SYMBOL_GPL(nf_queue_entry_release_refs);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void nf_queue_entry_get_br_nf_refs(struct sk_buff *skb)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
 | 
					#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
 | 
				
			||||||
	if (entry->skb->nf_bridge) {
 | 
						struct nf_bridge_info *nf_bridge = nf_bridge_info_get(skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if (nf_bridge) {
 | 
				
			||||||
		struct net_device *physdev;
 | 
							struct net_device *physdev;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		physdev = nf_bridge_get_physindev(entry->skb);
 | 
							physdev = nf_bridge_get_physindev(skb);
 | 
				
			||||||
		if (physdev)
 | 
							if (physdev)
 | 
				
			||||||
			dev_put(physdev);
 | 
								dev_hold(physdev);
 | 
				
			||||||
		physdev = nf_bridge_get_physoutdev(entry->skb);
 | 
							physdev = nf_bridge_get_physoutdev(skb);
 | 
				
			||||||
		if (physdev)
 | 
							if (physdev)
 | 
				
			||||||
			dev_put(physdev);
 | 
								dev_hold(physdev);
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
EXPORT_SYMBOL_GPL(nf_queue_entry_release_refs);
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
/* Bump dev refs so they don't vanish while packet is out */
 | 
					/* Bump dev refs so they don't vanish while packet is out */
 | 
				
			||||||
void nf_queue_entry_get_refs(struct nf_queue_entry *entry)
 | 
					void nf_queue_entry_get_refs(struct nf_queue_entry *entry)
 | 
				
			||||||
| 
						 | 
					@ -83,18 +109,8 @@ void nf_queue_entry_get_refs(struct nf_queue_entry *entry)
 | 
				
			||||||
		dev_hold(state->out);
 | 
							dev_hold(state->out);
 | 
				
			||||||
	if (state->sk)
 | 
						if (state->sk)
 | 
				
			||||||
		sock_hold(state->sk);
 | 
							sock_hold(state->sk);
 | 
				
			||||||
#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
 | 
					 | 
				
			||||||
	if (entry->skb->nf_bridge) {
 | 
					 | 
				
			||||||
		struct net_device *physdev;
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
		physdev = nf_bridge_get_physindev(entry->skb);
 | 
						nf_queue_entry_get_br_nf_refs(entry->skb);
 | 
				
			||||||
		if (physdev)
 | 
					 | 
				
			||||||
			dev_hold(physdev);
 | 
					 | 
				
			||||||
		physdev = nf_bridge_get_physoutdev(entry->skb);
 | 
					 | 
				
			||||||
		if (physdev)
 | 
					 | 
				
			||||||
			dev_hold(physdev);
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
#endif
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
EXPORT_SYMBOL_GPL(nf_queue_entry_get_refs);
 | 
					EXPORT_SYMBOL_GPL(nf_queue_entry_get_refs);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -727,13 +727,13 @@ nf_queue_entry_dup(struct nf_queue_entry *e)
 | 
				
			||||||
 */
 | 
					 */
 | 
				
			||||||
static void nf_bridge_adjust_skb_data(struct sk_buff *skb)
 | 
					static void nf_bridge_adjust_skb_data(struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	if (skb->nf_bridge)
 | 
						if (nf_bridge_info_get(skb))
 | 
				
			||||||
		__skb_push(skb, skb->network_header - skb->mac_header);
 | 
							__skb_push(skb, skb->network_header - skb->mac_header);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void nf_bridge_adjust_segmented_data(struct sk_buff *skb)
 | 
					static void nf_bridge_adjust_segmented_data(struct sk_buff *skb)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	if (skb->nf_bridge)
 | 
						if (nf_bridge_info_get(skb))
 | 
				
			||||||
		__skb_pull(skb, skb->network_header - skb->mac_header);
 | 
							__skb_pull(skb, skb->network_header - skb->mac_header);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
#else
 | 
					#else
 | 
				
			||||||
| 
						 | 
					@ -904,23 +904,22 @@ nfqnl_set_mode(struct nfqnl_instance *queue,
 | 
				
			||||||
static int
 | 
					static int
 | 
				
			||||||
dev_cmp(struct nf_queue_entry *entry, unsigned long ifindex)
 | 
					dev_cmp(struct nf_queue_entry *entry, unsigned long ifindex)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
 | 
					#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
 | 
				
			||||||
 | 
						int physinif, physoutif;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						physinif = nf_bridge_get_physinif(entry->skb);
 | 
				
			||||||
 | 
						physoutif = nf_bridge_get_physoutif(entry->skb);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if (physinif == ifindex || physoutif == ifindex)
 | 
				
			||||||
 | 
							return 1;
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
	if (entry->state.in)
 | 
						if (entry->state.in)
 | 
				
			||||||
		if (entry->state.in->ifindex == ifindex)
 | 
							if (entry->state.in->ifindex == ifindex)
 | 
				
			||||||
			return 1;
 | 
								return 1;
 | 
				
			||||||
	if (entry->state.out)
 | 
						if (entry->state.out)
 | 
				
			||||||
		if (entry->state.out->ifindex == ifindex)
 | 
							if (entry->state.out->ifindex == ifindex)
 | 
				
			||||||
			return 1;
 | 
								return 1;
 | 
				
			||||||
#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
 | 
					 | 
				
			||||||
	if (entry->skb->nf_bridge) {
 | 
					 | 
				
			||||||
		int physinif, physoutif;
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
		physinif = nf_bridge_get_physinif(entry->skb);
 | 
					 | 
				
			||||||
		physoutif = nf_bridge_get_physoutif(entry->skb);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		if (physinif == ifindex || physoutif == ifindex)
 | 
					 | 
				
			||||||
			return 1;
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
#endif
 | 
					 | 
				
			||||||
	return 0;
 | 
						return 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -33,7 +33,7 @@ physdev_mt(const struct sk_buff *skb, struct xt_action_param *par)
 | 
				
			||||||
	/* Not a bridged IP packet or no info available yet:
 | 
						/* Not a bridged IP packet or no info available yet:
 | 
				
			||||||
	 * LOCAL_OUT/mangle and LOCAL_OUT/nat don't know if
 | 
						 * LOCAL_OUT/mangle and LOCAL_OUT/nat don't know if
 | 
				
			||||||
	 * the destination device will be a bridge. */
 | 
						 * the destination device will be a bridge. */
 | 
				
			||||||
	if (!skb->nf_bridge) {
 | 
						if (!nf_bridge_info_exists(skb)) {
 | 
				
			||||||
		/* Return MATCH if the invert flags of the used options are on */
 | 
							/* Return MATCH if the invert flags of the used options are on */
 | 
				
			||||||
		if ((info->bitmask & XT_PHYSDEV_OP_BRIDGED) &&
 | 
							if ((info->bitmask & XT_PHYSDEV_OP_BRIDGED) &&
 | 
				
			||||||
		    !(info->invert & XT_PHYSDEV_OP_BRIDGED))
 | 
							    !(info->invert & XT_PHYSDEV_OP_BRIDGED))
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in a new issue