aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBenoît Ganne <bganne@cisco.com>2019-06-06 17:53:21 +0200
committerNeale Ranns <nranns@cisco.com>2019-06-26 11:37:24 +0000
commitc47b97ddacc35cb10e4a2b0dcfff3e690ec5bf76 (patch)
tree54795991d95324283fff26ba91eda78c2fe64adb
parentab05508e1eb96749b68de8ccd2f6f88ff3e64fad (diff)
gbp: enforce same endpoint mac and ip src
During packet classification, make sure packets coming from an EP also matches this specific EP IP address and vice-versa. This prevents and EP to send a packet on behalf of another EP. Type: fix Change-Id: I30287644ec73b90d9b6913952a82b2baedf6a5ff Signed-off-by: Benoît Ganne <bganne@cisco.com>
-rw-r--r--src/plugins/gbp/gbp_classify_node.c21
-rw-r--r--test/test_gbp.py16
2 files changed, 28 insertions, 9 deletions
diff --git a/src/plugins/gbp/gbp_classify_node.c b/src/plugins/gbp/gbp_classify_node.c
index a2d6d4c47ae..9ad2b06148d 100644
--- a/src/plugins/gbp/gbp_classify_node.c
+++ b/src/plugins/gbp/gbp_classify_node.c
@@ -359,12 +359,12 @@ gbp_lpm_classify_inline (vlib_main_t * vm,
while (n_left_from > 0 && n_left_to_next > 0)
{
u32 bi0, sw_if_index0, fib_index0, lbi0;
+ const gbp_endpoint_t *ge0, *ge_lpm0;
gbp_lpm_classify_next_t next0;
const ethernet_header_t *eh0;
const gbp_policy_dpo_t *gpd0;
const ip4_address_t *ip4_0;
const ip6_address_t *ip6_0;
- const gbp_endpoint_t *ge0;
const gbp_recirc_t *gr0;
const dpo_id_t *dpo0;
load_balance_t *lb0;
@@ -437,15 +437,15 @@ gbp_lpm_classify_inline (vlib_main_t * vm,
if (ip4_0)
{
- ge0 = gbp_endpoint_find_ip4 (ip4_0, fib_index0);
+ ge_lpm0 = gbp_endpoint_find_ip4 (ip4_0, fib_index0);
}
else if (ip6_0)
{
- ge0 = gbp_endpoint_find_ip6 (ip6_0, fib_index0);
+ ge_lpm0 = gbp_endpoint_find_ip6 (ip6_0, fib_index0);
}
else
{
- ge0 = NULL;
+ ge_lpm0 = NULL;
}
next0 = vnet_l2_feature_next
@@ -456,9 +456,18 @@ gbp_lpm_classify_inline (vlib_main_t * vm,
* if we found the EP by IP lookup, it must be from the EP
* not a network behind it
*/
- if (NULL != ge0)
+ if (NULL != ge_lpm0)
{
- sclass0 = ge0->ge_fwd.gef_sclass;
+ if (PREDICT_FALSE (ge0 != ge_lpm0))
+ {
+ /* an EP spoofing another EP */
+ sclass0 = SCLASS_INVALID;
+ next0 = GPB_LPM_CLASSIFY_DROP;
+ }
+ else
+ {
+ sclass0 = ge0->ge_fwd.gef_sclass;
+ }
goto trace;
}
}
diff --git a/test/test_gbp.py b/test/test_gbp.py
index cc26238276a..ac0fb222633 100644
--- a/test/test_gbp.py
+++ b/test/test_gbp.py
@@ -3618,6 +3618,16 @@ class TestGBP(VppTestCase):
rep.add_vpp_config()
#
+ # EP1 impersonating EP3 is dropped
+ #
+ p = (Ether(src=eep1.mac, dst="ff:ff:ff:ff:ff:ff") /
+ Dot1Q(vlan=100) /
+ ARP(op="who-has",
+ psrc="10.0.0.3", pdst="10.0.0.128",
+ hwsrc=eep1.mac, hwdst="ff:ff:ff:ff:ff:ff"))
+ self.send_and_assert_no_replies(self.pg0, p)
+
+ #
# ARP packet from External EPs are accepted and replied to
#
p_arp = (Ether(src=eep1.mac, dst="ff:ff:ff:ff:ff:ff") /
@@ -3630,11 +3640,11 @@ class TestGBP(VppTestCase):
#
# ARP packet from host in remote subnet are accepted and replied to
#
- p_arp = (Ether(src=vlan_102.remote_mac, dst="ff:ff:ff:ff:ff:ff") /
+ p_arp = (Ether(src=eep3.mac, dst="ff:ff:ff:ff:ff:ff") /
Dot1Q(vlan=102) /
ARP(op="who-has",
- psrc="10.0.0.17", pdst="10.0.0.128",
- hwsrc=vlan_102.remote_mac, hwdst="ff:ff:ff:ff:ff:ff"))
+ psrc=eep3.ip4.address, pdst="10.0.0.128",
+ hwsrc=eep3.mac, hwdst="ff:ff:ff:ff:ff:ff"))
rxs = self.send_and_expect(self.pg0, p_arp * 1, self.pg0)
#