This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

high precision timer using AT89S8252

I am trying to implement a high precision timer using AT89S8252 using the following
code:

void configureTimer0(void)
{
EA = 0;
TMOD &= 0xf0;
TMOD |= 0x01;
ET0 =1;
TH0 = TH_VAL
TL0 = TL_VAL
TR0= 1;
EA = 1;
}

// timer 0 interrupt handle
void timer0 (void) interrupt 1
{
TH0 = TH_VAL;
TL0 = TL_VAL;
P2_1 = !P2_1;
switch(val)
{
case 1: // code
break;
case 2: // code
break;
}
}

void main(void)
{
configureTimer0();
while(1);
}

The problem occurs when I try to insert any code inside the Timer 0 interrupt handle, such as a blinking LED ar a simple switch
statement. The code inside interrupt handle was as simple as possible.
In order to keep a constant rate, I have to use a digital osciloscope to adjust TH_VAL and TL_VAL.

Is there any other way to implement this ? Do I have to constantly calibrate TH_VAL and TL_VAL after inserting any piece of code inside the timer interrupt handle ?


Best regards,

Andre

Parents
  • You must note that the timer continues running when interrupt goes active. If a higher priority interrupt exists, you can add a constant to TH0-TL0 and not load a constant. You can adjust constant by calculting time to execute add.

    clr ea
    clr tr0
    xch a,tl0
    add a,#low(constant)
    xch a,tl0
    xch a,th0
    addc a,#high(constant
    xch a,th0
    setb tr0
    setb ea
    

    For example, if you have a constant of 500 cycles, you must load -500 in TH0-TL0. If timer ISR start 20 cycles after timer overflow, TH0-TL0 contains 20. If you add -500 to 20 you obtain 480. So next ISR takes place in 480 cycles and you obtain correctly 500 cycles since current ISR.

    If you use XCH instructions to make addition, you may to not save ACC in timer ISR.

Reply
  • You must note that the timer continues running when interrupt goes active. If a higher priority interrupt exists, you can add a constant to TH0-TL0 and not load a constant. You can adjust constant by calculting time to execute add.

    clr ea
    clr tr0
    xch a,tl0
    add a,#low(constant)
    xch a,tl0
    xch a,th0
    addc a,#high(constant
    xch a,th0
    setb tr0
    setb ea
    

    For example, if you have a constant of 500 cycles, you must load -500 in TH0-TL0. If timer ISR start 20 cycles after timer overflow, TH0-TL0 contains 20. If you add -500 to 20 you obtain 480. So next ISR takes place in 480 cycles and you obtain correctly 500 cycles since current ISR.

    If you use XCH instructions to make addition, you may to not save ACC in timer ISR.

Children
  • Eric,

    This is a good solution if programming in assembler, although I note you have not mentioned compensating for the 'lost' timer counts during the period the timer is disabled. Presumably you would recalculate your constant to take this into account?

    In 'C' techniques that rely on code being compiled into a specific sequence of instructions are too difficult to maintain for my liking.

    Stefan