]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - drivers/net/npe/IxNpeMhSolicitedCbMgr.c
doc: SPI: Add qspi test details on AM43xx
[karo-tx-uboot.git] / drivers / net / npe / IxNpeMhSolicitedCbMgr.c
1 /**
2  * @file IxNpeMhSolicitedCbMgr.c
3  *
4  * @author Intel Corporation
5  * @date 18 Jan 2002
6  *
7  * @brief This file contains the implementation of the private API for the
8  * Solicited Callback Manager module.
9  *
10  * 
11  * @par
12  * IXP400 SW Release version 2.0
13  * 
14  * -- Copyright Notice --
15  * 
16  * @par
17  * Copyright 2001-2005, Intel Corporation.
18  * All rights reserved.
19  * 
20  * @par
21  * SPDX-License-Identifier:     BSD-3-Clause
22  * @par
23  * -- End of Copyright Notice --
24 */
25 #ifndef IXNPEMHCONFIG_P_H
26 #       define IXNPEMHSOLICITEDCBMGR_C
27 #else
28 #       error "Error, IxNpeMhConfig_p.h should not be included before this definition."
29 #endif
30
31 /*
32  * Put the system defined include files required.
33  */
34
35
36 /*
37  * Put the user defined include files required.
38  */
39
40 #include "IxOsal.h"
41
42 #include "IxNpeMhMacros_p.h"
43 #include "IxNpeMhSolicitedCbMgr_p.h"
44 #include "IxNpeMhConfig_p.h"
45 /*
46  * #defines and macros used in this file.
47  */
48
49 /*
50  * Typedefs whose scope is limited to this file.
51  */
52
53 /**
54  * @struct IxNpeMhSolicitedCallbackListEntry
55  *
56  * @brief This structure is used to store the information associated with
57  * an entry in the callback list.  This consists of the ID of the send
58  * message (which indicates the ID of the corresponding response message)
59  * and the callback function pointer itself.
60  *
61  */
62
63 typedef struct IxNpeMhSolicitedCallbackListEntry
64 {
65     /** message ID */
66     IxNpeMhMessageId messageId;
67
68     /** callback function pointer */
69     IxNpeMhCallback callback;
70
71     /** pointer to next entry in the list */
72     struct IxNpeMhSolicitedCallbackListEntry *next;
73 } IxNpeMhSolicitedCallbackListEntry;
74
75 /**
76  * @struct IxNpeMhSolicitedCallbackList
77  *
78  * @brief This structure is used to maintain the list of response
79  * callbacks.  The number of entries in this list will be variable, and
80  * they will be stored in a linked list fashion for ease of addition and
81  * removal.  The entries themselves are statically allocated, and are
82  * organised into a "free" list and a "callback" list.  Adding an entry
83  * means taking an entry from the "free" list and adding it to the
84  * "callback" list.  Removing an entry means removing it from the
85  * "callback" list and returning it to the "free" list.
86  */
87
88 typedef struct
89 {
90     /** pointer to the head of the free list */
91     IxNpeMhSolicitedCallbackListEntry *freeHead;
92
93     /** pointer to the head of the callback list */
94     IxNpeMhSolicitedCallbackListEntry *callbackHead;
95
96     /** pointer to the tail of the callback list */
97     IxNpeMhSolicitedCallbackListEntry *callbackTail;
98
99     /** array of entries - the first entry is used as a dummy entry to */
100     /* avoid the scenario of having an empty list, hence '+ 1' */
101     IxNpeMhSolicitedCallbackListEntry entries[IX_NPEMH_MAX_CALLBACKS + 1];
102 } IxNpeMhSolicitedCallbackList;
103
104 /**
105  * @struct IxNpeMhSolicitedCbMgrStats
106  *
107  * @brief This structure is used to maintain statistics for the Solicited
108  * Callback Manager module.
109  */
110
111 typedef struct
112 {
113     UINT32 saves;     /**< callback list saves */
114     UINT32 retrieves; /**< callback list retrieves */
115 } IxNpeMhSolicitedCbMgrStats;
116
117 /*
118  * Variable declarations global to this file only.  Externs are followed by
119  * static variables.
120  */
121
122 PRIVATE IxNpeMhSolicitedCallbackList
123 ixNpeMhSolicitedCbMgrCallbackLists[IX_NPEMH_NUM_NPES];
124
125 PRIVATE IxNpeMhSolicitedCbMgrStats
126 ixNpeMhSolicitedCbMgrStats[IX_NPEMH_NUM_NPES];
127
128 /*
129  * Extern function prototypes.
130  */
131
132 /*
133  * Static function prototypes.
134  */
135
136 /*
137  * Function definition: ixNpeMhSolicitedCbMgrInitialize
138  */
139
140 void ixNpeMhSolicitedCbMgrInitialize (void)
141 {
142     IxNpeMhNpeId npeId;
143     UINT32 localIndex;
144     IxNpeMhSolicitedCallbackList *list = NULL;
145
146     IX_NPEMH_TRACE0 (IX_NPEMH_FN_ENTRY_EXIT, "Entering "
147                      "ixNpeMhSolicitedCbMgrInitialize\n");
148
149     /* for each NPE ... */
150     for (npeId = 0; npeId < IX_NPEMH_NUM_NPES; npeId++)
151     {
152         /* initialise a pointer to the list for convenience */
153         list = &ixNpeMhSolicitedCbMgrCallbackLists[npeId];
154
155         /* for each entry in the list, after the dummy entry ... */
156         for (localIndex = 1; localIndex <= IX_NPEMH_MAX_CALLBACKS; localIndex++)
157         {
158             /* initialise the entry */
159             list->entries[localIndex].messageId = 0x00;
160             list->entries[localIndex].callback = NULL;
161
162             /* if this entry is before the last entry */
163             if (localIndex < IX_NPEMH_MAX_CALLBACKS)
164             {
165                 /* chain this entry to the following entry */
166                 list->entries[localIndex].next = &(list->entries[localIndex + 1]);
167             }
168             else /* this entry is the last entry */
169             {
170                 /* the last entry isn't chained to anything */
171                 list->entries[localIndex].next = NULL;
172             }
173         }
174
175         /* set the free list pointer to point to the first real entry */
176         /* (all real entries begin chained together on the free list) */
177         list->freeHead = &(list->entries[1]);
178
179         /* set the callback list pointers to point to the dummy entry */
180         /* (the callback list is initially empty) */
181         list->callbackHead = &(list->entries[0]);
182         list->callbackTail = &(list->entries[0]);
183     }
184
185     IX_NPEMH_TRACE0 (IX_NPEMH_FN_ENTRY_EXIT, "Exiting "
186                      "ixNpeMhSolicitedCbMgrInitialize\n");
187 }
188
189 /*
190  * Function definition: ixNpeMhSolicitedCbMgrCallbackSave
191  */
192
193 IX_STATUS ixNpeMhSolicitedCbMgrCallbackSave (
194     IxNpeMhNpeId npeId,
195     IxNpeMhMessageId solicitedMessageId,
196     IxNpeMhCallback solicitedCallback)
197 {
198     IxNpeMhSolicitedCallbackList *list = NULL;
199     IxNpeMhSolicitedCallbackListEntry *callbackEntry = NULL;
200
201     IX_NPEMH_TRACE0 (IX_NPEMH_FN_ENTRY_EXIT, "Entering "
202                      "ixNpeMhSolicitedCbMgrCallbackSave\n");
203
204     /* initialise a pointer to the list for convenience */
205     list = &ixNpeMhSolicitedCbMgrCallbackLists[npeId];
206
207     /* check to see if there are any entries in the free list */
208     if (list->freeHead == NULL)
209     {
210         IX_NPEMH_ERROR_REPORT ("Solicited callback list is full\n");
211         return IX_FAIL;
212     }
213
214     /* there is an entry in the free list we can use */
215
216     /* update statistical info */
217     ixNpeMhSolicitedCbMgrStats[npeId].saves++;
218
219     /* remove a callback entry from the start of the free list */
220     callbackEntry = list->freeHead;
221     list->freeHead = callbackEntry->next;
222
223     /* fill in the callback entry with the new data */
224     callbackEntry->messageId = solicitedMessageId;
225     callbackEntry->callback = solicitedCallback;
226
227     /* the new callback entry will be added to the tail of the callback */
228     /* list, so it isn't chained to anything */
229     callbackEntry->next = NULL;
230
231     /* chain new callback entry to the last entry of the callback list */
232     list->callbackTail->next = callbackEntry;
233     list->callbackTail = callbackEntry;
234
235     IX_NPEMH_TRACE0 (IX_NPEMH_FN_ENTRY_EXIT, "Exiting "
236                      "ixNpeMhSolicitedCbMgrCallbackSave\n");
237
238     return IX_SUCCESS;
239 }
240
241 /*
242  * Function definition: ixNpeMhSolicitedCbMgrCallbackRetrieve
243  */
244
245 void ixNpeMhSolicitedCbMgrCallbackRetrieve (
246     IxNpeMhNpeId npeId,
247     IxNpeMhMessageId solicitedMessageId,
248     IxNpeMhCallback *solicitedCallback)
249 {
250     IxNpeMhSolicitedCallbackList *list = NULL;
251     IxNpeMhSolicitedCallbackListEntry *callbackEntry = NULL;
252     IxNpeMhSolicitedCallbackListEntry *previousEntry = NULL;
253
254     /* initialise a pointer to the list for convenience */
255     list = &ixNpeMhSolicitedCbMgrCallbackLists[npeId];
256
257     /* initialise the callback entry to the first entry of the callback */
258     /* list - we must skip over the dummy entry, which is the previous */
259     callbackEntry = list->callbackHead->next;
260     previousEntry = list->callbackHead;
261
262     /* traverse the callback list looking for an entry with a matching */
263     /* message ID.  note we also save the previous entry's pointer to */
264     /* allow us to unchain the matching entry from the callback list */
265     while ((callbackEntry != NULL) &&
266            (callbackEntry->messageId != solicitedMessageId))
267     {
268         previousEntry = callbackEntry;
269         callbackEntry = callbackEntry->next;
270     }
271
272     /* if we didn't find a matching callback entry */
273     if (callbackEntry == NULL)
274     {
275         /* return a NULL callback in the outgoing parameter */
276         *solicitedCallback = NULL;
277     }
278     else /* we found a matching callback entry */
279     {
280         /* update statistical info */
281         ixNpeMhSolicitedCbMgrStats[npeId].retrieves++;
282
283         /* return the callback in the outgoing parameter */
284         *solicitedCallback = callbackEntry->callback;
285
286         /* unchain callback entry by chaining previous entry to next */
287         previousEntry->next = callbackEntry->next;
288
289         /* if the callback entry is at the tail of the list */
290         if (list->callbackTail == callbackEntry)
291         {
292             /* update the tail of the callback list */
293             list->callbackTail = previousEntry;
294         }
295
296         /* re-initialise the callback entry */
297         callbackEntry->messageId = 0x00;
298         callbackEntry->callback = NULL;
299
300         /* add the callback entry to the start of the free list */
301         callbackEntry->next = list->freeHead;
302         list->freeHead = callbackEntry;
303     }
304 }
305
306 /*
307  * Function definition: ixNpeMhSolicitedCbMgrShow
308  */
309
310 void ixNpeMhSolicitedCbMgrShow (
311     IxNpeMhNpeId npeId)
312 {
313     /* show the solicited callback list save counter */
314     IX_NPEMH_SHOW ("Solicited callback list saves",
315                    ixNpeMhSolicitedCbMgrStats[npeId].saves);
316
317     /* show the solicited callback list retrieve counter */
318     IX_NPEMH_SHOW ("Solicited callback list retrieves",
319                    ixNpeMhSolicitedCbMgrStats[npeId].retrieves);
320 }
321
322 /*
323  * Function definition: ixNpeMhSolicitedCbMgrShowReset
324  */
325
326 void ixNpeMhSolicitedCbMgrShowReset (
327     IxNpeMhNpeId npeId)
328 {
329     /* reset the solicited callback list save counter */
330     ixNpeMhSolicitedCbMgrStats[npeId].saves = 0;
331
332     /* reset the solicited callback list retrieve counter */
333     ixNpeMhSolicitedCbMgrStats[npeId].retrieves = 0;
334 }