xref: /dpdk/lib/hash/compare_signatures_x86.h (revision ef801b590990c440f52cc8d3707ae269f8386027)
10668f68bSYoan Picchi /* SPDX-License-Identifier: BSD-3-Clause
20668f68bSYoan Picchi  * Copyright(c) 2010-2016 Intel Corporation
30668f68bSYoan Picchi  * Copyright(c) 2018-2024 Arm Limited
40668f68bSYoan Picchi  */
50668f68bSYoan Picchi 
60668f68bSYoan Picchi #ifndef COMPARE_SIGNATURES_X86_H
70668f68bSYoan Picchi #define COMPARE_SIGNATURES_X86_H
80668f68bSYoan Picchi 
90668f68bSYoan Picchi #include <inttypes.h>
100668f68bSYoan Picchi 
110668f68bSYoan Picchi #include <rte_common.h>
120668f68bSYoan Picchi #include <rte_vect.h>
130668f68bSYoan Picchi 
140668f68bSYoan Picchi #include "rte_cuckoo_hash.h"
150668f68bSYoan Picchi 
16*ef801b59SYoan Picchi /* x86's version uses a sparsely packed hitmask buffer: every other bit is padding. */
17*ef801b59SYoan Picchi #define DENSE_HASH_BULK_LOOKUP 0
18*ef801b59SYoan Picchi 
190668f68bSYoan Picchi static inline void
compare_signatures_sparse(uint32_t * prim_hash_matches,uint32_t * sec_hash_matches,const struct rte_hash_bucket * prim_bkt,const struct rte_hash_bucket * sec_bkt,uint16_t sig,enum rte_hash_sig_compare_function sig_cmp_fn)20*ef801b59SYoan Picchi compare_signatures_sparse(uint32_t *prim_hash_matches, uint32_t *sec_hash_matches,
210668f68bSYoan Picchi 			const struct rte_hash_bucket *prim_bkt,
220668f68bSYoan Picchi 			const struct rte_hash_bucket *sec_bkt,
230668f68bSYoan Picchi 			uint16_t sig,
240668f68bSYoan Picchi 			enum rte_hash_sig_compare_function sig_cmp_fn)
250668f68bSYoan Picchi {
260668f68bSYoan Picchi 	unsigned int i;
270668f68bSYoan Picchi 
280668f68bSYoan Picchi 	/* For match mask the first bit of every two bits indicates the match */
290668f68bSYoan Picchi 	switch (sig_cmp_fn) {
300668f68bSYoan Picchi #if defined(__SSE2__) && RTE_HASH_BUCKET_ENTRIES <= 8
310668f68bSYoan Picchi 	case RTE_HASH_COMPARE_SSE:
320668f68bSYoan Picchi 		/* Compare all signatures in the bucket */
330668f68bSYoan Picchi 		*prim_hash_matches = _mm_movemask_epi8(_mm_cmpeq_epi16(_mm_load_si128(
340668f68bSYoan Picchi 			(__m128i const *)prim_bkt->sig_current), _mm_set1_epi16(sig)));
350668f68bSYoan Picchi 		/* Extract the even-index bits only */
360668f68bSYoan Picchi 		*prim_hash_matches &= 0x5555;
370668f68bSYoan Picchi 		/* Compare all signatures in the bucket */
380668f68bSYoan Picchi 		*sec_hash_matches = _mm_movemask_epi8(_mm_cmpeq_epi16(_mm_load_si128(
390668f68bSYoan Picchi 			(__m128i const *)sec_bkt->sig_current), _mm_set1_epi16(sig)));
400668f68bSYoan Picchi 		/* Extract the even-index bits only */
410668f68bSYoan Picchi 		*sec_hash_matches &= 0x5555;
420668f68bSYoan Picchi 		break;
430668f68bSYoan Picchi #endif
440668f68bSYoan Picchi 	default:
450668f68bSYoan Picchi 		for (i = 0; i < RTE_HASH_BUCKET_ENTRIES; i++) {
460668f68bSYoan Picchi 			*prim_hash_matches |= (sig == prim_bkt->sig_current[i]) << (i << 1);
470668f68bSYoan Picchi 			*sec_hash_matches |= (sig == sec_bkt->sig_current[i]) << (i << 1);
480668f68bSYoan Picchi 		}
490668f68bSYoan Picchi 	}
500668f68bSYoan Picchi }
510668f68bSYoan Picchi #endif /* COMPARE_SIGNATURES_X86_H */
52