📄 prcmgr.c
字号:
}/* Start in-process subtask*/LOCAL WER _tkse_sta_tsk(ID id, W arg){ ER err; Lock(&ProcMgrLock); /* Start task */ err = tk_sta_tsk(id, arg); Unlock(&ProcMgrLock); return err;}/* Terminate in-process task*/LOCAL void _tkse_ext_tsk(void){ PINFO *pi; Lock(&ProcMgrLock); if ( GetPidToPinfo(0, &pi) < E_OK ) { Unlock(&ProcMgrLock); SYSLOG((LOG_ERR, "tkse_ext_tsk() in Not Process")); syslog_wait(); if ( _isDebugMode() != 0 ) { tm_monitor(); } tk_exd_tsk(); } else { KillTasks(pi, GetMyTid(), 0, 0); /* Terminate task */ ExitTask(pi, TSK_SELF); /* No Return */ }}/* Forced termination of in-process task*/LOCAL ER _tkse_ter_tsk(ID tid){ PINFO *pi; W i; ER err = E_OK; pi = GetPinfo(TSK_SELF); if ((pi == NULL ) ||( tid <= 0 )||( tid == GetMyTid() )) { return E_ID; } Lock(&ProcMgrLock); /* OK if task is included in current process, except for main task. */ for ( i = 1; i < MAX_SUBTASKS; ++i ) { if ( pi->tsk[i].tskid == tid ) { break; } } if ( i < MAX_SUBTASKS ) { /* Forced termination request * PINFO must not be locked, * otherwise the break handler is called. */ tk_ras_tex(tid, 0); } else { err = E_ID; } Unlock(&ProcMgrLock); return err;}/* Wait of in-process task*/LOCAL ER _tkse_dly_tsk(RELTIM dlytim){ return ( dlytim > 0U )? tk_dly_tsk(dlytim): tk_rot_rdq(TPRI_RUN);}/* Sleep of in-process task*/LOCAL ER _tkse_slp_tsk(TMO tmout){ return tk_slp_tsk(tmout);}/* Wakeup of in-process task*/LOCAL ER _tkse_wup_tsk(ID tid){ ER err; Lock(&ProcMgrLock); err = (CheckSubTask(tid) != 0) ? tk_wup_tsk(tid) : E_ID; Unlock(&ProcMgrLock); return err;}/* Cancel wakeup request of in-process task*/LOCAL WER _tkse_can_wup(ID tid){ ER err; Lock(&ProcMgrLock); err = (CheckSubTask(tid) != 0) ? tk_can_wup(tid) : E_ID; Unlock(&ProcMgrLock); return err;}/* Fetch task ID of in-process task*/LOCAL WER _tkse_get_tid(void){ return GetMyTid();}/* ------------------------------------------------------------------ */#define TEV_FFLOCK ( __CommArea->tev_fflock )/* Wait for FIFO lock*/LOCAL ER _tkse_wai_fflock( void ){ return tk_wai_tev((INT)(TSD_TWF_VAL_0X00000001 << (TEV_FFLOCK - 1)), TMO_FEVR);}/* Reset wait for FIFO lock*/LOCAL ER _tkse_wup_fflock( ID tid ){ ER err; Lock(&ProcMgrLock); err = (CheckSubTask(tid) != 0) ? tk_sig_tev(tid, TEV_FFLOCK): E_ID; Unlock(&ProcMgrLock); return err;}/* ------------------------------------------------------------------ *//* * Dynamic loading *//* * Load shared object */LOCAL WER _tkse_lod_mod2( LINK *lnk, P_DYNLDINF *info ){ PINFO *pi; ER err; POBJ_HDR pohdr; /* Parameter check */ err = CheckSpaceR(lnk, sizeof(LINK)); if ( err < E_OK ) { goto err_ret; } err = CheckSpaceRW(info, sizeof(P_DYNLDINF)); if ( err < E_OK ) { goto err_ret; } /* Dynamic loading cannot be used in initial process (INIT). */ pi = GetPinfo(TSK_SELF); if (( pi == INIT_PINFO )||( pi == NULL )) { err = E_CTX; goto err_ret; } /* Loading */#if VIRTUAL_ADDRESS pohdr.type = TMA_LINK; pohdr.src.lnk = lnk; err = LoadModule(&pohdr, info, pi);#else err = E_NOSPT;#endiferr_ret: return err;}/* * Load shared object (from SEIO) */LOCAL WER _tkse_lod_mod( T_LMOD *pk_mod, P_DYNLDINF *info ){ PINFO *pi; ATR atr; ER err; POBJ_HDR pohdr; if ((pk_mod == NULL) || (pk_mod && CheckSpaceR((VP)pk_mod, sizeof(T_LMOD) )) || (info && CheckSpaceR((VP)info , sizeof(P_DYNLDINF) )) ) { err = E_MACV; goto err_ret; } pi = GetPinfo(TSK_SELF); if ( (pi == INIT_PINFO) || (pi == NULL) ) { err = E_CTX; goto err_ret; } atr = pk_mod->modatr; if ((atr & ~TMA_INPUTMASK) != 0) { err = E_PAR; goto err_ret; } pohdr.type = (W)(atr & TMA_INPUTMASK); switch (pohdr.type) { case TMA_LINK: pohdr.src.lnk = (LINK*)pk_mod->modhdr; break; case TMA_SEIO: pohdr.src.path = (B*)pk_mod->modhdr; break; case TMA_PTR: pohdr.src.buf = (VP)pk_mod->modhdr; break; default: return E_PAR; }#if VIRTUAL_ADDRESS err = LoadModule(&pohdr, info, pi);#else err = E_NOSPT;#endiferr_ret: return err;}/* * Unload shared object */LOCAL ER _tkse_unl_mod( ID loadid ){ PINFO *pi; ER err; pi = GetPinfo(TSK_SELF); if ( pi == NULL ) { err = E_CTX; goto err_ret; } /* Unloading */#if VIRTUAL_ADDRESS err = UnloadModule(loadid, pi);#else err = E_NOSPT;#endiferr_ret: return err;}/*====================================================================== Initial processing of process task management======================================================================*//* SVC entry of process management*/#define FNO(n) ( (UW)(n) >> 16 )LOCAL WER ProcSVCentry(VP para, W fn, VP caller_gp){ switch ( FNO(fn) ) { case FNO(PM_CRE_PRC2_FN): { PM_CRE_PRC2_PARA *p = para; return _tkse_cre_prc2(p->lnk, p->pri, p->msg); } case FNO(PM_EXT_PRC_FN): { PM_EXT_PRC_PARA *p = para; _tkse_ext_prc(p->exit_code); /* no break */ } case FNO(PM_TER_PRC_FN): { PM_TER_PRC_PARA *p = para; return _tkse_ter_prc(p->pid, p->abort_code, p->opt); } case FNO(PM_CHG_PRI_FN): { PM_CHG_PRI_PARA *p = para; return _tkse_chg_pri(p->pid, p->new_pri, p->opt); } case FNO(PM_DLY_TSK_FN): { PM_DLY_TSK_PARA *p = para; return _tkse_dly_tsk(p->dlytim); } case FNO(PM_PRC_STS_FN): { PM_PRC_STS_PARA *p = para; return _tkse_prc_sts(p->pid, p->buff, p->path); } case FNO(PM_GET_INF_FN): { PM_GET_INF_PARA *p = para; return _tkse_get_inf(p->pid, p->buff); } case FNO(PM_CRS_TSK_FN): { PM_CRS_TSK_PARA *p = para; return _tkse_crs_tsk(p->entry, p->pri, p->arg, caller_gp); } case FNO(PM_CRE_TSK_FN): { PM_CRE_TSK_PARA *p = para; return _tkse_cre_tsk(p->entry, p->pri, caller_gp); } case FNO(PM_STA_TSK_FN): { PM_STA_TSK_PARA *p = para; return _tkse_sta_tsk(p->id, p->arg); } case FNO(PM_EXT_TSK_FN): { _tkse_ext_tsk(); } case FNO(PM_SLP_TSK_FN): { PM_SLP_TSK_PARA *p = para; return _tkse_slp_tsk(p->tmout); } case FNO(PM_WUP_TSK_FN): { PM_WUP_TSK_PARA *p = para; return _tkse_wup_tsk(p->tskid); } case FNO(PM_GET_TID_FN): { return _tkse_get_tid(); } case FNO(PM_CRE_SYSPRC_FN): { PM_CRE_SYSPRC_PARA *p = para; return _tkse_cre_sysprc(p->lnk, p->pri, p->msg); } case FNO(PM_TER_TSK_FN): { PM_TER_TSK_PARA *p = para; return _tkse_ter_tsk(p->tskid); } case FNO(PM_CAN_WUP_FN): { PM_CAN_WUP_PARA *p = para; return _tkse_can_wup(p->tskid); } case FNO(PM_REQ_EMG_FN): { PM_REQ_EMG_PARA *p = para; return _tkse_req_emg(p->pid, p->t_mask); } case FNO(PM_PRC_INF_FN): { PM_PRC_INF_PARA *p = para; return _tkse_prc_inf(p->pid, p->item, p->buf, p->len); } case FNO(PM_LOD_MOD2_FN): { PM_LOD_MOD2_PARA *p = para; return _tkse_lod_mod2(p->lnk, p->info); } case FNO(PM_UNL_MOD_FN): { PM_UNL_MOD_PARA *p = para; return _tkse_unl_mod(p->loadid); } /* Special system call for system */ case FNO(PM_KNLDEBUGFUNC_FN): { PM_KNLDEBUGFUNC_PARA *p = para; return _DebugFunc(p->fn, p->p1, p->p2, p->p3); } case FNO(PM_WAI_FFLOCK_FN): { return _tkse_wai_fflock(); } case FNO(PM_WUP_FFLOCK_FN): { PM_WUP_FFLOCK_PARA *p = para; return _tkse_wup_fflock(p->tid); } /* System call of system management */ case FNO(PM_GET_VER_FN): { PM_GET_VER_PARA *p = para; return _tkse_get_ver(p->version); } case FNO(PM_LOD_SPG2_FN): { PM_LOD_SPG2_PARA *p = para; return _tkse_lod_spg2(p->lnk, p->arg, p->info); } case FNO(PM_UNL_SPG_FN): { PM_UNL_SPG_PARA *p = para; return _tkse_unl_spg(p->progid ); } case FNO(PM_CRE_DBG_FN): { PM_CRE_DBG_PARA *p = para; return _tkse_cre_dbg(p->lnk, p->pri, p->msg); } case FNO(PM_SET_DBG_FN): { PM_SET_DBG_PARA *p = para; return _tkse_set_dbg(p->pid, p->mode); } case FNO(PM_CRE_PRC_FN): { PM_CRE_PRC_PARA *p = para; return _tkse_cre_prc(p->pk_cprc, p->msg); } case FNO(PM_LOD_MOD_FN): { PM_LOD_MOD_PARA *p = para; return _tkse_lod_mod(p->pk_mod, p->info); } case FNO(PM_LOD_SPG_FN): { PM_LOD_SPG_PARA *p = para; return _tkse_lod_spg(p->pk_sysprg, p->arg, p->info); } default: { /* nothing to do */ break; } } return E_RSFN;}/* Startup processing of system management*/LOCAL void ProcStartUp( ID resid, W pid ){ PRCMINFO *info; tk_get_res(resid, PM_SVC, (VP*)&info); /* Initialize specific management information for process management */ GetPidToPinfo(pid, &info->pinfo); QueInit(&info->dynldq);}/* Cleanup processing of process management*/LOCAL void ProcCleanUp( ID resid, W pid ){#if VIRTUAL_ADDRESS PRCMINFO *info; tk_get_res(resid, PM_SVC, (VP*)&info); /* Unload all shared objects */ UnloadAllModule(info, pid);#endif}/* Break processing of process management*/LOCAL void ProcBreak(ID taskid){ tk_dis_wai(taskid, TTW_DLY | (UW)TTW_SLP);}/* Process forced termination processing sysproc = 0 Forcedly terminate all normal processes. sysproc = 1 Forcedly terminate all system processes except for the initial process.*/LOCAL void KillProcess( UW sysproc ){ PINFO *pi, *npi; W cnt, nprc; Lock(&ProcMgrLock); for (pi = (PINFO*)UsedPI.next; pi != (PINFO*)&UsedPI; pi = npi) { npi = (PINFO*)pi->q.next; if ((pi->sysproc != sysproc )||( pi->procid <= 1)) { continue; } if (pi->exitkind != 0) { continue; /* Already in termination processing. */ } KillTasks(pi, TSD_KTK_VAL_M1, EXIT_FORCE, 0); /* Wait for process termination: MAX 500 ms */ Unlock(&ProcMgrLock); for (cnt = 0;(( pi->procid != 0 )&&( cnt < TSD_KPS_VAL_50)); cnt++) { tk_dly_tsk(TSD_KPS_TDT_10); } Lock(&ProcMgrLock); } Unlock(&ProcMgrLock); /* Check process termination: MAX 2000 ms */ for (cnt = 0; cnt < TSD_KPS_VAL_40; cnt++) { Lock(&ProcMgrLock); for (nprc = 0, pi = (PINFO*)UsedPI.next; pi != (PINFO*)&UsedPI; pi = (PINFO*)pi->q.next) { if ((pi->sysproc == sysproc )&&( pi->procid > 1)) { nprc++; } } Unlock(&ProcMgrLock); if (nprc == 0) { break; } tk_dly_tsk(TSD_KPS_TDT_50); }}/* Forced termination of all processes (called from initial process only)*/EXPORT void KillAllProcess( void ){ /* Forcedly terminate normal process */ KillProcess(0); /* Forcedly terminate system process * (Note) It is impossible to forcedly terminate a system process if it has called * system call directly from the kernel and is in the wait state. */ KillProcess(1);}/* Startup processing of process management*/EXPORT ER ProcessMgr( INT ac, UB *av[] ){IMPORT W LazyMode; /* debug.c */ W val[L_SYSCONF_VAL]; W i; ER err; PINFO *pi; T_DSSY dssy; if (ac < 0) { return E_OK; /* Omit termination processing */ } /* Initialization processing */ /* Fetch maximum number of processes. */ if ( GetSysConf((UB*)"MaxProc", val) < 1 ) { SYSLOG((LOG_ERR, "** MaxProc Not Configured")); return E_SYS; } MaxProc = val[0]; /* Fetch maximum number of subtasks. */ if ( GetSysConf((UB*)"MaxSubTsks", val) > 0 ) { MAX_SUBTASKS = val[0]; } /* Fetch system stack size of the process. */ if ( GetSysConf((UB*)"SysStkSz", val) > 0 ) { SYS_STKSZ = val[0]; } /* Obtain the area of process management information. */ PINFO_sz = (W)PINFO_SZ((UW)MAX_SUBTASKS); TopPI = (PINFO*)Icalloc((size_t)MaxProc, (size_t)PINFO_sz); if (! TopPI) { SYSLOG((LOG_ERR, "** Can\'t Alloc @InitProcessMgr")); return E_SYS; } /* Initialize process management information. */ QueInit(&FreePI); QueInit(&UsedPI); for (pi = TopPI, i = 0; i < MaxProc; i++) { QueInsert(&pi->q, &FreePI); pi = (PINFO*)((UB*)pi + PINFO_sz); }#if VIRTUAL_ADDRESS /* Initialize process map/system program loading. */ err = InitProcMap(); if (err < 0) { return err; }#else /* Initialize loading information. */ err = InitLoadInfo(MaxProc); if (err < 0) { return err; }#endif /* Generate lock. */ err = CreateLock(&_PinfoLock, (UB*)"Pinf"); if ( err < E_OK ) { return err; } err = CreateLock(&ProcMgrLock, (UB*)"PrcM"); if ( err < E_OK ) { return err; } /* Various initialization processing. */ LastProcID = 0; LazyMode = ( _isDebugMode() != 0 )? 0: 1; /* Set kernel shared data. */ __CommArea->PinfoLock = &_PinfoLock; __CommArea->SysResID = tk_get_rid(TSK_SELF); __CommArea->GetPinfo = (FUNCP)&_GetPinfo; __CommArea->GetPidToPinfo = (FUNCP)&_GetPidToPinfo; __CommArea->GetLSID = (FUNCP)&_GetLSID; __CommArea->GetUATB = (FUNCP)&_GetUATB;#if TA_GP { extern int _gp; __CommArea->gp = &_gp; }#endif /* Register the manager. */ dssy.ssyatr = TA_NULL; dssy.ssypri = PM_PRI; dssy.svchdr = (FP)ProcSVCentry; dssy.breakfn = ProcBreak; dssy.startupfn = ProcStartUp; dssy.cleanupfn = ProcCleanUp; dssy.eventfn = NULL; dssy.resblksz = sizeof(PRCMINFO); err = tk_def_ssy(PM_SVC, &dssy); if ( err < E_OK ) { return err; } return E_OK;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -