PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Wed Jul 16, 2008 4:04 pm |
|
|
Here is a simple multi-tasking program that can perform several tasks
at different rates. It polls the high bit of Timer0 to see when the timer
has rolled over from 0xFF to 0x00. In a normal PIC, you could poll
the TMR0IF bit, or you could use the #int_timer0 interrupt. In your PIC,
there are no interrupts, and there is no TMR0IF bit.
This test program is written for a 16F877, but the same principles can
be used for your 10F222 PIC.
Code: | #include <16F877.H>
#device adc=8
#fuses XT, NOWDT, NOPROTECT, BROWNOUT, PUT, NOLVP
#use delay(clock=4000000)
#use rs232(baud=9600, xmit=PIN_C6, rcv=PIN_C7, ERRORS)
#define LED_PIN PIN_B0
// This equation calculates the duration of each timer tick in
// ms. The timer is clocked at 1/4 of Fosc. Because we are
// using a 4 MHz crystal, the timer clock is therefore 1 MHz.
// We are using a pre-scaler of 32. Timer0 rolls over from
// 0xFF to 0x00 every 256 clocks
#define TICK_MS ((1000 * 256 * 32) / (4000000/4)) // 8 ms
#define TASK1_TIMER_VALUE (2000/TICK_MS) // Every 2 seconds
#define TASK2_TIMER_VALUE (500/TICK_MS) // Every 500 ms
#define TASK3_TIMER_VALUE (100/TICK_MS) // Every 100 ms
int16 task1_timer;
int16 task2_timer;
int16 task3_timer;
//--------------------------
void timer_tick(void);
void task1(void);
void task2(void);
void task3(void);
//==========================
void main()
{
// Setup Timer0 so it rolls over at a 122 Hz rate.
// This gives a timer tick of approximately 8 ms.
// All tasks (together) must execute in less than 8 ms.
setup_timer_0(RTCC_DIV_32);
task1_timer = TASK1_TIMER_VALUE;
task2_timer = TASK2_TIMER_VALUE;
task3_timer = TASK3_TIMER_VALUE;
// The sum of the time to complete all 3 tasks
// must be less than the timer tick duration.
// Currently the tick is set at 8 Ms.
while(1)
{
task1();
task2();
task3();
timer_tick();
}
}
//================================
// This task transmits a character (A to Z)
// to the PC once every 2 seconds.
void task1(void)
{
static char value = 'A';
if(task1_timer)
return;
else
task1_timer = TASK1_TIMER_VALUE;
putc(value);
value++;
if(value > 'Z')
value = 'A';
}
//--------------------------
// This task blinks an LED at a 1 Hz rate.
void task2(void)
{
static int8 led_on = FALSE;
if(task2_timer)
return;
else
task2_timer = TASK2_TIMER_VALUE;
// Toggle the LED on/off.
led_on = !led_on;
if(led_on)
output_high(LED_PIN);
else
output_low(LED_PIN);
}
//--------------------------
// This task does slightly more complex blinking
// of an LED. It is on for 100 ms, and off for 500 ms.
void task3(void)
{
if(task3_timer)
return;
else
task3_timer = TASK3_TIMER_VALUE;
// Task 3 doesn't do anything yet.
}
//--------------------------
// This function waits for the hardware timer0
// to count up to 0xFF and roll over to 0x00.
void timer_tick(void)
{
// Wait until the Timer0 rolls over from 0xFF to 0x00.
while(!bit_test(get_timer0(), 7)); // Wait until MSB goes high
while(bit_test(get_timer0(), 7)); // Wait until Timer rolls over to 0
if(task1_timer)
task1_timer--;
if(task2_timer)
task2_timer--;
if(task3_timer)
task3_timer--;
} |
|
|