/*! * ======== InterruptDsp_intPost ======== */ Void InterruptDsp_intPost(UInt16 srcProcId, IInterrupt_IntInfo *intInfo, UArg arg) { UInt key; UInt16 index; index = MBX_TABLE_IDX(srcProcId, MultiProc_self()); key = Hwi_disable(); if (REG32(MAILBOX_STATUS(index)) == 0) { REG32(MAILBOX_MESSAGE(index)) = arg; } Hwi_restore(key); }
/* * ======== Notify_unregisterEventSingle ======== */ Int Notify_unregisterEventSingle(UInt16 procId, UInt16 lineId, UInt32 eventId) { UInt32 strippedEventId = (eventId & 0xFFFF); UInt16 clusterId = ti_sdo_utils_MultiProc_getClusterId(procId); Int status; ti_sdo_ipc_Notify_Object *obj; UInt modKey; Assert_isTrue(procId < ti_sdo_utils_MultiProc_numProcessors && lineId < ti_sdo_ipc_Notify_numLines, ti_sdo_ipc_Notify_A_invArgument); Assert_isTrue(strippedEventId < ti_sdo_ipc_Notify_numEvents, ti_sdo_ipc_Notify_A_invArgument); Assert_isTrue(ISRESERVED(eventId), ti_sdo_ipc_Notify_A_reservedEvent); modKey = Gate_enterModule(); obj = (ti_sdo_ipc_Notify_Object *) Notify_module->notifyHandles[clusterId][lineId]; Assert_isTrue(obj != NULL, ti_sdo_ipc_Notify_A_notRegistered); if (obj->callbacks[strippedEventId].fnNotifyCbck) { if (procId != MultiProc_self()) { /* * First, Tell the remote notify driver that the event is now * unregistered */ INotifyDriver_unregisterEvent(obj->driverHandle, strippedEventId); } /* * No need to protect these modifications with the system gate because * we shouldn't get preempted by Notify_exec after INotifyDriver_ * unregisterEvent. */ obj->callbacks[strippedEventId].fnNotifyCbck = NULL; obj->callbacks[strippedEventId].cbckArg = NULL; status = Notify_S_SUCCESS; } else { /* No callback is registered. Fail. */ status = Notify_E_FAIL; } Gate_leaveModule(modKey); return (status); }
/* * ======== SemaphoreMP_post ======== */ Void SemaphoreMP_post(SemaphoreMP_Object *obj) { UInt tskKey; SemaphoreMP_PendElem *elem; IArg gateMPKey; Int status; /* Enter the gate */ gateMPKey = GateMP_enter((GateMP_Handle)obj->gate); if (ListMP_empty((ListMP_Handle)obj->pendQ)) { if (obj->mode == SemaphoreMP_Mode_BINARY) { obj->attrs->count = 1; } else { obj->attrs->count++; } if (obj->cacheEnabled) { Cache_wbInv(obj->attrs, sizeof(SemaphoreMP_Attrs), Cache_Type_ALL, TRUE); } /* Leave the gate */ GateMP_leave((GateMP_Handle)obj->gate, gateMPKey); return; } /* lock task scheduler */ tskKey = Task_disable(); /* dequeue tsk from semaphore queue */ elem = (SemaphoreMP_PendElem *)ListMP_getHead((ListMP_Handle)obj->pendQ); if (elem->procId != MultiProc_self()) { /* Unblock remote task */ status = Notify_sendEvent(elem->procId, 0, SemaphoreMP_notifyEventId, elem->task, TRUE); Assert_isTrue(status >= 0, ti_sdo_ipc_Ipc_A_internal); } else { /* put task back into readyQ */ Task_unblock((Task_Handle)elem->task); } /* Leave the gate */ GateMP_leave((GateMP_Handle)obj->gate, gateMPKey); Task_restore(tskKey); }
/* * ======== main ======== * Synchronizes all processors (in Ipc_start) and calls BIOS_start */ Int main(Int argc, Char* argv[]) { Int status; nextProcId = (MultiProc_self() + 1) % MultiProc_getNumProcessors(); /* Generate queue names based on own proc ID and total number of procs */ System_sprintf(localQueueName, "%s", MultiProc_getName(MultiProc_self())); System_sprintf(nextQueueName, "%s", MultiProc_getName(nextProcId)); /* * Ipc_start() calls Ipc_attach() to synchronize all remote processors * because 'Ipc.procSync' is set to 'Ipc.ProcSync_ALL' in *.cfg */ status = Ipc_start(); if (status < 0) { System_abort("Ipc_start failed\n"); } BIOS_start(); return (0); }
/* * ======== Notify_registerEventSingle ======== */ Int Notify_registerEventSingle(UInt16 procId, UInt16 lineId, UInt32 eventId, Notify_FnNotifyCbck fnNotifyCbck, UArg cbckArg) { UInt32 strippedEventId = (eventId & 0xFFFF); UInt16 clusterId = ti_sdo_utils_MultiProc_getClusterId(procId); UInt modKey; Int status; ti_sdo_ipc_Notify_Object *obj; Assert_isTrue(procId < ti_sdo_utils_MultiProc_numProcessors && lineId < ti_sdo_ipc_Notify_numLines, ti_sdo_ipc_Notify_A_invArgument); Assert_isTrue(strippedEventId < ti_sdo_ipc_Notify_numEvents, ti_sdo_ipc_Notify_A_invArgument); Assert_isTrue(ISRESERVED(eventId), ti_sdo_ipc_Notify_A_reservedEvent); modKey = Gate_enterModule(); obj = (ti_sdo_ipc_Notify_Object *) Notify_module->notifyHandles[clusterId][lineId]; Assert_isTrue(obj != NULL, ti_sdo_ipc_Notify_A_notRegistered); if (obj->callbacks[strippedEventId].fnNotifyCbck) { /* A callback is already registered. Fail. */ status = Notify_E_ALREADYEXISTS; } else { /* * No callback is registered. Register it. There is no need to protect * these modifications because the event isn't registered yet. */ obj->callbacks[strippedEventId].fnNotifyCbck = (Fxn)fnNotifyCbck; obj->callbacks[strippedEventId].cbckArg = cbckArg; if (procId != MultiProc_self()) { /* Tell the remote notify driver that the event is now registered */ INotifyDriver_registerEvent(obj->driverHandle, strippedEventId); } status = Notify_S_SUCCESS; } Gate_leaveModule(modKey); return (status); }
Void FirmwareLoad_printStatus (Void) { Int status = 0; ProcMgr_Handle handle = NULL; UInt16 numProcs; UInt16 i; ProcMgr_State state; Char strState [32u]; printf ("Current status of slave cores:\n"); numProcs = MultiProc_getNumProcessors (); for (i = 0 ; (i < numProcs) && (i != MultiProc_self ()) ; i++) { { status = ProcMgr_open (&handle, i); if (status >= 0) { state = ProcMgr_getState (handle); switch (state) { case ProcMgr_State_Unknown: strncpy (strState, "Unknown", 32u); break; case ProcMgr_State_Powered: strncpy (strState, "Powered", 32u); break; case ProcMgr_State_Reset: strncpy (strState, "Reset", 32u); break; case ProcMgr_State_Loaded: strncpy (strState, "Loaded", 32u); break; case ProcMgr_State_Running: strncpy (strState, "Running", 32u); break; case ProcMgr_State_Unavailable: strncpy (strState, "Unavailable", 32u); break; case ProcMgr_State_EndValue: /* Not a valid value. */ break; } printf ("Slave core %d: %8s [%s]\n", i, MultiProc_getName (i), strState); status = ProcMgr_close (&handle); } } } }
/** * Cache invalidate the total image memory (happens after the main core zeroizes all memory (at boot time and after/between the calculations) */ void CacheInvalTotalMemory(process_message_t* p_msg) { if (0 != MultiProc_self()) { #ifdef _TRACE_MC_ logout("[core_%u] CACHE INVALIDATE ZEROIZRD DATA ON SLAVE CORE (T %u bytes, R %u bytes)\n", p_msg->core_id, p_msg->info.Tsize, p_msg->info.Rsize); #endif Cache_inv((xdc_Ptr*) p_msg->info.Tvec, p_msg->info.Tsize , Cache_Type_ALL, CACHE_BLOCKING); } else { #ifdef _TRACE_MC_ //The following shouldn't happen ... logout("[core_%u] CACHE INVALIDATE ZEROIZRD DATA SKIPPED ON MAIN CORE (T %u bytes, R %u bytes)\n", p_msg->core_id, p_msg->info.Tsize, p_msg->info.Rsize); #endif } }
/*! * ======== InterruptDsp_intClear ======== * Clear interrupt */ UInt InterruptDsp_intClear(UInt16 remoteProcId, IInterrupt_IntInfo *intInfo) { UInt arg; UInt16 index; index = MBX_TABLE_IDX(remoteProcId, MultiProc_self()); arg = REG32(MAILBOX_MESSAGE(index)); REG32(MAILBOX_IRQSTATUS_CLR_DSP(index)) = MAILBOX_REG_VAL(SUBMBX_IDX(index)); /* Write to EOI (End Of Interrupt) register */ REG32(MAILBOX_EOI_REG(index)) = 0x1; return (arg); }
/* * ======== tsk0_func ======== * This function is executed only on CORE0. * It sends an event to the next processor then pends on a semaphore. * The semaphore is posted by the callback function. */ Void tsk0_func(UArg arg0, UArg arg1) { Int status; /* Send an event to the next processor */ if (MultiProc_self() == 0) { rawtimestamps[seq++] = Timestamp_get32(); status = Notify_sendEvent(dstProc, INTERRUPT_LINE, EVENTID, NULL, TRUE); if (status < 0) { System_abort("Notify_sendEvent failed\n"); } } Task_exit(); }
/* * ======== ti_sdo_ipc_Ipc_getSlaveAddr ======== */ Ptr ti_sdo_ipc_Ipc_getSlaveAddr(UInt16 remoteProcId, Ptr sharedAddr) { Int slot; UInt16 slaveId; volatile ti_sdo_ipc_Ipc_Reserved *slave; SizeT reservedSize = ti_sdo_ipc_Ipc_reservedSizePerProc(); /* determine the slave's procId and slot */ if (MultiProc_self() < remoteProcId) { slaveId = ti_sdo_utils_MultiProc_getClusterId(MultiProc_self()); slot = ti_sdo_utils_MultiProc_getClusterId(remoteProcId) - 1; } else { slaveId = ti_sdo_utils_MultiProc_getClusterId(remoteProcId); slot = ti_sdo_utils_MultiProc_getClusterId(MultiProc_self()) - 1; } /* determine the reserve address for slave between self and remote */ slave = (ti_sdo_ipc_Ipc_Reserved *)((UInt32)sharedAddr + ((slaveId * reservedSize) + (slot * sizeof(ti_sdo_ipc_Ipc_Reserved)))); return ((Ptr)slave); }
/* * ======== Ipc_isAttached ======== */ Bool Ipc_isAttached(UInt16 remoteProcId) { UInt16 clusterId = ti_sdo_utils_MultiProc_getClusterId(remoteProcId); /* Assert remoteProcId is in our cluster */ Assert_isTrue(clusterId < ti_sdo_utils_MultiProc_numProcsInCluster, ti_sdo_utils_MultiProc_A_invalidMultiProcId); if (remoteProcId == MultiProc_self()) { return (FALSE); } else { return (Ipc_module->procEntry[clusterId].attached); } }
/* * ======== Notify_numIntLines ======== */ UInt16 Notify_numIntLines(UInt16 procId) { UInt16 numIntLines; if (MultiProc_self() == procId) { /* There is always a single interrupt line to the loopback instance */ numIntLines = 1; } else { /* Query the NotifySetup module for the device */ numIntLines = ti_sdo_ipc_Notify_SetupProxy_numIntLines(procId); } return (numIntLines); }
/* ************************************************************************* * Instance functions ************************************************************************* */ Void NameServerMessageQ_Instance_init(NameServerMessageQ_Object *obj, UInt16 remoteProcId, const NameServerMessageQ_Params *params) { /* Assert that remoteProcId is valid */ Assert_isTrue(remoteProcId != MultiProc_self() && remoteProcId != MultiProc_INVALIDID, Ipc_A_invParam); obj->remoteProcId = remoteProcId; /* register the remote driver with NameServer */ ti_sdo_utils_NameServer_registerRemoteDriver( NameServerMessageQ_Handle_upCast(obj), remoteProcId); }
/* * ======== ti_sdo_ipc_Ipc_getMasterAddr ======== */ Ptr ti_sdo_ipc_Ipc_getMasterAddr(UInt16 remoteProcId, Ptr sharedAddr) { Int slot; UInt16 masterId; volatile ti_sdo_ipc_Ipc_Reserved *master; SizeT reservedSize = ti_sdo_ipc_Ipc_reservedSizePerProc(); /* determine the master's procId and slot */ if (MultiProc_self() < remoteProcId) { masterId = ti_sdo_utils_MultiProc_getClusterId(remoteProcId); slot = ti_sdo_utils_MultiProc_getClusterId(MultiProc_self()); } else { masterId = ti_sdo_utils_MultiProc_getClusterId(MultiProc_self()); slot = ti_sdo_utils_MultiProc_getClusterId(remoteProcId); } /* determine the reserve address for master between self and remote */ master = (ti_sdo_ipc_Ipc_Reserved *)((UInt32)sharedAddr + ((masterId * reservedSize) + (slot * sizeof(ti_sdo_ipc_Ipc_Reserved)))); return ((Ptr)master); }
/*! * ======== InterruptArp32_intRegister ======== */ Void InterruptArp32_intRegister(UInt16 remoteProcId, IInterrupt_IntInfo *intInfo, Fxn func, UArg arg) { UInt key; Hwi_Params hwiAttrs; Error_Block eb; InterruptArp32_FxnTable *table; Assert_isTrue(remoteProcId < ti_sdo_utils_MultiProc_numProcessors, ti_sdo_ipc_Ipc_A_internal); /* Assert that our MultiProc id is set correctly */ Assert_isTrue((InterruptArp32_arp32ProcId == MultiProc_self()), ti_sdo_ipc_Ipc_A_internal); /* init error block */ Error_init(&eb); /* Disable global interrupts */ key = Hwi_disable(); table = &(InterruptArp32_module->fxnTable); table->func = func; table->arg = arg; InterruptArp32_intClear(remoteProcId, intInfo); /* Make sure the interrupt only gets plugged once */ InterruptArp32_module->numPlugged++; if (InterruptArp32_module->numPlugged == 1) { /* Register interrupt to remote processor */ Hwi_Params_init(&hwiAttrs); hwiAttrs.arg = arg; hwiAttrs.vectorNum = intInfo->intVectorId; Hwi_create(ARP32INT, (Hwi_FuncPtr)InterruptArp32_intShmStub, &hwiAttrs, &eb); } /* enable the mailbox and Hwi */ InterruptArp32_intEnable(remoteProcId, intInfo); /* Restore global interrupts */ Hwi_restore(key); }
Int main(Int argc, char* argv[]) { Task_Params params; System_printf("%s starting..\n", MultiProc_getName(MultiProc_self())); /* Create a Task to respond to the ping from the Host side */ Task_Params_init(¶ms); params.instance->name = "ping"; params.arg0 = 51; Task_create(pingTaskFxn, ¶ms, NULL); BIOS_start(); return (0); }
/* * ======== MessageQ_msgInit ======== * This is a helper function to initialize a message. */ static Void MessageQ_msgInit(MessageQ_Msg msg) { UInt key; msg->replyId = (UInt16)MessageQ_INVALIDMESSAGEQ; msg->msgId = MessageQ_INVALIDMSGID; msg->dstId = (UInt16)MessageQ_INVALIDMESSAGEQ; msg->flags = ti_sdo_ipc_MessageQ_HEADERVERSION | MessageQ_NORMALPRI | (ti_sdo_ipc_MessageQ_TRACEMASK & (ti_sdo_ipc_MessageQ_traceFlag << ti_sdo_ipc_MessageQ_TRACESHIFT)); msg->srcProc = MultiProc_self(); key = Hwi_disable(); msg->seqNum = MessageQ_module->seqNum++; Hwi_restore(key); }
/** * Cache invalidate image data if necessary */ void CacheInvalImageData(process_message_t* p_msg) { if(0 != p_msg->info.NewImageDataArrived) { if (0 != MultiProc_self()) { #ifdef _TRACE_MC_ logout("[core_%u] CACHE INVALIDATE IMAGE DATA ON SLAVE CORE (T %u bytes, R %u bytes)\n", p_msg->core_id, p_msg->info.Tsize, p_msg->info.Rsize); #endif Cache_inv((xdc_Ptr*) p_msg->info.Tvec, p_msg->info.Tsize , Cache_Type_ALL, CACHE_BLOCKING); Cache_inv((xdc_Ptr*) p_msg->info.Rvec, p_msg->info.Rsize , Cache_Type_ALL, CACHE_BLOCKING); } else { #ifdef _TRACE_MC_ logout("[core_%u] CACHE INVALIDATE SKIPPED ON MAIN CORE (T %u bytes, R %u bytes)\n", p_msg->core_id, p_msg->info.Tsize, p_msg->info.Rsize); #endif } } }
/* * ======== IpcMgr_rpmsgStartup ======== * Initialize the RPMSG module. This calls VirtQueue_startup(). * * Use for stacks built on RPMessage only. */ Void IpcMgr_rpmsgStartup(Void) { Assert_isTrue(MultiProc_self() != MultiProc_getId("HOST"), NULL); RPMessage_init(MultiProc_getId("HOST")); #ifdef IpcMgr_USEDEH /* * When using DEH, initialize the Watchdog timers if not already done * (i.e. late-attach) */ #ifdef IpcMgr_DSP Watchdog_init((Void (*)(Void))ti_sysbios_family_c64p_Exception_handler); #elif IpcMgr_IPU Watchdog_init(ti_sysbios_family_arm_m3_Hwi_excHandlerAsm__I); #endif #endif }
/** * Public, called from shrinkImageDSP (on the main core) after entering shrinkImage_on_core() */ void CacheInvalReadyShrinkedData(const uint8_T *ImgSmall, const uint32_t yStart, const uint32_t yEnd, const uint32_t xWidthSmall) { #ifdef _NO_IPC_TEST_ if (0 == MultiProc_self()) //skip on main core return; #else //ASSERT(0 == MultiProc_self()); #endif #if 0 //Invalidate the output cache, we need the data the other cores wrote to. uint8_T* out_buf_start; uint32_T out_buf_size; CalcOutputBufferPos(ImgSmall, yStart, yEnd, xWidthSmall, out_buf_start, out_buf_size); Cache_inv((xdc_Ptr*) out_buf_start, out_buf_size, Cache_Type_ALL, CACHE_BLOCKING); //Blocking because we will process the data immediately #endif }
/*! * ======== InterruptArp32_intPost ======== * Simulate an interrupt from a remote processor */ Void InterruptArp32_intPost(UInt16 srcProcId, IInterrupt_IntInfo *intInfo, UArg arg) { UInt key; UInt16 index; index = MBX_TABLE_IDX(srcProcId, MultiProc_self()); /* disable interrupts */ key = Hwi_disable(); if (REG32(MAILBOX_STATUS(index)) == 0) { /* write the mailbox message to arp32 */ REG32(MAILBOX_MESSAGE(index)) = arg; } /* restore interrupts */ Hwi_restore(key); }
/* * ======== main ======== */ Int main(Int argc, Char* argv[]) { Task_Params params; Int i; System_printf("%s:main: MultiProc id = %d\n", __FILE__, MultiProc_self()); /* Create N threads to correspond with host side N thread test app: */ Task_Params_init(¶ms); params.priority = 3; for (i = 0; i < NUMTHREADS; i++) { params.arg0 = i; Task_create(loopbackFxn, ¶ms, NULL); } BIOS_start(); return (0); }
/*! * @brief Function to perform device specific destroy for Notify module. * This function deletes the Notify drivers. * * @sa NotifyCircSetupDm8168_attach */ Int NotifyCircSetupDm8168_detach (UInt16 procId) { Int32 status = Notify_S_SUCCESS; Int32 tmpStatus = Notify_S_SUCCESS; GT_0trace (curTrace, GT_ENTER, "NotifyCircSetupDm8168_detach"); GT_assert (curTrace, (procId != MultiProc_self ())); /* * Delete the notify driver to the DSP (Line 0) */ status = Notify_delete (&(NotifyCircSetup_notifyHandle [procId])); #if !defined(SYSLINK_BUILD_OPTIMIZE) if (status < 0) { GT_setFailureReason (curTrace, GT_4CLASS, "NotifyCircSetupDm8168_detach", status, "Notify_delete failed for line 0"); } #endif /* if !defined(SYSLINK_BUILD_OPTIMIZE) */ tmpStatus = NotifyDriverCirc_delete ( &(NotifyCircSetup_driverHandle [procId])); #if !defined(SYSLINK_BUILD_OPTIMIZE) if ((tmpStatus < 0) && (status >= 0)) { status = tmpStatus; GT_setFailureReason (curTrace, GT_4CLASS, "NotifyCircSetupDm8168_detach", status, "NotifyDriverCirc_delete failed for line 0"); } #endif /* if !defined(SYSLINK_BUILD_OPTIMIZE) */ GT_1trace (curTrace, GT_LEAVE, "NotifyCircSetupDm8168_detach", status); /*! @retval Notify_S_SUCCESS Operation successful */ return (status); }
/* * ======== Interrupt_Module_startup ======== */ Int Interrupt_Module_startup(Int phase) { volatile UInt32 *kick0 = (volatile UInt32 *)Interrupt_KICK0; volatile UInt32 *kick1 = (volatile UInt32 *)Interrupt_KICK1; UInt16 procId = MultiProc_self(); /* * If this assert fails, the MultiProc config has changed to break * an assumption in Linux rpmsg driver, that HOST is listed first in * MultiProc ID configuration. */ Assert_isTrue(0 == MultiProc_getId("HOST"), NULL); /* * Wait for Startup to be done (if MultiProc id not yet set) because a * user fxn should set it */ if (!Startup_Module_startupDone() && procId == MultiProc_INVALIDID) { return (Startup_NOTDONE); } if (!Interrupt_enableKick) { /* Do not unlock the kick registers */ return (Startup_DONE); } /* * Only write to the KICK registers if: * - This core is the SR0 owner * - There is no SR0 and this core has procId '1' (IPC 3.x: this case). */ /* TODO: What if CORE0 is not started, but the others are? */ if (DNUM == 0) { if (Interrupt_KICK0 && Interrupt_KICK1){ /* unlock the KICK mechanism in the Bootcfg MMRs if defined */ kick0[0] = 0x83e70b13; /* must be written with this value */ kick1[0] = 0x95a4f1e0; /* must be written with this value */ } } return (Startup_DONE); }
/*! * ======== VirtQueue_startup ======== */ Void VirtQueue_startup() { hostProcId = MultiProc_getId("HOST"); #ifndef SMP dspProcId = MultiProc_getId("DSP"); sysm3ProcId = MultiProc_getId("CORE0"); appm3ProcId = MultiProc_getId("CORE1"); #endif /* Initilize the IpcPower module */ IpcPower_init(); #if defined(M3_ONLY) && !defined(SMP) if (MultiProc_self() == sysm3ProcId) { OffloadM3_init(); } #endif InterruptProxy_intRegister(VirtQueue_isr); }
/*! * ======== NotifySetup_sharedMemReq ======== */ SizeT NotifySetup_sharedMemReq(UInt16 remoteProcId, Ptr sharedAddr) { SizeT memReq; NotifyDriverShm_Params notifyShmParams; UInt16 myId = MultiProc_self(); NotifyDriverShm_Params_init(¬ifyShmParams); notifyShmParams.sharedAddr = sharedAddr; /* Disable cache for inter-ducati NotifyDriverShm instances */ if ((myId == NotifySetup_core1ProcId && remoteProcId == NotifySetup_core0ProcId) || (myId == NotifySetup_core0ProcId && remoteProcId == NotifySetup_core1ProcId)) { notifyShmParams.cacheLineSize = 0; notifyShmParams.cacheEnabled = FALSE; } memReq = NotifyDriverShm_sharedMemReq(¬ifyShmParams); return (memReq); }
/* * ======== ti_sdo_ipc_Notify_Module_startup ======== */ Int ti_sdo_ipc_Notify_Module_startup(Int phase) { UInt16 procId = MultiProc_self(); /* * Wait for Startup to be done (if MultiProc id not yet set) because a * user fxn may set it */ if (!Startup_Module_startupDone() && procId == MultiProc_INVALIDID) { return (Startup_NOTDONE); } /* Ensure that the MultiProc ID has been configured */ Assert_isTrue(procId != MultiProc_INVALIDID, ti_sdo_utils_MultiProc_A_invalidMultiProcId); /* Create a local instance */ ti_sdo_ipc_Notify_create(NULL, procId, 0, NULL, NULL); return (Startup_DONE); }
/*! * ======== NotifySetup_attach ======== * Initialize interrupt */ Int NotifySetup_attach(UInt16 remoteProcId, Ptr sharedAddr) { NotifyDriverShm_Params notifyShmParams; NotifyDriverShm_Handle shmDrvHandle; ti_sdo_ipc_Notify_Handle notifyHandle; Int status = Notify_S_SUCCESS; Error_Block eb; Error_init(&eb); NotifyDriverShm_Params_init(¬ifyShmParams); notifyShmParams.sharedAddr = sharedAddr; notifyShmParams.remoteProcId = remoteProcId; /* Set the intVectorId if on the DSP */ if ((MultiProc_self() == NotifySetup_dsp0ProcId) || (MultiProc_self() == NotifySetup_dsp1ProcId)) { notifyShmParams.intVectorId = NotifySetup_dspIntVectId; } /* Set the intVectorId if on the EVE */ if ((MultiProc_self() == NotifySetup_eve0ProcId) || (MultiProc_self() == NotifySetup_eve1ProcId) || (MultiProc_self() == NotifySetup_eve2ProcId) || (MultiProc_self() == NotifySetup_eve3ProcId)) { if (PROCID(remoteProcId) < 4) { notifyShmParams.intVectorId = NotifySetup_eveIntVectId_INTC1; } else { notifyShmParams.intVectorId = NotifySetup_eveIntVectId_INTC0; } } shmDrvHandle = NotifyDriverShm_create(¬ifyShmParams, &eb); if (shmDrvHandle == NULL) { return (Notify_E_FAIL); } notifyHandle = ti_sdo_ipc_Notify_create( NotifyDriverShm_Handle_upCast(shmDrvHandle), remoteProcId, 0, NULL, &eb); if (notifyHandle == NULL) { NotifyDriverShm_delete(&shmDrvHandle); status = Notify_E_FAIL; } return (status); }
/* * ======== MultiProc_setLocalId ======== */ Int MultiProc_setLocalId(UInt16 id) { /* id must be less than the number of processors */ Assert_isTrue((id < ti_sdo_utils_MultiProc_numProcessors), ti_sdo_utils_MultiProc_A_invalidMultiProcId); /* * Check the following * 1. Make sure the statically configured constant was invalid. * To call setLocalId, the id must have been set to invalid. * 2. Make sure the call is made before module startup */ if ((MultiProc_self() == MultiProc_INVALIDID) && (Startup_rtsDone() == FALSE)) { /* It is ok to set the id */ MultiProc_module->id = id; return (MultiProc_S_SUCCESS); } return (MultiProc_E_FAIL); }
/*! * ======== MultiProcSetup_init ======== */ Void MultiProcSetup_init() { extern cregister volatile UInt DNUM; UInt16 procId; /* Skip if the procId has already been set */ if (MultiProc_self() != MultiProc_INVALIDID) { return; } procId = MultiProcSetup_getProcId(DNUM); /* * Assert that image is being loaded onto a core that was included in the * MultiProc name list (via setConfig) */ Assert_isTrue(procId != MultiProc_INVALIDID, MultiProcSetup_A_invalidProcessor); /* Set the local ID */ MultiProc_setLocalId(procId); }