From patchwork Wed Sep 14 23:40:05 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Mark Tomlinson X-Patchwork-Id: 670164 X-Patchwork-Delegate: davem@davemloft.net Return-Path: X-Original-To: patchwork-incoming@ozlabs.org Delivered-To: patchwork-incoming@ozlabs.org Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by ozlabs.org (Postfix) with ESMTP id 3sZJ29754wz9s9N for ; Thu, 15 Sep 2016 09:40:33 +1000 (AEST) Authentication-Results: ozlabs.org; dkim=pass (1024-bit key; unprotected) header.d=alliedtelesis.co.nz header.i=@alliedtelesis.co.nz header.b=Jjekls1P; dkim-atps=neutral Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1758433AbcINXk1 (ORCPT ); Wed, 14 Sep 2016 19:40:27 -0400 Received: from gate2.alliedtelesis.co.nz ([202.36.163.20]:60721 "EHLO gate2.alliedtelesis.co.nz" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1752008AbcINXkZ (ORCPT ); Wed, 14 Sep 2016 19:40:25 -0400 Received: from mmarshal3.atlnz.lc (mmarshal3.atlnz.lc [10.32.18.43]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (Client did not present a certificate) by gate2.alliedtelesis.co.nz (Postfix) with ESMTPS id 6030B80666; Thu, 15 Sep 2016 11:40:21 +1200 (NZST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=alliedtelesis.co.nz; s=mail; t=1473896421; bh=yRITsHkrMEqj3mQi7iQGtQa+1ZpT85M9ZJBVgS7zXHA=; h=From:To:Cc:Subject:Date:In-Reply-To:References; b=Jjekls1Ph8ob54vnQcAMQeee7z+jNkI+PMd8134klhNPK4/VDmpHfKmswRpsVg9pI GI6Mr1RlO0p6sR/QciWLSoiiqP2WWqDtRgsIyTMYBph1UFQ+bI3dH+lmKUV9OJXUuh 0PBhS0zw+ib1CRV6HZ6sYEK6qrL5u5KRGrraXvow= Received: from smtp (Not Verified[10.32.16.33]) by mmarshal3.atlnz.lc with Trustwave SEG (v7, 3, 6, 7949) id ; Thu, 15 Sep 2016 11:40:19 +1200 Received: from markto-dl.ws.atlnz.lc (markto-dl.ws.atlnz.lc [10.33.23.36]) by smtp (Postfix) with ESMTP id ABE9113EC2D; Thu, 15 Sep 2016 11:40:19 +1200 (NZST) Received: by markto-dl.ws.atlnz.lc (Postfix, from userid 1155) id BA56A2FEC9D; Thu, 15 Sep 2016 11:40:20 +1200 (NZST) From: Mark Tomlinson To: dsa@cumulusnetworks.com, netdev@vger.kernel.org Cc: Mark Tomlinson Subject: [PATCH v2] net: VRF: Pass original iif to ip_route_input() Date: Thu, 15 Sep 2016 11:40:05 +1200 Message-Id: <20160914234005.1240-1-mark.tomlinson@alliedtelesis.co.nz> X-Mailer: git-send-email 2.9.3 In-Reply-To: <20160912014553.20927-1-mark.tomlinson@alliedtelesis.co.nz> References: <20160912014553.20927-1-mark.tomlinson@alliedtelesis.co.nz> Sender: netdev-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: netdev@vger.kernel.org The function ip_rcv_finish() calls l3mdev_ip_rcv(). On any VRF except the global VRF, this replaces skb->dev with the VRF master interface. When calling ip_route_input_noref() from here, the checks for forwarding look at this master device instead of the initial ingress interface. This will allow packets to be routed which normally would be dropped. For example, an interface that is not assigned an IP address should drop packets, but because the checking is against the master device, the packet will be forwarded. The fix here is to still call l3mdev_ip_rcv(), but remember the initial net_device. This is passed to the other functions within ip_rcv_finish, so they still see the original interface. Signed-off-by: Mark Tomlinson Acked-by: David Ahern --- net/ipv4/ip_input.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/net/ipv4/ip_input.c b/net/ipv4/ip_input.c index 4b351af..d6feabb 100644 --- a/net/ipv4/ip_input.c +++ b/net/ipv4/ip_input.c @@ -312,6 +312,7 @@ static int ip_rcv_finish(struct net *net, struct sock *sk, struct sk_buff *skb) { const struct iphdr *iph = ip_hdr(skb); struct rtable *rt; + struct net_device *dev = skb->dev; /* if ingress device is enslaved to an L3 master device pass the * skb to its handler for processing @@ -341,7 +342,7 @@ static int ip_rcv_finish(struct net *net, struct sock *sk, struct sk_buff *skb) */ if (!skb_valid_dst(skb)) { int err = ip_route_input_noref(skb, iph->daddr, iph->saddr, - iph->tos, skb->dev); + iph->tos, dev); if (unlikely(err)) { if (err == -EXDEV) __NET_INC_STATS(net, LINUX_MIB_IPRPFILTER); @@ -370,7 +371,7 @@ static int ip_rcv_finish(struct net *net, struct sock *sk, struct sk_buff *skb) __IP_UPD_PO_STATS(net, IPSTATS_MIB_INBCAST, skb->len); } else if (skb->pkt_type == PACKET_BROADCAST || skb->pkt_type == PACKET_MULTICAST) { - struct in_device *in_dev = __in_dev_get_rcu(skb->dev); + struct in_device *in_dev = __in_dev_get_rcu(dev); /* RFC 1122 3.3.6: *