blob: 4a10878b689c349e4c6f2e0656770d9cd0f16a19 [file] [log] [blame]
Wolfgang Denk4646d2a2006-05-30 15:56:48 +02001/**
2 * @file IxEthDBSearch.c
3 *
4 * @par
5 * IXP400 SW Release version 2.0
6 *
7 * -- Copyright Notice --
8 *
9 * @par
10 * Copyright 2001-2005, Intel Corporation.
11 * All rights reserved.
12 *
13 * @par
14 * Redistribution and use in source and binary forms, with or without
15 * modification, are permitted provided that the following conditions
16 * are met:
17 * 1. Redistributions of source code must retain the above copyright
18 * notice, this list of conditions and the following disclaimer.
19 * 2. Redistributions in binary form must reproduce the above copyright
20 * notice, this list of conditions and the following disclaimer in the
21 * documentation and/or other materials provided with the distribution.
22 * 3. Neither the name of the Intel Corporation nor the names of its contributors
23 * may be used to endorse or promote products derived from this software
24 * without specific prior written permission.
25 *
26 * @par
27 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS''
28 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
29 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
30 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE
31 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
32 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
33 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
34 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
35 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
36 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
37 * SUCH DAMAGE.
38 *
39 * @par
40 * -- End of Copyright Notice --
41 */
42
43#include "IxEthDB_p.h"
44
45extern HashTable dbHashtable;
46
47/**
48 * @brief matches two database records based on their MAC addresses
49 *
50 * @param untypedReference record to match against
51 * @param untypedEntry record to match
52 *
53 * @return TRUE if the match is successful or FALSE otherwise
54 *
55 * @internal
56 */
57IX_ETH_DB_PUBLIC
58BOOL ixEthDBAddressRecordMatch(void *untypedReference, void *untypedEntry)
59{
60 MacDescriptor *entry = (MacDescriptor *) untypedEntry;
61 MacDescriptor *reference = (MacDescriptor *) untypedReference;
62
63 /* check accepted record types */
64 if ((entry->type & reference->type) == 0) return FALSE;
65
66 return (ixEthDBAddressCompare((UINT8 *) entry->macAddress, (UINT8 *) reference->macAddress) == 0);
67}
68
69/**
70 * @brief matches two database records based on their MAC addresses
71 * and VLAN IDs
72 *
73 * @param untypedReference record to match against
74 * @param untypedEntry record to match
75 *
76 * @return TRUE if the match is successful or FALSE otherwise
77 *
78 * @internal
79 */
80IX_ETH_DB_PUBLIC
81BOOL ixEthDBVlanRecordMatch(void *untypedReference, void *untypedEntry)
82{
83 MacDescriptor *entry = (MacDescriptor *) untypedEntry;
84 MacDescriptor *reference = (MacDescriptor *) untypedReference;
85
86 /* check accepted record types */
87 if ((entry->type & reference->type) == 0) return FALSE;
88
89 return (IX_ETH_DB_GET_VLAN_ID(entry->recordData.filteringVlanData.ieee802_1qTag) ==
90 IX_ETH_DB_GET_VLAN_ID(reference->recordData.filteringVlanData.ieee802_1qTag)) &&
91 (ixEthDBAddressCompare(entry->macAddress, reference->macAddress) == 0);
92}
93
94/**
95 * @brief matches two database records based on their MAC addresses
96 * and port IDs
97 *
98 * @param untypedReference record to match against
99 * @param untypedEntry record to match
100 *
101 * @return TRUE if the match is successful or FALSE otherwise
102 *
103 * @internal
104 */
105IX_ETH_DB_PUBLIC
106BOOL ixEthDBPortRecordMatch(void *untypedReference, void *untypedEntry)
107{
108 MacDescriptor *entry = (MacDescriptor *) untypedEntry;
109 MacDescriptor *reference = (MacDescriptor *) untypedReference;
110
111 /* check accepted record types */
112 if ((entry->type & reference->type) == 0) return FALSE;
113
114 return (entry->portID == reference->portID) &&
115 (ixEthDBAddressCompare(entry->macAddress, reference->macAddress) == 0);
116}
117
118/**
119 * @brief dummy matching function, registered for safety
120 *
121 * @param reference record to match against (unused)
122 * @param entry record to match (unused)
123 *
124 * This function is registered in the matching functions
125 * array on invalid types. Calling it will display an
126 * error message, indicating an error in the component logic.
127 *
128 * @return FALSE
129 *
130 * @internal
131 */
132IX_ETH_DB_PUBLIC
133BOOL ixEthDBNullMatch(void *reference, void *entry)
134{
135 /* display an error message */
136
137 ixOsalLog(IX_OSAL_LOG_LVL_WARNING, IX_OSAL_LOG_DEV_STDOUT, "DB: (Search) The NullMatch function was called, wrong key type?\n", 0, 0, 0, 0, 0, 0);
138
139
140 return FALSE;
141}
142
143/**
144 * @brief registers hash matching methods
145 *
146 * @param matchFunctions table of match functions to be populated
147 *
148 * This function registers the available record matching functions
149 * by indexing them on record types into the given function array.
150 *
151 * Note that it is compulsory to call this in ixEthDBInit(),
152 * otherwise hashtable searching and removal will not work
153 *
154 * @return number of registered functions
155 *
156 * @internal
157 */
158IX_ETH_DB_PUBLIC
159UINT32 ixEthDBMatchMethodsRegister(MatchFunction *matchFunctions)
160{
161 UINT32 i;
162
163 /* safety first */
164 for ( i = 0 ; i < IX_ETH_DB_MAX_KEY_INDEX + 1 ; i++)
165 {
166 matchFunctions[i] = ixEthDBNullMatch;
167 }
168
169 /* register MAC search method */
170 matchFunctions[IX_ETH_DB_MAC_KEY] = ixEthDBAddressRecordMatch;
171
172 /* register MAC/PortID search method */
173 matchFunctions[IX_ETH_DB_MAC_PORT_KEY] = ixEthDBPortRecordMatch;
174
175 /* register MAC/VLAN ID search method */
176 matchFunctions[IX_ETH_DB_MAC_VLAN_KEY] = ixEthDBVlanRecordMatch;
177
178 return 3; /* three methods */
179}
180
181/**
182 * @brief search a record in the Ethernet datbase
183 *
184 * @param macAddress MAC address to perform the search on
185 * @param typeFilter type of records to consider for matching
186 *
187 * @warning if searching is successful an implicit write lock
188 * to the search result is granted, therefore unlock the
189 * entry using @ref ixEthDBReleaseHashNode() as soon as possible.
190 *
191 * @see ixEthDBReleaseHashNode()
192 *
193 * @return the search result, or NULL if a record with the given
194 * MAC address was not found
195 *
196 * @internal
197 */
198IX_ETH_DB_PUBLIC
199HashNode* ixEthDBSearch(IxEthDBMacAddr *macAddress, IxEthDBRecordType typeFilter)
200{
201 HashNode *searchResult = NULL;
202 MacDescriptor reference;
203
204 TEST_FIXTURE_INCREMENT_DB_CORE_ACCESS_COUNTER;
205
206 if (macAddress == NULL)
207 {
208 return NULL;
209 }
210
211 /* fill search fields */
212 memcpy(reference.macAddress, macAddress, sizeof (IxEthDBMacAddr));
213
214 /* set acceptable record types */
215 reference.type = typeFilter;
216
217 BUSY_RETRY(ixEthDBSearchHashEntry(&dbHashtable, IX_ETH_DB_MAC_KEY, &reference, &searchResult));
218
219 return searchResult;
220}
221
222IX_ETH_DB_PUBLIC
223IxEthDBStatus ixEthDBPeek(IxEthDBMacAddr *macAddress, IxEthDBRecordType typeFilter)
224{
225 MacDescriptor reference;
226 IxEthDBStatus result;
227
228 TEST_FIXTURE_INCREMENT_DB_CORE_ACCESS_COUNTER;
229
230 if (macAddress == NULL)
231 {
232 return IX_ETH_DB_INVALID_ARG;
233 }
234
235 /* fill search fields */
236 memcpy(reference.macAddress, macAddress, sizeof (IxEthDBMacAddr));
237
238 /* set acceptable record types */
239 reference.type = typeFilter;
240
241 result = ixEthDBPeekHashEntry(&dbHashtable, IX_ETH_DB_MAC_KEY, &reference);
242
243 return result;
244}
245
246/**
247 * @brief search a record in the Ethernet datbase
248 *
249 * @param macAddress MAC address to perform the search on
250 * @param portID port ID to perform the search on
251 * @param typeFilter type of records to consider for matching
252 *
253 * @warning if searching is successful an implicit write lock
254 * to the search result is granted, therefore unlock the
255 * entry using @ref ixEthDBReleaseHashNode() as soon as possible.
256 *
257 * @see ixEthDBReleaseHashNode()
258 *
259 * @return the search result, or NULL if a record with the given
260 * MAC address/port ID combination was not found
261 *
262 * @internal
263 */
264IX_ETH_DB_PUBLIC
265HashNode* ixEthDBPortSearch(IxEthDBMacAddr *macAddress, IxEthDBPortId portID, IxEthDBRecordType typeFilter)
266{
267 HashNode *searchResult = NULL;
268 MacDescriptor reference;
269
270 if (macAddress == NULL)
271 {
272 return NULL;
273 }
274
275 /* fill search fields */
276 memcpy(reference.macAddress, macAddress, sizeof (IxEthDBMacAddr));
277 reference.portID = portID;
278
279 /* set acceptable record types */
280 reference.type = typeFilter;
281
282 BUSY_RETRY(ixEthDBSearchHashEntry(&dbHashtable, IX_ETH_DB_MAC_PORT_KEY, &reference, &searchResult));
283
284 return searchResult;
285}
286
287/**
288 * @brief search a record in the Ethernet datbase
289 *
290 * @param macAddress MAC address to perform the search on
291 * @param vlanID VLAN ID to perform the search on
292 * @param typeFilter type of records to consider for matching
293 *
294 * @warning if searching is successful an implicit write lock
295 * to the search result is granted, therefore unlock the
296 * entry using @ref ixEthDBReleaseHashNode() as soon as possible.
297 *
298 * @see ixEthDBReleaseHashNode()
299 *
300 * @return the search result, or NULL if a record with the given
301 * MAC address/VLAN ID combination was not found
302 *
303 * @internal
304 */
305IX_ETH_DB_PUBLIC
306HashNode* ixEthDBVlanSearch(IxEthDBMacAddr *macAddress, IxEthDBVlanId vlanID, IxEthDBRecordType typeFilter)
307{
308 HashNode *searchResult = NULL;
309 MacDescriptor reference;
310
311 if (macAddress == NULL)
312 {
313 return NULL;
314 }
315
316 /* fill search fields */
317 memcpy(reference.macAddress, macAddress, sizeof (IxEthDBMacAddr));
318 reference.recordData.filteringVlanData.ieee802_1qTag =
319 IX_ETH_DB_SET_VLAN_ID(reference.recordData.filteringVlanData.ieee802_1qTag, vlanID);
320
321 /* set acceptable record types */
322 reference.type = typeFilter;
323
324 BUSY_RETRY(ixEthDBSearchHashEntry(&dbHashtable, IX_ETH_DB_MAC_VLAN_KEY, &reference, &searchResult));
325
326 return searchResult;
327}