예제 #1
0
/*
 * @brief
 *    osekInterrupt_Initialize:中断初始化(内部函数)。
 * @param
 * @param[in]	无。
 * @param[out]  无。
 * @returns:    无。
 */
void osekInterrupt_Initialize(void)
{
	//获取核心ID
	CoreIDType core = GetCoreID();
	//为核心设置中断栈地址。isr2Stack[core]是一个指针
	osekKernel_osKernel[core].osekInterrupt_IsrStackTop = (OSDWORD)&isr2Stack[core][0] + (OSDWORD)(CONFIG_OSEK_INTERRUPT_STACK_SIZE - 0x20);
}
예제 #2
0
int main(void)
{
#if NUMBER_OF_CORES > 1
    StatusType rv;

    switch(GetCoreID())
    {
    case OS_CORE_ID_MASTER :
        TestRunner_start();
        SyncAllCores_Init();
        StartCore(OS_CORE_ID_1, &rv);
        if(rv == E_OK)
            StartOS(OSDEFAULTAPPMODE);
        break;
    case OS_CORE_ID_1 :
        StartOS(OSDEFAULTAPPMODE);
        break;
    default :
        /* Should not happen */
        break;
    }
#else
# error "This is a multicore example. NUMBER_OF_CORES should be > 1"
#endif
    return 0;
}
예제 #3
0
FUNC(int, OS_APPL_CODE) main(void)
{
#if NUMBER_OF_CORES > 1
    StatusType rv;

    switch(GetCoreID()){
      case OS_CORE_ID_MASTER :
        initLed();
        setLed(0, led_state1);
        /* Wakeup core 1 */
        StartCore(OS_CORE_ID_1, &rv);
        if(rv == E_OK)
          StartOS(OSDEFAULTAPPMODE);
        break;
      case OS_CORE_ID_1 :
        /* Core 1 : leds were already initialized by the core 0 at this step */
        setLed(1, led_state2);
        StartOS(OSDEFAULTAPPMODE);
        break;
      default :
        /* Should not happen */
        break;
    }
#else
    initLed();
    setLed(0, led_state1);
    StartOS(OSDEFAULTAPPMODE);
#endif

    return 0;
}
예제 #4
0
StatusType GetCounterInfo( CtrType ctrId, CtrInfoRefType info )
{
	//获取核心ID
	CoreIDType core=GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_OsKernelRef kernelPtr=&osekKernel_osKernel[core];
	T_OSEK_COUNTER_ControlBlockRef counterPtr;

// 如果使用了扩展状态
#if defined(CONFIG_OSEK_SYSTEM_EXTSTATUS)
	// 如果COUNTER ID超出范围,返回E_OS_ID
	if( ctrId > (kernelPtr->osCounters->counterCnt - 1) )
	{
		OSEK_HOOK_ErrorHook(E_OS_ID,OSServiceId_GetCounterInfo,ctrId) ;
	}
#endif

	counterPtr = &(kernelPtr->osCounters->osekCounter_CounterTable[ctrId]);
	// 获取计数器的配置信息到输出参数中
	//这里configTable未使用指针
	*info =  counterPtr->configTable;

	// 成功,返回E_OK
	return E_OK;

}
예제 #5
0
/*
 * @brief
 *    EnableAllInterrupts:使能所有中断。
 * @param
 * @param[in]	无。
 * @param[out]  无。
 * @returns:    无。
 */
void EnableAllInterrupts( void )
{
	//获取核心ID
	CoreIDType core = GetCoreID();

	OSEK_TARGET_EnableAllInt(core);
}
예제 #6
0
/*
 * @brief
 *    GetEvent:获取事件。
 * @param
 * @param[in]	taskId:任务的ID号。
 * @param[out]  mask:  事件掩码变量的引用。
 * @returns:    E_OK: 成功。
 * <p>          [E_OS_ID:无效的任务ID号。]
 * <p>          [E_OS_ACCESS:指定任务不是扩展任务。]
 * <p>          [E_OS_STATE:指定任务处于SUSPEND状态。]
 */
StatusType  GetEvent( TaskType taskId, EventMaskRefType mask )
{

	//获取核心ID
	CoreIDType core = GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_TaskControlRef taskControl=osekKernel_osKernel[core].osTasks;

#if defined(CONFIG_OSEK_SYSTEM_EXTSTATUS)
	// 如果任务ID超出范围,返回E_OS_ID
	if( taskId > (osekKernel_osKernel[core].osTasks->taskCnt -1 ) )
	{
		OSEK_HOOK_ErrorHook(E_OS_ID,OSServiceId_GetEvent,taskId) ;
	}

	// 如果指定任务不是扩展任务,返回E_OS_ACCESS
	if( ((taskControl->osekTask_TaskTable[taskId]).configTable.property & OSEK_TASK_EXTENDED) == 0 )
	{
		OSEK_HOOK_ErrorHook(E_OS_ACCESS,OSServiceId_GetEvent,taskId) ;
	}

	// 如果指定任务处于SUSPEND状态,返回E_OS_STATE
	if( taskControl->osekTask_TaskTable[taskId].status == SUSPENDED )
	{
		OSEK_HOOK_ErrorHook(E_OS_STATE,OSServiceId_GetEvent,taskId) ;
	}
#endif

	// 将指定任务已设置的事件输出到输出参数中
	*mask = taskControl->osekTask_TaskTable[taskId].setEvent;

	// 成功,返回E_OK
	return E_OK;

}
예제 #7
0
/* 核心初始化函数*/
void osekKernel_Initialize()
{//初始化各个核心的数据结构,可以由一个核心(如Core0)调用然后初始化全部数据,或者由每个核心自己负责核心数据的初始化

	//获取核心ID
	CoreIDType core = GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_OsKernelRef kernelPtr = &osekKernel_osKernel[core];

	//初始化主要模块的核心数据结构指针
	kernelPtr->osTasks = &(osekKernel_coreTasks[core]);
	kernelPtr->osCounters = &(osekKernel_coreCounters[core]);
	kernelPtr->osAlarms = &(osekKernel_coreAlarms[core]);

	//中断嵌套初始化
	kernelPtr->osekInterrupt_NestedLevl = 0;
	kernelPtr->osekInterrupt_NestedAllInt = 0;
	kernelPtr->osekInterrupt_NestedAllInt = 0;
	kernelPtr->osekInterrupt_NestedOsInt = 0;
	kernelPtr->osekInterrupt_IsrStackTop = 0;

	//Target初始化
	kernelPtr->osekTarget_OSIntMask = 0 ;
	kernelPtr->osekTarget_AllIntMask = 0 ;
	kernelPtr->osekTarget_NestedAllIntMask = 0 ;
	kernelPtr->osekTarget_NestedOsIntMask = 0 ;

	kernelPtr->osekTarget_SavedBTSP = 0 ;

	//Resource初始化

	//自旋锁初始化
}
예제 #8
0
/*
 * @brief
 *    ClearEvent:清除事件。
 * @param
 * @param[in]	mask:事件掩码。
 * @param[out]  无。
 * @returns:    E_OK: 成功。
 * <p>          [E_OS_ACCESS:运行任务不是扩展任务。]
 * <p>          [E_OS_CALLEVEL:在中断中调用了此函数。]
 */
StatusType  ClearEvent( EventMaskType mask )
{
	OSEK_TARGET_OSIntSave( osIntSave ) ;
	//获取核心ID
	CoreIDType core = GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_OsKernelRef kernelPtr = &osekKernel_osKernel[core];

#if defined(CONFIG_OSEK_SYSTEM_EXTSTATUS)
	// 如果运行任务不是扩展任务,返回E_OS_ACCESS
	if( (kernelPtr->osekTask_RunningTask->taskControlBlock->configTable.property & OSEK_TASK_EXTENDED) == 0 )
	{
		OSEK_HOOK_ErrorHook(E_OS_ACCESS,OSServiceId_ClearEvent,0) ;
	}

	// 如果是从中断中调用的此函数,返回E_OS_CALLEVEL
	if( kernelPtr->osekInterrupt_NestedLevl != 0 )
	{
		OSEK_HOOK_ErrorHook(E_OS_CALLEVEL,OSServiceId_ClearEvent,0) ;
	}
#endif

	OSEK_TARGET_DisableOSInt(osIntSave);
	// 将指定事件从任务的已设置事件集中清除掉
	kernelPtr->osekTask_RunningTask->taskControlBlock->setEvent &= (EventMaskType)(~mask);
	OSEK_TARGET_EnableOSInt(osIntSave);

	// 成功,返回E_OK
	return E_OK;

}
예제 #9
0
/*
 * @brief
 *    SuspendAllInterrupts:挂起所有中断。
 * @param
 * @param[in]	无。
 * @param[out]  无。
 * @returns:    无。
 */
void SuspendAllInterrupts( void )
{
	//获取核心ID
	CoreIDType core = GetCoreID();
	if( osekKernel_osKernel[core].osekInterrupt_NestedAllInt == 0 )
	{
		OSEK_TARGET_DisableNestedAllInt(core);
	}

	osekKernel_osKernel[core].osekInterrupt_NestedAllInt++;
}
예제 #10
0
void ShutdownHook(StatusType error)
{
    switch(GetCoreID())
    {
    case OS_CORE_ID_MASTER :
        TestRunner_end();
        break;
    default :
        while(1); /* Slave cores wait here */
        break;
    }
}
예제 #11
0
/** @req OS383 */
StatusType GetCounterValue( CounterType counter_id , TickRefType tick_ref)
{
    StatusType rv = E_OK;
    OsCounterType *cPtr;
    cPtr = Os_CounterGet(counter_id);


#if (OS_SC3==STD_ON) || (OS_SC4==STD_ON)
    OsTaskVarType *currPcbPtr = Os_SysTaskGetCurr();

    if( currPcbPtr->constPtr->applOwnerId != cPtr->applOwnerId ) {
        /* @req SWS_Os_00056 */
        APPL_CHECK_STATE(cPtr->applOwnerId);
        APPL_CHECK_ACCESS(currPcbPtr->constPtr->applOwnerId, cPtr->accessingApplMask);


#if	(OS_NUM_CORES > 1)
        if (Os_ApplGetCore(cPtr->applOwnerId) != GetCoreID()) {
            StatusType status = Os_NotifyCore(Os_ApplGetCore(cPtr->applOwnerId),
                                              OSServiceId_GetCounterValue,
                                              counter_id,
                                              (uint32_t)tick_ref,
                                              0);
            return status;
        }
#endif
    }
#endif

    OS_VALIDATE(IsCounterValid(counter_id),E_OS_ID);    /* @req 4.1.2/SWS_Os_00376 */

    /** @req OS377 */
    if( cPtr->type == COUNTER_TYPE_HARD ) {
        if( cPtr->driver == NULL ) {
            /* It's OSINTERNAL */
            *tick_ref = OS_SYS_PTR->tick;
        } else {
#if 0
            /* We support only GPT for now */
            *tick_ref  = (TickType)Gpt_GetTimeElapsed(cPtr->driver.OsGptChannelRef);
#endif

        }
    } else {
        *tick_ref = cPtr->val;
    }

    COUNTER_STD_END;
}
예제 #12
0
/** @req OS399 */
StatusType IncrementCounter( CounterType counter_id ) {
    StatusType rv = E_OK;
    OsCounterType *cPtr;
    uint32_t flags;
#if (OS_SC3==STD_ON) || (OS_SC4==STD_ON)
    OsTaskVarType *currPcbPtr;
#endif

    OS_VALIDATE( IsCounterValid(counter_id), E_OS_ID );
    cPtr = Os_CounterGet(counter_id);

    OS_VALIDATE( !( ( cPtr->type != COUNTER_TYPE_SOFT ) ||
                    ( counter_id >= OS_COUNTER_CNT )), E_OS_ID );

#if (OS_SC3==STD_ON) || (OS_SC4==STD_ON)
    currPcbPtr = Os_SysTaskGetCurr();

    if( currPcbPtr->constPtr->applOwnerId != cPtr->applOwnerId ) {
        /* @req SWS_Os_00056 */
        APPL_CHECK_STATE(cPtr->applOwnerId);
        APPL_CHECK_ACCESS(currPcbPtr->constPtr->applOwnerId, cPtr->accessingApplMask);


#if (OS_CORE_CNT > 1)
        OS_EXT_VALIDATE( Os_ApplGetCore(cPtr->applOwnerId) != GetCoreID(), E_OS_ACCESS );
#endif
    }
#endif

    Irq_Save(flags);

    /** @req OS286 */
    cPtr->val = Os_CounterAdd( cPtr->val, Os_CounterGetMaxValue(cPtr), 1 );

#if OS_ALARM_CNT!=0
    Os_AlarmCheck(cPtr);
#endif
#if OS_SCHTBL_CNT!=0
    Os_SchTblCheck(cPtr);
#endif

    Irq_Restore(flags);

    /** @req OS321 */
    COUNTER_STD_END;
}
예제 #13
0
StatusType CounterTrigger( CtrType ctrId )
{
	//获取核心ID
	CoreIDType core=GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_OsKernelRef kernelPtr = &osekKernel_osKernel[core];

	T_OSEK_COUNTER_ControlBlockRef ctrPtr;
	OSEK_TARGET_OSIntSave( osIntSave ) ;

#if defined(CONFIG_OSEK_SYSTEM_EXTSTATUS)
	// 如果使用了扩展状态,判断COUNTER ID是否超出范围,如是返回E_OS_ID
	if( ctrId > (kernelPtr->osCounters->counterCnt - 1) )
	{
		OSEK_HOOK_ErrorHook(E_OS_ID,OSServiceId_CounterTrigger,ctrId) ;
	}
#endif

	//获取对应Counter的指针
	ctrPtr = (kernelPtr->osCounters->osekCounter_CounterTable + ctrId);

	OSEK_TARGET_DisableOSInt(osIntSave);

	// 如果COUNTER 当前计数值等于配置的最大计数值,则将计数值复位至0
	/****目前configTable未使用指针,使用.而不是->****/
    if( ctrPtr->currentTick == ctrPtr->configTable.maxallowedvalue )
    {
        ctrPtr->currentTick = 0;
    }
	// 否则COUNTER 当前计数值加1
    else
    {
        ctrPtr->currentTick++;
    }

#if defined(CONFIG_OSEK_ALARM)
	// 检查是否有ALARM 到期并做相应处理(调用回调函数、设置事件或激活任务)
    osekAlarm_Check1( ctrId );
#endif

    OSEK_TARGET_EnableOSInt(osIntSave);

	// 成功,返回E_OK
	return E_OK;

}
예제 #14
0
/*
 * @brief
 *    ResumeAllInterrupts:恢复所有中断。
 * @param
 * @param[in]	无。
 * @param[out]  无。
 * @returns:    无。
 */
void ResumeAllInterrupts( void )
{
	//获取核心ID
	CoreIDType core = GetCoreID();
	// 如果禁止中断层数为0,直接返回
	if( osekKernel_osKernel[core].osekInterrupt_NestedAllInt == 0)
	{
		return;
	}

	// 禁止中断层数减1,减到0时使能所有中断
	osekKernel_osKernel[core].osekInterrupt_NestedAllInt--;
	if( osekKernel_osKernel[core].osekInterrupt_NestedAllInt == 0 )
	{
		OSEK_TARGET_EnableNestedAllInt(core);
	}
}
예제 #15
0
void osekCounter_Initialize( void )
{
	int i;

	//获取核心ID
	CoreIDType core=GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_CounterControlRef osCounters = osekKernel_osKernel[core].osCounters;

	//如何初始化osekCounter_CounterTable这个指针
	//memset((void*)osekCounter_CounterTable,0,sizeof(osekCounter_CounterTable));
	memset(osCounters->osekCounter_CounterTable,0,(osCounters->counterCnt)*(sizeof(T_OSEK_COUNTER_ControlBlock)));

	for( i = 0; i < osCounters->counterCnt; i++)
	{
		//初始化Counter的配置结构体
		(osCounters->osekCounter_CounterTable[i]).configTable = osCounters->osekConfig_CounterTable[i];
	}

}
예제 #16
0
/** @req 4.1.2/SWS_Os_00392 */
StatusType GetElapsedValue ( CounterType counter_id, TickRefType val, TickRefType elapsed_val)
{
    StatusType rv = E_OK;
    OsCounterType *cPtr;
    TickType currTick = 0;
    TickType max;

    cPtr = Os_CounterGet(counter_id);

    /** @req SWS_Os_00381 */
    OS_VALIDATE(IsCounterValid(counter_id),E_OS_ID);
    max = Os_CounterGetMaxValue(cPtr);

    /** @req SWS_Os_00391 */
    OS_VALIDATE( *val <= max,E_OS_VALUE );

#if	(OS_APPLICATION_CNT > 1) && (OS_NUM_CORES > 1)
    if (Os_ApplGetCore(cPtr->applOwnerId) != GetCoreID()) {
        StatusType status = Os_NotifyCore(Os_ApplGetCore(cPtr->applOwnerId),
                                          OSServiceId_GetElapsedValue,
                                          counter_id,
                                          (int32_t)val,
                                          (int32_t)elapsed_val);
        return status;
    }
#endif

    GetCounterValue(counter_id,&currTick);

    /** @req OS382 */
    *elapsed_val = Os_CounterDiff(currTick,*val,max);

    /** @req OS460 */
    *val = currTick;

    COUNTER_STD_END;
}
예제 #17
0
StatusType InitCounter( CtrType ctrId, TickType value )
{
	//获取核心ID
	CoreIDType core=GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_OsKernelRef kernelPtr=&osekKernel_osKernel[core];
	T_OSEK_COUNTER_ControlBlockRef counterPtr;

#if defined(CONFIG_OSEK_SYSTEM_EXTSTATUS)
	// 如果COUNTER ID超出范围,返回E_OS_ID
	if( ctrId > (kernelPtr->osCounters->counterCnt - 1) )
	{
		OSEK_HOOK_ErrorHook(E_OS_ID,OSServiceId_InitCounter,ctrId) ;
	}
	counterPtr = &(kernelPtr->osCounters->osekCounter_CounterTable[ctrId]);

	// 如果输入的计数值超出配置的最大值,返回E_OS_VALUE
	if( value > counterPtr->configTable.maxallowedvalue )
	{
		OSEK_HOOK_ErrorHook(E_OS_VALUE,OSServiceId_InitCounter,ctrId) ;
	}

	// 如果在中断中调用此函数,返回E_OS_CALLEVEL
	if( kernelPtr->osekInterrupt_NestedLevl != 0 )
	{
		OSEK_HOOK_ErrorHook(E_OS_CALLEVEL,OSServiceId_InitCounter,ctrId) ;
	}
#endif

	// 用输入的计数值设置COUNTER的当前计数值
	counterPtr->currentTick = value ;

	// 成功,返回E_OK
	return E_OK;

}
예제 #18
0
/*
 * 获取本地核心上Counter的计数值,函数只能在本地核心调用.
 * ctrId只能是本地Counter的ID
 */
StatusType GetCounterValue( CtrType ctrId, TickRefType ticks )
{
	//获取核心ID
	CoreIDType core=GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_OsKernelRef kernelPtr=&osekKernel_osKernel[core];
	T_OSEK_COUNTER_ControlBlockRef counterPtr;

#if defined(CONFIG_OSEK_SYSTEM_EXTSTATUS)
	// 如果COUNTER ID超出范围,返回E_OS_ID
	if( ctrId > (kernelPtr->osCounters->counterCnt - 1) )
	{
		OSEK_HOOK_ErrorHook(E_OS_ID,OSServiceId_GetCounterValue,ctrId) ;
	}
#endif

	counterPtr = &(kernelPtr->osCounters->osekCounter_CounterTable[ctrId]);

	// 读取指定计数器的当前计数值到输出参数中
	*ticks =  counterPtr->currentTick ;

	return E_OK;

}
예제 #19
0
/*
 * @brief
 *    SetEvent:设置事件。
 * @param
 * @param[in]	taskId:任务ID号。
 *          	mask:事件掩码。
 * @param[out]  无。
 * @returns:    E_OK: 成功。
 * <p>          [E_OS_ID:无效的任务ID号。]
 * <p>          [E_OS_ACCESS:指定任务不是扩展任务。]
 * <p>          [E_OS_STATE:指定任务处于SUSPEND状态。]
 */
StatusType  SetEvent( TaskType taskId, EventMaskType mask )
{
	T_OSEK_TASK_ControlBlock *tcbPtr;
	StatusType status;
	OSEK_TARGET_OSIntSave( osIntSave ) ;

	//获取核心ID
	CoreIDType core=GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_OsKernelRef kernelPtr=&osekKernel_osKernel[core];
	//获取任务映射表项
	LocalTaskType localTask;

#if defined(CONFIG_OSEK_SYSTEM_EXTSTATUS)
	// 如果任务ID超出范围,返回E_OS_ID
	if( taskId > CONFIG_OSEK_TASK_MAX_ID )
	{
		OSEK_HOOK_ErrorHook(E_OS_ID,OSServiceId_SetEvent,taskId) ;
	}
#endif

	//获取局部任务ID
	localTask=osekTask_tasksMap[taskId];
	//判断任务是否是本地任务
	if(core != GET_LOCAL_CORE_ID(localTask))
	{

		status = rpc_setEvent_stub(GET_LOCAL_TASK_ID(localTask),mask,GET_LOCAL_CORE_ID(localTask));
		return status;
	}
	else
	{
		tcbPtr = &(kernelPtr->osTasks->osekTask_TaskTable[GET_LOCAL_TASK_ID(localTask)]);

		OSEK_TARGET_DisableOSInt(osIntSave);

		// 调用内部函数osekEvent_SetEvent设置事件
		status = osekEvent_SetEvent(kernelPtr,tcbPtr,mask);

		// 如果需要,实施调度,此处会切换到另一个任务执行
		if( status == OSEK_TASK_NEED_DISPATCH )
		{
			osekTask_Dispatch();
		}
		else
		{
			OSEK_TARGET_EnableOSInt(osIntSave);
			if( status != E_OK )
			{
				OSEK_HOOK_ErrorHook(status,OSServiceId_SetEvent,taskId) ;
			}
			else
			{
				return status;
			}
		}

		OSEK_TARGET_EnableOSInt(osIntSave);
	}

	return E_OK;

}
예제 #20
0
StatusType SetEvent( TaskType TaskID, EventMaskType Mask ) {
	StatusType rv = E_OK;
	OsTaskVarType *destPcbPtr;
	OsTaskVarType *currPcbPtr;
	uint32_t flags;

	OS_DEBUG(D_EVENT,"# SetEvent %s\n",Os_SysTaskGetCurr()->constPtr->name);

	TASK_CHECK_ID(TaskID);

	destPcbPtr = Os_TaskGet(TaskID);
	currPcbPtr = Os_SysTaskGetCurr();

#if (OS_SC3==STD_ON) || (OS_SC4==STD_ON)

	if( destPcbPtr->constPtr->applOwnerId != OS_SYS_PTR->currApplId ) {
		ApplicationType appId;
	    APPL_CHECK_STATE(destPcbPtr->constPtr->applOwnerId);
    	/* Do we have access to the task we are activating */
        if(OS_SYS_PTR->intNestCnt == 0 ) {
        	appId = currPcbPtr->constPtr->applOwnerId;
        } else {
        	appId = Os_SysIsrGetCurr()->constPtr->appOwner;
        }

        APPL_CHECK_ACCESS( appId , destPcbPtr->constPtr->accessingApplMask);

#if (OS_NUM_CORES > 1)
	    if (Os_ApplGetCore(destPcbPtr->constPtr->applOwnerId) != GetCoreID()) {
	                StatusType status = Os_NotifyCore(Os_ApplGetCore(destPcbPtr->constPtr->applOwnerId),
	                                                  OSServiceId_SetEvent,
	                                                  TaskID,
	                                                  Mask,
	                                                  0);
	                return status;
#endif

	}
#endif

	OS_VALIDATE( destPcbPtr->constPtr->proc_type == PROC_EXTENDED, E_OS_ACCESS );
	OS_VALIDATE( !(destPcbPtr->state & ST_SUSPENDED ), E_OS_STATE);

	Irq_Save(flags);

	/* Calling  SetEvent  causes  the  task  <TaskID>  to be  transferred
	 * to  the  ready  state,  if  it  was  waiting  for  at  least one of the
	 * events specified in <Mask>.
	 *
	 * OSEK/VDX 4.6.1,  rescheduling is performed in all of the following cases:
	 * ..
	 * Setting an event to a waiting task at task level (e.g. system service SetEvent,
	 * see chapter 13.5.3.1, message notification mechanism, alarm expiration, if event setting
	 * defined, see chapter 9.2)
	 * ... */

	destPcbPtr->ev_set |= Mask;

	if( (Mask & destPcbPtr->ev_wait) ) {
		/* We have an event match */
		if( destPcbPtr->state & ST_WAITING) {
			Os_TaskMakeReady(destPcbPtr);

			currPcbPtr = Os_SysTaskGetCurr();
			/* Checking "4.6.2  Non preemptive scheduling" it does not dispatch if NON  */
			if( (OS_SYS_PTR->intNestCnt == 0) &&
				(currPcbPtr->constPtr->scheduling == FULL) &&
				(destPcbPtr->activePriority > currPcbPtr->activePriority) &&
				(Os_SchedulerResourceIsFree()) )
			{
				Os_Dispatch(OP_SET_EVENT);
			}

		}  else if(destPcbPtr->state & (ST_READY|ST_RUNNING|ST_SLEEPING) ) {
			/* Hmm, we do nothing */
		} else {
			assert( 0 );
		}
	}

	Irq_Restore(flags);

	OS_STD_END_2(OSServiceId_SetEvent,TaskID, Mask);
}


/**
 * This service returns the current state of all event bits of the task
 * <TaskID>, not the events that the task is waiting for.
 * The service may be called from interrupt service routines, task
 * level and some hook routines (see Figure 12-1).
 *  The current status of the event mask of task <TaskID> is copied
 * to <Event>.
 *
 * @param TaskId Task whose event mask is to be returned.
 * @param Mask   Reference to the memory of the return data.
 * @return
 */
StatusType GetEvent( TaskType TaskId, EventMaskRefType Mask) {

	OsTaskVarType *destPcbPtr;
	StatusType rv = E_OK;

	TASK_CHECK_ID(TaskId);

	destPcbPtr = Os_TaskGet(TaskId);

	OS_VALIDATE( (destPcbPtr->constPtr->proc_type == PROC_EXTENDED) ,E_OS_ACCESS);
	OS_VALIDATE( !(destPcbPtr->state & ST_SUSPENDED),E_OS_STATE);

	*Mask = destPcbPtr->ev_set;

	if (0) goto err;

	OS_STD_END_2(OSServiceId_GetEvent,TaskId, Mask);
}
예제 #21
0
/*
 * @brief
 *    WaitEvent:等待事件。
 * @param
 * @param[in]	mask:事件掩码。
 * @param[out]  无。
 * @returns:    E_OK: 成功。
 * <p>          [E_OS_ACCESS:运行任务不是扩展任务。]
 * <p>          [E_OS_RESOURCE:运行任务还拥有其他资源或系统处于关调度的情况。]
 * <p>          [E_OS_CALLEVEL:在中断中使用了此调用。]
 */
StatusType  WaitEvent( EventMaskType mask )
{
	OSEK_TARGET_OSIntSave( osIntSave ) ;
	//获取核心ID
	CoreIDType core = GetCoreID();
	//获取核心数据指针
	T_OSEK_KERNEL_OsKernelRef kernelPtr = &osekKernel_osKernel[core];

	/* 如果任务占用了自旋锁,则不允许挂起自己 */
	if(kernelPtr->osekTask_RunningTask->taskControlBlock->spinLockList != NULL)
	{
		OSEK_HOOK_ErrorHook(E_OS_SPINLOCK,OSServiceId_WaitEvent,0) ;
	}

#if defined(CONFIG_OSEK_SYSTEM_EXTSTATUS)
	// 如果运行任务不是扩展任务,返回E_OS_ACCESS
	if( (kernelPtr->osekTask_RunningTask->taskControlBlock->configTable.property & OSEK_TASK_EXTENDED) == 0 )
	{
		OSEK_HOOK_ErrorHook(E_OS_ACCESS,OSServiceId_WaitEvent,0) ;
	}

#if defined(CONFIG_OSEK_RESOURCE)
	// 如果运行任务资源列表不为0,返回E_OS_RESOURCE
	if( kernelPtr->osekTask_RunningTask->taskControlBlock->resourceList != 0 )
	{
		OSEK_HOOK_ErrorHook(E_OS_RESOURCE,OSServiceId_WaitEvent,0) ;
	}

#if defined(CONFIG_OSEK_RESOURCE_ISR)
	// 如果中断资源没有释放,返回E_OS_RESOURCE
    if (osekResource_ISRLast != 0)
    {
        OSEK_HOOK_ErrorHook(E_OS_RESOURCE,OSServiceId_WaitEvent,0) ;
    }
#endif  /* defined(CONFIG_OSEK_RESOURCE_ISR) */

#endif

	// 如果调度锁不为0,返回E_OS_RESOURCE
	if( kernelPtr->osekTask_SchedulerLockLevel != 0 )
	{
		OSEK_HOOK_ErrorHook(E_OS_RESOURCE,OSServiceId_WaitEvent,0) ;
	}

	// 如果中断嵌套数不为0,返回E_OS_CALLEVEL
	if( kernelPtr->osekInterrupt_NestedLevl != 0 )
	{
		OSEK_HOOK_ErrorHook(E_OS_CALLEVEL,OSServiceId_WaitEvent,0) ;
	}
#endif

	// 关中断
	OSEK_TARGET_DisableOSInt(osIntSave);

	// 设置运行任务的等待事件掩码
	kernelPtr->osekTask_RunningTask->taskControlBlock->waitEvent = mask;

	// 如果运行任务已被设置的事件不符合其等待的事件,则将任务切换到等待状态
	if( (kernelPtr->osekTask_RunningTask->taskControlBlock->setEvent & mask) == 0 )
	{
		osekTask_WaitTask(kernelPtr);
	}

	// 开中断
	OSEK_TARGET_EnableOSInt(osIntSave);

	// 成功,返回E_OK
	return E_OK;

}