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

Strange behaviour in TIMER0 ISR

Hi all, I have a problem with the ISR of TIMER0.
I'm using keil uVision2 and my target is SIlicon Laboratories C8051F040.

I've tried to make a very simple project in assembler to use Timer0 ISR (below you will find the relatives code) and it works fine.

If I try to translate this project in C, the ISR is called just a few time (around 10 or 11 times) but after this, it is never called!

But... if, instead of Timer0, I use Timer1, all work fine both in C and in Assembler

I can't understand why?
There is someone wich can help me?

NOTE: Is not important the reload value so i don't set it, and although if I set this value the behaviour not change.
NOTE: Timer0 is a 16-bit timer
NOTE: In the examples below I've hided the not relevant code like oscillator init, port init,...

--------------
ASSEMBLY CODE:
--------------

        ...
        ...
        ...

;TIMER_0 Overflow
ORG 0x000B
        LCALL TIMER0_INT

        ...
        ...
        ...


TIMER_INIT:
        NOP

;------
;TIMER0
;TIMER1
;------
        MOV SFRPAGE, #TIMER01_PAGE
        MOV TCON, #01000101b
        MOV TMOD, #00100001b

        ...
        ...
        ...

INTERRUPTS_INIT:
        MOV IE, #10010111b
        MOV IP, #00000000b
        MOV EIE1, #00001000b
        MOV EIE2, #01000000b
        MOV EIP1, #00001000b
        MOV EIP2, #00000000b

        ...
        ...
        ...


MAIN:
        MOV SFRPAGE, TIMER01_PAGE
        SETB TR0                        ;START TIMER

        JMP $


        ...
        ...
        ...


TIMER0_INT:

        RETI

-------
C CODE:
-------

...
...
...


void Timer_Init() { SFRPAGE = TIMER01_PAGE; TCON = 0x45; TMOD = 0x21; CKCON = 0x18; SFRPAGE = TMR2_PAGE; TMR2CN = 0x04; TMR2CF = 0x08; SFRPAGE = TMR3_PAGE; TMR3CN = 0x04; TMR3CF = 0x08; SFRPAGE = TMR4_PAGE; TMR4CN = 0x04; TMR4CF = 0x08; }
... ... ...
void Interrupts_Init() { IE = 0x97; EIE1 = 0x08; EIE2 = 0x40; EIP1 = 0x08; }
... ... ...
void main(void){
Timer_Init(); Interrupts_Init() ... ... ...
SFRPAGE = TIMER01_PAGE; TR0 = 1; //START TIMER
while(1);
}
void timer0_int(void) reentrant interrupt 1 {
}

  • void timer0_int(void) reentrant interrupt 1 {
    


    Why reentrant?

    That sounds like a Really Bad Idea for an ISR - and is a major difference between the 'C' and assembler...

  • Thanks, but "reentrant" is not important, if you delete it, the behaviour not change.

  • Just to clarify:
    I used reentrant function just for test an idea, you can delete it and you will not find any changes in this behaviour.
    Also if I use "using n" no changes appears.

  • TIMER_INIT:
            NOP
    
    ;------
    ;TIMER0
    ;TIMER1
    ;------
            MOV SFRPAGE, #TIMER01_PAGE
    

    but:


    MAIN: MOV SFRPAGE, TIMER01_PAGE


    Surely, one of them must be wrong?

  • yes, it was a my mistake when I copied the code into the post, the correct command must be:

    MAIN:
        MOV SFRPAGE, #TIMER01_PAGE
    

    Thanks for your note but this is not the issue.
    ;)

  • ORG 0x000B
            LCALL TIMER0_INT
    ...
    TIMER0_INT:
    
            RETI
    


    you blow the stack and return to the wrong place, it should be

    ORG 0x000B
            LJMP TIMER0_INT
    ...
    TIMER0_INT:
    
            RETI
    

    yes, it was a my mistake when I copied the code into the post, the correct command must be:
    do not "copy the code into the post" use cut-and-paste, then there is no mistake. If the reason for "copying the code into the post" is to get rid of tabs, get rid of them in your code before the cut-and-paste.

    Erik

  • It seems the discussion are going out of the initial goal!
    We are talking about formal method of copying-and-paste and not about my original issue.

    Please is possible to focus the attention to this?
    Thanks a lot

    Maurizio

  • We are talking about formal method of copying-and-paste and not about my original issue.
    First I show you what (part of) your problem is. Then I suggest a mistake free means of showing your code so no replies happen to be re the mistakes in copying but all replies relate to actual problems in your code.

    If you feel it is OK to waste the free helpers time finding errors in your copying, then I suggest you check your attitude.

    Erik

  • "We are talking about formal method of copying-and-paste and not about my original issue."

    It has already been demonstrated that the code you posted is not the same as the code you run.

    So who knows what other transcription errors might have been introduced...??

    Therefore any further comment on the code as posted is pointless - you need to repost it as instructed so that we know for sure that we are looking at the real code, and not just debugging more of your transcription errors!

  • --------------
    ASSEMBLY CODE:
    --------------
    
            ...
            ...
            ...
    
    ;TIMER_0 Overflow
    ORG 0x000B
            LJMP TIMER0_INT
    
            ...
            ...
            ...
    
    
    TIMER_INIT:
            NOP
    
    ;------
    ;TIMER0
    ;TIMER1
    ;------
            MOV SFRPAGE, #TIMER01_PAGE
            MOV TCON, #01000101b
            MOV TMOD, #00100001b
    
            ...
            ...
            ...
    
    INTERRUPTS_INIT:
            MOV IE, #10010111b
            MOV IP, #00000000b
            MOV EIE1, #00001000b
            MOV EIE2, #01000000b
            MOV EIP1, #00001000b
            MOV EIP2, #00000000b
    
            ...
            ...
            ...
    
    
    MAIN:
            MOV SFRPAGE, #TIMER01_PAGE
            SETB TR0                        ;START TIMER
    
            JMP $
    
    
            ...
            ...
            ...
    
    
    TIMER0_INT:
    
            RETI
    -------
    C CODE:
    -------
    
    ...
    ...
    ...
    
    
    
    void Timer_Init()
    {
        SFRPAGE   = TIMER01_PAGE;
        TCON      = 0x45;
        TMOD      = 0x21;
        CKCON     = 0x18;
        SFRPAGE   = TMR2_PAGE;
        TMR2CN    = 0x04;
        TMR2CF    = 0x08;
        SFRPAGE   = TMR3_PAGE;
        TMR3CN    = 0x04;
        TMR3CF    = 0x08;
        SFRPAGE   = TMR4_PAGE;
        TMR4CN    = 0x04;
        TMR4CF    = 0x08;
    }
    
    
    
    ...
    ...
    ...
    
    
    
    void Interrupts_Init()
    {
        IE        = 0x97;
        EIE1      = 0x08;
        EIE2      = 0x40;
        EIP1      = 0x08;
    }
    
    
    
    ...
    ...
    ...
    
    
    
    
    void main(void){
    
    
    
            Timer_Init();
            Interrupts_Init()
            ...
            ...
            ...
    
    
    
            SFRPAGE = TIMER01_PAGE;
            TR0 = 1;                        //START TIMER
    
    
    
            while(1);
    
    
    
    }
    
    
    
    
    
    void timer0_int(void) reentrant interrupt 1 {
    
    
    
    }
    

    All errors you have found, correctly, are not related my issue, because:
    1) The assembly code I run works fine
    2) The problem is inside C code
    3) All these errors should be detected from Assembler/Compiler, so I should have to realize before start my debug.
    In any case above, you will find the correct code.
    I know you help me using your time, and I appreciate this, but just for this, I would reduce your waste of time focusing on real problem, to be more precise: why the c code don't run and asm code yes?

  • but just for this, I would reduce your waste of time focusing on real problem
    how can we do that when the first thing we see is a glaring error (resulting from your 'copying'). Do you ASS U ME that we would know that this "is not your problem"?, if so you are sadly mistaken. YOU and only YOU can "reduce your waste of time" by posting what you have and not an erroneous copy of it.

    Anyhow in your code you will generate T1 interrupts and you show no T1 ISR, is there one in the assembler and not in the C

    Erik

  • How can we "focus" on the real problem if we don't have the real code to look at?!

    You still have the 'reentrant' qualifier on your ISR declaration - why?

    Are you sure you have tested it without this qualifier?

  • Yes, I'm sure.
    I think this is not a code issue but it depend from some other things.
    For example compiler settings, memory settings, some init file to add at my project........and so!!!!

  • Anyhow in your code you will generate T1 interrupts and you show no T1 ISR, is there one in the assembler and not in the C

    The above is a question in my previous post and the sequence in debugging, be it 'live' or via a forum, is questions and answers till the right question finally emerges.

    Erik