⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 usertimer.c

📁 本人编写的无线电话程序,给予PIC18C801设计,包括了uCOS的移植以及菜单,自己设计的拼音注入法,完整地一级汉字库,希望对大家有所帮助
💻 C
字号:
/********************************************************
 *
 * File:	BscTimer.c
 *
 * Description:
 *	This file contains routines about Timer Manager Module.
 *
 * Author:	Weiming Zhang
 *
 * Created Date:    Feb 2,2002
 * Completed Date:	Feb 23,2002
 *
 ********************************************************/

#include "Includes.h"
#include "UserTimer.h"

IUT iut[MAXIUT];					/* allocate memory for MAXIUT iuts */
IUT *FreeIutHead;					/* pointing to the FIRST availabel IUTs */
IUT *FreeIutTail;					/* pointing to the LAST available IUTs */
IUT *ChainHead;

extern OS_EVENT *rom peventTimer;
extern OS_MEM	*pMemSml;
//extern OS_EVENT *rom MsgQueue[OS_LOWEST_PRIO+1];                            /* Message queue pointer                         */
extern void Func_Clear_Msg(INT8U rom * pMsg);
extern void OSTrap(INT8U);
extern void TimerISR(void);

//TIMERPRO xdata timerpro[MAXPRO];

//extern unsigned char SendMsg(unsigned char len,unsigned char srcid,unsigned char destid,unsigned char msgid,unsigned char *info);

void TimerMgtInit()
{
	char i;

	/* Initialize the available IUTs */
	FreeIutHead=&iut[0];
	FreeIutTail=&iut[MAXIUT-1];
	for(i=0;i<MAXIUT-1;i++)
		iut[i].next=&iut[i+1];
	iut[MAXIUT-1].next=NULL;
	
	/* Initialize the available TIMERPROs array */
//	for(i=0;i<=MAXPRO-1;i++){
//		timerpro[i].source=0;
//		timerpro[i].type=0;
//		timerpro[i].interval=0;
//	}
	
	/* Initialize the head of IUT-chain */
	ChainHead=NULL;

	return;
}


//void TickPostSem()
//{
//	if(ChainHead!=NULL)
//		OSQPost(MsgQueue[TASK_TIMER_PRIO],(rom INT8U *)TIMER_SEM);
//}

/* 
void TimerSendMsg(INT8U prio,INT16U timer_id)
{
	INT8U err;
	
	TIMER_MESSAGE *addr1;
	
	addr1=(TIMER_MESSAGE *)OSMemGet(pMemSml,&err);
	if(err!=OS_NO_ERR){
		OSTrap(TASK_TIMER_PRIO+80);
	}
	addr1->Len=8;
	addr1->Src=TASK_TIMER_PRIO;
	addr1->Des=prio;
	addr1->MID=Timer_TimeOut;
	addr1->TID=timer_id;
	addr1->Val=0xEEEE;
    OSQPost(MsgQueue[prio],(rom INT8U *)addr1);
}
*/

/* Calculate the Timer interval and position of IUT */
void IutInsert(IUT * piut)
{
	unsigned short val;
	IUT *p1;
	IUT *p2;									/* p1 is front-pointer,p2 is rear-pointer */
	
	val=piut->interval;
	
	p1=ChainHead;								/* p1 points to the front IUT */
	p2=p1->next;								/* p2 points to the back IUT */

	if(p1!=NULL){
		if(val<p1->interval){
			piut->interval=val;					/* "piut" should be the first IUT (This line is useless.) */
			piut->next=p1;
			ChainHead=piut;
			p1->interval-=val;					/* modify the next IUT's interval */
		}
		else{
			val-=p1->interval;
			while(p2!=NULL&&val>=p2->interval){	/* shift backward */
				p1=p2;
				p2=p2->next;
				val-=p1->interval;
			}
			piut->interval=val;					/* Insert "piut" into the chain */
			piut->next=p2;
			p1->next=piut;
			if(p2!=NULL)	p2->interval-=val;	/* not the end of chain */
		}
		
	}
	else{										/* "piut" is the first IUT of that chain */
		piut->interval=val;
		piut->next=NULL;
		ChainHead=piut;
	}
}

	
void StartTimer(OS_EVENT *psrc,unsigned short typ,unsigned short val)
{
	IUT *pfront;
	IUT *p;									/* p to the desired IUT, pfront's IUT is in front of p's IUT */
	unsigned char iutfound;
	unsigned char i;
	
//	if(src==0 || typ==0 || val==0)	return;
	
//	if(typ&0x8000){							/* for SPECIAL timer */
//		for(i=0;i<MAXPRO;i++){				/* Clear the original reload infomation */
//			if(timerpro[i].source==src && timerpro[i].type==typ){
//				timerpro[i].source=0;
//				timerpro[i].type=0;			/* This line is useless! */
//			}
//		}
//		for(i=0;i<MAXPRO;i++){				/* Load the new information of SPECIAL timer */
//			if(timerpro[i].source==0){		/* Get a free TIMERPRO */
//				timerpro[i].source=src;
//				timerpro[i].type=typ;
//				timerpro[i].interval=val;
//				break;						/* Load successful! So break, i<MAXPRO. */
//			}
//		}
//		if(i>=MAXPRO){						/* No room for this timer, i++ --> i=MAXPRO. */
//			/* What happens when there is not enough room for TIMERPRO-unit? Send timeout message directly? */
//			return;
//		}
//	}


	iutfound=0;
	
	OS_ENTER_CRITICAL();
	pfront=ChainHead;
	p=ChainHead;

	/* If the desired IUT cannot be found in the chain, get a free-IUT */
	while(p!=NULL){
		if((p->Origin==psrc)&&(p->type==typ)){
			if(p->next!=NULL)					
				p->next->interval+=p->interval;	/* Modify next-IUT's interval */

			if(p==ChainHead)					/* Pick the desired IUT out */ 
				ChainHead=p->next;				/* p is to the First IUT */
			else
				pfront->next=p->next;			/* p is not to the First IUT */

			if(typ&0x8000)						/* for SPECIAL timer */
				p->initcnt=val;
			else								/* for NORMAL timer */
				p->initcnt=0;

			p->interval=val;					/* modify the interval */
			IutInsert(p);

			iutfound=1;							/* found the IUT in the working chain */
			break;
		}
		else{
			pfront=p;							/* shift backward and go on looking for ... */
			p=p->next;
		}
	}
	OS_EXIT_CRITICAL();

	if(iutfound!=1){						/* If IUT cannot be found in the chain,then catch a NEW IUT from the free-iut-chain. */
		OS_ENTER_CRITICAL();
		if(FreeIutHead->next!=NULL){		/* Be sure that there is at least one IUT in the free-chain. */
			p=FreeIutHead;
			FreeIutHead=FreeIutHead->next;
		
			if(typ&0x8000)						/* for SPECIAL timer */
				p->initcnt=val;
			else								/* for NORMAL timer */
				p->initcnt=0;

			p->interval=val;
			p->type=typ;
			p->Origin=psrc;
			p->next=NULL;

			IutInsert(p);					/* Insert the IUT into the working-chain. */
		}
		OS_EXIT_CRITICAL();
//		else{
//			/* What happens when there is not enough free-IUT? Send timeout message directly? */
//			return;
//		}
	}
}


void StopTimer(OS_EVENT *psrc,unsigned short typ)
{
	IUT *pfront;
	IUT *p;						/* p pointing to the desired IUT */
	unsigned char i;
	
//	if(typ&0x8000){								/* Stop the SPECIAL timer */
//		for(i=0;i<MAXPRO;i++){
//			if(timerpro[i].source==src && timerpro[i].type==typ){
//				timerpro[i].source=0;			/* Clear the reload value */
//				timerpro[i].type=0;
//				timerpro[i].interval=0;
//				break;							/* break from "for" */
//			}
//		}
//	}

	OS_ENTER_CRITICAL();
	pfront=ChainHead;
	p=ChainHead;

	/* If the desired IUT cannot be found in the working chain, nothing ought to do */
	while(p!=NULL){	
		if((p->Origin==psrc)&&(p->type==typ)){

			if(p->next!=NULL)					
				p->next->interval+=p->interval;	/* Modify next-IUT's interval */

			if(p==ChainHead)					/* Pick the desired IUT out */ 
				ChainHead=p->next;				/* p is to the First IUT */
			else
				pfront->next=p->next;			/* p is not to the First IUT */

			p->next=NULL;						/* Free the IUT */
			FreeIutTail->next=p;
			FreeIutTail=p;
			break;
		}
		else{
			pfront=p;							/* shift backwards */
			p=p->next;
		}
	}
	OS_EXIT_CRITICAL();
}


void TimerISR(void)
{
	IUT *p;
//	unsigned char i;
//	unsigned short timer_id;

	INT8U err;
	TIMER_MESSAGE *addr1;
	
	if(ChainHead!=NULL){
		ChainHead->interval-=1;		/* count down for 1 */
		while(ChainHead!=NULL && ChainHead->interval==0){

			addr1=(TIMER_MESSAGE *)OSMemGet(pMemSml,&err);
			if(err!=OS_NO_ERR){
				OSTrap(TASK_TIMER_PRIO+160);
			}
			
			((MSG_HEAD *)addr1)->Msg_ID=MSG_TIMER_EXPIRE;
			((MSG_HEAD *)addr1)->Origin=peventTimer;		//should be changed to peventTimer
			((MSG_HEAD *)addr1)->Attached=FALSE;
			((MSG_HEAD *)addr1)->pmemME=pMemSml;
			((MSG_HEAD *)addr1)->LenOfBody=2;
			((TIMER_MESSAGE *)addr1)->TID=ChainHead->type;
			
		    OSQPost(ChainHead->Origin,(rom INT8U *)addr1);

//			timer_id=ChainHead->type;
//			TimerSendMsg(ChainHead->source,timer_id);			/* Here is a CONSTANT(6) */
			/* send timer expiry message ChainHead->type from TimerProc_module to ChainHead->source */

			p=ChainHead;
			ChainHead=ChainHead->next;
			
			if(p->type & 0x8000){
				p->interval=p->initcnt;						/* reload the timer inteval */
				IutInsert(p);

//				for(i=0;i<MAXPRO;i++){
//					if(timerpro[i].source==p->source && timerpro[i].type==p->type){
//						p->interval=timerpro[i].interval;	/* reload the timer inteval */
//						IutInsert(p);
//						break;								/* break from "for" */
//					}
//				}
//				if(i>=MAXPRO){
//				/* What happens when the TIMERPRO cannot be found? */
//					FreeIutTail->next=p;					/* free the IUT */
//					FreeIutTail=p;
//					FreeIutTail->next=NULL;					/* Should be at the end */
//				}

			}
			else{
				FreeIutTail->next=p;
				FreeIutTail=p;
				FreeIutTail->next=NULL;						/* Should be at the end */
			}
		}
	}
}

void TimerManager(OS_EVENT *peventTimer)
{
	void rom * pMsg;
	INT8U err;

 		pMsg=OSQPend(peventTimer,0,&err);
 		if(err==OS_NO_ERR){
			if((INT24U)pMsg >= PTR_MAX){
				OSTrap(TASK_TIMER_PRIO+64);
			}
			else{
				if(((MSG_HEAD *)pMsg)->Attached)
					OSTrap(TASK_TIMER_PRIO+96);

				if(((MSG_HEAD *)pMsg)->LenOfBody!=2 && ((MSG_HEAD *)pMsg)->LenOfBody!=4)
					OSTrap(TASK_TIMER_PRIO+96);

				switch (((MSG_HEAD *)pMsg)->Msg_ID){
					case MSG_TIMER_START:
						StartTimer(((MSG_HEAD *)pMsg)->Origin,((TIMER_MESSAGE *)pMsg)->TID,((TIMER_MESSAGE *)pMsg)->Val);
					break;
					case MSG_TIMER_STOP:
						StopTimer(((MSG_HEAD *)pMsg)->Origin,((TIMER_MESSAGE *)pMsg)->TID);
					break;
					default:
						OSTrap(TASK_TIMER_PRIO+96);
					break;
				}
				Func_Clear_Msg(pMsg);
				//err=OSMemPut(((MSG_HEAD *)pMsg)->pmemME, pMsg);
				//if(err!=OS_NO_ERR){
				//	OSTrap(TASK_TIMER_PRIO+128);
				//}
			}
		}
		else{
			OSTrap(TASK_TIMER_PRIO);
		}
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -