VPP-113: BVI shall filter unicast DMAC for L2 to L3 forwading
[vpp.git] / vnet / vnet / ethernet / ethernet.h
index 04e07b7..97c66e7 100644 (file)
@@ -96,7 +96,7 @@ typedef struct ethernet_interface {
   u8 address[6];
 } ethernet_interface_t;
 
-vnet_hw_interface_class_t ethernet_hw_interface_class;
+extern vnet_hw_interface_class_t ethernet_hw_interface_class;
 
 typedef struct {
   /* Name (a c string). */
@@ -308,9 +308,54 @@ ethernet_buffer_get_header (vlib_buffer_t * b)
      + vnet_buffer (b)->ethernet.start_of_ethernet_header);
 }
 
+/** Returns the number of VLAN headers in the current Ethernet frame in the
+ * buffer. Returns 0, 1, 2 for the known header count. The value 3 indicates
+ * the number of headers is not known.
+ */
+#define ethernet_buffer_get_vlan_count(b) ( \
+    ((b)->flags & ETH_BUFFER_VLAN_BITS) >> LOG2_ETH_BUFFER_VLAN_1_DEEP \
+)
+
+/** Sets the number of VLAN headers in the current Ethernet frame in the
+ * buffer. Values 0, 1, 2 indicate  the header count. The value 3 indicates
+ * the number of headers is not known.
+ */
+#define ethernet_buffer_set_vlan_count(b, v) ( \
+    (b)->flags = ((b)->flags & ~ETH_BUFFER_VLAN_BITS) | \
+        (((v) << LOG2_ETH_BUFFER_VLAN_1_DEEP) & ETH_BUFFER_VLAN_BITS) \
+)
+
+/** Adjusts the vlan count by the delta in 'v' */
+#define ethernet_buffer_adjust_vlan_count(b, v) ( \
+  ethernet_buffer_set_vlan_count(b,  \
+      (word)ethernet_buffer_get_vlan_count(b) + (word)(v)) \
+)
+
+/** Adjusts the vlan count by the header size byte delta in 'v' */
+#define ethernet_buffer_adjust_vlan_count_by_bytes(b, v) ( \
+    (b)->flags = ((b)->flags & ~ETH_BUFFER_VLAN_BITS) | (( \
+        ((b)->flags & ETH_BUFFER_VLAN_BITS) + \
+        ((v) << (LOG2_ETH_BUFFER_VLAN_1_DEEP - 2)) \
+    ) & ETH_BUFFER_VLAN_BITS) \
+)
+
+/**
+ * Determine the size of the Ethernet headers of the current frame in
+ * the buffer. This uses the VLAN depth flags that are set by
+ * ethernet-input. Because these flags are stored in the vlib_buffer_t
+ * "flags" field this count is valid regardless of the node so long as it's
+ * checked downstream of ethernet-input; That is, the value is not stored in
+ * the opaque space.
+ */
+#define ethernet_buffer_header_size(b) ( \
+        ethernet_buffer_get_vlan_count((b)) * sizeof(ethernet_vlan_header_t) + \
+        sizeof(ethernet_header_t) \
+)
+
 ethernet_main_t * ethernet_get_main (vlib_main_t * vm);
 u32 ethernet_set_flags (vnet_main_t * vnm, u32 hw_if_index, u32 flags);
 void ethernet_sw_interface_set_l2_mode (vnet_main_t * vnm, u32 sw_if_index, u32 l2);
+void ethernet_sw_interface_set_l2_mode_noport (vnet_main_t * vnm, u32 sw_if_index, u32 l2);
 void ethernet_set_rx_redirect (vnet_main_t * vnm, vnet_hw_interface_t * hi, u32 enable);
 
 int
@@ -427,6 +472,14 @@ eth_identify_subint (vnet_hw_interface_t * hi,
   return 1;
 }
 
+// Compare two ethernet macs. Return 1 if they are the same, 0 if different
+always_inline u32
+eth_mac_equal (u8 * mac1, u8 * mac2) {
+  return (*((u32 *)(mac1+0)) == *((u32 *)(mac2+0)) &&
+          *((u32 *)(mac1+2)) == *((u32 *)(mac2+2)));
+}
+
+
 always_inline ethernet_main_t * 
 vnet_get_ethernet_main (void)
 {
@@ -448,6 +501,8 @@ int vnet_add_del_ip4_arp_change_event (vnet_main_t * vnm,
                                        uword type_opaque,
                                        uword data, int is_add);
 
-vlib_node_registration_t ethernet_input_node;
+u32 vnet_arp_glean_add(u32 fib_index, void * next_hop_arg);
+
+extern vlib_node_registration_t ethernet_input_node;
 
 #endif /* included_ethernet_h */