1 /*
2 * Copyright (c) 2012, Texas Instruments Incorporated
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * * Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 *
12 * * Redistributions in binary form must reproduce the above copyright
13 * notice, this list of conditions and the following disclaimer in the
14 * documentation and/or other materials provided with the distribution.
15 *
16 * * Neither the name of Texas Instruments Incorporated nor the names of
17 * its contributors may be used to endorse or promote products derived
18 * from this software without specific prior written permission.
19 *
20 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
22 * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
23 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
24 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
27 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
28 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
29 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
30 * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31 * */
32 /*
33 * ======== rm_test.c ========
34 * RM multicore test example
35 *
36 * This is an example program that uses MessageQ to pass a message
37 * from one processor to another.
38 *
39 * Each processor creates its own MessageQ first and then will try to open
40 * a remote processor's MessageQ.
41 *
42 * See message_multicore.k file for expected output.
43 */
45 #include <c6x.h>
46 #include <xdc/std.h>
47 #include <stdio.h>
48 #include <string.h>
49 #include <stdbool.h>
51 /* -----------------------------------XDC.RUNTIME module Headers */
52 #include <xdc/runtime/System.h>
53 #include <xdc/runtime/IHeap.h>
55 /* ----------------------------------- IPC module Headers */
56 #include <ti/ipc/Ipc.h>
57 #include <ti/ipc/MessageQ.h>
58 #include <ti/ipc/HeapBufMP.h>
59 #include <ti/ipc/MultiProc.h>
61 /* ----------------------------------- BIOS6 module Headers */
62 #include <ti/sysbios/BIOS.h>
63 #include <ti/sysbios/knl/Task.h>
65 /* ----------------------------------- Resource Manager Headers */
66 #include <ti/drv/rm/rm.h>
67 #include <ti/drv/rm/rm_osal.h>
68 #include <ti/drv/rm/rm_transport.h>
69 #include <ti/drv/rm/rm_services.h>
71 /* ======== Task Handles ======== */
72 Task_Handle startupRmTskHandle;
73 Task_Handle testReceiveTskHandle;
74 Task_Handle testRmTskHandle;
76 /* ======== Application Heaps ======== */
77 #define RM_PKT_HEAP_NAME "rmHeapBuf"
78 HeapBufMP_Handle rmPktHeapHandle = NULL;
80 #define MSGQ_HEAP_NAME "msgQHeapBuf"
81 #define MSGQ_HEAP_ID 0
83 /* ======== RM Instance Names ======== */
84 Char rmServerName[RM_INSTANCE_NAME_MAX_CHARS] = "RM_Server";
85 Char rmClientDelegateName[RM_INSTANCE_NAME_MAX_CHARS] = "RM_Client_Delegate";
86 Char rmClientName[RM_INSTANCE_NAME_MAX_CHARS] = "RM_Client";
88 /* ======== RM IPC MessageQ Names ======== */
89 Char serverCdQueueName[30] = "RM_Server_CD_Queue";
90 Char cdServerQueueName[30] = "RM_CD_Server_Queue";
91 Char cdClientQueueName[30] = "RM_CD_Client_Queue";
92 Char clientCdQueueName[30] = "RM_Client_CD_Queue";
94 /* ======== RM Instance Handles ======== */
95 Rm_Handle rmServerHandle = NULL;
96 Rm_Handle rmClientDelegateHandle = NULL;
97 Rm_Handle rmClientHandle = NULL;
99 /* ======== RM Instance Service Ports ======== */
100 Rm_ServicePort *rmServerServicePort = NULL;
101 Rm_ServicePort *rmClientDelegateServicePort = NULL;
102 Rm_ServicePort *rmClientServicePort = NULL;
104 /* ======== RM Transport Packet Definition ======== */
105 typedef struct {
106 MessageQ_MsgHeader msgQHeader;
107 /* Pointer to packet provided by RM */
108 Rm_Packet *rmPkt;
109 } MsgQ_RmPacket;
111 /* ======== RM Transport Mapping Tables for Application ======== */
112 /* Core 0 Map Entry Indices */
113 #define SERVER_TO_CD_MAP_ENTRY 0
114 /* Core 1 Map Entry Indicies */
115 #define CD_TO_SERVER_MAP_ENTRY 0
116 #define CD_TO_CLIENT_MAP_ENTRY 1
117 #define CLIENT_TO_CD_MAP_ENTRY 2
119 /* Max map entries across all cores */
120 #define MAX_MAPPING_ENTRIES 3
122 typedef struct {
123 Rm_TransportHandle transportHandle;
124 MessageQ_Handle receiveMsgQ;
125 MessageQ_QueueId remoteMsgQId;
126 } Transport_MapEntry;
128 /* Core 1 will have three mapping entries
129 * Two map entries for the Client Delegate
130 * One map entry for the Client */
131 Transport_MapEntry rmTransportMap[MAX_MAPPING_ENTRIES];
133 uint32_t waitForBlockingOperation = 0;
134 Rm_ServiceRespInfo responseInfo;
136 /* ======== RM Application Sync APIs ======== */
138 typedef struct {
139 uint32_t sem;
140 uint32_t pad[31];
141 } syncObj;
143 #pragma DATA_SECTION (testSyncObj, ".syncObj");
144 #pragma DATA_ALIGN (testSyncObj, 16)
145 syncObj testSyncObj;
147 void initSyncObj(void)
148 {
149 Rm_osalBeginMemAccess((void *) &testSyncObj, sizeof(syncObj));
150 testSyncObj.sem = 0;
151 Rm_osalEndMemAccess((void *) &testSyncObj, sizeof(syncObj));
152 }
154 void takeSyncObj(void)
155 {
156 Rm_osalBeginMemAccess((void *) &testSyncObj, sizeof(syncObj));
157 testSyncObj.sem = 1;
158 Rm_osalEndMemAccess((void *) &testSyncObj, sizeof(syncObj));
159 }
161 void waitOnSyncObj(void)
162 {
163 do
164 {
165 /* Yield for other tasks */
166 Task_yield();
167 Rm_osalBeginMemAccess((void *) &testSyncObj, sizeof(syncObj));
168 } while (testSyncObj.sem == 1);
169 }
171 void releaseSyncObj(void)
172 {
173 Rm_osalBeginMemAccess((void *) &testSyncObj, sizeof(syncObj));
174 testSyncObj.sem = 0;
175 Rm_osalEndMemAccess((void *) &testSyncObj, sizeof(syncObj));
176 }
178 /* ======== RM Application Transport APIs ======== */
180 Rm_Packet *TransportAlloc (Rm_TransportHandle transportHandle, uint32_t pktSize)
181 {
182 Rm_Packet *pkt = NULL;
184 /* All transports will allocate from the same heap */
186 pkt = HeapBufMP_alloc(rmPktHeapHandle, pktSize, 0);
188 if (pkt != NULL)
189 {
190 pkt->pktLenBytes = pktSize;
191 }
193 return (pkt);
194 }
196 int32_t TransportFree (Rm_TransportHandle transportHandle, Rm_Packet *pkt)
197 {
198 uint32_t pktSize = pkt->pktLenBytes;
200 /* All transports will free to the same heap */
202 HeapBufMP_free(rmPktHeapHandle, pkt, pktSize);
204 return (0);
205 }
207 int32_t TransportSend (Rm_TransportHandle transportHandle, Rm_Packet *pkt)
208 {
209 MsgQ_RmPacket *rmMsg = NULL;
210 MessageQ_QueueId remoteQueueId;
211 bool handleValid = false;
212 int32_t status, i;
214 /* Get the remoteQueueId based on the transportHandle */
215 for (i = 0; i < MAX_MAPPING_ENTRIES; i++)
216 {
217 /* transportHandle found in mapping table. Get the remoteQueueId associated
218 * with it */
219 if (rmTransportMap[i].transportHandle == transportHandle)
220 {
221 remoteQueueId = rmTransportMap[i].remoteMsgQId;
222 /* Break out of the search loop */
223 handleValid = true;
224 break;
225 }
226 }
228 if (handleValid)
229 {
230 /* Allocate a messageQ message for containing the RM packet */
231 rmMsg = (MsgQ_RmPacket *)MessageQ_alloc(MSGQ_HEAP_ID, sizeof(MsgQ_RmPacket));
232 if (rmMsg == NULL)
233 {
234 System_printf("Core %d: MessageQ_alloc failed in TransportSend\n", MultiProc_self());
235 }
237 /* Attach the RM packet to the MessageQ message */
238 Rm_osalEndMemAccess((void *) pkt, pkt->pktLenBytes);
239 rmMsg->rmPkt = pkt;
240 /* Send the message to the remote side */
241 status = MessageQ_put(remoteQueueId, (MessageQ_Msg)rmMsg);
242 if (status < 0)
243 {
244 System_printf("Core %d: MessageQ_put had a failure/error in TransportSend\n", MultiProc_self());
245 }
246 }
247 else
248 {
249 /* Could not find a registered transport handle that matched the handle provided by RM.
250 * Return an error to RM. */
251 System_printf("Core %d: TransportSend couldn't find transportHandle in transport map\n", MultiProc_self());
252 status = -1;
253 }
255 return (status);
256 }
258 void *TransportReceive (Rm_TransportHandle transportHandle)
259 {
260 MessageQ_Handle receiveQ;
261 MessageQ_Msg rmMsg = NULL;
262 Rm_Packet *rmPkt = NULL;
263 bool queueValid = false;
264 int32_t status, i;
266 /* Get the receiveQ based on the transportHandle */
267 for (i = 0; i < MAX_MAPPING_ENTRIES; i++)
268 {
269 /* transportHandle found in mapping table. Get the receiveQ associated
270 * with it */
271 if (rmTransportMap[i].transportHandle == transportHandle)
272 {
273 receiveQ = rmTransportMap[i].receiveMsgQ;
274 /* Break out of the search loop */
275 queueValid = true;
276 break;
277 }
278 }
280 if (queueValid)
281 {
282 /* Get the next message from the receiveQ */
283 status = (int32_t) MessageQ_get(receiveQ, &rmMsg, MessageQ_FOREVER);
284 if (status < 0)
285 {
286 System_abort("This should not happen since timeout is forever\n");
287 }
288 if (rmMsg == NULL)
289 {
290 System_printf("Core %d: MessageQ_get failed returning a null packet in TransportReceive\n", MultiProc_self());
291 }
293 /* Extract the Rm_Packet from the RM msg */
294 rmPkt = ((MsgQ_RmPacket *)rmMsg)->rmPkt;
295 Rm_osalBeginMemAccess((void *) rmPkt, rmPkt->pktLenBytes);
297 /* Free the messageQ message now that RM packet pointer has been extracted */
298 status = MessageQ_free(rmMsg);
299 if (status < 0)
300 {
301 System_printf("Core %d: MessageQ_free had a failure/error in TransportReceive\n", MultiProc_self());
302 }
303 }
304 else
305 {
306 /* Could not find a registered transport handle that matched the handle provided by RM.
307 * Return an error to RM. */
308 System_printf("Core %d: TransportReceive couldn't find transportHandle in transport map\n", MultiProc_self());
309 }
311 /* Pass the RM packet back to RM */
312 return ((void *)rmPkt);
313 }
315 int32_t TransportNumPktsReceived (Rm_TransportHandle transportHandle)
316 {
317 MessageQ_Handle receiveQ;
318 bool queueValid = false;
319 int32_t numPkts, i;
321 /* Get the receiveQ based on the transportHandle */
322 for (i = 0; i < MAX_MAPPING_ENTRIES; i++)
323 {
324 /* transportHandle found in mapping table. Get the receiveQ associated
325 * with it */
326 if (rmTransportMap[i].transportHandle == transportHandle)
327 {
328 receiveQ = rmTransportMap[i].receiveMsgQ;
329 /* Break out of the search loop */
330 queueValid = true;
331 break;
332 }
333 }
335 if (queueValid)
336 {
337 /* Get the number of messages in the receiveQ */
338 numPkts = (int32_t) MessageQ_count(receiveQ);
339 }
340 else
341 {
342 /* Could not find a registered transport handle that matched the handle provided by RM.
343 * Return an error to RM. */
344 System_printf("Core %d: TransportNumPktsReceived couldn't find transportHandle in transport map\n", MultiProc_self());
345 numPkts = -1;
346 }
348 return (numPkts);
349 }
351 /*
352 * ======== testServiceCallback ========
353 * Application's callback function given to RM on service requests
354 */
355 void testServiceCallback(Rm_ServiceRespInfo *serviceResponse)
356 {
357 if (serviceResponse->serviceId == waitForBlockingOperation)
358 {
359 waitForBlockingOperation = 0;
360 strcpy(responseInfo.resourceName, serviceResponse->resourceName);
361 responseInfo.resourceBase = serviceResponse->resourceBase;
362 responseInfo.resourceLength = serviceResponse->resourceLength;
363 responseInfo.serviceState = serviceResponse->serviceState;
364 }
365 }
367 bool blockForResponse(Rm_ServiceRespInfo *respInfo)
368 {
369 waitForBlockingOperation = respInfo->serviceId;
370 /* Block and wait for the response if the RM needed to perform a blocking operation
371 * to complete the request */
372 while(waitForBlockingOperation)
373 {
374 /* Yield to receive task to see if there are any packets for RM instance */
375 Task_yield();
376 }
378 if ((respInfo->serviceState != RM_SERVICE_PROCESSING) &&
379 (respInfo->serviceState != RM_SERVICE_APPROVED_AND_COMPLETED))
380 {
381 System_printf("Core %d: Service request encountered error or denial: %d\n", MultiProc_self(),
382 respInfo->serviceState);
383 return(FALSE);
384 }
386 return(TRUE);
387 }
389 /*
390 * ======== testRmTsk ========
391 * RM cleanup task
392 */
393 void cleanupRmTsk(UArg arg0, UArg arg1)
394 {
395 /* Delete the RM test task */
396 System_printf("Core %d: Deleting RM test task...\n", MultiProc_self());
397 if (testRmTskHandle)
398 {
399 Task_delete(&testRmTskHandle);
400 /* Set the task handle to be NULL so that the delete only occurs once */
401 testRmTskHandle = NULL;
402 }
403 /* Delete the RM receive task */
404 System_printf("Core %d: Deleting RM receive task...\n", MultiProc_self());
405 if (testReceiveTskHandle)
406 {
407 Task_delete(&testReceiveTskHandle);
408 /* Set the task handle to be NULL so that the delete only occurs once */
409 testReceiveTskHandle = NULL;
410 }
414 /* Cleanup all service ports, transport handles, RM instances, and IPC constructs */
416 BIOS_exit(0);
417 }
419 /*
420 * ======== testRmTsk ========
421 * RM test task
422 */
423 void testReceiveTsk(UArg arg0, UArg arg1)
424 {
425 int32_t retVal;
427 while(1)
428 {
430 /* Run the RM polling functions for each RM instance. */
431 if (MultiProc_self() == 0)
432 {
433 retVal = Rm_receivePktPolling(rmTransportMap[SERVER_TO_CD_MAP_ENTRY].transportHandle);
434 if (retVal != RM_TRANSPORT_SUCCESSFUL)
435 {
436 System_printf("Core %d: %s to %s transport receive error %d\n", MultiProc_self(),
437 rmServerName,
438 rmClientDelegateName,
439 retVal);
440 }
441 }
442 else if (MultiProc_self() == 1)
443 {
444 retVal = Rm_receivePktPolling(rmTransportMap[CD_TO_SERVER_MAP_ENTRY].transportHandle);
445 if (retVal != RM_TRANSPORT_SUCCESSFUL)
446 {
447 System_printf("Core %d: %s to %s transport receive error %d\n", MultiProc_self(),
448 rmClientDelegateName,
449 rmServerName,
450 retVal);
451 }
453 retVal = Rm_receivePktPolling(rmTransportMap[CD_TO_CLIENT_MAP_ENTRY].transportHandle);
454 if (retVal != RM_TRANSPORT_SUCCESSFUL)
455 {
456 System_printf("Core %d: %s to %s transport receive error %d\n", MultiProc_self(),
457 rmClientDelegateName,
458 rmClientName,
459 retVal);
460 }
462 retVal = Rm_receivePktPolling(rmTransportMap[CLIENT_TO_CD_MAP_ENTRY].transportHandle);
463 if (retVal != RM_TRANSPORT_SUCCESSFUL)
464 {
465 System_printf("Core %d: %s to %s transport receive error %d\n", MultiProc_self(),
466 rmClientName,
467 rmClientDelegateName,
468 retVal);
469 }
470 }
472 /* Yield for main test task */
473 Task_yield();
474 }
475 }
477 /*
478 * ======== testRmTsk ========
479 * RM test task
480 */
481 void testRmTsk(UArg arg0, UArg arg1)
482 {
483 Rm_ServiceReqInfo requestInfo;
484 Task_Params taskParams;
486 /* Delete the RM startup task */
487 System_printf("Core %d: Deleting RM startup task...\n", MultiProc_self());
488 if (startupRmTskHandle)
489 {
490 Task_delete(&startupRmTskHandle);
491 /* Set the task handle to be NULL so that the delete only occurs once */
492 startupRmTskHandle = NULL;
493 }
495 /* Open service ports on all the RM instances to test service requests from the different
496 * RM instances */
497 if (MultiProc_self() == 0)
498 {
499 rmServerServicePort = Rm_getServicePort(rmServerHandle);
500 }
501 else if (MultiProc_self() == 1)
502 {
503 rmClientDelegateServicePort = Rm_getServicePort(rmClientDelegateHandle);
504 rmClientServicePort = Rm_getServicePort(rmClientHandle);
505 }
507 memset((void *)&requestInfo, 0, sizeof(Rm_ServiceReqInfo));
508 memset((void *)&responseInfo, 0, sizeof(Rm_ServiceRespInfo));
510 System_printf("Core %d: Testing NameServer features...\n", MultiProc_self());
512 /* Use the service ports to test the service requests */
513 if (MultiProc_self() == 0)
514 {
515 char resourceName[RM_RESOURCE_NAME_MAX_CHARS] = "gp-queue";
516 char resourceNsName[RM_RESOURCE_NAME_MAX_CHARS] = "My_Favorite_Queue";
518 char aifName[RM_RESOURCE_NAME_MAX_CHARS] = "aif-rx-ch";
519 char memRegionName[RM_RESOURCE_NAME_MAX_CHARS] = "memory-regions";
521 /* Issue the service request create a new NameServer object via the service port */
522 requestInfo.type = Rm_service_RESOURCE_MAP_TO_NAME;
523 requestInfo.resourceName = resourceName;
524 requestInfo.resourceBase = 1002;
525 requestInfo.resourceLength = 1;
526 requestInfo.resourceNsName = resourceNsName;
527 requestInfo.callback.serviceCallback = testServiceCallback;
529 System_printf("Core %d: %s creating NameServer object...\n", MultiProc_self(), rmServerName);
530 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
531 if (blockForResponse(&responseInfo))
532 {
533 System_printf("Core %d: %s created NameServer object: %s base: %d length: %d\n", MultiProc_self(),
534 rmServerName,
535 resourceNsName,
536 requestInfo.resourceBase,
537 requestInfo.resourceLength);
538 }
540 /* Wait for Client Delegate and Client to retrieve resource via the name and allocate it */
541 waitOnSyncObj();
543 Rm_printResourceStatus(rmServerHandle);
545 /* Wait for Client to free resource via the NameServer and delete the NameServer object. */
546 waitOnSyncObj();
548 Rm_printResourceStatus(rmServerHandle);
550 /* Try to allocate the memory region taken by the Linux Kernel */
551 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
552 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
553 requestInfo.resourceName = memRegionName;
554 requestInfo.resourceBase = 12;
555 requestInfo.resourceLength = 1;
556 requestInfo.callback.serviceCallback = testServiceCallback;
558 System_printf("Core %d: %s Trying to reserve memory region taken by Linux...\n", MultiProc_self(), rmServerName);
559 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
560 if (blockForResponse(&responseInfo))
561 {
562 System_printf("Core %d: %s allocated resource (SHOULD NOT HAPPEN): %s base: %d length: %d\n", MultiProc_self(),
563 rmServerName,
564 requestInfo.resourceName,
565 requestInfo.resourceBase,
566 requestInfo.resourceLength);
567 }
569 /* Allocate some resources for testing tree interaction with multiple allocations from different instances */
570 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
571 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
572 requestInfo.resourceName = aifName;
573 requestInfo.resourceBase = 14;
574 requestInfo.resourceLength = 5;
575 requestInfo.callback.serviceCallback = testServiceCallback;
577 System_printf("Core %d: %s Allocating resource...\n", MultiProc_self(), rmServerName);
578 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
579 if (blockForResponse(&responseInfo))
580 {
581 System_printf("Core %d: %s allocated resource: %s base: %d length: %d\n", MultiProc_self(),
582 rmServerName,
583 requestInfo.resourceName,
584 requestInfo.resourceBase,
585 requestInfo.resourceLength);
586 }
587 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
588 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
589 requestInfo.resourceName = aifName;
590 requestInfo.resourceBase = 19;
591 requestInfo.resourceLength = 31;
592 requestInfo.callback.serviceCallback = testServiceCallback;
594 System_printf("Core %d: %s Allocating resource...\n", MultiProc_self(), rmServerName);
595 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
596 if (blockForResponse(&responseInfo))
597 {
598 System_printf("Core %d: %s allocated resource: %s base: %d length: %d\n", MultiProc_self(),
599 rmServerName,
600 requestInfo.resourceName,
601 requestInfo.resourceBase,
602 requestInfo.resourceLength);
603 }
605 /* Wait for Client and Client Delegate to do their allocates */
606 waitOnSyncObj();
608 Rm_printResourceStatus(rmServerHandle);
610 /* Free resources to show tree handling of different frees */
611 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
612 requestInfo.type = Rm_service_RESOURCE_FREE;
613 requestInfo.resourceName = aifName;
614 requestInfo.resourceBase = 25;
615 requestInfo.resourceLength = 3;
616 requestInfo.callback.serviceCallback = testServiceCallback;
618 System_printf("Core %d: %s freeing resource...\n", MultiProc_self(), rmServerName);
619 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
620 if (blockForResponse(&responseInfo))
621 {
622 System_printf("Core %d: %s freed resource: %s base: %d length: %d\n", MultiProc_self(),
623 rmServerName,
624 requestInfo.resourceName,
625 requestInfo.resourceBase,
626 requestInfo.resourceLength);
627 }
629 Rm_printResourceStatus(rmServerHandle);
631 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
632 requestInfo.type = Rm_service_RESOURCE_FREE;
633 requestInfo.resourceName = aifName;
634 requestInfo.resourceBase = 34;
635 requestInfo.resourceLength = 3;
636 requestInfo.callback.serviceCallback = testServiceCallback;
638 System_printf("Core %d: %s freeing resource...\n", MultiProc_self(), rmServerName);
639 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
640 if (blockForResponse(&responseInfo))
641 {
642 System_printf("Core %d: %s freed resource: %s base: %d length: %d\n", MultiProc_self(),
643 rmServerName,
644 requestInfo.resourceName,
645 requestInfo.resourceBase,
646 requestInfo.resourceLength);
647 }
649 Rm_printResourceStatus(rmServerHandle);
651 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
652 requestInfo.type = Rm_service_RESOURCE_FREE;
653 requestInfo.resourceName = aifName;
654 requestInfo.resourceBase = 28;
655 requestInfo.resourceLength = 6;
656 requestInfo.callback.serviceCallback = testServiceCallback;
658 System_printf("Core %d: %s freeing resource...\n", MultiProc_self(), rmServerName);
659 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
660 if (blockForResponse(&responseInfo))
661 {
662 System_printf("Core %d: %s freed resource: %s base: %d length: %d\n", MultiProc_self(),
663 rmServerName,
664 requestInfo.resourceName,
665 requestInfo.resourceBase,
666 requestInfo.resourceLength);
667 }
669 Rm_printResourceStatus(rmServerHandle);
671 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
672 requestInfo.type = Rm_service_RESOURCE_FREE;
673 requestInfo.resourceName = aifName;
674 requestInfo.resourceBase = 29;
675 requestInfo.resourceLength = 2;
676 requestInfo.callback.serviceCallback = testServiceCallback;
678 System_printf("Core %d: %s freeing resource...\n", MultiProc_self(), rmServerName);
679 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
680 if (blockForResponse(&responseInfo))
681 {
682 System_printf("Core %d: %s freed resource: %s base: %d length: %d\n", MultiProc_self(),
683 rmServerName,
684 requestInfo.resourceName,
685 requestInfo.resourceBase,
686 requestInfo.resourceLength);
687 }
688 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
689 requestInfo.type = Rm_service_RESOURCE_FREE;
690 requestInfo.resourceName = aifName;
691 requestInfo.resourceBase = 46;
692 requestInfo.resourceLength = 4;
693 requestInfo.callback.serviceCallback = testServiceCallback;
695 System_printf("Core %d: %s freeing resource...\n", MultiProc_self(), rmServerName);
696 rmServerServicePort->rmService(rmServerServicePort->rmHandle, &requestInfo, &responseInfo);
697 if (blockForResponse(&responseInfo))
698 {
699 System_printf("Core %d: %s freed resource: %s base: %d length: %d\n", MultiProc_self(),
700 rmServerName,
701 requestInfo.resourceName,
702 requestInfo.resourceBase,
703 requestInfo.resourceLength);
704 }
706 Rm_printResourceStatus(rmServerHandle);
708 /* Wait for Client and Client Delegate to do their UNSPECIFIED allocates */
709 waitOnSyncObj();
711 Rm_printResourceStatus(rmServerHandle);
713 }
714 else if (MultiProc_self() == 1)
715 {
716 char resourceName[RM_RESOURCE_NAME_MAX_CHARS] = "gp-queue";
717 char resourceNsName[RM_RESOURCE_NAME_MAX_CHARS] = "My_Favorite_Queue";
719 char aifName[RM_RESOURCE_NAME_MAX_CHARS] = "aif-rx-ch";
720 char accumChName[RM_RESOURCE_NAME_MAX_CHARS] = "accumulator-ch";
722 /* Issue the service request for the resources tied to the name via the service port */
723 requestInfo.type = Rm_service_RESOURCE_GET_BY_NAME;
724 requestInfo.resourceNsName = resourceNsName;
725 requestInfo.callback.serviceCallback = testServiceCallback;
727 System_printf("Core %d: %s getting resources tied to NameServer object...\n", MultiProc_self(),
728 rmClientDelegateName);
729 rmClientDelegateServicePort->rmService(rmClientDelegateServicePort->rmHandle, &requestInfo, &responseInfo);
730 if (blockForResponse(&responseInfo))
731 {
732 System_printf("Core %d: %s got Name: %s base: %d length: %d\n", MultiProc_self(),
733 rmClientDelegateName,
734 resourceNsName,
735 responseInfo.resourceBase,
736 responseInfo.resourceLength);
737 }
739 /* Allocate the resources via the service port from the Client */
740 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
741 requestInfo.resourceName = responseInfo.resourceName;
742 requestInfo.resourceBase = responseInfo.resourceBase;
743 requestInfo.resourceLength = responseInfo.resourceLength;
744 requestInfo.resourceNsName = NULL;
745 requestInfo.callback.serviceCallback = testServiceCallback;
747 System_printf("Core %d: %s allocating resources...\n", MultiProc_self(), rmClientName);
748 rmClientServicePort->rmService(rmClientServicePort->rmHandle, &requestInfo, &responseInfo);
749 if (blockForResponse(&responseInfo))
750 {
751 System_printf("Core %d: %s allocated resources: %s base: %d length: %d\n", MultiProc_self(),
752 rmClientName,
753 resourceNsName,
754 responseInfo.resourceBase,
755 responseInfo.resourceLength);
756 }
758 /* Release the syncObj so Server can print results of NameServer object add and resource allocate */
759 releaseSyncObj();
761 /* Take the syncObj to free the name resource via the name, rather than the base+length */
762 takeSyncObj();
764 /* Free the named resource using the name via the service port from the Client */
765 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
766 requestInfo.type = Rm_service_RESOURCE_FREE;
767 requestInfo.resourceNsName = resourceNsName;
768 requestInfo.callback.serviceCallback = testServiceCallback;
770 System_printf("Core %d: %s freeing resource via name...\n", MultiProc_self(), rmClientName);
771 rmClientServicePort->rmService(rmClientServicePort->rmHandle, &requestInfo, &responseInfo);
772 if (blockForResponse(&responseInfo))
773 {
774 System_printf("Core %d: %s freed resource with name: %s\n", MultiProc_self(),
775 rmClientName,
776 resourceNsName);
777 }
779 /* Delete the name object from the NameServer */
780 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
781 requestInfo.type = Rm_service_RESOURCE_UNMAP_NAME;
782 requestInfo.resourceNsName = resourceNsName;
783 requestInfo.callback.serviceCallback = testServiceCallback;
785 System_printf("Core %d: %s Deleting NameServer object: %s...\n", MultiProc_self(),
786 rmClientName,
787 resourceNsName);
788 rmClientServicePort->rmService(rmClientServicePort->rmHandle, &requestInfo, &responseInfo);
789 if (blockForResponse(&responseInfo))
790 {
791 System_printf("Core %d: %s deleted NameServer object: %s\n", MultiProc_self(),
792 rmClientName,
793 resourceNsName);
794 }
796 /* Release the syncObj so Server can print results of resource free and NameServer object delete. */
797 releaseSyncObj();
799 /* Take the syncObj to allocate resources for testing resource tree interactions. */
800 takeSyncObj();
802 /* Allocate some resources for testing tree interaction with multiple allocations from different instances */
803 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
804 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
805 requestInfo.resourceName = aifName;
806 requestInfo.resourceBase = 0;
807 requestInfo.resourceLength = 6;
808 requestInfo.callback.serviceCallback = testServiceCallback;
810 System_printf("Core %d: %s Allocating resource...\n", MultiProc_self(), rmClientName);
811 rmClientServicePort->rmService(rmClientServicePort->rmHandle, &requestInfo, &responseInfo);
812 if (blockForResponse(&responseInfo))
813 {
814 System_printf("Core %d: %s allocated resource: %s base: %d length: %d\n", MultiProc_self(),
815 rmClientName,
816 requestInfo.resourceName,
817 requestInfo.resourceBase,
818 requestInfo.resourceLength);
819 }
821 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
822 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
823 requestInfo.resourceName = aifName;
824 requestInfo.resourceBase = 50;
825 requestInfo.resourceLength = 7;
826 requestInfo.callback.serviceCallback = testServiceCallback;
828 System_printf("Core %d: %s Allocating resource...\n", MultiProc_self(), rmClientDelegateName);
829 rmClientDelegateServicePort->rmService(rmClientDelegateServicePort->rmHandle, &requestInfo, &responseInfo);
830 if (blockForResponse(&responseInfo))
831 {
832 System_printf("Core %d: %s allocated resource: %s base: %d length: %d\n", MultiProc_self(),
833 rmClientDelegateName,
834 requestInfo.resourceName,
835 requestInfo.resourceBase,
836 requestInfo.resourceLength);
837 }
839 /* Release the syncObj so Server can print results of resource allocations */
840 releaseSyncObj();
842 /* Take the syncObj to allocate resources using the UNSPECIFIED parameters. */
843 takeSyncObj();
845 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
846 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
847 requestInfo.resourceName = accumChName;
848 requestInfo.resourceBase = RM_RESOURCE_BASE_UNSPECIFIED;
849 requestInfo.resourceLength = 5;
850 requestInfo.resourceAlignment = 4;
851 requestInfo.callback.serviceCallback = testServiceCallback;
853 System_printf("Core %d: %s Allocating resource...\n", MultiProc_self(), rmClientDelegateName);
854 rmClientDelegateServicePort->rmService(rmClientDelegateServicePort->rmHandle, &requestInfo, &responseInfo);
855 if (blockForResponse(&responseInfo))
856 {
857 System_printf("Core %d: %s allocated resource: %s base: %d length: %d\n", MultiProc_self(),
858 rmClientDelegateName,
859 responseInfo.resourceName,
860 responseInfo.resourceBase,
861 responseInfo.resourceLength);
862 }
864 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
865 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
866 requestInfo.resourceName = accumChName;
867 requestInfo.resourceBase = RM_RESOURCE_BASE_UNSPECIFIED;
868 requestInfo.resourceLength = 2;
869 requestInfo.resourceAlignment = RM_RESOURCE_ALIGNMENT_UNSPECIFIED;
870 requestInfo.callback.serviceCallback = testServiceCallback;
872 System_printf("Core %d: %s Allocating resource...\n", MultiProc_self(), rmClientName);
873 rmClientServicePort->rmService(rmClientServicePort->rmHandle, &requestInfo, &responseInfo);
874 if (blockForResponse(&responseInfo))
875 {
876 System_printf("Core %d: %s allocated resource: %s base: %d length: %d\n", MultiProc_self(),
877 rmClientName,
878 responseInfo.resourceName,
879 responseInfo.resourceBase,
880 responseInfo.resourceLength);
881 }
883 memset((void *) &requestInfo, 0, sizeof(Rm_ServiceReqInfo));
884 requestInfo.type = Rm_service_RESOURCE_ALLOCATE;
885 requestInfo.resourceName = accumChName;
886 requestInfo.resourceBase = RM_RESOURCE_BASE_UNSPECIFIED;
887 requestInfo.resourceLength = 2;
888 requestInfo.resourceAlignment = 20;
889 requestInfo.callback.serviceCallback = testServiceCallback;
891 System_printf("Core %d: %s Allocating resource...\n", MultiProc_self(), rmClientName);
892 rmClientServicePort->rmService(rmClientServicePort->rmHandle, &requestInfo, &responseInfo);
893 if (blockForResponse(&responseInfo))
894 {
895 System_printf("Core %d: %s allocated resource: %s base: %d length: %d\n", MultiProc_self(),
896 rmClientName,
897 responseInfo.resourceName,
898 responseInfo.resourceBase,
899 responseInfo.resourceLength);
900 }
902 /* Release the syncObj so Server can print results of resource allocations */
903 releaseSyncObj();
904 }
906 System_printf("Core %d: Testing is complete\n", MultiProc_self());
908 /* Create the RM cleanup task. */
909 System_printf("Core %d: Creating RM cleanup task...\n", MultiProc_self());
910 Task_Params_init (&taskParams);
911 Task_create (cleanupRmTsk, &taskParams, NULL);
912 }
914 /*
915 * ======== startupRmTsk ========
916 * Configures application transports and registers them with RM
917 */
918 Void startupRmTsk(UArg arg0, UArg arg1)
919 {
920 MessageQ_Handle serverCdMsgQ, cdServerMsgQ, cdClientMsgQ, clientCdMsgQ;
921 MessageQ_QueueId serverCdQId, cdServerQId, cdClientQId, clientCdQId;
922 Int status, i;
923 HeapBufMP_Handle msgQHeapHandle;
924 HeapBufMP_Params heapBufParams;
925 Rm_TransportCfg rmTransportCfg;
926 Rm_TransportHandle serverCdHandle, cdServerHandle, cdClientHandle, clientCdHandle;
927 Task_Params taskParams;
929 if (MultiProc_self() == 1)
930 {
931 /* Take the syncObj on core 1, preparing for RM testing */
932 takeSyncObj();
933 }
935 /* Initialize the transport map */
936 for (i = 0; i < MAX_MAPPING_ENTRIES; i++)
937 {
938 rmTransportMap[i].transportHandle = NULL;
939 }
941 if (MultiProc_self() == 0)
942 {
943 /* Create the heap that will be used to allocate RM messages. This
944 * heap is a multi-processor heap. It will be shared amongst
945 * all RM instances. */
946 HeapBufMP_Params_init(&heapBufParams);
947 heapBufParams.regionId = 0;
948 heapBufParams.name = RM_PKT_HEAP_NAME;
949 heapBufParams.numBlocks = 64;
950 heapBufParams.blockSize = sizeof(Rm_Packet);
951 rmPktHeapHandle = HeapBufMP_create(&heapBufParams);
952 if (rmPktHeapHandle == NULL)
953 {
954 System_abort("HeapBufMP_create failed for RM packet heap\n" );
955 }
956 System_printf("Core %d: RM packet heap created\n", MultiProc_self());
958 /* Create the heap that will be used to allocate messageQ messages. */
959 HeapBufMP_Params_init(&heapBufParams);
960 heapBufParams.regionId = 0;
961 heapBufParams.name = MSGQ_HEAP_NAME;
962 heapBufParams.numBlocks = 64;
963 heapBufParams.blockSize = sizeof(MsgQ_RmPacket);
964 msgQHeapHandle = HeapBufMP_create(&heapBufParams);
965 if (msgQHeapHandle == NULL)
966 {
967 System_abort("HeapBufMP_create failed MessageQ message heap\n" );
968 }
969 System_printf("Core %d: IPC MessageQ message heap created\n", MultiProc_self());
970 }
971 else
972 {
973 /* Open the heaps created by the other processor. Loop until opened. */
974 do
975 {
976 status = HeapBufMP_open(RM_PKT_HEAP_NAME, &rmPktHeapHandle);
977 /*
978 * Sleep for 1 clock tick to avoid inundating remote processor
979 * with interrupts if open failed
980 */
981 if (status < 0)
982 {
983 Task_sleep(1);
984 }
985 } while (status < 0);
986 System_printf("Core %d: RM packet heap opened\n", MultiProc_self());
988 do
989 {
990 status = HeapBufMP_open(MSGQ_HEAP_NAME, &msgQHeapHandle);
991 /*
992 * Sleep for 1 clock tick to avoid inundating remote processor
993 * with interrupts if open failed
994 */
995 if (status < 0)
996 {
997 Task_sleep(1);
998 }
999 } while (status < 0);
1000 System_printf("Core %d: IPC MessageQ message heap opened\n", MultiProc_self());
1001 }
1003 /* Register the MessageQ heap with MessageQ */
1004 MessageQ_registerHeap((IHeap_Handle)msgQHeapHandle, MSGQ_HEAP_ID);
1006 /* Create the messageQ's for each RM instance connection
1007 * Need four queues. Topology will be:
1008 * RM Server <---> RM Client Delegate <---> RM Client
1009 * 1 queue on RM Server
1010 * 2 queues on RM Client Delegate
1011 * 1 queue on RM Client */
1012 if (MultiProc_self() == 0)
1013 {
1014 /* Create the RM Server messageQ used by the RM Client Delegate */
1015 serverCdMsgQ = MessageQ_create(serverCdQueueName, NULL);
1016 if (serverCdMsgQ == NULL)
1017 {
1018 System_abort("MessageQ_create failed for RM Server - Client Delegate queue\n" );
1019 }
1020 System_printf("Core %d: RM Server MessageQ created for receiving packets from RM CD\n", MultiProc_self());
1021 }
1022 else if (MultiProc_self() == 1)
1023 {
1024 /* Create the RM Client Delegate messageQ used by the RM Server */
1025 cdServerMsgQ = MessageQ_create(cdServerQueueName, NULL);
1026 if (cdServerMsgQ == NULL)
1027 {
1028 System_abort("MessageQ_create failed for RM Client Delegate - Server queue\n" );
1029 }
1030 System_printf("Core %d: RM CD MessageQ created for receiving packets from RM Server\n", MultiProc_self());
1031 /* Create the RM Client Delegate messageQ used by the RM Client */
1032 cdClientMsgQ = MessageQ_create(cdClientQueueName, NULL);
1033 if (cdClientMsgQ == NULL)
1034 {
1035 System_abort("MessageQ_create failed for RM Client Delegate - Client queue\n" );
1036 }
1037 System_printf("Core %d: RM CD MessageQ created for receiving packets from RM Client\n", MultiProc_self());
1038 /* Create the RM Client messageQ used by the RM Client Delegate */
1039 clientCdMsgQ = MessageQ_create(clientCdQueueName, NULL);
1040 if (clientCdMsgQ == NULL)
1041 {
1042 System_abort("MessageQ_create failed for RM Client - Client Delegate queue\n" );
1043 }
1044 System_printf("Core %d: RM Client MessageQ created for receiving packets from RM CD\n", MultiProc_self());
1045 }
1047 /* Open the remote message queues. Also register the RM transports with each RM instance */
1048 if (MultiProc_self() == 0)
1049 {
1050 /* Open the Client Delegate messageQ from the Server */
1051 do
1052 {
1053 status = MessageQ_open(cdServerQueueName, &serverCdQId);
1054 /*
1055 * Sleep for 1 clock tick to avoid inundating remote processor
1056 * with interrupts if open failed
1057 */
1058 if (status < 0)
1059 {
1060 Task_sleep(1);
1061 }
1062 } while (status < 0);
1063 System_printf("Core %d: RM CD MessageQ opened from RM Server\n", MultiProc_self());
1065 /* Register the Client Delegate with the RM Server Instance */
1066 rmTransportCfg.remoteInstType = Rm_instType_CLIENT_DELEGATE;
1067 rmTransportCfg.remoteInstName = &rmClientDelegateName[0];
1068 /* Set the callouts as valid for the first transport configuration on Server instance */
1069 rmTransportCfg.transportCalloutsValid = true;
1070 rmTransportCfg.transportCallouts.rmAllocPkt = TransportAlloc;
1071 rmTransportCfg.transportCallouts.rmFreePkt = TransportFree;
1072 rmTransportCfg.transportCallouts.rmSend = TransportSend;
1073 rmTransportCfg.transportCallouts.rmReceive = TransportReceive;
1074 rmTransportCfg.transportCallouts.rmNumPktsReceived = TransportNumPktsReceived;
1076 serverCdHandle = Rm_transportRegister(rmServerHandle, &rmTransportCfg);
1078 /* Store the mapping information in the transport map */
1079 rmTransportMap[SERVER_TO_CD_MAP_ENTRY].transportHandle = serverCdHandle;
1080 rmTransportMap[SERVER_TO_CD_MAP_ENTRY].receiveMsgQ = serverCdMsgQ;
1081 rmTransportMap[SERVER_TO_CD_MAP_ENTRY].remoteMsgQId = serverCdQId;
1082 System_printf("Core %d: Registered RM Server <=> RM CD transport with RM Server instance\n", MultiProc_self());
1084 }
1085 else if (MultiProc_self() == 1)
1086 {
1087 /* Open the Server messageQ from the Client Delegate */
1088 do
1089 {
1090 status = MessageQ_open(serverCdQueueName, &cdServerQId);
1091 /*
1092 * Sleep for 1 clock tick to avoid inundating remote processor
1093 * with interrupts if open failed
1094 */
1095 if (status < 0)
1096 {
1097 Task_sleep(1);
1098 }
1099 } while (status < 0);
1100 System_printf("Core %d: RM Server MessageQ opened from RM CD\n", MultiProc_self());
1102 /* Register the Server with the RM Client Delegate Instance */
1103 rmTransportCfg.remoteInstType = Rm_instType_SERVER;
1104 rmTransportCfg.remoteInstName = &rmServerName[0];
1105 /* Set the callouts as valid for the first transport configuration on Client Delegate instance */
1106 rmTransportCfg.transportCalloutsValid = true;
1107 rmTransportCfg.transportCallouts.rmAllocPkt = TransportAlloc;
1108 rmTransportCfg.transportCallouts.rmFreePkt = TransportFree;
1109 rmTransportCfg.transportCallouts.rmSend = TransportSend;
1110 rmTransportCfg.transportCallouts.rmReceive = TransportReceive;
1111 rmTransportCfg.transportCallouts.rmNumPktsReceived = TransportNumPktsReceived;
1113 cdServerHandle = Rm_transportRegister(rmClientDelegateHandle, &rmTransportCfg);
1115 /* Store the mapping information in the transport map */
1116 rmTransportMap[CD_TO_SERVER_MAP_ENTRY].transportHandle = cdServerHandle;
1117 rmTransportMap[CD_TO_SERVER_MAP_ENTRY].receiveMsgQ = cdServerMsgQ;
1118 rmTransportMap[CD_TO_SERVER_MAP_ENTRY].remoteMsgQId = cdServerQId;
1119 System_printf("Core %d: Registered RM CD <=> RM Server transport with RM CD instance\n", MultiProc_self());
1121 /* Open the Client messageQ from the Client Delegate */
1122 do
1123 {
1124 status = MessageQ_open(clientCdQueueName, &cdClientQId);
1125 /*
1126 * Sleep for 1 clock tick to avoid inundating remote processor
1127 * with interrupts if open failed
1128 */
1129 if (status < 0)
1130 {
1131 Task_sleep(1);
1132 }
1133 } while (status < 0);
1134 System_printf("Core %d: RM Client MessageQ opened from RM CD\n", MultiProc_self());
1136 /* Register the Client with the RM Client Delegate Instance */
1137 rmTransportCfg.remoteInstType = Rm_instType_CLIENT;
1138 rmTransportCfg.remoteInstName = &rmClientName[0];
1139 /* Callouts already set on the Client Delegate so set them as invalid */
1140 rmTransportCfg.transportCalloutsValid = false;
1142 cdClientHandle = Rm_transportRegister(rmClientDelegateHandle, &rmTransportCfg);
1144 /* Store the mapping information in the transport map */
1145 rmTransportMap[CD_TO_CLIENT_MAP_ENTRY].transportHandle = cdClientHandle;
1146 rmTransportMap[CD_TO_CLIENT_MAP_ENTRY].receiveMsgQ = cdClientMsgQ;
1147 rmTransportMap[CD_TO_CLIENT_MAP_ENTRY].remoteMsgQId = cdClientQId;
1148 System_printf("Core %d: Registered RM CD <=> RM Client transport with RM CD instance\n", MultiProc_self());
1150 /* Open the Client Delegate messageQ from the Client */
1151 do
1152 {
1153 status = MessageQ_open(cdClientQueueName, &clientCdQId);
1154 /*
1155 * Sleep for 1 clock tick to avoid inundating remote processor
1156 * with interrupts if open failed
1157 */
1158 if (status < 0)
1159 {
1160 Task_sleep(1);
1161 }
1162 } while (status < 0);
1163 System_printf("Core %d: RM CD MessageQ opened from RM Client\n", MultiProc_self());
1165 /* Register the Client Delegate with the RM Client Instance */
1166 rmTransportCfg.remoteInstType = Rm_instType_CLIENT_DELEGATE;
1167 rmTransportCfg.remoteInstName = &rmClientDelegateName[0];
1168 /* Set the callouts as valid for the first transport configuration on Client instance */
1169 rmTransportCfg.transportCalloutsValid = true;
1170 rmTransportCfg.transportCallouts.rmAllocPkt = TransportAlloc;
1171 rmTransportCfg.transportCallouts.rmFreePkt = TransportFree;
1172 rmTransportCfg.transportCallouts.rmSend = TransportSend;
1173 rmTransportCfg.transportCallouts.rmReceive = TransportReceive;
1174 rmTransportCfg.transportCallouts.rmNumPktsReceived = TransportNumPktsReceived;
1176 clientCdHandle = Rm_transportRegister(rmClientHandle, &rmTransportCfg);
1178 /* Store the mapping information in the transport map */
1179 rmTransportMap[CLIENT_TO_CD_MAP_ENTRY].transportHandle = clientCdHandle;
1180 rmTransportMap[CLIENT_TO_CD_MAP_ENTRY].receiveMsgQ = clientCdMsgQ;
1181 rmTransportMap[CLIENT_TO_CD_MAP_ENTRY].remoteMsgQId = clientCdQId;
1182 System_printf("Core %d: Registered RM Client <=> RM CD transport with RM Client instance\n", MultiProc_self());
1183 }
1185 /* Creat the RM receive task. */
1186 System_printf("Core %d: Creating RM receive task...\n", MultiProc_self());
1187 Task_Params_init (&taskParams);
1188 testReceiveTskHandle = Task_create (testReceiveTsk, &taskParams, NULL);
1191 /* Create the RM test task. */
1192 System_printf("Core %d: Creating RM test task...\n", MultiProc_self());
1193 Task_Params_init (&taskParams);
1194 testRmTskHandle = Task_create (testRmTsk, &taskParams, NULL);
1195 }
1197 /*
1198 * ======== main ========
1199 * Synchronizes all processors (in Ipc_start) and calls BIOS_start
1200 */
1201 Int main(Int argc, Char* argv[])
1202 {
1203 Rm_InitCfg rmInitCfg;
1204 Task_Params taskParams;
1205 FILE *globalResourceFp;
1206 FILE *linuxDtbFp;
1207 FILE *globalPolicyFp;
1208 Int globalResourceFileSize;
1209 Int linuxDtbFileSize;
1210 Int globalPolicyFileSize;
1211 void *globalResourceList = NULL;
1212 void *linuxDtb = NULL;
1213 void *globalPolicy = NULL;
1214 Int status;
1215 Int readSize;
1217 System_printf ("*********************************************************\n");
1218 System_printf ("********************** RM Testing ***********************\n");
1219 System_printf ("*********************************************************\n");
1221 System_printf ("RM Version : 0x%08x\nVersion String: %s\n", Rm_getVersion(), Rm_getVersionStr());
1223 /* Initialize the RM instances - RM must be initialized before anything else in the system
1224 * Core 0: 1 RM Instance - RM Server
1225 * Core 1: 2 RM Instances - RM Client Delegate
1226 * RM Client
1227 */
1228 if (MultiProc_self()== 0)
1229 {
1230 initSyncObj();
1232 /* Open the Global Resource and Policy DTB files */
1233 globalResourceFp = fopen("C:\\ti\\pdk_tci6614_1_0_0_11\\packages\\ti\\drv\\rm\\device\\tci6614-global-resources.dtb", "rb");
1234 linuxDtbFp = fopen("C:\\ti\\pdk_tci6614_1_0_0_11\\packages\\ti\\drv\\rm\\device\\tci6614-linux-evm.dtb", "rb");
1235 globalPolicyFp = fopen("C:\\ti\\pdk_tci6614_1_0_0_11\\packages\\ti\\drv\\rm\\device\\tci6614-server-policy.dtb", "rb");
1237 /* Get the size of the Global Resource List, Linux DTB, and Global Policy */
1238 fseek(globalResourceFp, 0, SEEK_END);
1239 globalResourceFileSize = ftell(globalResourceFp);
1240 rewind(globalResourceFp);
1242 fseek(linuxDtbFp, 0, SEEK_END);
1243 linuxDtbFileSize = ftell(linuxDtbFp);
1244 rewind(linuxDtbFp);
1246 fseek(globalPolicyFp, 0, SEEK_END);
1247 globalPolicyFileSize = ftell(globalPolicyFp);
1248 rewind(globalPolicyFp);
1250 /* Allocate buffers to hold the Global Resource List, Linux DTB, and Global Policy */
1251 globalResourceList = Osal_rmMalloc(globalResourceFileSize);
1252 linuxDtb = Osal_rmMalloc(linuxDtbFileSize);
1253 globalPolicy = Osal_rmMalloc(globalPolicyFileSize);
1255 /* Read the file data into the allocated buffers */
1256 readSize = fread(globalResourceList, 1, globalResourceFileSize, globalResourceFp);
1257 System_printf("Read Size compared to file size: %d : %d\n", readSize, globalResourceFileSize);
1258 readSize = fread(linuxDtb, 1, linuxDtbFileSize, linuxDtbFp);
1259 System_printf("Read Size compared to file size: %d : %d\n", readSize, linuxDtbFileSize);
1260 readSize = fread(globalPolicy, 1, globalPolicyFileSize, globalPolicyFp);
1261 System_printf("Read Size compared to file size: %d : %d\n", readSize, globalPolicyFileSize);
1263 /* Create the RM Server instance */
1264 rmInitCfg.instName = &rmServerName[0];
1265 rmInitCfg.instType = Rm_instType_SERVER;
1266 /* Provide the DTBs to the RM Server */
1267 rmInitCfg.globalResourceList = globalResourceList;
1268 rmInitCfg.linuxDtb = linuxDtb;
1269 rmInitCfg.policy = globalPolicy;
1271 /* Get the RM Server handle */
1272 rmServerHandle = Rm_init(&rmInitCfg);
1273 System_printf("Core %d: RM Server instance created\n", MultiProc_self());
1275 Rm_printResourceStatus(rmServerHandle);
1276 }
1277 else if (MultiProc_self()== 1)
1278 {
1279 /* Create the RM Client Delegate instance */
1280 rmInitCfg.instName = &rmClientDelegateName[0];
1281 rmInitCfg.instType = Rm_instType_CLIENT_DELEGATE;
1282 /* SET TO NULL - FEATURES NOT ADDED YET */
1283 rmInitCfg.globalResourceList = NULL;
1284 rmInitCfg.policy = NULL;
1286 /* Get the RM Client Delegate handle */
1287 rmClientDelegateHandle = Rm_init(&rmInitCfg);
1288 System_printf("Core %d: RM Client Delegate instance created\n", MultiProc_self());
1290 /* Create the RM Client instance */
1291 rmInitCfg.instName = &rmClientName[0];
1292 rmInitCfg.instType = Rm_instType_CLIENT;
1293 /* SET TO NULL - FEATURES NOT ADDED YET */
1294 rmInitCfg.globalResourceList = NULL;
1295 rmInitCfg.policy = NULL;
1297 /* Get the RM Client handle */
1298 rmClientHandle = Rm_init(&rmInitCfg);
1299 System_printf("Core %d: RM Client instance created\n", MultiProc_self());
1300 }
1302 /*
1303 * Ipc_start() calls Ipc_attach() to synchronize all remote processors
1304 * because 'Ipc.procSync' is set to 'Ipc.ProcSync_ALL' in *.cfg
1305 */
1306 System_printf("Core %d: Starting IPC...\n", MultiProc_self());
1307 status = Ipc_start();
1308 if (status < 0)
1309 {
1310 System_abort("Ipc_start failed\n");
1311 }
1313 /* Create the RM startup task */
1314 System_printf("Core %d: Creating RM startup task...\n", MultiProc_self());
1315 Task_Params_init (&taskParams);
1316 startupRmTskHandle = Task_create (startupRmTsk, &taskParams, NULL);
1318 System_printf("Core %d: Starting BIOS...\n", MultiProc_self());
1319 BIOS_start();
1321 return (0);
1322 }