Quick and dirty CoOS + LWIP ( Webserver )

Dependencies:   mbed lwip

Committer:
astroboy
Date:
Sat Sep 10 22:41:10 2011 +0000
Revision:
0:94897d537b31

        

Who changed what in which revision?

UserRevisionLine numberNew contents of line
astroboy 0:94897d537b31 1 /**
astroboy 0:94897d537b31 2 *******************************************************************************
astroboy 0:94897d537b31 3 * @file task.c
astroboy 0:94897d537b31 4 * @version V1.1.4
astroboy 0:94897d537b31 5 * @date 2011.04.20
astroboy 0:94897d537b31 6 * @brief task management implementation code of CooCox CoOS kernel.
astroboy 0:94897d537b31 7 *******************************************************************************
astroboy 0:94897d537b31 8 * @copy
astroboy 0:94897d537b31 9 *
astroboy 0:94897d537b31 10 * INTERNAL FILE,DON'T PUBLIC.
astroboy 0:94897d537b31 11 *
astroboy 0:94897d537b31 12 * <h2><center>&copy; COPYRIGHT 2009 CooCox </center></h2>
astroboy 0:94897d537b31 13 *******************************************************************************
astroboy 0:94897d537b31 14 */
astroboy 0:94897d537b31 15
astroboy 0:94897d537b31 16
astroboy 0:94897d537b31 17 /*---------------------------- Include ---------------------------------------*/
astroboy 0:94897d537b31 18 #include <coocox.h>
astroboy 0:94897d537b31 19
astroboy 0:94897d537b31 20 /*---------------------------- Variable Define -------------------------------*/
astroboy 0:94897d537b31 21
astroboy 0:94897d537b31 22 /*!< Table use to save TCB pointer. */
astroboy 0:94897d537b31 23 OSTCB TCBTbl[CFG_MAX_USER_TASKS+SYS_TASK_NUM] = {{0}};
astroboy 0:94897d537b31 24
astroboy 0:94897d537b31 25 /*!< The stack of IDLE task. */
astroboy 0:94897d537b31 26 OS_STK idle_stk[CFG_IDLE_STACK_SIZE] = {0};
astroboy 0:94897d537b31 27
astroboy 0:94897d537b31 28 P_OSTCB FreeTCB = 0; /*!< pointer to free TCB */
astroboy 0:94897d537b31 29 P_OSTCB TCBRdy = 0; /*!< Pointer to the READY list. */
astroboy 0:94897d537b31 30 P_OSTCB TCBNext = 0; /*!< Poniter to task that next scheduled by OS */
astroboy 0:94897d537b31 31 P_OSTCB TCBRunning = 0; /*!< Pointer to TCB that current running task. */
astroboy 0:94897d537b31 32 U64 OSCheckTime = 0; /*!< The counter of system tick. */
astroboy 0:94897d537b31 33
astroboy 0:94897d537b31 34 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 35 OS_TID PriNum;
astroboy 0:94897d537b31 36 U8 ActivePri[CFG_MAX_USER_TASKS+SYS_TASK_NUM];
astroboy 0:94897d537b31 37 U8 TaskNumPerPri[CFG_MAX_USER_TASKS+SYS_TASK_NUM];
astroboy 0:94897d537b31 38 OS_TID RdyTaskPri[CFG_MAX_USER_TASKS+SYS_TASK_NUM] = {0};
astroboy 0:94897d537b31 39 U32 RdyTaskPriInfo[(CFG_MAX_USER_TASKS+SYS_TASK_NUM+31)/32];
astroboy 0:94897d537b31 40 #endif
astroboy 0:94897d537b31 41
astroboy 0:94897d537b31 42
astroboy 0:94897d537b31 43 /**
astroboy 0:94897d537b31 44 *******************************************************************************
astroboy 0:94897d537b31 45 * @brief Create a TCB list.
astroboy 0:94897d537b31 46 * @param[in] None
astroboy 0:94897d537b31 47 * @param[out] None
astroboy 0:94897d537b31 48 * @retval None
astroboy 0:94897d537b31 49 *
astroboy 0:94897d537b31 50 * @par Description
astroboy 0:94897d537b31 51 * @details This function is called by CoOSInit() to initial the empty list
astroboy 0:94897d537b31 52 * of OS_TCBS,supply a pointer to free TCB.
astroboy 0:94897d537b31 53 *******************************************************************************
astroboy 0:94897d537b31 54 */
astroboy 0:94897d537b31 55 void CreateTCBList(void)
astroboy 0:94897d537b31 56 {
astroboy 0:94897d537b31 57 U8 i;
astroboy 0:94897d537b31 58 P_OSTCB ptcb1,ptcb2;
astroboy 0:94897d537b31 59
astroboy 0:94897d537b31 60 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 61 PriNum = 0;
astroboy 0:94897d537b31 62 #endif
astroboy 0:94897d537b31 63
astroboy 0:94897d537b31 64 ptcb1 = &TCBTbl[0]; /* Build the free TCB list */
astroboy 0:94897d537b31 65 ptcb2 = &TCBTbl[1];
astroboy 0:94897d537b31 66 for(i=0;i< (CFG_MAX_USER_TASKS+SYS_TASK_NUM-1);i++ )
astroboy 0:94897d537b31 67 {
astroboy 0:94897d537b31 68 ptcb1->taskID = i;
astroboy 0:94897d537b31 69 ptcb1->state = TASK_DORMANT;
astroboy 0:94897d537b31 70 ptcb1->TCBnext = ptcb2;
astroboy 0:94897d537b31 71 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 72 RdyTaskPri[i] = INVALID_ID;
astroboy 0:94897d537b31 73 ActivePri[i] = INVALID_ID;
astroboy 0:94897d537b31 74 #endif
astroboy 0:94897d537b31 75 ptcb1++;
astroboy 0:94897d537b31 76 ptcb2++;
astroboy 0:94897d537b31 77 }
astroboy 0:94897d537b31 78 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 79 ActivePri[i] = INVALID_ID;
astroboy 0:94897d537b31 80 #endif
astroboy 0:94897d537b31 81
astroboy 0:94897d537b31 82 ptcb1->taskID = i;
astroboy 0:94897d537b31 83 ptcb1->TCBnext = 0;
astroboy 0:94897d537b31 84 FreeTCB = &TCBTbl[0]; /* Initialize FreeTCB as head item of list */
astroboy 0:94897d537b31 85 }
astroboy 0:94897d537b31 86
astroboy 0:94897d537b31 87
astroboy 0:94897d537b31 88
astroboy 0:94897d537b31 89 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 90
astroboy 0:94897d537b31 91 /**
astroboy 0:94897d537b31 92 *******************************************************************************
astroboy 0:94897d537b31 93 * @brief Get sequence number for Assign priority
astroboy 0:94897d537b31 94 * @param[in] pri Assign priority
astroboy 0:94897d537b31 95 * @param[out] SequenceNum priority number
astroboy 0:94897d537b31 96 * @retval Co_TRUE Assign priority in priority queue.
astroboy 0:94897d537b31 97 * Co_FALSE Assign priority not in priority queue.
astroboy 0:94897d537b31 98 *
astroboy 0:94897d537b31 99 * @par Description
astroboy 0:94897d537b31 100 * @details This function is called in Binary-Scheduling Algorithm
astroboy 0:94897d537b31 101 * to get sequence number for Assign priority.
astroboy 0:94897d537b31 102 *******************************************************************************
astroboy 0:94897d537b31 103 */
astroboy 0:94897d537b31 104 static BOOL GetPriSeqNum(U8 pri,OS_TID* SequenceNum)
astroboy 0:94897d537b31 105 {
astroboy 0:94897d537b31 106 OS_TID seqNum;
astroboy 0:94897d537b31 107 OS_TID num,tmpNum;
astroboy 0:94897d537b31 108 num = 0;
astroboy 0:94897d537b31 109 seqNum = PriNum;
astroboy 0:94897d537b31 110 while(num != seqNum)
astroboy 0:94897d537b31 111 {
astroboy 0:94897d537b31 112 tmpNum = num;
astroboy 0:94897d537b31 113 num = (num+seqNum)/2;
astroboy 0:94897d537b31 114 if(pri == ActivePri[num])
astroboy 0:94897d537b31 115 {
astroboy 0:94897d537b31 116 *SequenceNum = num;
astroboy 0:94897d537b31 117 return Co_TRUE;
astroboy 0:94897d537b31 118 }
astroboy 0:94897d537b31 119 else if (pri < ActivePri[num])
astroboy 0:94897d537b31 120 {
astroboy 0:94897d537b31 121 seqNum = num;
astroboy 0:94897d537b31 122 num = tmpNum;
astroboy 0:94897d537b31 123 }
astroboy 0:94897d537b31 124 else
astroboy 0:94897d537b31 125 {
astroboy 0:94897d537b31 126 num++;
astroboy 0:94897d537b31 127 }
astroboy 0:94897d537b31 128 }
astroboy 0:94897d537b31 129 *SequenceNum = num;
astroboy 0:94897d537b31 130 return Co_FALSE;
astroboy 0:94897d537b31 131 }
astroboy 0:94897d537b31 132
astroboy 0:94897d537b31 133
astroboy 0:94897d537b31 134 /**
astroboy 0:94897d537b31 135 *******************************************************************************
astroboy 0:94897d537b31 136 * @brief Get the nearest ready priority sequence number for Assign number
astroboy 0:94897d537b31 137 * @param[in] seqNum Assign sequence number
astroboy 0:94897d537b31 138 * @param[out] None
astroboy 0:94897d537b31 139 * @retval INVALID_ID Cannot find higher ready priority.
astroboy 0:94897d537b31 140 * Others Nearest ready priority sequence number
astroboy 0:94897d537b31 141 *
astroboy 0:94897d537b31 142 * @par Description
astroboy 0:94897d537b31 143 * @details This function is called in Binary-Scheduling Algorithm
astroboy 0:94897d537b31 144 * to get the nearest ready priority sequence number.
astroboy 0:94897d537b31 145 *******************************************************************************
astroboy 0:94897d537b31 146 */
astroboy 0:94897d537b31 147 static U8 GetRdyPriSeqNum(U8 seqNum)
astroboy 0:94897d537b31 148 {
astroboy 0:94897d537b31 149 U32 tmp;
astroboy 0:94897d537b31 150 U8 i,j,num;
astroboy 0:94897d537b31 151 S8 cnt;
astroboy 0:94897d537b31 152 i = seqNum/32;
astroboy 0:94897d537b31 153 j = seqNum%32;
astroboy 0:94897d537b31 154
astroboy 0:94897d537b31 155 do
astroboy 0:94897d537b31 156 {
astroboy 0:94897d537b31 157 tmp = RdyTaskPriInfo[i];
astroboy 0:94897d537b31 158 if(tmp != 0)
astroboy 0:94897d537b31 159 {
astroboy 0:94897d537b31 160 num = j/8;
astroboy 0:94897d537b31 161 do
astroboy 0:94897d537b31 162 {
astroboy 0:94897d537b31 163 if((tmp&(0xff<<(num*8))) !=0 )
astroboy 0:94897d537b31 164 {
astroboy 0:94897d537b31 165 if((tmp&(0xf0<<(num*8))) !=0)
astroboy 0:94897d537b31 166 {
astroboy 0:94897d537b31 167 for(cnt=j; cnt >=(num*8+4); cnt--)
astroboy 0:94897d537b31 168 {
astroboy 0:94897d537b31 169 if( (tmp&(1<<cnt)) !=0)
astroboy 0:94897d537b31 170 {
astroboy 0:94897d537b31 171 return (32*i+cnt);
astroboy 0:94897d537b31 172 }
astroboy 0:94897d537b31 173 }
astroboy 0:94897d537b31 174 }
astroboy 0:94897d537b31 175
astroboy 0:94897d537b31 176 if((j&0x4)==4)
astroboy 0:94897d537b31 177 j = (j|0x3) -4;
astroboy 0:94897d537b31 178
astroboy 0:94897d537b31 179 for(cnt=j; cnt >=num*8; cnt--)
astroboy 0:94897d537b31 180 {
astroboy 0:94897d537b31 181 if( (tmp&(1<<cnt)) !=0)
astroboy 0:94897d537b31 182 {
astroboy 0:94897d537b31 183 return (32*i+cnt);
astroboy 0:94897d537b31 184 }
astroboy 0:94897d537b31 185 }
astroboy 0:94897d537b31 186 }
astroboy 0:94897d537b31 187 j = num*8 -1;
astroboy 0:94897d537b31 188 }while((num--)!=0);
astroboy 0:94897d537b31 189 }
astroboy 0:94897d537b31 190 j=31;
astroboy 0:94897d537b31 191 }while((i--)!=0);
astroboy 0:94897d537b31 192 return INVALID_ID;
astroboy 0:94897d537b31 193 }
astroboy 0:94897d537b31 194
astroboy 0:94897d537b31 195
astroboy 0:94897d537b31 196 /**
astroboy 0:94897d537b31 197 *******************************************************************************
astroboy 0:94897d537b31 198 * @brief Remap the ready status of priority queue from Assign sequence number
astroboy 0:94897d537b31 199 * @param[in] seqNum Assign sequence number
astroboy 0:94897d537b31 200 * @param[out] None
astroboy 0:94897d537b31 201 * @retval None
astroboy 0:94897d537b31 202 *
astroboy 0:94897d537b31 203 * @par Description
astroboy 0:94897d537b31 204 * @details This function is called in Binary-Scheduling Algorithm
astroboy 0:94897d537b31 205 * to Remap the ready status for priority queue.
astroboy 0:94897d537b31 206 *******************************************************************************
astroboy 0:94897d537b31 207 */
astroboy 0:94897d537b31 208 static void PrioRemap(OS_TID seqNum)
astroboy 0:94897d537b31 209 {
astroboy 0:94897d537b31 210 U8 i,j;
astroboy 0:94897d537b31 211 U32 tmp;
astroboy 0:94897d537b31 212 tmp = j = 0;
astroboy 0:94897d537b31 213 j = seqNum/32;
astroboy 0:94897d537b31 214 for(i=0;i<seqNum%32;i++)
astroboy 0:94897d537b31 215 {
astroboy 0:94897d537b31 216 tmp |= 1<<i;
astroboy 0:94897d537b31 217 }
astroboy 0:94897d537b31 218 tmp &= RdyTaskPriInfo[j];
astroboy 0:94897d537b31 219
astroboy 0:94897d537b31 220 for(i=seqNum; i<PriNum; i++)
astroboy 0:94897d537b31 221 {
astroboy 0:94897d537b31 222 if((i%32==0)&&(i!=seqNum))
astroboy 0:94897d537b31 223 {
astroboy 0:94897d537b31 224 RdyTaskPriInfo[j++] = tmp;
astroboy 0:94897d537b31 225 tmp = 0;
astroboy 0:94897d537b31 226 }
astroboy 0:94897d537b31 227 if(RdyTaskPri[i] != INVALID_ID)
astroboy 0:94897d537b31 228 {
astroboy 0:94897d537b31 229 tmp = tmp | (1<<(i%32));
astroboy 0:94897d537b31 230 }
astroboy 0:94897d537b31 231 }
astroboy 0:94897d537b31 232 RdyTaskPriInfo[j++] = tmp;
astroboy 0:94897d537b31 233 }
astroboy 0:94897d537b31 234
astroboy 0:94897d537b31 235
astroboy 0:94897d537b31 236 /**
astroboy 0:94897d537b31 237 *******************************************************************************
astroboy 0:94897d537b31 238 * @brief Get the ready status for assign sequence number
astroboy 0:94897d537b31 239 * @param[in] seqNum Assign sequence number
astroboy 0:94897d537b31 240 * @param[out] None
astroboy 0:94897d537b31 241 * @retval Co_TRUE This priority has ready task
astroboy 0:94897d537b31 242 * Co_FALSE This priority doesn't have ready task
astroboy 0:94897d537b31 243 *
astroboy 0:94897d537b31 244 * @par Description
astroboy 0:94897d537b31 245 * @details This function is called in Binary-Scheduling Algorithm
astroboy 0:94897d537b31 246 * to get the ready status for assign sequence number.
astroboy 0:94897d537b31 247 *******************************************************************************
astroboy 0:94897d537b31 248 */
astroboy 0:94897d537b31 249 static BOOL GetPrioSeqNumStatus(U8 seqNum)
astroboy 0:94897d537b31 250 {
astroboy 0:94897d537b31 251 if( (RdyTaskPriInfo[seqNum/32] & (1<<(seqNum%32))) == 0)
astroboy 0:94897d537b31 252 {
astroboy 0:94897d537b31 253 return Co_FALSE;
astroboy 0:94897d537b31 254 }
astroboy 0:94897d537b31 255 return Co_TRUE;
astroboy 0:94897d537b31 256 }
astroboy 0:94897d537b31 257
astroboy 0:94897d537b31 258
astroboy 0:94897d537b31 259 /**
astroboy 0:94897d537b31 260 *******************************************************************************
astroboy 0:94897d537b31 261 * @brief Set the ready status for assign sequence number
astroboy 0:94897d537b31 262 * @param[in] seqNum Assign sequence number
astroboy 0:94897d537b31 263 * @param[in] isRdy Ready statues for assign sequence number
astroboy 0:94897d537b31 264 * @param[out] None
astroboy 0:94897d537b31 265 * @retval None
astroboy 0:94897d537b31 266 *
astroboy 0:94897d537b31 267 * @par Description
astroboy 0:94897d537b31 268 * @details This function is called in Binary-Scheduling Algorithm
astroboy 0:94897d537b31 269 * to set the ready status for assign sequence number.
astroboy 0:94897d537b31 270 *******************************************************************************
astroboy 0:94897d537b31 271 */
astroboy 0:94897d537b31 272 static void SetPrioSeqNumStatus(U8 seqNum, BOOL isRdy)
astroboy 0:94897d537b31 273 {
astroboy 0:94897d537b31 274 U32 tmp;
astroboy 0:94897d537b31 275 tmp = RdyTaskPriInfo[seqNum/32];
astroboy 0:94897d537b31 276 tmp &= ~(1<<(seqNum%32));
astroboy 0:94897d537b31 277 tmp |= isRdy<<(seqNum%32);
astroboy 0:94897d537b31 278 RdyTaskPriInfo[seqNum/32] = tmp;
astroboy 0:94897d537b31 279 }
astroboy 0:94897d537b31 280
astroboy 0:94897d537b31 281
astroboy 0:94897d537b31 282 /**
astroboy 0:94897d537b31 283 *******************************************************************************
astroboy 0:94897d537b31 284 * @brief Active priority in queue
astroboy 0:94897d537b31 285 * @param[in] pri Task priority
astroboy 0:94897d537b31 286 * @param[in] None
astroboy 0:94897d537b31 287 * @param[out] None
astroboy 0:94897d537b31 288 * @retval None
astroboy 0:94897d537b31 289 *
astroboy 0:94897d537b31 290 * @par Description
astroboy 0:94897d537b31 291 * @details This function is called in Binary-Scheduling Algorithm
astroboy 0:94897d537b31 292 * to active priority in queue, if this priority had been in activation,
astroboy 0:94897d537b31 293 * increate the task num for this priority.
astroboy 0:94897d537b31 294 *******************************************************************************
astroboy 0:94897d537b31 295 */
astroboy 0:94897d537b31 296 void ActiveTaskPri(U8 pri)
astroboy 0:94897d537b31 297 {
astroboy 0:94897d537b31 298 OS_TID seqNum,num;
astroboy 0:94897d537b31 299 if(GetPriSeqNum(pri,&seqNum) == Co_FALSE)
astroboy 0:94897d537b31 300 {
astroboy 0:94897d537b31 301 for(num=PriNum;num>seqNum;num--)
astroboy 0:94897d537b31 302 {
astroboy 0:94897d537b31 303 ActivePri[num] = ActivePri[num-1];
astroboy 0:94897d537b31 304 TaskNumPerPri[num] = TaskNumPerPri[num-1];
astroboy 0:94897d537b31 305 RdyTaskPri[num] = RdyTaskPri[num-1];
astroboy 0:94897d537b31 306 }
astroboy 0:94897d537b31 307 ActivePri[seqNum] = pri;
astroboy 0:94897d537b31 308 TaskNumPerPri[seqNum] = 1;
astroboy 0:94897d537b31 309 RdyTaskPri[seqNum] = INVALID_ID;
astroboy 0:94897d537b31 310 PriNum++;
astroboy 0:94897d537b31 311 PrioRemap(seqNum);
astroboy 0:94897d537b31 312 }
astroboy 0:94897d537b31 313 else
astroboy 0:94897d537b31 314 {
astroboy 0:94897d537b31 315 TaskNumPerPri[seqNum]++;
astroboy 0:94897d537b31 316 }
astroboy 0:94897d537b31 317 }
astroboy 0:94897d537b31 318
astroboy 0:94897d537b31 319
astroboy 0:94897d537b31 320
astroboy 0:94897d537b31 321 /**
astroboy 0:94897d537b31 322 *******************************************************************************
astroboy 0:94897d537b31 323 * @brief Delete priority in queue
astroboy 0:94897d537b31 324 * @param[in] pri Task priority
astroboy 0:94897d537b31 325 * @param[in] None
astroboy 0:94897d537b31 326 * @param[out] None
astroboy 0:94897d537b31 327 * @retval None
astroboy 0:94897d537b31 328 *
astroboy 0:94897d537b31 329 * @par Description
astroboy 0:94897d537b31 330 * @details This function is called in Binary-Scheduling Algorithm
astroboy 0:94897d537b31 331 * to decrease the task num for this priority, if the num goto 0,
astroboy 0:94897d537b31 332 * remove the priority for queue.
astroboy 0:94897d537b31 333 *******************************************************************************
astroboy 0:94897d537b31 334 */
astroboy 0:94897d537b31 335 void DeleteTaskPri(U8 pri)
astroboy 0:94897d537b31 336 {
astroboy 0:94897d537b31 337 OS_TID seqNum,num;
astroboy 0:94897d537b31 338
astroboy 0:94897d537b31 339 GetPriSeqNum(pri,&seqNum);
astroboy 0:94897d537b31 340 TaskNumPerPri[seqNum]--;
astroboy 0:94897d537b31 341 if(TaskNumPerPri[seqNum]==0)
astroboy 0:94897d537b31 342 {
astroboy 0:94897d537b31 343 for(num=seqNum; num<(PriNum-1); num++)
astroboy 0:94897d537b31 344 {
astroboy 0:94897d537b31 345 ActivePri[num] = ActivePri[num+1];
astroboy 0:94897d537b31 346 TaskNumPerPri[num] = TaskNumPerPri[num+1];
astroboy 0:94897d537b31 347 RdyTaskPri[num] = RdyTaskPri[num+1];
astroboy 0:94897d537b31 348 }
astroboy 0:94897d537b31 349 PriNum--;
astroboy 0:94897d537b31 350 PrioRemap(seqNum);
astroboy 0:94897d537b31 351 }
astroboy 0:94897d537b31 352 }
astroboy 0:94897d537b31 353
astroboy 0:94897d537b31 354 #endif
astroboy 0:94897d537b31 355
astroboy 0:94897d537b31 356
astroboy 0:94897d537b31 357 /**
astroboy 0:94897d537b31 358 *******************************************************************************
astroboy 0:94897d537b31 359 * @brief Insert a task to the ready list
astroboy 0:94897d537b31 360 * @param[in] tcbInsert A pointer to task will be inserted.
astroboy 0:94897d537b31 361 * @param[out] None
astroboy 0:94897d537b31 362 * @retval None
astroboy 0:94897d537b31 363 *
astroboy 0:94897d537b31 364 * @par Description
astroboy 0:94897d537b31 365 * @details This function is called to insert a task to the READY list.
astroboy 0:94897d537b31 366 *******************************************************************************
astroboy 0:94897d537b31 367 */
astroboy 0:94897d537b31 368 void InsertToTCBRdyList(P_OSTCB tcbInsert)
astroboy 0:94897d537b31 369 {
astroboy 0:94897d537b31 370 P_OSTCB ptcbNext,ptcb;
astroboy 0:94897d537b31 371 U8 prio;
astroboy 0:94897d537b31 372 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 373 U8 seqNum;
astroboy 0:94897d537b31 374 U8 RdyTaskSeqNum;
astroboy 0:94897d537b31 375 #endif
astroboy 0:94897d537b31 376
astroboy 0:94897d537b31 377 prio = tcbInsert->prio; /* Get PRI of inserted task */
astroboy 0:94897d537b31 378 tcbInsert->state = TASK_READY; /* Set task as TASK_READY */
astroboy 0:94897d537b31 379
astroboy 0:94897d537b31 380 #if CFG_ROBIN_EN >0
astroboy 0:94897d537b31 381 ptcb = TCBRunning;
astroboy 0:94897d537b31 382 /* Set schedule time for the same PRI task as TCBRunning. */
astroboy 0:94897d537b31 383 if(prio == ptcb->prio) /* Is PRI of inserted task equal to running task? */
astroboy 0:94897d537b31 384 {
astroboy 0:94897d537b31 385 if(ptcb != tcbInsert) /* Yes,is inserted task equal to running task? */
astroboy 0:94897d537b31 386 {
astroboy 0:94897d537b31 387 if(ptcb != Co_NULL) /* No,TCBRunning == Co_NULL? */
astroboy 0:94897d537b31 388 { /* N0,OSCheckTime < OSTickCnt? */
astroboy 0:94897d537b31 389 if(OSCheckTime < OSTickCnt)
astroboy 0:94897d537b31 390 { /* Yes,set OSCheckTime for task robin */
astroboy 0:94897d537b31 391 OSCheckTime = OSTickCnt + ptcb->timeSlice;
astroboy 0:94897d537b31 392 }
astroboy 0:94897d537b31 393 }
astroboy 0:94897d537b31 394 }
astroboy 0:94897d537b31 395 }
astroboy 0:94897d537b31 396 #endif
astroboy 0:94897d537b31 397
astroboy 0:94897d537b31 398
astroboy 0:94897d537b31 399 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 400 GetPriSeqNum(prio,&seqNum);
astroboy 0:94897d537b31 401 if(GetPrioSeqNumStatus(seqNum) == Co_TRUE)
astroboy 0:94897d537b31 402 {
astroboy 0:94897d537b31 403 ptcb = &TCBTbl[RdyTaskPri[seqNum]];
astroboy 0:94897d537b31 404 RdyTaskPri[seqNum] = tcbInsert->taskID;
astroboy 0:94897d537b31 405 }
astroboy 0:94897d537b31 406 else
astroboy 0:94897d537b31 407 {
astroboy 0:94897d537b31 408 RdyTaskPri[seqNum] = tcbInsert->taskID;
astroboy 0:94897d537b31 409 RdyTaskSeqNum = GetRdyPriSeqNum(seqNum);
astroboy 0:94897d537b31 410 SetPrioSeqNumStatus(seqNum, 1);
astroboy 0:94897d537b31 411 if(RdyTaskSeqNum == INVALID_ID)
astroboy 0:94897d537b31 412 {
astroboy 0:94897d537b31 413 ptcb = TCBRdy;
astroboy 0:94897d537b31 414 TaskSchedReq = Co_TRUE;
astroboy 0:94897d537b31 415 if(ptcb == Co_NULL)
astroboy 0:94897d537b31 416 {
astroboy 0:94897d537b31 417 TCBRdy = tcbInsert;
astroboy 0:94897d537b31 418 }
astroboy 0:94897d537b31 419 else
astroboy 0:94897d537b31 420 {
astroboy 0:94897d537b31 421 tcbInsert->TCBnext = ptcb; /* Yes,set tcbInsert as head item of list */
astroboy 0:94897d537b31 422 ptcb->TCBprev = tcbInsert;
astroboy 0:94897d537b31 423 TCBRdy = tcbInsert;
astroboy 0:94897d537b31 424 }
astroboy 0:94897d537b31 425 return;
astroboy 0:94897d537b31 426 }
astroboy 0:94897d537b31 427 else
astroboy 0:94897d537b31 428 {
astroboy 0:94897d537b31 429 ptcb = &TCBTbl[RdyTaskPri[RdyTaskSeqNum]];
astroboy 0:94897d537b31 430 }
astroboy 0:94897d537b31 431 }
astroboy 0:94897d537b31 432
astroboy 0:94897d537b31 433 ptcbNext = ptcb->TCBnext;
astroboy 0:94897d537b31 434 tcbInsert->TCBnext = ptcbNext; /* Set link for list */
astroboy 0:94897d537b31 435 ptcb->TCBnext = tcbInsert;
astroboy 0:94897d537b31 436 tcbInsert->TCBprev = ptcb;
astroboy 0:94897d537b31 437 if(ptcbNext != Co_NULL)
astroboy 0:94897d537b31 438 {
astroboy 0:94897d537b31 439 ptcbNext->TCBprev = tcbInsert;
astroboy 0:94897d537b31 440 }
astroboy 0:94897d537b31 441
astroboy 0:94897d537b31 442
astroboy 0:94897d537b31 443 #else
astroboy 0:94897d537b31 444 ptcb = TCBRdy;
astroboy 0:94897d537b31 445 if (ptcb == Co_NULL) /* Is ready list Co_NULL? */
astroboy 0:94897d537b31 446 {
astroboy 0:94897d537b31 447 TaskSchedReq = Co_TRUE;
astroboy 0:94897d537b31 448 TCBRdy = tcbInsert; /* Yse,set tcbInsert as head item of list */
astroboy 0:94897d537b31 449 }
astroboy 0:94897d537b31 450 else if (prio < ptcb->prio)/* Is PRI of inserted task higher than TCBRdy? */
astroboy 0:94897d537b31 451 {
astroboy 0:94897d537b31 452 TaskSchedReq = Co_TRUE;
astroboy 0:94897d537b31 453 tcbInsert->TCBnext = ptcb; /* Yes,set tcbInsert as head item of list */
astroboy 0:94897d537b31 454 ptcb->TCBprev = tcbInsert;
astroboy 0:94897d537b31 455 TCBRdy = tcbInsert;
astroboy 0:94897d537b31 456 }
astroboy 0:94897d537b31 457 else /* No,find correct place */
astroboy 0:94897d537b31 458 {
astroboy 0:94897d537b31 459 ptcbNext = ptcb->TCBnext; /* Get next item */
astroboy 0:94897d537b31 460 while(ptcbNext != Co_NULL) /* Is last item in ready list? */
astroboy 0:94897d537b31 461 { /* No,find correct place */
astroboy 0:94897d537b31 462 if(prio < ptcbNext->prio) /* Is correct place? */
astroboy 0:94897d537b31 463 break; /* Yes,break circulation */
astroboy 0:94897d537b31 464 ptcb = ptcbNext; /* Save current item */
astroboy 0:94897d537b31 465 ptcbNext = ptcbNext->TCBnext; /* Get next item */
astroboy 0:94897d537b31 466 }
astroboy 0:94897d537b31 467 tcbInsert->TCBnext = ptcbNext; /* Set link for list */
astroboy 0:94897d537b31 468 ptcb->TCBnext = tcbInsert;
astroboy 0:94897d537b31 469 tcbInsert->TCBprev = ptcb;
astroboy 0:94897d537b31 470 if(ptcbNext != Co_NULL)
astroboy 0:94897d537b31 471 {
astroboy 0:94897d537b31 472 ptcbNext->TCBprev = tcbInsert;
astroboy 0:94897d537b31 473 }
astroboy 0:94897d537b31 474 }
astroboy 0:94897d537b31 475 #endif
astroboy 0:94897d537b31 476 }
astroboy 0:94897d537b31 477
astroboy 0:94897d537b31 478
astroboy 0:94897d537b31 479
astroboy 0:94897d537b31 480 /**
astroboy 0:94897d537b31 481 *******************************************************************************
astroboy 0:94897d537b31 482 * @brief Remove a task from the READY list
astroboy 0:94897d537b31 483 * @param[in] ptcb A pointer to task which be removed.
astroboy 0:94897d537b31 484 * @param[out] None
astroboy 0:94897d537b31 485 * @retval None
astroboy 0:94897d537b31 486 *
astroboy 0:94897d537b31 487 * @par Description
astroboy 0:94897d537b31 488 * @details This function is called to remove a task from the READY list.
astroboy 0:94897d537b31 489 *******************************************************************************
astroboy 0:94897d537b31 490 */
astroboy 0:94897d537b31 491 void RemoveFromTCBRdyList(P_OSTCB ptcb)
astroboy 0:94897d537b31 492 {
astroboy 0:94897d537b31 493
astroboy 0:94897d537b31 494 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 495 U8 prio;
astroboy 0:94897d537b31 496 U8 seqNum;
astroboy 0:94897d537b31 497 BOOL isChange;
astroboy 0:94897d537b31 498 isChange = Co_FALSE;
astroboy 0:94897d537b31 499 prio = ptcb->prio;
astroboy 0:94897d537b31 500 GetPriSeqNum(prio,&seqNum);
astroboy 0:94897d537b31 501 #endif
astroboy 0:94897d537b31 502
astroboy 0:94897d537b31 503 /* Is there only one item in READY list? */
astroboy 0:94897d537b31 504 if((ptcb->TCBnext == Co_NULL) && (ptcb->TCBprev == Co_NULL) )
astroboy 0:94897d537b31 505 {
astroboy 0:94897d537b31 506 TCBRdy = 0; /* Yes,set READY list as Co_NULL */
astroboy 0:94897d537b31 507 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 508 isChange = Co_TRUE;
astroboy 0:94897d537b31 509 #endif
astroboy 0:94897d537b31 510 }
astroboy 0:94897d537b31 511 else if(ptcb->TCBprev == 0) /* Is the first item in READY list? */
astroboy 0:94897d537b31 512 {
astroboy 0:94897d537b31 513 /* Yes,remove task from the list,and reset the head of READY list */
astroboy 0:94897d537b31 514 TCBRdy = ptcb->TCBnext;
astroboy 0:94897d537b31 515 ptcb->TCBnext = 0;
astroboy 0:94897d537b31 516 TCBRdy->TCBprev = 0;
astroboy 0:94897d537b31 517 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 518 if(TCBRdy->prio != prio)
astroboy 0:94897d537b31 519 isChange = Co_TRUE;
astroboy 0:94897d537b31 520
astroboy 0:94897d537b31 521 #endif
astroboy 0:94897d537b31 522 }
astroboy 0:94897d537b31 523 else if( ptcb->TCBnext == 0) /* Is the last item in READY list? */
astroboy 0:94897d537b31 524 { /* Yes,remove task from list */
astroboy 0:94897d537b31 525 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 526 if(ptcb->TCBprev->prio != prio)
astroboy 0:94897d537b31 527 isChange = Co_TRUE;
astroboy 0:94897d537b31 528 else
astroboy 0:94897d537b31 529 RdyTaskPri[seqNum] = ptcb->TCBprev->taskID;
astroboy 0:94897d537b31 530 #endif
astroboy 0:94897d537b31 531 ptcb->TCBprev->TCBnext = 0;
astroboy 0:94897d537b31 532 ptcb->TCBprev = 0;
astroboy 0:94897d537b31 533 }
astroboy 0:94897d537b31 534 else /* No, remove task from list */
astroboy 0:94897d537b31 535 {
astroboy 0:94897d537b31 536 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 537 if((ptcb->TCBprev->prio != prio) && (ptcb->TCBnext->prio != prio))
astroboy 0:94897d537b31 538 isChange = Co_TRUE;
astroboy 0:94897d537b31 539 else if((ptcb->TCBprev->prio == prio) && (ptcb->TCBnext->prio != prio))
astroboy 0:94897d537b31 540 RdyTaskPri[seqNum] = ptcb->TCBprev->taskID;
astroboy 0:94897d537b31 541 #endif
astroboy 0:94897d537b31 542 ptcb->TCBprev->TCBnext = ptcb->TCBnext;
astroboy 0:94897d537b31 543 ptcb->TCBnext->TCBprev = ptcb->TCBprev;
astroboy 0:94897d537b31 544 ptcb->TCBnext = 0;
astroboy 0:94897d537b31 545 ptcb->TCBprev = 0;
astroboy 0:94897d537b31 546 }
astroboy 0:94897d537b31 547 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 548 if(isChange == Co_TRUE)
astroboy 0:94897d537b31 549 {
astroboy 0:94897d537b31 550 RdyTaskPri[seqNum] = INVALID_ID;
astroboy 0:94897d537b31 551 SetPrioSeqNumStatus(seqNum, 0);
astroboy 0:94897d537b31 552 }
astroboy 0:94897d537b31 553 #endif
astroboy 0:94897d537b31 554 }
astroboy 0:94897d537b31 555
astroboy 0:94897d537b31 556
astroboy 0:94897d537b31 557 #if CFG_MUTEX_EN > 0
astroboy 0:94897d537b31 558 #define CFG_PRIORITY_SET_EN (1)
astroboy 0:94897d537b31 559 #endif
astroboy 0:94897d537b31 560 #if CFG_PRIORITY_SET_EN >0
astroboy 0:94897d537b31 561 /**
astroboy 0:94897d537b31 562 *******************************************************************************
astroboy 0:94897d537b31 563 * @brief Change task priority
astroboy 0:94897d537b31 564 * @param[in] taskID Specify task id.
astroboy 0:94897d537b31 565 * @param[in] priority New priority.
astroboy 0:94897d537b31 566 * @param[out] None
astroboy 0:94897d537b31 567 * @retval E_OK Change priority successful.
astroboy 0:94897d537b31 568 * @retval E_INVALID_ID Invalid id,change priority fail.
astroboy 0:94897d537b31 569 * @retval E_PROTECTED_TASK Can't change idle task priority.
astroboy 0:94897d537b31 570 *
astroboy 0:94897d537b31 571 * @par Description
astroboy 0:94897d537b31 572 * @details This function is called to change priority for a specify task.
astroboy 0:94897d537b31 573 *******************************************************************************
astroboy 0:94897d537b31 574 */
astroboy 0:94897d537b31 575 StatusType CoSetPriority(OS_TID taskID,U8 priority)
astroboy 0:94897d537b31 576 {
astroboy 0:94897d537b31 577 P_OSTCB ptcb;
astroboy 0:94897d537b31 578 #if CFG_MUTEX_EN >0
astroboy 0:94897d537b31 579 U8 prio;
astroboy 0:94897d537b31 580 P_MUTEX pMutex;
astroboy 0:94897d537b31 581 #endif
astroboy 0:94897d537b31 582 #if CFG_EVENT_EN >0
astroboy 0:94897d537b31 583 P_ECB pecb;
astroboy 0:94897d537b31 584 #endif
astroboy 0:94897d537b31 585
astroboy 0:94897d537b31 586 if(taskID == 0) /* Is idle task? */
astroboy 0:94897d537b31 587 {
astroboy 0:94897d537b31 588 return E_PROTECTED_TASK; /* Yes,error return */
astroboy 0:94897d537b31 589 }
astroboy 0:94897d537b31 590
astroboy 0:94897d537b31 591 #if CFG_PAR_CHECKOUT_EN >0 /* Check validity of parameter */
astroboy 0:94897d537b31 592 if(taskID >= CFG_MAX_USER_TASKS + SYS_TASK_NUM)
astroboy 0:94897d537b31 593 {
astroboy 0:94897d537b31 594 return E_INVALID_ID;
astroboy 0:94897d537b31 595 }
astroboy 0:94897d537b31 596 #endif
astroboy 0:94897d537b31 597 ptcb = &TCBTbl[taskID]; /* Get TCB of task ID */
astroboy 0:94897d537b31 598 #if CFG_PAR_CHECKOUT_EN >0
astroboy 0:94897d537b31 599 if(ptcb->state == TASK_DORMANT)
astroboy 0:94897d537b31 600 {
astroboy 0:94897d537b31 601 return E_INVALID_ID;
astroboy 0:94897d537b31 602 }
astroboy 0:94897d537b31 603 if(priority > CFG_LOWEST_PRIO)
astroboy 0:94897d537b31 604 {
astroboy 0:94897d537b31 605 return E_INVALID_ID;
astroboy 0:94897d537b31 606 }
astroboy 0:94897d537b31 607 #endif
astroboy 0:94897d537b31 608
astroboy 0:94897d537b31 609 if(ptcb->prio != priority) /* Is PRI equal to original PRI? */
astroboy 0:94897d537b31 610 { /* No */
astroboy 0:94897d537b31 611 #if CFG_MUTEX_EN >0
astroboy 0:94897d537b31 612 if(ptcb->mutexID != INVALID_ID)
astroboy 0:94897d537b31 613 {
astroboy 0:94897d537b31 614 pMutex = &MutexTbl[ptcb->mutexID];
astroboy 0:94897d537b31 615 if(pMutex->taskID == ptcb->taskID) /* Task hold mutex? */
astroboy 0:94897d537b31 616 {
astroboy 0:94897d537b31 617 pMutex->originalPrio= priority;/* Yes,change original PRI in mutex*/
astroboy 0:94897d537b31 618 if(ptcb->prio < priority) /* Is task priority higher than set?*/
astroboy 0:94897d537b31 619 {
astroboy 0:94897d537b31 620 return E_OK; /* Yes,do nothing,return OK */
astroboy 0:94897d537b31 621 }
astroboy 0:94897d537b31 622 }
astroboy 0:94897d537b31 623 }
astroboy 0:94897d537b31 624
astroboy 0:94897d537b31 625 #endif
astroboy 0:94897d537b31 626
astroboy 0:94897d537b31 627 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 628 DeleteTaskPri(ptcb->prio);
astroboy 0:94897d537b31 629 ActiveTaskPri(priority);
astroboy 0:94897d537b31 630 #endif
astroboy 0:94897d537b31 631
astroboy 0:94897d537b31 632 ptcb->prio = priority; /* Change task PRI */
astroboy 0:94897d537b31 633 if(ptcb->state == TASK_READY) /* Is task in READY list? */
astroboy 0:94897d537b31 634 {
astroboy 0:94897d537b31 635 OsSchedLock(); /* Yes,reorder task in READY list */
astroboy 0:94897d537b31 636 RemoveFromTCBRdyList(ptcb);
astroboy 0:94897d537b31 637 InsertToTCBRdyList(ptcb);
astroboy 0:94897d537b31 638 OsSchedUnlock();
astroboy 0:94897d537b31 639 }
astroboy 0:94897d537b31 640 else if(ptcb->state == TASK_RUNNING)/* Is task running? */
astroboy 0:94897d537b31 641 {
astroboy 0:94897d537b31 642 if(ptcb->prio > TCBRdy->prio) /* Yes,Is PRI higher than TCBRdy? */
astroboy 0:94897d537b31 643 {
astroboy 0:94897d537b31 644 OsSchedLock(); /* Yes,reorder task in READY list */
astroboy 0:94897d537b31 645 TaskSchedReq = Co_TRUE;
astroboy 0:94897d537b31 646 OsSchedUnlock();
astroboy 0:94897d537b31 647 }
astroboy 0:94897d537b31 648 }
astroboy 0:94897d537b31 649 else
astroboy 0:94897d537b31 650 { /* No,task in WAITING list */
astroboy 0:94897d537b31 651 #if CFG_MUTEX_EN >0
astroboy 0:94897d537b31 652 if(ptcb->mutexID != INVALID_ID) /* Is task in mutex WAITING list? */
astroboy 0:94897d537b31 653 {
astroboy 0:94897d537b31 654 /* Yes,reset the highest PRI in the list */
astroboy 0:94897d537b31 655 OsSchedLock();
astroboy 0:94897d537b31 656 pMutex = &MutexTbl[ptcb->mutexID];
astroboy 0:94897d537b31 657 ptcb = pMutex->waittingList;
astroboy 0:94897d537b31 658 prio = pMutex->originalPrio;
astroboy 0:94897d537b31 659 pMutex->hipriTaskID = pMutex->taskID;
astroboy 0:94897d537b31 660 while(ptcb != Co_NULL)
astroboy 0:94897d537b31 661 {
astroboy 0:94897d537b31 662 if(ptcb->prio < prio)
astroboy 0:94897d537b31 663 {
astroboy 0:94897d537b31 664 prio = ptcb->prio;
astroboy 0:94897d537b31 665 pMutex->hipriTaskID = ptcb->taskID;
astroboy 0:94897d537b31 666 }
astroboy 0:94897d537b31 667 ptcb = ptcb->TCBnext;
astroboy 0:94897d537b31 668 }
astroboy 0:94897d537b31 669 OsSchedUnlock();
astroboy 0:94897d537b31 670 if(pMutex->originalPrio != prio)
astroboy 0:94897d537b31 671 {
astroboy 0:94897d537b31 672 CoSetPriority(pMutex->taskID,prio);
astroboy 0:94897d537b31 673 }
astroboy 0:94897d537b31 674 }
astroboy 0:94897d537b31 675 #endif
astroboy 0:94897d537b31 676
astroboy 0:94897d537b31 677 #if CFG_EVENT_EN >0
astroboy 0:94897d537b31 678 ptcb = &TCBTbl[taskID];
astroboy 0:94897d537b31 679 if(ptcb->eventID != INVALID_ID) /* Is task in event WAITING list? */
astroboy 0:94897d537b31 680 {
astroboy 0:94897d537b31 681 pecb = &EventTbl[ptcb->eventID];
astroboy 0:94897d537b31 682
astroboy 0:94897d537b31 683 /* Yes,is event sort type as preemptive PRI? */
astroboy 0:94897d537b31 684 if(pecb->eventSortType == EVENT_SORT_TYPE_PRIO)
astroboy 0:94897d537b31 685 {
astroboy 0:94897d537b31 686 /* Yes,reorder task in the list */
astroboy 0:94897d537b31 687 RemoveEventWaittingList(ptcb);
astroboy 0:94897d537b31 688 EventTaskToWait(pecb,ptcb);
astroboy 0:94897d537b31 689 }
astroboy 0:94897d537b31 690 }
astroboy 0:94897d537b31 691 #endif
astroboy 0:94897d537b31 692 }
astroboy 0:94897d537b31 693 }
astroboy 0:94897d537b31 694 return E_OK;
astroboy 0:94897d537b31 695 }
astroboy 0:94897d537b31 696 #endif
astroboy 0:94897d537b31 697
astroboy 0:94897d537b31 698 /**
astroboy 0:94897d537b31 699 *******************************************************************************
astroboy 0:94897d537b31 700 * @brief Schedule function
astroboy 0:94897d537b31 701 * @param[in] None
astroboy 0:94897d537b31 702 * @param[out] None
astroboy 0:94897d537b31 703 * @retval None
astroboy 0:94897d537b31 704 *
astroboy 0:94897d537b31 705 * @par Description
astroboy 0:94897d537b31 706 * @details This function is called by every where need to switch context,
astroboy 0:94897d537b31 707 * It is schedule function of OS kernel.
astroboy 0:94897d537b31 708 *******************************************************************************
astroboy 0:94897d537b31 709 */
astroboy 0:94897d537b31 710 void Schedule(void)
astroboy 0:94897d537b31 711 {
astroboy 0:94897d537b31 712 U8 RunPrio,RdyPrio;
astroboy 0:94897d537b31 713 P_OSTCB pRdyTcb,pCurTcb;
astroboy 0:94897d537b31 714
astroboy 0:94897d537b31 715
astroboy 0:94897d537b31 716 pCurTcb = TCBRunning;
astroboy 0:94897d537b31 717 pRdyTcb = TCBRdy;
astroboy 0:94897d537b31 718
astroboy 0:94897d537b31 719 if((pRdyTcb==Co_NULL) || (pCurTcb != TCBNext) || (OSSchedLock >1) || (OSIntNesting >0))
astroboy 0:94897d537b31 720 {
astroboy 0:94897d537b31 721 return;
astroboy 0:94897d537b31 722 }
astroboy 0:94897d537b31 723
astroboy 0:94897d537b31 724 TaskSchedReq = Co_FALSE;
astroboy 0:94897d537b31 725 RunPrio = pCurTcb->prio;
astroboy 0:94897d537b31 726 RdyPrio = pRdyTcb->prio;
astroboy 0:94897d537b31 727
astroboy 0:94897d537b31 728 /* Is Running task status was changed? */
astroboy 0:94897d537b31 729 if(pCurTcb->state != TASK_RUNNING)
astroboy 0:94897d537b31 730 {
astroboy 0:94897d537b31 731 TCBNext = pRdyTcb; /* Yes,set TCBNext and reorder READY list */
astroboy 0:94897d537b31 732 pRdyTcb->state = TASK_RUNNING;
astroboy 0:94897d537b31 733 RemoveFromTCBRdyList(pRdyTcb);
astroboy 0:94897d537b31 734 }
astroboy 0:94897d537b31 735
astroboy 0:94897d537b31 736 else if(RdyPrio < RunPrio ) /* Is higher PRI task coming in? */
astroboy 0:94897d537b31 737 {
astroboy 0:94897d537b31 738 TCBNext = pRdyTcb; /* Yes,set TCBNext and reorder READY list */
astroboy 0:94897d537b31 739 InsertToTCBRdyList(pCurTcb);
astroboy 0:94897d537b31 740 RemoveFromTCBRdyList(pRdyTcb);
astroboy 0:94897d537b31 741 pRdyTcb->state = TASK_RUNNING;
astroboy 0:94897d537b31 742 }
astroboy 0:94897d537b31 743
astroboy 0:94897d537b31 744 #if CFG_ROBIN_EN >0 /* Is time for robinning */
astroboy 0:94897d537b31 745 else if((RunPrio == RdyPrio) && (OSCheckTime == OSTickCnt))
astroboy 0:94897d537b31 746 {
astroboy 0:94897d537b31 747 TCBNext = pRdyTcb; /* Yes,set TCBNext and reorder READY list */
astroboy 0:94897d537b31 748 InsertToTCBRdyList(pCurTcb);
astroboy 0:94897d537b31 749 RemoveFromTCBRdyList(pRdyTcb);
astroboy 0:94897d537b31 750 pRdyTcb->state = TASK_RUNNING;
astroboy 0:94897d537b31 751 }
astroboy 0:94897d537b31 752 #endif
astroboy 0:94897d537b31 753 else
astroboy 0:94897d537b31 754 {
astroboy 0:94897d537b31 755 return;
astroboy 0:94897d537b31 756 }
astroboy 0:94897d537b31 757
astroboy 0:94897d537b31 758 #if CFG_ROBIN_EN >0
astroboy 0:94897d537b31 759 if(TCBNext->prio == TCBRdy->prio) /* Reset OSCheckTime for task robinnig */
astroboy 0:94897d537b31 760 OSCheckTime = OSTickCnt + TCBNext->timeSlice;
astroboy 0:94897d537b31 761 #endif
astroboy 0:94897d537b31 762
astroboy 0:94897d537b31 763
astroboy 0:94897d537b31 764 #if CFG_STK_CHECKOUT_EN > 0 /* Is stack overflow? */
astroboy 0:94897d537b31 765 if((pCurTcb->stkPtr < pCurTcb->stack)||(*(U32*)(pCurTcb->stack) != MAGIC_WORD))
astroboy 0:94897d537b31 766 {
astroboy 0:94897d537b31 767 CoStkOverflowHook(pCurTcb->taskID); /* Yes,call handler */
astroboy 0:94897d537b31 768 }
astroboy 0:94897d537b31 769 #endif
astroboy 0:94897d537b31 770
astroboy 0:94897d537b31 771 SwitchContext(); /* Call task context switch */
astroboy 0:94897d537b31 772 }
astroboy 0:94897d537b31 773
astroboy 0:94897d537b31 774
astroboy 0:94897d537b31 775 /**
astroboy 0:94897d537b31 776 *******************************************************************************
astroboy 0:94897d537b31 777 * @brief Assign a TCB to task being created
astroboy 0:94897d537b31 778 * @param[in] None
astroboy 0:94897d537b31 779 * @param[out] None
astroboy 0:94897d537b31 780 *
astroboy 0:94897d537b31 781 * @retval XXXX
astroboy 0:94897d537b31 782 *
astroboy 0:94897d537b31 783 * @par Description
astroboy 0:94897d537b31 784 * @details This function is called to assign a task control block for task
astroboy 0:94897d537b31 785 * being created.
astroboy 0:94897d537b31 786 *******************************************************************************
astroboy 0:94897d537b31 787 */
astroboy 0:94897d537b31 788 static P_OSTCB AssignTCB(void)
astroboy 0:94897d537b31 789 {
astroboy 0:94897d537b31 790 P_OSTCB ptcb;
astroboy 0:94897d537b31 791
astroboy 0:94897d537b31 792 OsSchedLock(); /* Lock schedule */
astroboy 0:94897d537b31 793 if(FreeTCB == 0) /* Is there no free TCB */
astroboy 0:94897d537b31 794 {
astroboy 0:94897d537b31 795 OsSchedUnlock(); /* Yes,unlock schedule */
astroboy 0:94897d537b31 796 return 0; /* Error return */
astroboy 0:94897d537b31 797 }
astroboy 0:94897d537b31 798 ptcb = FreeTCB; /* Yes,assgin free TCB for this task */
astroboy 0:94897d537b31 799 /* Set next item as the head of free TCB list */
astroboy 0:94897d537b31 800 FreeTCB = FreeTCB->TCBnext;
astroboy 0:94897d537b31 801 OsSchedUnlock();
astroboy 0:94897d537b31 802 return ptcb;
astroboy 0:94897d537b31 803 }
astroboy 0:94897d537b31 804
astroboy 0:94897d537b31 805
astroboy 0:94897d537b31 806 /**
astroboy 0:94897d537b31 807 *******************************************************************************
astroboy 0:94897d537b31 808 * @brief Create a task
astroboy 0:94897d537b31 809 * @param[in] task Task code entry.
astroboy 0:94897d537b31 810 * @param[in] argv The parameter passed to task.
astroboy 0:94897d537b31 811 * @param[in] parameter Task priority + stack size + time slice + isWaitting.
astroboy 0:94897d537b31 812 * @param[in] stk Pointer to stack top of task.
astroboy 0:94897d537b31 813 * @param[out] None
astroboy 0:94897d537b31 814 * @retval E_CREATE_FAIL Fail to create a task .
astroboy 0:94897d537b31 815 * @retval others Valid task id.
astroboy 0:94897d537b31 816 *
astroboy 0:94897d537b31 817 * @par Description
astroboy 0:94897d537b31 818 * @details This function is called by application to create a task,return a id
astroboy 0:94897d537b31 819 * to mark this task.
astroboy 0:94897d537b31 820 *******************************************************************************
astroboy 0:94897d537b31 821 */
astroboy 0:94897d537b31 822 OS_TID CreateTask(FUNCPtr task,void *argv,U32 parameter,OS_STK *stk)
astroboy 0:94897d537b31 823 {
astroboy 0:94897d537b31 824 OS_STK* stkTopPtr;
astroboy 0:94897d537b31 825 P_OSTCB ptcb;
astroboy 0:94897d537b31 826 U8 prio;
astroboy 0:94897d537b31 827 #if CFG_ROBIN_EN >0
astroboy 0:94897d537b31 828 U16 timeSlice;
astroboy 0:94897d537b31 829 #endif
astroboy 0:94897d537b31 830
astroboy 0:94897d537b31 831 #if CFG_STK_CHECKOUT_EN >0 /* Check validity of parameter */
astroboy 0:94897d537b31 832 U16 sktSz;
astroboy 0:94897d537b31 833 sktSz = (parameter&0xfff00)>>8;
astroboy 0:94897d537b31 834 #endif
astroboy 0:94897d537b31 835 prio = parameter&0xff;
astroboy 0:94897d537b31 836
astroboy 0:94897d537b31 837 #if CFG_PAR_CHECKOUT_EN >0 /* Check validity of parameter */
astroboy 0:94897d537b31 838 if(task == 0)
astroboy 0:94897d537b31 839 {
astroboy 0:94897d537b31 840 return E_CREATE_FAIL;
astroboy 0:94897d537b31 841 }
astroboy 0:94897d537b31 842 if(stk == 0)
astroboy 0:94897d537b31 843 {
astroboy 0:94897d537b31 844 return E_CREATE_FAIL;
astroboy 0:94897d537b31 845 }
astroboy 0:94897d537b31 846 if(prio > CFG_LOWEST_PRIO)
astroboy 0:94897d537b31 847 {
astroboy 0:94897d537b31 848 return E_CREATE_FAIL;
astroboy 0:94897d537b31 849 }
astroboy 0:94897d537b31 850 #if CFG_STK_CHECKOUT_EN >0
astroboy 0:94897d537b31 851 if(sktSz < 20)
astroboy 0:94897d537b31 852 {
astroboy 0:94897d537b31 853 return E_CREATE_FAIL;
astroboy 0:94897d537b31 854 }
astroboy 0:94897d537b31 855 #endif // CFG_STK_CHECKOUT_EN
astroboy 0:94897d537b31 856 #endif // CFG_PAR_CHECKOUT_EN
astroboy 0:94897d537b31 857
astroboy 0:94897d537b31 858 #if CFG_TASK_SCHEDULE_EN == 0
astroboy 0:94897d537b31 859 if(TCBRunning != 0)
astroboy 0:94897d537b31 860 return E_CREATE_FAIL;
astroboy 0:94897d537b31 861 #endif
astroboy 0:94897d537b31 862
astroboy 0:94897d537b31 863 stkTopPtr = InitTaskContext(task,argv,stk); /* Initialize task context. */
astroboy 0:94897d537b31 864
astroboy 0:94897d537b31 865 ptcb = AssignTCB(); /* Get free TCB to use */
astroboy 0:94897d537b31 866
astroboy 0:94897d537b31 867 if(ptcb == 0) /* Is free TCB equal to Co_NULL? */
astroboy 0:94897d537b31 868 {
astroboy 0:94897d537b31 869 return E_CREATE_FAIL; /* Yes,error return */
astroboy 0:94897d537b31 870 }
astroboy 0:94897d537b31 871
astroboy 0:94897d537b31 872 ptcb->stkPtr = stkTopPtr; /* Initialize TCB as user set */
astroboy 0:94897d537b31 873 ptcb->prio = prio;
astroboy 0:94897d537b31 874 #if CFG_STK_CHECKOUT_EN >0
astroboy 0:94897d537b31 875 ptcb->stack = stk+1 - sktSz; /* Set bottom stack for stack overflow check */
astroboy 0:94897d537b31 876 *(U32*)(ptcb->stack) = MAGIC_WORD;
astroboy 0:94897d537b31 877 #endif
astroboy 0:94897d537b31 878
astroboy 0:94897d537b31 879 #if CFG_TASK_WAITTING_EN >0
astroboy 0:94897d537b31 880 ptcb->delayTick = INVALID_VALUE;
astroboy 0:94897d537b31 881 #endif
astroboy 0:94897d537b31 882
astroboy 0:94897d537b31 883 #if CFG_TASK_SCHEDULE_EN == 0
astroboy 0:94897d537b31 884 ptcb->taskFuc = task;
astroboy 0:94897d537b31 885 ptcb->taskStk = stk;
astroboy 0:94897d537b31 886 #endif
astroboy 0:94897d537b31 887 ptcb->TCBnext = 0; /* Initialize TCB link in READY list */
astroboy 0:94897d537b31 888 ptcb->TCBprev = 0;
astroboy 0:94897d537b31 889
astroboy 0:94897d537b31 890 #if CFG_ROBIN_EN >0 /* Set task time slice for task robin */
astroboy 0:94897d537b31 891 timeSlice = (parameter&0x7fff0000)>>20;
astroboy 0:94897d537b31 892 if(timeSlice == 0)
astroboy 0:94897d537b31 893 {
astroboy 0:94897d537b31 894 timeSlice = CFG_TIME_SLICE;
astroboy 0:94897d537b31 895 }
astroboy 0:94897d537b31 896 ptcb->timeSlice = timeSlice;
astroboy 0:94897d537b31 897 #endif
astroboy 0:94897d537b31 898
astroboy 0:94897d537b31 899 #if CFG_FLAG_EN > 0
astroboy 0:94897d537b31 900 ptcb->pnode = 0; /* Initialize task as no flag waiting */
astroboy 0:94897d537b31 901 #endif
astroboy 0:94897d537b31 902
astroboy 0:94897d537b31 903 #if CFG_EVENT_EN > 0
astroboy 0:94897d537b31 904 ptcb->eventID = INVALID_ID; /* Initialize task as no event waiting*/
astroboy 0:94897d537b31 905 ptcb->pmail = 0;
astroboy 0:94897d537b31 906 ptcb->waitNext = 0;
astroboy 0:94897d537b31 907 ptcb->waitPrev = 0;
astroboy 0:94897d537b31 908 #endif
astroboy 0:94897d537b31 909
astroboy 0:94897d537b31 910 #if CFG_MUTEX_EN > 0
astroboy 0:94897d537b31 911 /* Initialize task as no mutex holding or waiting */
astroboy 0:94897d537b31 912 ptcb->mutexID = INVALID_ID;
astroboy 0:94897d537b31 913 #endif
astroboy 0:94897d537b31 914
astroboy 0:94897d537b31 915 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 916 ActiveTaskPri(prio);
astroboy 0:94897d537b31 917 #endif
astroboy 0:94897d537b31 918
astroboy 0:94897d537b31 919 if((parameter>>31) == 0) /* Is task in waitting state? */
astroboy 0:94897d537b31 920 { /* No,set it into ready list */
astroboy 0:94897d537b31 921 OsSchedLock(); /* Lock schedule */
astroboy 0:94897d537b31 922 InsertToTCBRdyList(ptcb); /* Insert into the READY list */
astroboy 0:94897d537b31 923 OsSchedUnlock(); /* Unlock schedule */
astroboy 0:94897d537b31 924 }
astroboy 0:94897d537b31 925 else
astroboy 0:94897d537b31 926 { /* Yes,Set task status as TASK_WAITING*/
astroboy 0:94897d537b31 927 ptcb->state = TASK_WAITING;
astroboy 0:94897d537b31 928 }
astroboy 0:94897d537b31 929 return ptcb->taskID; /* Return task ID */
astroboy 0:94897d537b31 930 }
astroboy 0:94897d537b31 931
astroboy 0:94897d537b31 932
astroboy 0:94897d537b31 933 /**
astroboy 0:94897d537b31 934 *******************************************************************************
astroboy 0:94897d537b31 935 * @brief Delete Task
astroboy 0:94897d537b31 936 * @param[in] taskID Task ID
astroboy 0:94897d537b31 937 * @param[out] None
astroboy 0:94897d537b31 938 * @retval E_INVALID_ID Invalid task ID.
astroboy 0:94897d537b31 939 * @retval E_PROTECTED_TASK Protected task in OS.
astroboy 0:94897d537b31 940 * @retval E_OK Delete successful.
astroboy 0:94897d537b31 941 *
astroboy 0:94897d537b31 942 * @par Description
astroboy 0:94897d537b31 943 * @details This function is called to delete assign task.
astroboy 0:94897d537b31 944 *******************************************************************************
astroboy 0:94897d537b31 945 */
astroboy 0:94897d537b31 946 StatusType CoDelTask(OS_TID taskID)
astroboy 0:94897d537b31 947 {
astroboy 0:94897d537b31 948 P_OSTCB ptcb;
astroboy 0:94897d537b31 949
astroboy 0:94897d537b31 950 #if CFG_PAR_CHECKOUT_EN >0 /* Check validity of parameter */
astroboy 0:94897d537b31 951 if(taskID >= CFG_MAX_USER_TASKS + SYS_TASK_NUM)
astroboy 0:94897d537b31 952 {
astroboy 0:94897d537b31 953 return E_INVALID_ID;
astroboy 0:94897d537b31 954 }
astroboy 0:94897d537b31 955 #endif
astroboy 0:94897d537b31 956 ptcb = &TCBTbl[taskID];
astroboy 0:94897d537b31 957 #if CFG_PAR_CHECKOUT_EN >0
astroboy 0:94897d537b31 958 if(ptcb->state == TASK_DORMANT)
astroboy 0:94897d537b31 959 {
astroboy 0:94897d537b31 960 return E_INVALID_ID;
astroboy 0:94897d537b31 961 }
astroboy 0:94897d537b31 962 #endif
astroboy 0:94897d537b31 963 if(taskID == 0) /* Is idle task? */
astroboy 0:94897d537b31 964 {
astroboy 0:94897d537b31 965 return E_PROTECTED_TASK; /* Yes,error return */
astroboy 0:94897d537b31 966 }
astroboy 0:94897d537b31 967
astroboy 0:94897d537b31 968 if(ptcb->state == TASK_RUNNING) /* Is task running? */
astroboy 0:94897d537b31 969 {
astroboy 0:94897d537b31 970 if(OSSchedLock != 0) /* Yes,is OS lock? */
astroboy 0:94897d537b31 971 {
astroboy 0:94897d537b31 972 return E_OS_IN_LOCK; /* Yes,error return */
astroboy 0:94897d537b31 973 }
astroboy 0:94897d537b31 974 }
astroboy 0:94897d537b31 975
astroboy 0:94897d537b31 976 #if CFG_MUTEX_EN >0 /* Do task hold mutex? */
astroboy 0:94897d537b31 977 if(ptcb->mutexID != INVALID_ID)
astroboy 0:94897d537b31 978 {
astroboy 0:94897d537b31 979 if(MutexTbl[ptcb->mutexID].taskID == ptcb->taskID)
astroboy 0:94897d537b31 980 { /* Yes,leave the mutex */
astroboy 0:94897d537b31 981 CoLeaveMutexSection(ptcb->mutexID);
astroboy 0:94897d537b31 982 }
astroboy 0:94897d537b31 983 }
astroboy 0:94897d537b31 984
astroboy 0:94897d537b31 985 #endif
astroboy 0:94897d537b31 986
astroboy 0:94897d537b31 987 OsSchedLock(); /* Lock schedule */
astroboy 0:94897d537b31 988
astroboy 0:94897d537b31 989 if(ptcb->state == TASK_READY) /* Is task in READY list? */
astroboy 0:94897d537b31 990 {
astroboy 0:94897d537b31 991 RemoveFromTCBRdyList(ptcb); /* Yes,remove task from the READY list*/
astroboy 0:94897d537b31 992 }
astroboy 0:94897d537b31 993
astroboy 0:94897d537b31 994 #if CFG_TASK_WAITTING_EN > 0
astroboy 0:94897d537b31 995 else if(ptcb->state == TASK_WAITING)/* Is task in the WAITING list? */
astroboy 0:94897d537b31 996 {
astroboy 0:94897d537b31 997 /* Yes,Is task in delay list? */
astroboy 0:94897d537b31 998 if(ptcb->delayTick != INVALID_VALUE)
astroboy 0:94897d537b31 999 {
astroboy 0:94897d537b31 1000 RemoveDelayList(ptcb); /* Yes,remove task from READY list */
astroboy 0:94897d537b31 1001 }
astroboy 0:94897d537b31 1002
astroboy 0:94897d537b31 1003 #if CFG_EVENT_EN > 0
astroboy 0:94897d537b31 1004 if(ptcb->eventID != INVALID_ID) /* Is task in event waiting list? */
astroboy 0:94897d537b31 1005 {
astroboy 0:94897d537b31 1006 /* Yes,remove task from event waiting list */
astroboy 0:94897d537b31 1007 RemoveEventWaittingList(ptcb);
astroboy 0:94897d537b31 1008 }
astroboy 0:94897d537b31 1009 #endif
astroboy 0:94897d537b31 1010
astroboy 0:94897d537b31 1011 #if CFG_FLAG_EN > 0
astroboy 0:94897d537b31 1012 if(ptcb->pnode != 0) /* Is task in flag waiting list? */
astroboy 0:94897d537b31 1013 {
astroboy 0:94897d537b31 1014 /* Yes,remove task from flag waiting list */
astroboy 0:94897d537b31 1015 RemoveLinkNode((P_FLAG_NODE)ptcb->pnode);
astroboy 0:94897d537b31 1016 }
astroboy 0:94897d537b31 1017 #endif
astroboy 0:94897d537b31 1018
astroboy 0:94897d537b31 1019 #if CFG_MUTEX_EN >0
astroboy 0:94897d537b31 1020 if(ptcb->mutexID != INVALID_ID) /* Is task in mutex waiting list? */
astroboy 0:94897d537b31 1021 {
astroboy 0:94897d537b31 1022 RemoveMutexList(ptcb); /* Yes,remove task from mutex waiting list*/
astroboy 0:94897d537b31 1023 }
astroboy 0:94897d537b31 1024 #endif
astroboy 0:94897d537b31 1025 }
astroboy 0:94897d537b31 1026 #endif
astroboy 0:94897d537b31 1027 ptcb->state = TASK_DORMANT; /* Release TCB */
astroboy 0:94897d537b31 1028 TaskSchedReq = Co_TRUE;
astroboy 0:94897d537b31 1029
astroboy 0:94897d537b31 1030 #if CFG_ORDER_LIST_SCHEDULE_EN ==0
astroboy 0:94897d537b31 1031 DeleteTaskPri(ptcb->prio);
astroboy 0:94897d537b31 1032 #endif
astroboy 0:94897d537b31 1033
astroboy 0:94897d537b31 1034 #if CFG_TASK_SCHEDULE_EN >0
astroboy 0:94897d537b31 1035 ptcb->TCBnext = FreeTCB;
astroboy 0:94897d537b31 1036 FreeTCB = ptcb;
astroboy 0:94897d537b31 1037 #endif
astroboy 0:94897d537b31 1038 OsSchedUnlock(); /* Unlock schedule */
astroboy 0:94897d537b31 1039 return E_OK; /* return OK */
astroboy 0:94897d537b31 1040 }
astroboy 0:94897d537b31 1041
astroboy 0:94897d537b31 1042
astroboy 0:94897d537b31 1043 /**
astroboy 0:94897d537b31 1044 *******************************************************************************
astroboy 0:94897d537b31 1045 * @brief Exit Task
astroboy 0:94897d537b31 1046 * @param[in] None
astroboy 0:94897d537b31 1047 * @param[out] None
astroboy 0:94897d537b31 1048 * @retval None
astroboy 0:94897d537b31 1049 *
astroboy 0:94897d537b31 1050 * @par Description
astroboy 0:94897d537b31 1051 * @details This function is called to exit current task.
astroboy 0:94897d537b31 1052 *******************************************************************************
astroboy 0:94897d537b31 1053 */
astroboy 0:94897d537b31 1054 void CoExitTask(void)
astroboy 0:94897d537b31 1055 {
astroboy 0:94897d537b31 1056 CoDelTask(TCBRunning->taskID); /* Call task delete function */
astroboy 0:94897d537b31 1057 }
astroboy 0:94897d537b31 1058
astroboy 0:94897d537b31 1059
astroboy 0:94897d537b31 1060 #if CFG_TASK_SCHEDULE_EN ==0
astroboy 0:94897d537b31 1061 /**
astroboy 0:94897d537b31 1062 *******************************************************************************
astroboy 0:94897d537b31 1063 * @brief Activate Task
astroboy 0:94897d537b31 1064 * @param[in] taskID Task ID
astroboy 0:94897d537b31 1065 * @param[in] argv Task argv
astroboy 0:94897d537b31 1066 * @param[out] None
astroboy 0:94897d537b31 1067 * @retval E_INVALID_ID Invalid task ID.
astroboy 0:94897d537b31 1068 * @retval E_OK Activate task successful.
astroboy 0:94897d537b31 1069 *
astroboy 0:94897d537b31 1070 * @par Description
astroboy 0:94897d537b31 1071 * @details This function is called to activate current task.
astroboy 0:94897d537b31 1072 *******************************************************************************
astroboy 0:94897d537b31 1073 */
astroboy 0:94897d537b31 1074 StatusType CoActivateTask(OS_TID taskID,void *argv)
astroboy 0:94897d537b31 1075 {
astroboy 0:94897d537b31 1076 P_OSTCB ptcb;
astroboy 0:94897d537b31 1077 OS_STK* stkTopPtr;
astroboy 0:94897d537b31 1078 #if CFG_PAR_CHECKOUT_EN >0 /* Check validity of parameter */
astroboy 0:94897d537b31 1079 if(taskID >= CFG_MAX_USER_TASKS + SYS_TASK_NUM)
astroboy 0:94897d537b31 1080 {
astroboy 0:94897d537b31 1081 return E_INVALID_ID;
astroboy 0:94897d537b31 1082 }
astroboy 0:94897d537b31 1083 #endif
astroboy 0:94897d537b31 1084 ptcb = &TCBTbl[taskID];
astroboy 0:94897d537b31 1085 #if CFG_PAR_CHECKOUT_EN >0
astroboy 0:94897d537b31 1086 if(ptcb->stkPtr == Co_NULL)
astroboy 0:94897d537b31 1087 return E_INVALID_ID;
astroboy 0:94897d537b31 1088 #endif
astroboy 0:94897d537b31 1089 if(ptcb->state != TASK_DORMANT)
astroboy 0:94897d537b31 1090 return E_OK;
astroboy 0:94897d537b31 1091
astroboy 0:94897d537b31 1092
astroboy 0:94897d537b31 1093 /* Initialize task context. */
astroboy 0:94897d537b31 1094 stkTopPtr = InitTaskContext(ptcb->taskFuc,argv,ptcb->taskStk);
astroboy 0:94897d537b31 1095
astroboy 0:94897d537b31 1096 ptcb->stkPtr = stkTopPtr; /* Initialize TCB as user set */
astroboy 0:94897d537b31 1097 OsSchedLock(); /* Lock schedule */
astroboy 0:94897d537b31 1098 InsertToTCBRdyList(ptcb); /* Insert into the READY list */
astroboy 0:94897d537b31 1099 OsSchedUnlock(); /* Unlock schedule */
astroboy 0:94897d537b31 1100 return E_OK;
astroboy 0:94897d537b31 1101 }
astroboy 0:94897d537b31 1102 #endif
astroboy 0:94897d537b31 1103
astroboy 0:94897d537b31 1104
astroboy 0:94897d537b31 1105 /**
astroboy 0:94897d537b31 1106 *******************************************************************************
astroboy 0:94897d537b31 1107 * @brief Get current task id
astroboy 0:94897d537b31 1108 * @param[in] None
astroboy 0:94897d537b31 1109 * @param[out] None
astroboy 0:94897d537b31 1110 * @retval ID of the current task.
astroboy 0:94897d537b31 1111 *
astroboy 0:94897d537b31 1112 * @par Description
astroboy 0:94897d537b31 1113 * @details This function is called to get current task id.
astroboy 0:94897d537b31 1114 *******************************************************************************
astroboy 0:94897d537b31 1115 */
astroboy 0:94897d537b31 1116 OS_TID CoGetCurTaskID(void)
astroboy 0:94897d537b31 1117 {
astroboy 0:94897d537b31 1118 return (TCBRunning->taskID); /* Return running task ID */
astroboy 0:94897d537b31 1119 }
astroboy 0:94897d537b31 1120
astroboy 0:94897d537b31 1121 #if CFG_TASK_SUSPEND_EN >0
astroboy 0:94897d537b31 1122 /**
astroboy 0:94897d537b31 1123 *******************************************************************************
astroboy 0:94897d537b31 1124 * @brief Suspend Task
astroboy 0:94897d537b31 1125 * @param[in] taskID ID of task that want to suspend.
astroboy 0:94897d537b31 1126 * @param[out] None
astroboy 0:94897d537b31 1127 * @retval E_OK Task suspend successful.
astroboy 0:94897d537b31 1128 * @retval E_INVALID_ID Invalid event ID.
astroboy 0:94897d537b31 1129 * @retval E_PROTECTED_TASK Can't suspend idle task.
astroboy 0:94897d537b31 1130 * @retval E_ALREADY_IN_WAITING Task now in waiting state.
astroboy 0:94897d537b31 1131
astroboy 0:94897d537b31 1132 *
astroboy 0:94897d537b31 1133 * @par Description
astroboy 0:94897d537b31 1134 * @details This function is called to exit current task.
astroboy 0:94897d537b31 1135 *******************************************************************************
astroboy 0:94897d537b31 1136 */
astroboy 0:94897d537b31 1137 StatusType CoSuspendTask(OS_TID taskID)
astroboy 0:94897d537b31 1138 {
astroboy 0:94897d537b31 1139 P_OSTCB ptcb;
astroboy 0:94897d537b31 1140
astroboy 0:94897d537b31 1141 if(taskID == 0) /* Is idle task? */
astroboy 0:94897d537b31 1142 {
astroboy 0:94897d537b31 1143 return E_PROTECTED_TASK; /* Yes,error return */
astroboy 0:94897d537b31 1144 }
astroboy 0:94897d537b31 1145 #if CFG_PAR_CHECKOUT_EN >0 /* Check validity of parameter */
astroboy 0:94897d537b31 1146 if(taskID >= CFG_MAX_USER_TASKS + SYS_TASK_NUM)
astroboy 0:94897d537b31 1147 {
astroboy 0:94897d537b31 1148 return E_INVALID_ID;
astroboy 0:94897d537b31 1149 }
astroboy 0:94897d537b31 1150 #endif
astroboy 0:94897d537b31 1151 ptcb = &TCBTbl[taskID];
astroboy 0:94897d537b31 1152 #if CFG_PAR_CHECKOUT_EN >0
astroboy 0:94897d537b31 1153 if(ptcb->state == TASK_DORMANT)
astroboy 0:94897d537b31 1154 {
astroboy 0:94897d537b31 1155 return E_INVALID_ID;
astroboy 0:94897d537b31 1156 }
astroboy 0:94897d537b31 1157 #endif
astroboy 0:94897d537b31 1158 if(OSSchedLock != 0)
astroboy 0:94897d537b31 1159 {
astroboy 0:94897d537b31 1160 return E_OS_IN_LOCK;
astroboy 0:94897d537b31 1161 }
astroboy 0:94897d537b31 1162 if(ptcb->state == TASK_WAITING) /* Is task in WAITING list? */
astroboy 0:94897d537b31 1163 {
astroboy 0:94897d537b31 1164 return E_ALREADY_IN_WAITING; /* Yes,error return */
astroboy 0:94897d537b31 1165 }
astroboy 0:94897d537b31 1166
astroboy 0:94897d537b31 1167 OsSchedLock();
astroboy 0:94897d537b31 1168 if(ptcb != TCBRunning) /* Is runing task? */
astroboy 0:94897d537b31 1169 {
astroboy 0:94897d537b31 1170 RemoveFromTCBRdyList(ptcb); /* No,Remove task from READY list */
astroboy 0:94897d537b31 1171 }
astroboy 0:94897d537b31 1172 else
astroboy 0:94897d537b31 1173 {
astroboy 0:94897d537b31 1174 TaskSchedReq = Co_TRUE;
astroboy 0:94897d537b31 1175 }
astroboy 0:94897d537b31 1176
astroboy 0:94897d537b31 1177 ptcb->state = TASK_WAITING; /* Set task status as TASK_WAITING */
astroboy 0:94897d537b31 1178 OsSchedUnlock(); /* Call task schedule */
astroboy 0:94897d537b31 1179 return E_OK; /* Return OK */
astroboy 0:94897d537b31 1180 }
astroboy 0:94897d537b31 1181
astroboy 0:94897d537b31 1182
astroboy 0:94897d537b31 1183 /**
astroboy 0:94897d537b31 1184 *******************************************************************************
astroboy 0:94897d537b31 1185 * @brief Awake Task
astroboy 0:94897d537b31 1186 * @param[in] taskID ID of task that will been awaked.
astroboy 0:94897d537b31 1187 * @param[out] None
astroboy 0:94897d537b31 1188 * @retval E_OK Task awake successful.
astroboy 0:94897d537b31 1189 * @retval E_INVALID_ID Invalid task ID.
astroboy 0:94897d537b31 1190 * @retval E_TASK_NOT_WAITING Task now not in waiting state.
astroboy 0:94897d537b31 1191 * @retval E_TASK_WAIT_OTHER Task now waiting other awake event.
astroboy 0:94897d537b31 1192 * @retval E_PROTECTED_TASK Idle task mustn't be awaked.
astroboy 0:94897d537b31 1193 *
astroboy 0:94897d537b31 1194 * @par Description
astroboy 0:94897d537b31 1195 * @details This function is called to awake current task.
astroboy 0:94897d537b31 1196 *******************************************************************************
astroboy 0:94897d537b31 1197 */
astroboy 0:94897d537b31 1198 StatusType CoAwakeTask(OS_TID taskID)
astroboy 0:94897d537b31 1199 {
astroboy 0:94897d537b31 1200 P_OSTCB ptcb;
astroboy 0:94897d537b31 1201
astroboy 0:94897d537b31 1202 if(taskID == 0) /* Is idle task? */
astroboy 0:94897d537b31 1203 {
astroboy 0:94897d537b31 1204 return E_PROTECTED_TASK; /* Yes,error return */
astroboy 0:94897d537b31 1205 }
astroboy 0:94897d537b31 1206 #if CFG_PAR_CHECKOUT_EN >0 /* Check validity of parameter */
astroboy 0:94897d537b31 1207 if(taskID >= CFG_MAX_USER_TASKS + SYS_TASK_NUM)
astroboy 0:94897d537b31 1208 {
astroboy 0:94897d537b31 1209 return E_INVALID_ID;
astroboy 0:94897d537b31 1210 }
astroboy 0:94897d537b31 1211 #endif
astroboy 0:94897d537b31 1212 ptcb = &TCBTbl[taskID];
astroboy 0:94897d537b31 1213 #if CFG_PAR_CHECKOUT_EN >0
astroboy 0:94897d537b31 1214 if(ptcb->state == TASK_DORMANT)
astroboy 0:94897d537b31 1215 {
astroboy 0:94897d537b31 1216 return E_INVALID_ID;
astroboy 0:94897d537b31 1217 }
astroboy 0:94897d537b31 1218 #endif
astroboy 0:94897d537b31 1219
astroboy 0:94897d537b31 1220 if(ptcb->state != TASK_WAITING) /* Is task in WAITING list */
astroboy 0:94897d537b31 1221 {
astroboy 0:94897d537b31 1222 return E_TASK_NOT_WAITING; /* No,error return */
astroboy 0:94897d537b31 1223 }
astroboy 0:94897d537b31 1224
astroboy 0:94897d537b31 1225 #if CFG_TASK_WAITTING_EN > 0
astroboy 0:94897d537b31 1226 if(ptcb->delayTick != INVALID_VALUE)/* Is task in READY list */
astroboy 0:94897d537b31 1227 {
astroboy 0:94897d537b31 1228 return E_TASK_WAIT_OTHER; /* Yes,error return */
astroboy 0:94897d537b31 1229 }
astroboy 0:94897d537b31 1230
astroboy 0:94897d537b31 1231 #if CFG_FLAG_EN > 0
astroboy 0:94897d537b31 1232 if(ptcb->pnode != Co_NULL) /* Is task in flag waiting list */
astroboy 0:94897d537b31 1233 {
astroboy 0:94897d537b31 1234 return E_TASK_WAIT_OTHER; /* Yes,error return */
astroboy 0:94897d537b31 1235 }
astroboy 0:94897d537b31 1236 #endif
astroboy 0:94897d537b31 1237
astroboy 0:94897d537b31 1238 #if CFG_EVENT_EN>0
astroboy 0:94897d537b31 1239 if(ptcb->eventID != INVALID_ID) /* Is task in event waiting list */
astroboy 0:94897d537b31 1240 {
astroboy 0:94897d537b31 1241 return E_TASK_WAIT_OTHER; /* Yes,error return */
astroboy 0:94897d537b31 1242 }
astroboy 0:94897d537b31 1243 #endif
astroboy 0:94897d537b31 1244
astroboy 0:94897d537b31 1245 #if CFG_MUTEX_EN > 0
astroboy 0:94897d537b31 1246 if(ptcb->mutexID != INVALID_ID) /* Is task in mutex waiting list */
astroboy 0:94897d537b31 1247 {
astroboy 0:94897d537b31 1248 return E_TASK_WAIT_OTHER; /* Yes,error return */
astroboy 0:94897d537b31 1249 }
astroboy 0:94897d537b31 1250 #endif
astroboy 0:94897d537b31 1251
astroboy 0:94897d537b31 1252 #endif //CFG_TASK_WAITTING_EN
astroboy 0:94897d537b31 1253
astroboy 0:94897d537b31 1254 /* All no,so WAITING state was set by CoSuspendTask() */
astroboy 0:94897d537b31 1255 OsSchedLock(); /* Lock schedule */
astroboy 0:94897d537b31 1256 InsertToTCBRdyList(ptcb); /* Insert the task into the READY list*/
astroboy 0:94897d537b31 1257 OsSchedUnlock(); /* Unlock schedule */
astroboy 0:94897d537b31 1258 return E_OK; /* return OK */
astroboy 0:94897d537b31 1259 }
astroboy 0:94897d537b31 1260 #endif