X-Git-Url: https://gerrit.fd.io/r/gitweb?a=blobdiff_plain;ds=sidebyside;f=vnet%2Fvnet%2Fl2%2Fl2_fib.h;h=4a2da59bc017279237493811cf5876f9101f86a6;hb=d7cb1b5f22948eba272e1a8844c75a2b87706fc4;hp=d1b8534dfde81cc45753c2e6ffd594f1f3034b0e;hpb=97d8dc2317780740af5faa3dc205d95d838fbd04;p=vpp.git diff --git a/vnet/vnet/l2/l2_fib.h b/vnet/vnet/l2/l2_fib.h index d1b8534dfde..4a2da59bc01 100644 --- a/vnet/vnet/l2/l2_fib.h +++ b/vnet/vnet/l2/l2_fib.h @@ -48,6 +48,8 @@ typedef struct }; } l2fib_entry_key_t; +STATIC_ASSERT_SIZEOF (l2fib_entry_key_t, 8); + /* * The l2fib entry results */ @@ -62,8 +64,7 @@ typedef struct u8 static_mac:1; /* static mac, no dataplane learning */ u8 bvi:1; /* mac is for a bridged virtual interface */ u8 filter:1; /* drop packets to/from this mac */ - u8 refresh:1; /* refresh flag for aging */ - u8 unused1:4; + u8 unused1:5; u8 timestamp; /* timestamp for aging */ u16 unused2; } fields; @@ -71,6 +72,7 @@ typedef struct }; } l2fib_entry_result_t; +STATIC_ASSERT_SIZEOF (l2fib_entry_result_t, 8); /** * Compute the hash for the given key and return @@ -105,7 +107,7 @@ l2fib_make_key (u8 * mac_address, u16 bd_index) * Create the in-register key as F:E:D:C:B:A:H:L * In memory the key is L:H:A:B:C:D:E:F */ - temp = *((u64 *) (mac_address - 2)); + temp = *((u64 *) (mac_address)) << 16; temp = (temp & ~0xffff) | (u64) (bd_index); #else /* @@ -233,6 +235,83 @@ l2fib_lookup_2 (BVT (clib_bihash) * mac_table, } } +static_always_inline void +l2fib_lookup_4 (BVT (clib_bihash) * mac_table, + l2fib_entry_key_t * cached_key, + l2fib_entry_result_t * cached_result, + u8 * mac0, + u8 * mac1, + u8 * mac2, + u8 * mac3, + u16 bd_index0, + u16 bd_index1, + u16 bd_index2, + u16 bd_index3, + l2fib_entry_key_t * key0, + l2fib_entry_key_t * key1, + l2fib_entry_key_t * key2, + l2fib_entry_key_t * key3, + u32 * bucket0, + u32 * bucket1, + u32 * bucket2, + u32 * bucket3, + l2fib_entry_result_t * result0, + l2fib_entry_result_t * result1, + l2fib_entry_result_t * result2, + l2fib_entry_result_t * result3) +{ + /* set up key */ + key0->raw = l2fib_make_key (mac0, bd_index0); + key1->raw = l2fib_make_key (mac1, bd_index1); + key2->raw = l2fib_make_key (mac2, bd_index2); + key3->raw = l2fib_make_key (mac3, bd_index3); + + if ((key0->raw == cached_key->raw) && (key1->raw == cached_key->raw) && + (key2->raw == cached_key->raw) && (key3->raw == cached_key->raw)) + { + /* Both hit in the one-entry cache */ + result0->raw = cached_result->raw; + result1->raw = cached_result->raw; + result2->raw = cached_result->raw; + result3->raw = cached_result->raw; + *bucket0 = ~0; + *bucket1 = ~0; + *bucket2 = ~0; + *bucket3 = ~0; + + } + else + { + BVT (clib_bihash_kv) kv0, kv1, kv2, kv3; + + /* + * Do a regular mac table lookup + * Interleave lookups for packet 0 and packet 1 + */ + kv0.key = key0->raw; + kv1.key = key1->raw; + kv2.key = key2->raw; + kv3.key = key3->raw; + kv0.value = ~0ULL; + kv1.value = ~0ULL; + kv2.value = ~0ULL; + kv3.value = ~0ULL; + + BV (clib_bihash_search_inline) (mac_table, &kv0); + BV (clib_bihash_search_inline) (mac_table, &kv1); + BV (clib_bihash_search_inline) (mac_table, &kv2); + BV (clib_bihash_search_inline) (mac_table, &kv3); + + result0->raw = kv0.value; + result1->raw = kv1.value; + result2->raw = kv2.value; + result3->raw = kv3.value; + + /* Update one-entry cache */ + cached_key->raw = key1->raw; + cached_result->raw = result1->raw; + } +} BVT (clib_bihash) * get_mac_table (void); void