📄 taskschedule.c
字号:
/* task TaskSchdule.c */
/* 头文件 */
#include "vxWorks.h"
#include "stdio.h"
#include "stdlib.h"
#include "msgQLib.h"
#include "loglib.h"
#include "taskLib.h"
#include "string.h"
#include "semLib.h"
#include "tylib.h"
#include "ctype.h"
/* 宏定义 */
#define MAX_MSGS (10) /* 消息队列长度 */
#define MAX_MSG_LEN sizeof(MESSAGE) /* 消息队列中消息的最大长度 */
#define MAX_STR_LEN (100)
#define STACK_SIZE 20000 /* 分配给每个任务的堆栈大小 */
/* 类型定义 */
typedef struct _MESSAGE
{
int mSendId; /* 发送任务的MESSAGE ID */
char aStr[MAX_STR_LEN]; /* 消息中传递的数据 */
}MESSAGE;
/* 全局变量 */
SEM_ID dataSemId; /* 同步信号量 */
int tidTask1; /* 任务ID定义 */
int tidTask2;
int tidTask3;
MSG_Q_ID myMsgQId1; /* 消息队列ID定义 */
MSG_Q_ID myMsgQId2;
MSG_Q_ID myMsgQId3;
int stdIN, stdOUT; /* 标准输入/输出设备的文件描述符 */
char TaskStatus[MAX_STR_LEN];
char OverFlowFile[MAX_STR_LEN];
/* 函数声明 */
STATUS progStart(void);
STATUS task1(void);
STATUS task2(void);
STATUS task3(void);
void command(void);
/******************************************************************
*
* progStart - 启动实例程序
*
* 负责创建消息队列与任务
*
* RETURNS: OK, ERROR
*/
STATUS progStart(void)
{
/* 创建消息队列 */
int i;
myMsgQId1 = msgQCreate(MAX_MSGS, MAX_MSG_LEN, MSG_Q_PRIORITY);
myMsgQId2 = msgQCreate(MAX_MSGS, MAX_MSG_LEN, MSG_Q_PRIORITY);
myMsgQId3 = msgQCreate(MAX_MSGS, MAX_MSG_LEN, MSG_Q_PRIORITY);
if (myMsgQId1 == NULL||myMsgQId2 == NULL||myMsgQId3 == NULL)
{
return (ERROR);
}
/* 创建信号量 */
dataSemId = semBCreate(SEM_Q_FIFO, SEM_EMPTY);
/* 创建任务 */
tidTask1 = taskSpawn("tTask1", 240, 0, STACK_SIZE,
(FUNCPTR)task1,0,0,0,0,0,0,0,0,0,0);
tidTask2 = taskSpawn("tTask2", 220, 0, STACK_SIZE,
(FUNCPTR)task2,0,0,0,0,0,0,0,0,0,0);
tidTask3 = taskSpawn("tTask3", 230, 0, STACK_SIZE,
(FUNCPTR)task3,0,0,0,0,0,0,0,0,0,0);
/* 取标准输入/输出设备文件描述符 */
stdIN = ioGlobalStdGet(0);
stdOUT = ioGlobalStdGet(1);
for (i=0; i<100; i++) OverFlowFile[i] = 'a';
return (OK);
}
/******************************************************************
*
*Task1--管理Task
*
*利用信号量的semFlash()负责系统启动时同步系统中其他Task的启动同步
*接收各Task的告警信息,并编号以logmsg()方式输出
*负责系统结束时的Task删除处理
*
* RETURNS: OK
*/
STATUS task1(void)
{
MESSAGE rxMsg; /* 用于从消息队列中接收消息 */
char msgBuf[MAX_MSG_LEN];
semFlush(dataSemId);
FOREVER
{
/* 清空消息接收缓冲 */
memset(rxMsg.aStr, 0, MAX_STR_LEN);
memset(msgBuf, 0, MAX_MSG_LEN);
/* 从消息队列接收消息,当消息队列空时阻塞(Pend)等待 */
if (msgQReceive(myMsgQId1, (char*)&rxMsg, MAX_MSG_LEN,WAIT_FOREVER)== ERROR)
{
return (ERROR);
}
if(rxMsg.mSendId == 2 && strcmp(rxMsg.aStr,"q") ==0 )
{
semDelete(dataSemId);
/* 释放信号量资源 */
msgQDelete(myMsgQId1);
msgQDelete(myMsgQId2);
msgQDelete(myMsgQId3);
/*delete task*/
taskDelete(tidTask2);
taskDelete(tidTask3);
printf("Exit already!\n");
taskDelete(0);
return OK;
}
sprintf(msgBuf,"\nwarning: %s from Task(%d)\n\n",&rxMsg.aStr,rxMsg.mSendId);
logMsg(msgBuf,0,0,0,0,0,0);
command();
}
return OK;
}
/******************************************************************
*
*Task2--console命令行接收Task,分析console发来的命令行及参数
*
*设置5种命令,并依据其内容向Task3发送激励消息
*实现系统退出命令,使系统以适当方式安全退出
*收到非法命令向Task1告警
*
* RETURNS: OK
*/
STATUS task2(void)
{
char bStr[3][20]; /* string buffer */
MESSAGE txMsg; /* 用于向消息队列中发送消息 */
char c; /* 字符变量 */
int i = 0;
int j = 0;
struct timespec * res;
char TishiStr[35] = "\nplease input your order here!\n\n"; /**/
semTake(dataSemId,WAIT_FOREVER);
/* 将标准输出设备输出模式设置为RAW */
ioctl(stdOUT, FIOSETOPTIONS, OPT_RAW);
write(stdOUT, TishiStr, sizeof(TishiStr));
command();
FOREVER
{
i = 0; j = 0;
/* 清空消息接收缓冲 */
memset(bStr, 0, 3*20);
memset(txMsg.aStr, 0, MAX_STR_LEN);
/* 向消息队列发送一条普通优先级的消息,
* 当消息队列满时,阻塞(Pend)等待*/
/*scanf("%s",bStr);*/
/* 主循环 */
while(1)
{
/* 在标准输入设备等待键盘输入字符 */
read(stdIN,&c,1);
write(stdOUT,&c,1);
/* 判断若输入字符为"ESC键"则退出主循环 */
if(c == '\r')
{
write(stdOUT,"\n",1);
break;
}
if(c == ' ' || c == ',')
{
i++;
j = -1;
}
bStr[i][j++] = c;
}
/*for(i = 0;i<3; i++)
{
printf("\njj:%s\n",bStr[i]);
}
read(stdIN,bStr,MAX_STR_LEN);
strncpy(bStr,bStr,strlen(bStr)-1);
bStr[strlen(bStr)-1] = '\0';*/
txMsg.mSendId = 2;
if(strcmp(bStr[0],"q") == 0)/*安全退出系统*/
{
/*删除信号量,消息队列*/
strcpy(txMsg.aStr,bStr[0]);
if (msgQSend(myMsgQId1, (char*)&txMsg, MAX_MSG_LEN,WAIT_FOREVER, MSG_PRI_NORMAL) == ERROR)
{
return (ERROR);
}
return OK;
}
if(strcmp(bStr[0],"taskShow") == 0)
{
if(strcmp(bStr[1],"1") == 0)
{
taskShow(tidTask1,0);
write(stdOUT,"\n",1);
command();
continue;
}
else if(strcmp(bStr[1],"3") == 0)
{
taskShow(tidTask3,0);
write(stdOUT,"\n",1);
command();
continue;
}
}
if(strcmp(bStr[0],"toupper") == 0)
{
strncpy(&c,bStr[1],1);
sprintf(txMsg.aStr,"\nupper form: %c\n\n",toupper(c));
if (msgQSend(myMsgQId3, (char*)&txMsg, MAX_MSG_LEN,WAIT_FOREVER, MSG_PRI_NORMAL) == ERROR)
{
return (ERROR);
}
continue;
}
if(strcmp(bStr[0],"taskStatusString") == 0)
{
memset(TaskStatus, 0, MAX_STR_LEN);
if(strcmp(bStr[1],"1") == 0 )
{
taskStatusString(tidTask1,TaskStatus);
sprintf(txMsg.aStr,"\nTask1's Status: %s\n\n",TaskStatus);
if (msgQSend(myMsgQId3, (char*)&txMsg, MAX_MSG_LEN,WAIT_FOREVER, MSG_PRI_NORMAL) == ERROR)
{
return (ERROR);
}
continue;
}
else if(strcmp(bStr[1],"3") == 0)
{
/*taskStatusString(tidTask3,TaskStatus);*/
sprintf(txMsg.aStr,"\nTask3's Status: %s\n\n",TaskStatus);
if (msgQSend(myMsgQId3, (char*)&txMsg, MAX_MSG_LEN,WAIT_FOREVER, MSG_PRI_NORMAL) == ERROR)
{
return (ERROR);
}
continue;
}
}
if(strcmp(bStr[0],"OutFile") == 0)
{
strcpy(txMsg.aStr,OverFlowFile);
if (msgQSend(myMsgQId3, (char*)&txMsg, MAX_MSG_LEN,WAIT_FOREVER, MSG_PRI_NORMAL) == ERROR)
{
return (ERROR);
}
continue;
}
if(strcmp(bStr[0],"Info") == 0)
{
strcpy(txMsg.aStr,"\nBUPT VXWORKS HOMEWORK, by KongFeng:)\n\n");
if (msgQSend(myMsgQId3, (char*)&txMsg, MAX_MSG_LEN,WAIT_FOREVER, MSG_PRI_NORMAL) == ERROR)
{
return (ERROR);
}
continue;
}
/*命令错误,非法*/
strcpy(txMsg.aStr," invalid command! ");
if (msgQSend(myMsgQId1, (char*)&txMsg, MAX_MSG_LEN,WAIT_FOREVER, MSG_PRI_NORMAL) == ERROR)
{
return (ERROR);
}
}
ioctl (stdOUT, FIOSETOPTIONS, OPT_TERMINAL);
return (OK);
}
/******************************************************************
*
*Task3--console输出Task
*接收需打印输出的字串消息(命令),输出到控制台
*收到长度为0或超长字串向Task1告警
*
* RETURNS: OK
*/
STATUS task3(void)
{
MESSAGE rxMsg; /* 用于从消息队列中接收消息 */
MESSAGE txMsg; /* 用于向消息队列中发送消息 */
int msglen;
semTake(dataSemId,WAIT_FOREVER);
txMsg.mSendId = 3;
FOREVER
{
/* 清空消息接收缓冲 */
memset(rxMsg.aStr, 0, MAX_STR_LEN);
/* 从消息队列接收消息,当消息队列空时阻塞(Pend)等待 */
if (msgQReceive(myMsgQId3, (char*)&rxMsg, MAX_MSG_LEN,WAIT_FOREVER)== ERROR)
{
return (ERROR);
}
msglen = strlen(rxMsg.aStr);
if(msglen == 0 || msglen > 80)
{
/*send msg to Task1 to warn*/
strcpy(txMsg.aStr,"receive 0 or overlength string! ");
if (msgQSend(myMsgQId1, (char*)&txMsg, MAX_MSG_LEN,WAIT_FOREVER, MSG_PRI_NORMAL) == ERROR)
{
return (ERROR);
}
}
else
write(stdOUT, rxMsg.aStr, sizeof(rxMsg.aStr));
command();
}
return OK;
}
void command()
{
write(stdOUT,">>",2);
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -