Minor updates
[keystone-rtos/rm-lld.git] / src / rm_transport.c
1 /**\r
2  *   @file  rm_transport.c\r
3  *\r
4  *   @brief   \r
5  *      This is the Resource Manager transport source.\r
6  *\r
7  *  \par\r
8  *  ============================================================================\r
9  *  @n   (C) Copyright 2012-2013, Texas Instruments, Inc.\r
10  * \r
11  *  Redistribution and use in source and binary forms, with or without \r
12  *  modification, are permitted provided that the following conditions \r
13  *  are met:\r
14  *\r
15  *    Redistributions of source code must retain the above copyright \r
16  *    notice, this list of conditions and the following disclaimer.\r
17  *\r
18  *    Redistributions in binary form must reproduce the above copyright\r
19  *    notice, this list of conditions and the following disclaimer in the \r
20  *    documentation and/or other materials provided with the   \r
21  *    distribution.\r
22  *\r
23  *    Neither the name of Texas Instruments Incorporated nor the names of\r
24  *    its contributors may be used to endorse or promote products derived\r
25  *    from this software without specific prior written permission.\r
26  *\r
27  *  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS \r
28  *  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT \r
29  *  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR\r
30  *  A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT \r
31  *  OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, \r
32  *  SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT \r
33  *  LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,\r
34  *  DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY\r
35  *  THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT \r
36  *  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE \r
37  *  OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\r
38  *\r
39  *  \par\r
40 */\r
41 \r
42 /* Standard includes */\r
43 #include <string.h>\r
44 #include <stdbool.h>\r
45 \r
46 /* RM external includes */\r
47 #include <ti/drv/rm/rm.h>\r
48 #include <ti/drv/rm/rm_transport.h>\r
49 \r
50 /* RM internal includes */\r
51 #include <ti/drv/rm/include/rm_loc.h>\r
52 #include <ti/drv/rm/include/rm_transportloc.h>\r
53 \r
54 /* RM OSAL layer */\r
55 #include <rm_osal.h>\r
56 \r
57 /**********************************************************************\r
58  ************************ Local Functions *****************************\r
59  **********************************************************************/\r
60 \r
61 /* FUNCTION PURPOSE: Adds a transport\r
62  ***********************************************************************\r
63  * DESCRIPTION: Returns a pointer to a transport structure that\r
64  *              was created, initialized, and added to the \r
65  *              instance transport list.\r
66  */\r
67 static Rm_Transport *transportAdd(const Rm_TransportCfg *transportCfg)\r
68 {\r
69     Rm_Inst      *rmInst = (Rm_Inst *) transportCfg->rmHandle;\r
70     Rm_Transport *transports = rmInst->transports;\r
71     Rm_Transport *newTransport = NULL;\r
72 \r
73     newTransport = Rm_osalMalloc (sizeof(Rm_Transport));\r
74     memset((void *)newTransport, 0, sizeof(Rm_Transport));\r
75 \r
76     if (newTransport) {\r
77         newTransport->rmHandle = transportCfg->rmHandle;\r
78         newTransport->appTransportHandle = transportCfg->appTransportHandle;\r
79         newTransport->remoteInstType = transportCfg->remoteInstType;\r
80         strncpy(newTransport->remoteInstName, transportCfg->remoteInstName, RM_NAME_MAX_CHARS);\r
81         newTransport->nextTransport = NULL;\r
82 \r
83         if (transports) {\r
84             while (transports->nextTransport) {\r
85                 transports = transports->nextTransport;\r
86             }\r
87             transports->nextTransport = newTransport;\r
88         }\r
89         else {\r
90             rmInst->transports = (void *)newTransport;\r
91         }\r
92     }\r
93     return (newTransport);\r
94 }\r
95 \r
96 /* FUNCTION PURPOSE: Tests if a transport is registered to an instance\r
97  ***********************************************************************\r
98  * DESCRIPTION: Returns TRUE if the supplied transport is found in\r
99  *              the instance transport list.  Otherwise, returns FALSE\r
100  */\r
101 static bool transportIsRegistered(Rm_Handle rmHandle, Rm_Transport *transport)\r
102 {\r
103     Rm_Inst      *rmInst = (Rm_Inst *)rmHandle;\r
104     Rm_Transport *transportList = (Rm_Transport *)rmInst->transports;\r
105     \r
106     while (transportList) {\r
107         if (transportList == transport) {\r
108             return(true);             \r
109         }\r
110         transportList = transportList->nextTransport;\r
111     }\r
112     return (false);\r
113 }\r
114 \r
115 /* FUNCTION PURPOSE: Deletes a transport\r
116  ***********************************************************************\r
117  * DESCRIPTION: Removes a transport from an instance transport list\r
118  *              and then frees the memory associated with the transport\r
119  *              data structure\r
120  */\r
121 static void transportDelete(Rm_Transport *transport)\r
122 {\r
123     Rm_Inst      *rmInst = (Rm_Inst *)transport->rmHandle;\r
124     Rm_Transport *transportList = (Rm_Transport *)rmInst->transports;\r
125     Rm_Transport *prevTransport = NULL;\r
126 \r
127     /* Get previous transport in list */\r
128     while (transportList) {\r
129         if (transportList == transport) {\r
130             break;             \r
131         }\r
132         prevTransport = transportList;\r
133         transportList = transportList->nextTransport;\r
134     }\r
135 \r
136     if (prevTransport == NULL) {\r
137          rmInst->transports = (void *)transport->nextTransport;\r
138     }\r
139     else {\r
140          prevTransport->nextTransport = transport->nextTransport;\r
141     }\r
142     Rm_osalFree((void *)transport, sizeof(Rm_Transport));\r
143 }\r
144 \r
145 /**********************************************************************\r
146  ********************** Internal Functions ****************************\r
147  **********************************************************************/\r
148 \r
149 /* FUNCTION PURPOSE: Finds a transport based on remote inst name\r
150  ***********************************************************************\r
151  * DESCRIPTION: Returns a pointer to the transport within an instance's\r
152  *              transport list that matches the provided remote\r
153  *              instance name.  NULL is returned if no transports in \r
154  *              the list match the remote instance name.\r
155  */\r
156 Rm_Transport *rmTransportFindRemoteName(Rm_Transport *transports, char *remoteName)\r
157 {\r
158     while (transports) {\r
159         if (strncmp(transports->remoteInstName, remoteName, RM_NAME_MAX_CHARS) == 0) {\r
160             break;             \r
161         }\r
162         transports = transports->nextTransport;\r
163     }\r
164     return (transports);\r
165 }\r
166 \r
167 /* FUNCTION PURPOSE: Finds a transport based on remote inst type\r
168  ***********************************************************************\r
169  * DESCRIPTION: Returns a pointer to the transport within an instance's\r
170  *              transport list that matches the provided remote\r
171  *              instance type.  NULL is returned if no transports in \r
172  *              the list match the remote instance type.\r
173  */\r
174 Rm_Transport *rmTransportFindRemoteInstType(Rm_Transport *transports, Rm_InstType remoteInstType)\r
175 {\r
176     while (transports) {\r
177         if (transports->remoteInstType == remoteInstType) {\r
178             break;             \r
179         }\r
180         transports = transports->nextTransport;\r
181     }\r
182     return (transports);\r
183 }\r
184 \r
185 /* FUNCTION PURPOSE: Creates a resource request packet\r
186  ***********************************************************************\r
187  * DESCRIPTION: Returns a RM packet handle that points to a RM\r
188  *              resource request packet that has been prepared\r
189  *              for sending to another RM instance.  The packet\r
190  *              is allocated via the rmAllocPkt API using the\r
191  *              appTransport handle provided by the application\r
192  */\r
193 Rm_PacketHandle rmTransportCreateResourceReqPkt(Rm_Inst *rmInst, Rm_AppTransportHandle appTransport,\r
194                                                 Rm_Transaction *transaction)\r
195 {\r
196     Rm_Packet             *rmPkt = NULL;\r
197     Rm_PacketHandle        pktHandle = NULL;\r
198     Rm_ResourceRequestPkt *resourceReqPkt = NULL;\r
199 \r
200     if (rmInst->transportCallouts.rmAllocPkt) {\r
201         if ((rmPkt = rmInst->transportCallouts.rmAllocPkt(appTransport, \r
202                                                           sizeof(Rm_Packet),\r
203                                                           &pktHandle)) == NULL) {\r
204             transaction->state = RM_ERROR_TRANSPORT_ALLOC_PKT_ERROR;\r
205             return (NULL);\r
206         }\r
207        \r
208         rmPkt->pktType = Rm_pktType_RESOURCE_REQUEST;\r
209         resourceReqPkt = (Rm_ResourceRequestPkt *) rmPkt->data;\r
210         resourceReqPkt->requestId = transaction->localId;\r
211         if (transaction->type == Rm_service_RESOURCE_ALLOCATE_INIT) {\r
212             resourceReqPkt->resourceReqType = Rm_resReqPktType_ALLOCATE_INIT;\r
213         }\r
214         else if (transaction->type == Rm_service_RESOURCE_ALLOCATE_USE) {\r
215             resourceReqPkt->resourceReqType = Rm_resReqPktType_ALLOCATE_USE;\r
216         }    \r
217         else if (transaction->type == Rm_service_RESOURCE_FREE) {\r
218             resourceReqPkt->resourceReqType = Rm_resReqPktType_FREE;\r
219         }\r
220         else if (transaction->type == Rm_service_RESOURCE_GET_BY_NAME) {\r
221             resourceReqPkt->resourceReqType = Rm_resReqPktType_GET_NAMED;\r
222         }\r
223         strncpy(resourceReqPkt->pktSrcInstName, rmInst->instName, RM_NAME_MAX_CHARS);\r
224         strncpy(resourceReqPkt->serviceSrcInstName, transaction->serviceSrcInstName, RM_NAME_MAX_CHARS);\r
225         memcpy ((void *)&(resourceReqPkt->resourceInfo), (void *)&(transaction->resourceInfo),\r
226                 sizeof(Rm_ResourceInfo));\r
227     }\r
228     else {\r
229         transaction->state = RM_ERROR_TRANSPORT_ALLOC_PKT_NOT_REGD;\r
230     }        \r
231     \r
232     return (pktHandle);\r
233 }\r
234 \r
235 /* FUNCTION PURPOSE: Creates a resource response packet\r
236  ***********************************************************************\r
237  * DESCRIPTION: Returns a RM packet handle that points to a RM\r
238  *              resource response packet that has been prepared\r
239  *              for sending to another RM instance.  The packet\r
240  *              is allocated via the rmAllocPkt API using the\r
241  *              appTransport handle provided by the application\r
242  */\r
243 Rm_PacketHandle rmTransportCreateResourceResponsePkt(Rm_Inst *rmInst, Rm_AppTransportHandle appTransport,\r
244                                                      Rm_Transaction *transaction)\r
245 {\r
246     Rm_Packet              *rmPkt = NULL;\r
247     Rm_PacketHandle         pktHandle = NULL;\r
248     Rm_ResourceResponsePkt *resourceRespPkt = NULL;\r
249 \r
250     if (rmInst->transportCallouts.rmAllocPkt) {\r
251         if ((rmPkt = rmInst->transportCallouts.rmAllocPkt(appTransport, \r
252                                                           sizeof(Rm_Packet),\r
253                                                           &pktHandle)) == NULL) {\r
254             transaction->state = RM_ERROR_TRANSPORT_ALLOC_PKT_ERROR;\r
255             return (NULL);\r
256         }\r
257      \r
258         rmPkt->pktType = Rm_pktType_RESOURCE_RESPONSE;                 \r
259         resourceRespPkt = (Rm_ResourceResponsePkt *)rmPkt->data;\r
260         resourceRespPkt->responseId = transaction->remoteOriginatingId;\r
261         resourceRespPkt->requestState = transaction->state;\r
262         memcpy ((void *)&(resourceRespPkt->resourceInfo), (void *)&(transaction->resourceInfo),\r
263                 sizeof(Rm_ResourceInfo));\r
264     }\r
265     else {\r
266         transaction->state = RM_ERROR_TRANSPORT_ALLOC_PKT_NOT_REGD;\r
267     }        \r
268 \r
269     return (pktHandle);\r
270 }\r
271 \r
272 /* FUNCTION PURPOSE: Creates a NameServer request packet\r
273  ***********************************************************************\r
274  * DESCRIPTION: Returns a RM packet handle that points to a RM\r
275  *              NameServer request packet that has been prepared\r
276  *              for sending to another RM instance.  The packet\r
277  *              is allocated via the rmAllocPkt API using the\r
278  *              appTransport handle provided by the application\r
279  */\r
280 Rm_PacketHandle rmTransportCreateNsRequestPkt(Rm_Inst *rmInst, Rm_AppTransportHandle appTransport,\r
281                                               Rm_Transaction *transaction)\r
282 {\r
283     Rm_Packet       *rmPkt = NULL;\r
284     Rm_PacketHandle  pktHandle = NULL;    \r
285     Rm_NsRequestPkt *nsReqPkt = NULL;\r
286 \r
287     if (rmInst->transportCallouts.rmAllocPkt) {\r
288         if ((rmPkt = rmInst->transportCallouts.rmAllocPkt(appTransport, \r
289                                                           sizeof(Rm_Packet),\r
290                                                           &pktHandle)) == NULL) {\r
291             transaction->state = RM_ERROR_TRANSPORT_ALLOC_PKT_ERROR;\r
292             return (NULL);\r
293         }\r
294 \r
295         rmPkt->pktType = Rm_pktType_NAMESERVER_REQUEST;                   \r
296         nsReqPkt = (Rm_NsRequestPkt *)rmPkt->data;\r
297         nsReqPkt->requestId = transaction->localId;\r
298         if (transaction->type == Rm_service_RESOURCE_MAP_TO_NAME) {\r
299             nsReqPkt->nsRequestType = Rm_nsReqPktType_MAP_RESOURCE;\r
300         }\r
301         else if (transaction->type == Rm_service_RESOURCE_UNMAP_NAME) {\r
302             nsReqPkt->nsRequestType = Rm_nsReqPktType_UNMAP_RESOURCE;\r
303         }\r
304         strncpy(nsReqPkt->pktSrcInstName, rmInst->instName, RM_NAME_MAX_CHARS);\r
305         strncpy(nsReqPkt->serviceSrcInstName, transaction->serviceSrcInstName, RM_NAME_MAX_CHARS);\r
306         memcpy ((void *)&(nsReqPkt->resourceInfo), (void *)&(transaction->resourceInfo),\r
307                 sizeof(Rm_ResourceInfo));\r
308     }\r
309     else {\r
310         transaction->state = RM_ERROR_TRANSPORT_ALLOC_PKT_NOT_REGD;\r
311     }        \r
312     \r
313     return (pktHandle);\r
314 }\r
315 \r
316 /* FUNCTION PURPOSE: Creates a NameServer response packet\r
317  ***********************************************************************\r
318  * DESCRIPTION: Returns a RM packet handle that points to a RM\r
319  *              NameServer response packet that has been prepared\r
320  *              for sending to another RM instance.  The packet\r
321  *              is allocated via the rmAllocPkt API using the\r
322  *              appTransport handle provided by the application\r
323  */\r
324 Rm_PacketHandle rmTransportCreateNsResponsePkt(Rm_Inst *rmInst, Rm_AppTransportHandle appTransport,\r
325                                                Rm_Transaction *transaction)\r
326 {\r
327     Rm_Packet        *rmPkt = NULL;\r
328     Rm_PacketHandle   pktHandle = NULL;\r
329     Rm_NsResponsePkt *nsRespPkt = NULL;\r
330 \r
331     if (rmInst->transportCallouts.rmAllocPkt) {\r
332         if ((rmPkt = rmInst->transportCallouts.rmAllocPkt(appTransport, \r
333                                                           sizeof(Rm_Packet),\r
334                                                           &pktHandle)) == NULL) {\r
335             transaction->state = RM_ERROR_TRANSPORT_ALLOC_PKT_ERROR;\r
336             return (NULL);\r
337         }\r
338      \r
339         rmPkt->pktType = Rm_pktType_NAMESERVER_RESPONSE;                \r
340         nsRespPkt = (Rm_NsResponsePkt *)rmPkt->data;\r
341         nsRespPkt->responseId = transaction->remoteOriginatingId;\r
342         nsRespPkt->requestState = transaction->state;\r
343     }\r
344     else {\r
345         transaction->state = RM_ERROR_TRANSPORT_ALLOC_PKT_NOT_REGD;\r
346     }\r
347 \r
348     return (pktHandle);\r
349 }\r
350 \r
351 /**********************************************************************\r
352  ********************* Application visible APIs ***********************\r
353  **********************************************************************/\r
354 \r
355 /* FUNCTION PURPOSE: Registers an app transport with a RM instance\r
356  ***********************************************************************\r
357  * DESCRIPTION: Returns a transport handle to the application that\r
358  *              has been registered with an RM instance.  The handle\r
359  *              is used by the application to route packets to the\r
360  *              proper RM instance's based on the application\r
361  *              transport receive code.  The handle is also used\r
362  *              internally by RM to route request and response \r
363  *              packets to the correct application transports. NULL\r
364  *              is returned for the transport handle if any errors\r
365  *              are encountered.\r
366  */\r
367 Rm_TransportHandle Rm_transportRegister (const Rm_TransportCfg *transportCfg, int32_t *result)\r
368 {\r
369     Rm_Inst      *rmInst = (Rm_Inst *) transportCfg->rmHandle;\r
370     Rm_Transport *transport = NULL;\r
371 \r
372     /* RM Servers cannot connect to other Servers.  \r
373      * RM Client Delegates cannot connect to other Client Delegates.\r
374      * RM Clients cannot connect to other Clients */\r
375     if (((rmInst->instType == Rm_instType_SERVER) &&\r
376          (transportCfg->remoteInstType == Rm_instType_SERVER)) ||\r
377         ((rmInst->instType == Rm_instType_CLIENT_DELEGATE) &&\r
378          (transportCfg->remoteInstType == Rm_instType_CLIENT_DELEGATE)) ||\r
379         ((rmInst->instType == Rm_instType_CLIENT) &&\r
380          (transportCfg->remoteInstType == Rm_instType_CLIENT))) {\r
381         *result = RM_ERROR_INVALID_REMOTE_INST_TYPE;\r
382         return(NULL);\r
383     }\r
384 \r
385     /* Verify Clients are not registering with more than one Client Delegate or Server. And\r
386      * that Client Delegate is not registering with more than one Server. */\r
387     if (rmInst->registeredWithDelegateOrServer &&\r
388         (((rmInst->instType == Rm_instType_CLIENT) &&\r
389           (transportCfg->remoteInstType == Rm_instType_CLIENT_DELEGATE)) || \r
390          ((rmInst->instType == Rm_instType_CLIENT_DELEGATE) &&\r
391           (transportCfg->remoteInstType == Rm_instType_SERVER)))) {\r
392         *result = RM_ERROR_ALREADY_REGD_SERVER_OR_CD;\r
393         return(NULL);\r
394     }         \r
395     \r
396     if (transportCfg->transportCalloutsValid &&\r
397         ((transportCfg->transportCallouts.rmAllocPkt == NULL) ||\r
398          (transportCfg->transportCallouts.rmSendPkt == NULL))) {\r
399         *result = RM_ERROR_NULL_CALLOUTS_WHEN_VALID;\r
400         return(NULL);\r
401     }\r
402     else {\r
403         rmInst->transportCallouts.rmAllocPkt = transportCfg->transportCallouts.rmAllocPkt;\r
404         rmInst->transportCallouts.rmSendPkt = transportCfg->transportCallouts.rmSendPkt;\r
405     }\r
406 \r
407     transport = transportAdd(transportCfg);\r
408 \r
409     if ((transport->remoteInstType == Rm_instType_CLIENT_DELEGATE) ||\r
410         (transport->remoteInstType == Rm_instType_SERVER)) {\r
411         rmInst->registeredWithDelegateOrServer = true;\r
412     }\r
413 \r
414     *result = RM_OK;\r
415     return ((Rm_TransportHandle) transport);\r
416 }\r
417 \r
418 /* FUNCTION PURPOSE: Unregisters an app transport from a RM instance\r
419  ***********************************************************************\r
420  * DESCRIPTION: Deletes a registered transport from the transport\r
421  *              list and cleans up the memory associated with the\r
422  *              transport data structure.\r
423  */\r
424 int32_t Rm_transportUnregister(Rm_TransportHandle transportHandle)\r
425 {\r
426     Rm_Transport *transport = (Rm_Transport *)transportHandle;\r
427     Rm_Inst      *rmInst = (Rm_Inst *)transport->rmHandle;\r
428     int32_t       retVal = RM_OK;  \r
429 \r
430     if (transportIsRegistered(transport->rmHandle, transport)) {\r
431         if ((transport->remoteInstType == Rm_instType_CLIENT_DELEGATE) ||\r
432             (transport->remoteInstType == Rm_instType_SERVER)) {\r
433             rmInst->registeredWithDelegateOrServer = false;\r
434         }\r
435         transportDelete(transport);\r
436     }\r
437     else {\r
438         retVal = RM_ERROR_TRANSPORT_HANDLE_DOES_NOT_EXIST;\r
439     }\r
440     return (retVal);\r
441 }\r
442 \r
443 /* FUNCTION PURPOSE: Receives RM packets\r
444  ***********************************************************************\r
445  * DESCRIPTION: The application provides RM packets received on the\r
446  *              application transports to RM via this API.  Function\r
447  *              can be called from polling or ISR contexts. */\r
448 int32_t Rm_receivePacket(Rm_TransportHandle transportHandle, const Rm_Packet *pkt)\r
449 {\r\r\r
450     Rm_Transport   *transport = (Rm_Transport *)transportHandle;\r
451     Rm_Inst        *rmInst = (Rm_Inst *)transport->rmHandle;\r
452     Rm_Transaction *transaction;\r
453 \r
454     if (!transportIsRegistered(transport->rmHandle, transport)) {\r
455         return (RM_ERROR_TRANSPORT_HANDLE_DOES_NOT_EXIST);\r
456     }\r
457 \r
458     switch (pkt->pktType) {\r
459         case Rm_pktType_RESOURCE_REQUEST:\r
460         {\r
461             Rm_ResourceRequestPkt *resourceReqPkt = (Rm_ResourceRequestPkt *)pkt->data;\r
462 \r
463             transaction = rmTransactionQueueAdd(rmInst);\r
464             transaction->remoteOriginatingId = resourceReqPkt->requestId;\r
465             if (resourceReqPkt->resourceReqType == Rm_resReqPktType_ALLOCATE_INIT) {\r
466                 transaction->type = Rm_service_RESOURCE_ALLOCATE_INIT;\r
467             }\r
468             else if (resourceReqPkt->resourceReqType == Rm_resReqPktType_ALLOCATE_USE) {\r
469                 transaction->type = Rm_service_RESOURCE_ALLOCATE_USE;\r
470             }            \r
471             else if (resourceReqPkt->resourceReqType == Rm_resReqPktType_FREE) {\r
472                 transaction->type = Rm_service_RESOURCE_FREE;\r
473             }\r
474             else if (resourceReqPkt->resourceReqType == Rm_resReqPktType_GET_NAMED) {\r
475                 transaction->type = Rm_service_RESOURCE_GET_BY_NAME;\r
476             }            \r
477             strncpy(transaction->pktSrcInstName, resourceReqPkt->pktSrcInstName, RM_NAME_MAX_CHARS);\r
478             strncpy(transaction->serviceSrcInstName, resourceReqPkt->serviceSrcInstName, RM_NAME_MAX_CHARS);\r
479             transaction->state = RM_SERVICE_PROCESSING;\r
480             memcpy ((void *)&(transaction->resourceInfo), (void *)&(resourceReqPkt->resourceInfo),\r
481                     sizeof(Rm_ResourceInfo));\r
482             rmTransactionProcessor(rmInst, transaction);\r
483             break;\r
484         }\r
485         case Rm_pktType_RESOURCE_RESPONSE:\r
486         {\r
487             Rm_ResourceResponsePkt *resourceRespPkt = (Rm_ResourceResponsePkt *)pkt->data;\r
488 \r
489             if (transaction = rmTransactionQueueFind(rmInst,resourceRespPkt->responseId)) {\r
490                 if ((transaction->state == RM_SERVICE_APPROVED_STATIC) &&\r
491                     (resourceRespPkt->requestState != RM_SERVICE_APPROVED)) {\r
492                     /* Lock the RM instance since service validated against static policy failed against \r
493                      * Server's global policy */\r
494                     rmInst->isLocked = true;\r
495                 }\r
496                 transaction->state = resourceRespPkt->requestState;\r
497 \r
498                 if ((transaction->state == RM_SERVICE_APPROVED) &&\r
499                     ((transaction->type == Rm_service_RESOURCE_ALLOCATE_INIT) ||\r
500                      (transaction->type == Rm_service_RESOURCE_ALLOCATE_USE) ||\r
501                      (transaction->type == Rm_service_RESOURCE_GET_BY_NAME))) {\r
502                     memcpy ((void *)&(transaction->resourceInfo), (void *)&(resourceRespPkt->resourceInfo),\r
503                             sizeof(Rm_ResourceInfo));\r
504                 }\r
505                 rmTransactionProcessor(rmInst, transaction);\r
506             }\r
507             else {\r
508                 return (RM_ERROR_PKT_RESP_DOES_NOT_MATCH_ANY_REQ);\r
509             }\r
510             break;\r
511         }\r
512         case Rm_pktType_NAMESERVER_REQUEST:\r
513         {\r
514             Rm_NsRequestPkt *nsRequestPkt = (Rm_NsRequestPkt *)pkt->data;\r
515 \r
516             transaction = rmTransactionQueueAdd(rmInst);\r
517             transaction->remoteOriginatingId = nsRequestPkt->requestId;\r
518 \r
519             if (nsRequestPkt->nsRequestType == Rm_nsReqPktType_MAP_RESOURCE) {\r
520                 transaction->type = Rm_service_RESOURCE_MAP_TO_NAME;\r
521             }\r
522             else if (nsRequestPkt->nsRequestType == Rm_nsReqPktType_UNMAP_RESOURCE) {\r
523                 transaction->type = Rm_service_RESOURCE_UNMAP_NAME;\r
524             }\r
525 \r
526             strncpy(transaction->pktSrcInstName, nsRequestPkt->pktSrcInstName, RM_NAME_MAX_CHARS);\r
527             strncpy(transaction->serviceSrcInstName, nsRequestPkt->serviceSrcInstName, RM_NAME_MAX_CHARS);\r
528             transaction->state = RM_SERVICE_PROCESSING;\r
529             memcpy ((void *)&(transaction->resourceInfo), (void *)&(nsRequestPkt->resourceInfo),\r
530                     sizeof(Rm_ResourceInfo));\r
531             rmTransactionProcessor(rmInst, transaction);            \r
532             break;\r
533         }\r
534         case Rm_pktType_NAMESERVER_RESPONSE:\r
535         {\r
536             Rm_NsResponsePkt *nsResponsePkt = (Rm_NsResponsePkt *)pkt->data;\r
537 \r
538             if (transaction = rmTransactionQueueFind(rmInst, nsResponsePkt->responseId)) {\r
539                 if ((transaction->state == RM_SERVICE_APPROVED_STATIC) &&\r
540                     (nsResponsePkt->requestState != RM_SERVICE_APPROVED)) {\r
541                     /* Lock the RM instance since service validated against static policy failed against \r
542                      * Server's global policy */                    \r
543                     rmInst->isLocked = true;\r
544                 }                \r
545                 transaction->state = nsResponsePkt->requestState;            \r
546                 rmTransactionProcessor(rmInst, transaction);\r
547             }\r
548             else {\r
549                 return (RM_ERROR_PKT_RESP_DOES_NOT_MATCH_ANY_REQ);\r
550             }\r
551             break;\r
552         }\r
553         default:\r
554             return (RM_ERROR_RECEIVED_INVALID_PACKET_TYPE);\r
555       }\r
556 \r
557     return (RM_OK);\r
558 }\r
559 \r