1 /* SPDX-License-Identifier: BSD-3-Clause
2 * Copyright(c) 2010-2014 Intel Corporation
8 #include <rte_common.h>
10 #include <rte_memory.h>
11 #include <rte_malloc.h>
14 #include "rte_table_array.h"
16 #ifdef RTE_TABLE_STATS_COLLECT
18 #define RTE_TABLE_ARRAY_STATS_PKTS_IN_ADD(table, val) \
19 table->stats.n_pkts_in += val
20 #define RTE_TABLE_ARRAY_STATS_PKTS_LOOKUP_MISS(table, val) \
21 table->stats.n_pkts_lookup_miss += val
25 #define RTE_TABLE_ARRAY_STATS_PKTS_IN_ADD(table, val)
26 #define RTE_TABLE_ARRAY_STATS_PKTS_LOOKUP_MISS(table, val)
30 struct rte_table_array
{
31 struct rte_table_stats stats
;
33 /* Input parameters */
39 uint32_t entry_pos_mask
;
42 uint8_t array
[0] __rte_cache_aligned
;
43 } __rte_cache_aligned
;
46 rte_table_array_create(void *params
, int socket_id
, uint32_t entry_size
)
48 struct rte_table_array_params
*p
= params
;
49 struct rte_table_array
*t
;
50 uint32_t total_cl_size
, total_size
;
52 /* Check input parameters */
54 (p
->n_entries
== 0) ||
55 (!rte_is_power_of_2(p
->n_entries
)))
58 /* Memory allocation */
59 total_cl_size
= (sizeof(struct rte_table_array
) +
60 RTE_CACHE_LINE_SIZE
) / RTE_CACHE_LINE_SIZE
;
61 total_cl_size
+= (p
->n_entries
* entry_size
+
62 RTE_CACHE_LINE_SIZE
) / RTE_CACHE_LINE_SIZE
;
63 total_size
= total_cl_size
* RTE_CACHE_LINE_SIZE
;
64 t
= rte_zmalloc_socket("TABLE", total_size
, RTE_CACHE_LINE_SIZE
, socket_id
);
67 "%s: Cannot allocate %u bytes for array table\n",
68 __func__
, total_size
);
72 /* Memory initialization */
73 t
->entry_size
= entry_size
;
74 t
->n_entries
= p
->n_entries
;
75 t
->offset
= p
->offset
;
76 t
->entry_pos_mask
= t
->n_entries
- 1;
82 rte_table_array_free(void *table
)
84 struct rte_table_array
*t
= table
;
86 /* Check input parameters */
88 RTE_LOG(ERR
, TABLE
, "%s: table parameter is NULL\n", __func__
);
92 /* Free previously allocated resources */
99 rte_table_array_entry_add(
106 struct rte_table_array
*t
= table
;
107 struct rte_table_array_key
*k
= key
;
108 uint8_t *table_entry
;
110 /* Check input parameters */
112 RTE_LOG(ERR
, TABLE
, "%s: table parameter is NULL\n", __func__
);
116 RTE_LOG(ERR
, TABLE
, "%s: key parameter is NULL\n", __func__
);
120 RTE_LOG(ERR
, TABLE
, "%s: entry parameter is NULL\n", __func__
);
123 if (key_found
== NULL
) {
124 RTE_LOG(ERR
, TABLE
, "%s: key_found parameter is NULL\n",
128 if (entry_ptr
== NULL
) {
129 RTE_LOG(ERR
, TABLE
, "%s: entry_ptr parameter is NULL\n",
134 table_entry
= &t
->array
[k
->pos
* t
->entry_size
];
135 memcpy(table_entry
, entry
, t
->entry_size
);
137 *entry_ptr
= (void *) table_entry
;
143 rte_table_array_lookup(
145 struct rte_mbuf
**pkts
,
147 uint64_t *lookup_hit_mask
,
150 struct rte_table_array
*t
= (struct rte_table_array
*) table
;
151 __rte_unused
uint32_t n_pkts_in
= __builtin_popcountll(pkts_mask
);
152 RTE_TABLE_ARRAY_STATS_PKTS_IN_ADD(t
, n_pkts_in
);
153 *lookup_hit_mask
= pkts_mask
;
155 if ((pkts_mask
& (pkts_mask
+ 1)) == 0) {
156 uint64_t n_pkts
= __builtin_popcountll(pkts_mask
);
159 for (i
= 0; i
< n_pkts
; i
++) {
160 struct rte_mbuf
*pkt
= pkts
[i
];
161 uint32_t entry_pos
= RTE_MBUF_METADATA_UINT32(pkt
,
162 t
->offset
) & t
->entry_pos_mask
;
164 entries
[i
] = (void *) &t
->array
[entry_pos
*
168 for ( ; pkts_mask
; ) {
169 uint32_t pkt_index
= __builtin_ctzll(pkts_mask
);
170 uint64_t pkt_mask
= 1LLU << pkt_index
;
171 struct rte_mbuf
*pkt
= pkts
[pkt_index
];
172 uint32_t entry_pos
= RTE_MBUF_METADATA_UINT32(pkt
,
173 t
->offset
) & t
->entry_pos_mask
;
175 entries
[pkt_index
] = (void *) &t
->array
[entry_pos
*
177 pkts_mask
&= ~pkt_mask
;
185 rte_table_array_stats_read(void *table
, struct rte_table_stats
*stats
, int clear
)
187 struct rte_table_array
*array
= table
;
190 memcpy(stats
, &array
->stats
, sizeof(array
->stats
));
193 memset(&array
->stats
, 0, sizeof(array
->stats
));
198 struct rte_table_ops rte_table_array_ops
= {
199 .f_create
= rte_table_array_create
,
200 .f_free
= rte_table_array_free
,
201 .f_add
= rte_table_array_entry_add
,
204 .f_delete_bulk
= NULL
,
205 .f_lookup
= rte_table_array_lookup
,
206 .f_stats
= rte_table_array_stats_read
,