📄 ex51l.c
字号:
/* $Id: ex51l.c,v 1.2 1997/07/17 14:03:01 gianpi Exp $
*
* Description:
* uC/OS-51 - Example program (CC51 - large model)
*
* Author[s]:
* Gianpaolo Macario gianpi@geocities.com
*/
#include <ctype.h>
#include <stdarg.h>
#include <stdio.h>
#include <string.h>
#include "includes.h"
#include "isr51.h"
#include "../paulmon.h" /* PM_pStr() */
#define USE_TIMER0 1 /* 1=Timer0, 0=Timer1 */
#define TASK_STK_SIZE 64 /* was 32 */
ISR_PTR OldTimeTick;
#define KEY_Q_SIZE 16 /* Size of keyboard queue */
void *KeyQ[KEY_Q_SIZE]; /* Keyboard queue */
OS_EVENT *DpySemPtr; /* Ptr to display semaphore */
OS_EVENT *KeyQPtr; /* Ptr to keyboard queue */
/* ------------------------------------------------------------------------- */
/* Debugging Functions */
static void ser_putc(u_int8_t ch)
{
UBYTE err;
OSSemPend(DpySemPtr, 0, &err);
SBUF = ch;
} /* ser_putc() */
/* Return bytes written */
static u_int8_t ser_write(const u_int8_t *buf, u_int8_t buflen)
{
u_int8_t k;
for (k = 0; k < buflen; k++) {
ser_putc(*buf++);
}
return k;
} /* ser_write() */
static int ser_getc(void)
{
UBYTE err;
int val;
val = (u_int8_t) OSQPend(KeyQPtr, 0, &err);
return val;
} /* ser_getc() */
static _xdat char dbg_buffer[80];
void dbg_printf(const char *format, ...)
{
_xdat va_list ap;
u_int8_t l;
va_start(ap, format);
strcpy(dbg_buffer, "DBG: ");
vsprintf(dbg_buffer+strlen(dbg_buffer), format, ap);
strcat(dbg_buffer, "\r\n");
l = strlen(dbg_buffer);
if (OSRunning)
ser_write((const u_int8_t *)dbg_buffer, l);
else
PM_pStr(dbg_buffer);
} /* dbg_printf() */
/* ------------------------------------------------------------------------- */
/* Customization for CC51 low-level stdio functions */
int _iowrite(int c, FILE *stream)
{
switch ((int)stream) {
case 1: /* stdout */
case 2: /* stderr */
ser_putc(c);
return c;
}
return EOF;
} /* _iowrite() */
int _ioread(FILE *stream)
{
switch ((int)stream) {
case 0: /* stdin */
return ser_getc();
}
return EOF;
} /* _ioread() */
/* ------------------------------------------------------------------------- */
void OSSerial(void)
{
if (RI) {
u_int8_t val;
RI = 0;
val = SBUF;
OSQPost(KeyQPtr, (void *)val);
}
if (TI) {
TI = 0;
OSSemPost(DpySemPtr);
}
} /* OSSerial() */
/* ------------------------------------------------------------------------- */
/* Some debugging functions for uC/OS Internal Data Structures */
static void pr_ucos_status(void)
{
dbg_printf("OSCtxSwCtr=%u, OSIdleCtr=%lu, OSIntNesting=%d, OSRunning=%d",
OSCtxSwCtr, OSIdleCtr, OSIntNesting, (int)OSRunning);
dbg_printf("OSTCBCur=%04X, OSTCBHighRdy=%04X",
(u_int16_t)OSTCBCur, (u_int16_t)OSTCBHighRdy);
} /* pr_ucos_status() */
/* ------------------------------------------------------------------------- */
/* Datan[] is organized as "bitno,delay" */
char Data1[] = "7,1";
char Data2[] = "6,2";
char Data3[] = "5,3";
/* TBD: don't know how to make reentrant functions... */
OS_STK_TYPE Stk1[TASK_STK_SIZE];
void Task1(void /* OS_FAR */ *pdata)
{
xdat unsigned char mask = 1 << (((char *)pdata)[0] - '0');
xdat unsigned dlay = (1 << (((char *)pdata)[2] - '0')) * 2;
pdata = pdata; /* avoid compiler warning */
while (1) {
P1 ^= mask; /* Toggle P1.<bitno> */
#if 1
/* When P1 toggles we are in the lowest priority task */
#else
P2 &= ~mask; /* Reset P2.<bitno> */
ser_putc('1');
OSTimeDly(dlay);
P2 |= mask; /* Set P2.<bitno> */
#endif
}
} /* Task1() */
OS_STK_TYPE Stk2[TASK_STK_SIZE];
void Task2(void /* OS_FAR */ *pdata)
{
xdat unsigned char mask = 1 << (((char *)pdata)[0] - '0');
xdat unsigned dlay = (1 << (((char *)pdata)[2] - '0')) * 2;
pdata = pdata; /* avoid compiler warning */
while (1) {
P1 ^= mask; /* Toggle P1.<bitno> */
P2 &= ~mask; /* Reset P2.<bitno> */
ser_putc('2');
OSTimeDly(dlay);
P2 |= mask; /* Set P2.<bitno> */
}
} /* Task2() */
OS_STK_TYPE Stk3[TASK_STK_SIZE];
void Task3(void /* OS_FAR */ *pdata)
{
xdat unsigned char mask = 1 << (((char *)pdata)[0] - '0');
xdat unsigned dlay = (1 << (((char *)pdata)[2] - '0')) * 2;
pdata = pdata; /* avoid compiler warning */
while (1) {
P1 ^= mask; /* Toggle P1.<bitno> */
P2 &= ~mask; /* Reset P2.<bitno> */
ser_putc('3');
OSTimeDly(dlay);
P2 |= mask; /* Set P2.<bitno> */
}
} /* Task3() */
OS_STK_TYPE stk_key[TASK_STK_SIZE];
void task_key(void *pdata)
{
pdata = pdata; /* avoid compiler warning */
while (1) {
static char buf[40];
char *s;
s = fgets(buf, sizeof(buf), stdin);
if (s != NULL) {
buf[strlen(buf)-1] = '\0'; /* Remove trailing '\n' */
dbg_printf("task_key: fgets() returned \"%s\"", buf);
/* Parse command */
switch (buf[0]) {
case 'e':
dbg_printf("This is the 'e' command");
continue;
case 's':
pr_ucos_status();
continue;
} /* switch ()... */
}
else {
dbg_printf("task_key: fgets() returned NULL");
}
} /* while (1)... */
} /* task_key() */
static void start_serial(void)
{
dbg_printf("start_serial: before IE=%02X, IP=%02X, PCON=%02X, SCON=%02X, TMOD=%02X",
IE, IP, PCON, SCON, TMOD);
/* Chain Serial ISR */
dbg_printf("setvect(INT_RI_TI, %04X)", (u_int16_t)OSSerialISR);
setvect(INT_RI_TI, OSSerialISR);
ES = 1; /* Enable Serial Port Interrupt */
dbg_printf("start_serial: after IE=%02X, IP=%02X, PCON=%02X, SCON=%02X, TMOD=%02X",
IE, IP, PCON, SCON, TMOD);
} /* start_serial() */
#if USE_TIMER0
void start_timer0(void)
{
OldTimeTick = getvect(INT_TF0);
/* dbg_printf("OldTick=%04X", (u_int16_t)OldTimeTick); */
/* dbg_printf("setvect(INT_TF0, %04X)", (u_int16_t)OSTimeTick); */
setvect(INT_TF0, OSTimeTick);
/* Program Timer 0:
* Gate = 0 => timer enabled on TR0
* C/nT = 0 => source = 1/12 fOSC
* mode = 1 => 16-Bit counter/timer
*/
#pragma asm
mov a, TMOD
anl a, #0F0h
orl a, #01h
mov TMOD, a
mov a, #00h
mov TL0, a
mov a, #00h
mov TH0, a
#pragma endasm
ET0 = 1; /* Enable Interrupt on Timer 0 Overflow */
TR0 = 1; /* Start Timer 0 */
} /* start_timer0() */
#endif /* start_timer0() */
#if (!USE_TIMER0)
void start_timer1(void)
{
OldTimeTick = getvect(INT_TF1);
/* dbg_printf("OldTick=%04X", (u_int16_t)OldTimeTick); */
/* dbg_printf("setvect(INT_TF1, %04X)", (u_int16_t)OSTimeTick); */
setvect(INT_TF1, OSTimeTick);
/* Program Timer 1:
* Gate = 0 => timer enabled on TR1
* C/nT = 0 => source = 1/12 fOSC
* mode = 0 => 13-bit counter
*/
#pragma asm
mov a, TMOD
anl a, #0Fh
orl a, #00h
mov TMOD, a
mov a, #00h
mov TL1, a
mov a, #00h
mov TH1, a
#pragma endasm
ET1 = 1; /* Enable Interrupt on Timer 1 Overflow */
TR1 = 1; /* Start Timer 1 */
} /* start_timer1() */
#endif /* (!USE_TIMER0) */
int main(/* int argc, char *argv[] */)
{
OSInit();
DpySemPtr = OSSemCreate(1); /* Dpy semaphore */
KeyQPtr = OSQCreate(&KeyQ[0], KEY_Q_SIZE); /* Kbd queue */
OSTaskCreate(task_key, NULL, stk_key, 8);
OSTaskCreate(Task3, Data3, Stk3, 30);
OSTaskCreate(Task2, Data2, Stk2, 40);
OSTaskCreate(Task1, Data1, Stk1, 50);
OS_ENTER_CRITICAL();
#if USE_TIMER0
start_timer0();
#else
start_timer1();
#endif
start_serial();
dbg_printf("before OSStart IE=%02X, IP=%02X, TMOD=%02X",
IE, IP, TMOD);
/* Flush Transmitter Interrupt */
while (!TI)
;
TI = 0;
/* Start multitasking - will do OS_EXIT_CRITICAL() */
OSStart();
return 0; /* will never happen... */
} /* main() */
/* === End of File === */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -