BasicMicro - Forums

www.basicmicro.com
It is currently Mon May 21, 2012 8:17 pm

All times are UTC - 8 hours [ DST ]




Post new topic Reply to topic  [ 9 posts ] 
Author Message
 Post subject: ONASMINTERRUPT issues
PostPosted: Sun Jun 19, 2011 5:44 pm 
Offline
Citizen

Joined: Sun Jan 16, 2011 6:22 pm
Posts: 7
I'm trying to convert interrupt code to use ASM but I'm not getting too far using ONASMINTERRUPT command with WKPINT interrupts. the error I get is "[TOKEN WKPINT_2]:unknown command".


Could someone look over this code and give me some advice.
Also... when do you use ASM{} versus BEGIN/END ASMSUB? Where do I put the Subroutine name and RTE?

Thanks

Code:
'Variables
'======================================================================
LOOPTIMER    var long      'increments 256 times per second
SENCODER    var slong
RTime    var slong
cIndex    var long
CAPTURE1    var slong
CAPTURE2    var slong
CAPTURE3    var slong
CAPTURE4    var slong
'======================================================================
'SetupTimerAndInterrupts
'======================================================================

PMR5.bit2 = 1      ' enables pin2 as WKP interrupt instead of normal I/O - Laser input
IEGR2.bit2 = 1      ' 0 = Pin2 will interrupt on a falling edge, 1 to interrupt on a rising edge.

TMA = (TMA & 0xf0) | 0x4                ' Sets TimerA to increment once every 256 clock cycles.

ONASMINTERRUPT TIMERAINT,HANDLE_TIMERA
ENABLE TIMERAINT                  ' enable timer interrupt

ONASMINTERRUPT WKPINT_2, LASERINTERRUPT    ' Define interrupt action
ENABLE WKPINT_2                  ' enable Laser Sensor interrupt

'======================================================================
'  ASM version of TimerA handler...
'  Increments TIMERCOUNT every 256 clock cycles
'======================================================================

HANDLE_TIMERA
asm{
   push.l   er0               ; Save work registers
   bclr   #6,@IRR1:8            ; clear the cooresponding bit in the interrupt pending mask
   mov.l   @LOOPTIMER,er0         ; increment "Loop timer clock" count
   inc.l   #1,er0
   mov.l   er0, @LOOPTIMER
   ;
   pop.l   er0
   }

RESUME


'======================================================================
LASERINTERRUPT
'======================================================================

asm{               ; Mark as assembly code
   push.l  er1                     
   bclr    #2,@IWPR:8               ; clear the WKP2 bit in the interrupt pending mask
   andc    #0x7f,ccr               ; allow other interrupts to happen

   mov.l   @CAPTURE3:32,er1            ; Move in CAPTURE3 count
   mov.l   er1,@CAPTURE4:32          ; move out to CAPTURE4 count
   mov.l   @CAPTURE2:32,er1            ; Move in CAPTURE2 count
   mov.l   er1,@CAPTURE3:32          ; move out to CAPTURE3 count
   mov.l   @CAPTURE1:32,er1            ; Move in CAPTURE1 count
   mov.l   er1,@CAPTURE2:32          ; move out to CAPTURE2 count
   mov.l   @SENCODER:32,er1            ; Move in current count
   mov.l   er1,@CAPTURE1:32          ; move out to CAPTURE1 count
   mov.l   @CINDEX:32,er1            ; Move in cindex
   inc.l   #1,er1                        ; increment our count
   mov.l   er1,@CINDEX:32          ; move out to cindex count
   pop.l   er1                ; clean up
   }                  ; Unmark assembly code

Resume

'======================================================================



Top
 Profile  
 
 Post subject: Re: ONASMINTERRUPT issues
PostPosted: Sun Jun 19, 2011 8:14 pm 
Offline
Master

Joined: Tue Nov 21, 2006 9:34 am
Posts: 528
Hi Chett,

I will give it a shot...

First WKPINT_2 is not a real ASM interrupt. That is there is one interrupt for WKP interrupts (WKPINT). The handler must figure out which of the 6 WKP pins caused the interrupt and clear it. Obviously if you only enable one that is pretty easy to do. When you do an ONINTERRUPT WKPINT_2 in basic, the actual interrupt handler does this for you...

You use the BEGINASMSUB/ENDASMSUB tags to tell the compiler to not generate any enter ASM from basic code and leave asm back to Basic code. That it you can write normal code that has inline asm and the compiler adds a bunch of extra code to transition you into and out of ASM. Which when you are dong an ASM interrupt handler you do not need or want this.

The ASM{} bracketing tells the code that everything inside is ASM and don't try to interrupt as basic. This is sometimes needed when the compiler mistakes some of your code for basic and gives you some strange error messages. Also when you are in the asm{} block you have the full power of the macro assembler. What this also implies is things like:
#ifdef X
will not work inside one of these blocks, but instead it is something like: .if ...

Good Luck
Kurt


Top
 Profile  
 
 Post subject: Re: ONASMINTERRUPT issues
PostPosted: Mon Jun 20, 2011 9:29 am 
Offline
Site Admin
User avatar

Joined: Thu Mar 01, 2001 11:00 am
Posts: 903
Location: Temecula, CA
Kurt is correct. If you are using asm interrupt for the WKP pins you must use the WKPINT interrupt. THe WKPINT_# interrupts are basic only, because we add a handler for them as Kurt said. For asm interrupts you must handle them your self in the single WKP interrupt vector.

_________________
Tech Support
Basic Micro - Robotic Technology Evolved


Top
 Profile  
 
 Post subject: Re: ONASMINTERRUPT issues
PostPosted: Mon Jun 20, 2011 2:45 pm 
Offline
Citizen

Joined: Sun Jan 16, 2011 6:22 pm
Posts: 7
Thank you both for your responses. You guys (and a few other notables) are great and people like me have learned a lot from reading your postings.
I've been working with interrupts and I come to the conclusion that I need to use assembly code in the interrupt routines. I've lifted as much code as I can from your past posts(encoders, timers, etc.) and it's been very instructive but I'd like to do more. Is ther some assembly language manual somewhere? Can you point me to a website?

I see now how the WKP interrupt works. In fact I had an old post of yours that discussed an assembly language routine that would determine which of the WKPint_X had been set. Now it makes sense! I'll solve my problem by switching to an available IRQ.
I still don't understand the distinction between BEGINASMSUB/ENDASMSUB and the ASM{} instructions. Could you give an example of when you would use one over the other.

Thanks


Top
 Profile  
 
 Post subject: Re: ONASMINTERRUPT issues
PostPosted: Mon Jun 20, 2011 4:56 pm 
Offline
Master

Joined: Tue Nov 21, 2006 9:34 am
Posts: 528
You need the BEGINASMSUB/ENDASMSUB stuff around an interrupt handler as without it screwy things happen in particular If you have something like:

Code:
; some basic code
...
    goto foo
HANDLE_TIMERA_ASM:
   push.w    r1                  ; first save away ER1 as we will mess with it.
   bclr    #6,@IRR1:8               ; clear the corresponding bit in the interrupt pending mask
   mov.w    @WTIMERCNT:16,r1      ; Add 256 to our counter
   add.w   #256,r1
   mov.w    r1, @WTIMERCNT:16
   pop.w    r1
   rte
MyBasicFunction:
         x = y

What the compiler will do here without the BEGIN/END stuff is at the start of the HANDLE_TIMERA_ASM, it will install additional code to transition from basic to asm, which you don't want. Like wise at MyBasicFunction it will insert code to transition back from ASM, which again you don't want. I had programs bombing without these tags.

As for ASM {}, I often don't use them unless the compiler gives me some screwy problems. Often it will show up with some error like something is multiply defined...

Kurt


Top
 Profile  
 
 Post subject: Re: ONASMINTERRUPT issues
PostPosted: Mon Jun 20, 2011 6:00 pm 
Offline
Citizen

Joined: Sun Jan 16, 2011 6:22 pm
Posts: 7
I don't know...
This one using ASM{} does compile
Code:
LOOPTIMER    var long      'increments 256 times per second

TMA = (TMA & 0xf0) | 0x4    ' Sets TimerA to increment once every 256 clock cycles.
ONASMINTERRUPT TIMERAINT,HANDLE_TIMERA_ASM
ENABLE TIMERAINT               ' enable timer interrupt


HANDLE_TIMERA_ASM

asm{
   push.l   er0                     ; Save work registers
   bclr   #6,@IRR1:8               ; clear the cooresponding bit in the interrupt pending mask
   mov.l   @LOOPTIMER,er0         ; increment "Loop timer clock" count
   inc.l   #1,er0
   mov.l   er0, @LOOPTIMER
   pop.l   er0
   RTE
}


But this one using BEGINASMSUB/ENDASMSUB does not compile and gives the following error
- TST.BAS[line 15] : [TOKEN INC] : Redefining to VAR


Code:
LOOPTIMER    var long      'increments 256 times per second

TMA = (TMA & 0xf0) | 0x4    ' Sets TimerA to increment once every 256 clock cycles.
ONASMINTERRUPT TIMERAINT,HANDLE_TIMERA_ASM
ENABLE TIMERAINT               ' enable timer interrupt


HANDLE_TIMERA_ASM

BEGINASMSUB
   push.l   er0                     ; Save work registers
   bclr   #6,@IRR1:8               ; clear the cooresponding bit in the interrupt pending mask
   mov.l   @LOOPTIMER,er0         ; increment "Loop timer clock" count
   inc.l   #1,er0
   mov.l   er0, @LOOPTIMER
   pop.l   er0
   RTE
ENDASMSUB


If I use both BEGINASMSUB and ASM{} it all compiles but do I gain anything by doing that?


Top
 Profile  
 
 Post subject: Re: ONASMINTERRUPT issues
PostPosted: Mon Jun 20, 2011 8:17 pm 
Offline
Master

Joined: Tue Nov 21, 2006 9:34 am
Posts: 528
chettt wrote:
- TST.BAS[line 15] : [TOKEN INC] : Redefining to VAR
If I use both BEGINASMSUB and ASM{} it all compiles but do I gain anything by doing that?

Yep, as I mentioned, the ASM{} is needed when you get that redefine error... But yes with the ONASMINT... use the begin/end as well.

Kurt


Top
 Profile  
 
 Post subject: Re: ONASMINTERRUPT issues
PostPosted: Tue Jun 21, 2011 12:33 am 
Offline
Citizen

Joined: Sun Jan 16, 2011 6:22 pm
Posts: 7
Now I get it.

Thanks for your help on this one.


Top
 Profile  
 
 Post subject: Re: ONASMINTERRUPT issues
PostPosted: Sat Jun 25, 2011 8:39 pm 
Offline
Site Admin
User avatar

Joined: Thu Mar 01, 2001 11:00 am
Posts: 903
Location: Temecula, CA
Just to clarify. BEGINASMSUB/ENDASMSUB just tells the compiler not to try adding basic to asm entry/exit code. It doesn't do anything else. ASM{} tells the compiler to consider everything in the braces to be asm code. Without the BEGINASMSUB/ENDASMSUB the compiler would still try to add entry/exit code for the asm{} block and without the asm{} it would still try to compile the code inside the BEGINASMSUB/ENDASMSUB as if it may have basic code in it. SO you must use both in this particular example.

_________________
Tech Support
Basic Micro - Robotic Technology Evolved


Top
 Profile  
 
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 9 posts ] 

All times are UTC - 8 hours [ DST ]


Who is online

Users browsing this forum: No registered users and 1 guest


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Jump to:  
cron
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group

phpBB SEO