Searching \ for '[PIC] Context Saving' in subject line. ()
Make payments with PayPal - it's fast, free and secure! Help us get a faster server
FAQ page: www.piclist.com/techref/microchip/devices.htm?key=pic
Search entire site for: 'Context Saving'.

Exact match. Not showing close matches.
PICList Thread
'[PIC] Context Saving'
2005\06\13@120302 by Francois Robbertze

flavicon
face
"For the PIC16F873/874 devices, the register W_TEMP must be defined in both
banks 0 and 1 and must be defined at the same offset from the bank base
address (i.e., If W_TEMP is defined at 0x20 in bank 0, it must also be
defined at 0xA0 in bank 1). The registers, PCLATH_TEMP and STATUS_TEMP, are
only defined in bank 0."

To define W_TEMP in bank 0 is easy:

W_TEMP                equ    0x20
STATUS_TEMP    equ    0x21

How do one define W_TEMP in bank _1 again?

regards

Francois

2005\06\13@122838 by Alan B. Pearce

face picon face
>How do one define W_TEMP in bank _1 again?

The easiest and best way is to use a location in RAM that is in both banks.
However another method is to define another register, say W_TEMP_1 in bank 1
to reserve the location. The fact that the name is different as the actual
name is not important because it will be hidden by the different bank if the
interrupt occurs while the main code is in bank 1.

It does take a little bit of thinking about to get your head around what
happens, but it does work out correctly.

2005\06\13@125154 by PicDude

flavicon
face
Funny you should ask.  This one bit me this weekend...

First, to define W_Temp in bank 1, just add 0x80 to the first location, so
also define the same var (change the name slightly to something like W_TEMP1)
in location 0xA0.  That "mirrors" it in bank 1.  Fig 2-4 on the 16F87x
datasheer will help.

Here's the part that bit me, so I'll save you some grief just in case...

On other 16F PICs (such as the 16F874), there is a small data-RAM section that
is shared/accessible in all the other banks, but that section on the
16F873/F874 is not completely shared in the other banks.  Ex: locations
0x70-0x7F is not accessible in bank 1.  Since I ported code over from a
16F872, I still had the original context-saving routine at the start of the
ISR, but had to modify it to explicitly save W in bank 0.  Example 12-1 on
the 16F87x datasheet shows this as the 3rd instruction ("CLRF   STATUS") to
switch back to bank 0 before saving W.

Cost me a few hours of very manual debugging before I realized this. :-(

Cheers,
-Neil.


On Monday 13 June 2005 11:02 am, Francois Robbertze scribbled:
{Quote hidden}

2005\06\13@141852 by Wouter van Ooijen

face picon face
> To define W_TEMP in bank 0 is easy:
>
> W_TEMP                equ    0x20
> STATUS_TEMP    equ    0x21
>
> How do one define W_TEMP in bank _1 again?

No need to define it, just make sure that it is not used by any other
function.

Wouter van Ooijen

-- -------------------------------------------
Van Ooijen Technische Informatica: http://www.voti.nl
consultancy, development, PICmicro products
docent Hogeschool van Utrecht: http://www.voti.nl/hvu


2005\06\13@142219 by olin piclist

face picon face
Francois Robbertze wrote:
> "For the PIC16F873/874 devices, the register W_TEMP must be defined in
> both banks 0 and 1 and must be defined at the same offset from the bank
> base address (i.e., If W_TEMP is defined at 0x20 in bank 0, it must
> also be defined at 0xA0 in bank 1). The registers, PCLATH_TEMP and
> STATUS_TEMP, are only defined in bank 0."
>
> To define W_TEMP in bank 0 is easy:
>
> W_TEMP                equ    0x20

Apparently not so easy.  This only defines the symbol W_TEMP but does
nothing to reserve the data memory location at 20h or A0h.  The best way to
handle this is probably to define a SHAREBANK in your linker file.  The
873/874 don't really have shared RAM locations, but that way you can define
W_TEMP in a UDATA_SHR section.  This will make the source code compatible
with processors like the 876 that do have a shared RAM region.  In any case,
you should not hard code RAM addresses into the source code.  This is just
asking for trouble when the code is moved to another PIC, and is inviting
you to make a mistake.

> STATUS_TEMP    equ    0x21

Again, this should be

bank0  udata_shr
STATUS_TEMP  RES 1

since you don't care where it ends up other than you want it in bank 0.  I
would define a 1 byte SHAREBANK to be used for W_TEMP, then define
everything left over as DATABANK and define the section .BANK0 to that
DATABANK.  This will put the machine specifics in the linker file and keep
the source code as compatible with other PICs as possible.  It also
minimizes the chance of human error.


*****************************************************************
Embed Inc, embedded system specialists in Littleton Massachusetts
(978) 742-9014, http://www.embedinc.com

2005\06\13@144214 by Bob Ammerman

picon face
Olin,

You will also need to create a section .BANK1 to cover the bank 1 RAM, and
when you do, you will have to be careful to leave out the byte that sits as
the same relative location as your pseudo-SHAREBANK.

Bob Ammerman
RAm Systems

{Original Message removed}

2005\06\13@175159 by olin piclist

face picon face
Bob Ammerman wrote:
> You will also need to create a section .BANK1 to cover the bank 1
> RAM,

Yes.  I didn't mention that because the question wasn't about that.

> and when you do, you will have to be careful to leave out the
> byte that sits as the same relative location as your pseudo-SHAREBANK.

You will have to leave out the address range used by the SHAREBANK from both
the bank 0 and bank 1 regions.  There is nothing special about bank 1 in
this case.  The linker should give you an error anyway if you accidentally
define overlapping regions, so there isn't much danger here.

>> bank0  udata_shr
>> STATUS_TEMP  RES 1

I noticed I wrote this wrong when I got the message back.  STATUS_TEMP does
not need be allocated at the same offset in all banks.  I meant to say UDATA
instead of UDATA_SHR.  In the scenario we are discussing, the SHAREBANK is
only one byte, and is used only by W_SAVE.


*****************************************************************
Embed Inc, embedded system specialists in Littleton Massachusetts
(978) 742-9014, http://www.embedinc.com

2005\06\14@040810 by Francois Robbertze

flavicon
face
Thanks for all the help.

Seems fine now. I have defined the W_Temp  in register 0x7B and stay clear
of register 0xFB in Bank1

Francois


> > To define W_TEMP in bank 0 is easy:
> >
> > W_TEMP                equ    0x20
> > STATUS_TEMP    equ    0x21
> >
> > How do one define W_TEMP in bank _1 again?


2005\06\14@114457 by PicDude

flavicon
face
On Monday 13 June 2005 02:51 pm, Francois Robbertze scribbled:
> Thanks for all the help.
>
> Seems fine now. I have defined the W_Temp  in register 0x7B and stay clear
> of register 0xFB in Bank1
>
> Francois

Not sure if this was mentioned before, but you can also add a definition
"W_Temp1   EQU 0xFB" so that it's easier to see later that that spot is
taken.

Cheers,
-Neil.


2005\06\17@061923 by Francois Robbertze

flavicon
face
> Not sure if this was mentioned before, but you can also add a definition
> "W_Temp1   EQU 0xFB" so that it's easier to see later that that spot is
> taken.
>
> Cheers,
> -Neil.

Thanks Neil, someone mentioned it.

I still have a problem with the PAGE selection in the interrupt routine...

  Org     0x04

  movwf   savedW
  swapf   STATUS, w
  bcf  STATUS,RP0
  movwf   savedSTAT

  goto INT_handler


INT_handler                        ;Located in Page 0 of Program Memory
  ...
  #page_1
  goto       ABC                   ;goto ABC in Page 1
  ...
ABC                                    ;Located in Page1 Program Memory
  ...
EndInterupt                         ;Located in Page1 Program Memory
  swapf   savedSTAT, w
  movwf   STATUS
  swapf   savedW, f
  swapf   savedW, w
  #page_0                           ;????????????????????????????
  retfie

If I omit the #page_0 before the retfie, then the program don't function
correctly.
(THIS IS NOT RIGHT, BECAUSE MY MAIN PROGRAM MIGHT BE IN PAGE1 IN THE EVENT
OF A INTERRUPT TRIGGER)

According to me, the STATUS register (including the Page Selection Bits) is
save at the beginning of the Interrupt and it is restored just before the
retfie.

If the Interrupt is triggered when the program was running in page1 then
Page Selection Bits should be according to page1 and the same with interrups
from page0...after the retfie command.

Could someone give me clarity on this.

Thanks

Francois

2005\06\17@070230 by Peter Onion

flavicon
face
On Fri, 2005-06-17 at 12:19 +0200, Francois Robbertze wrote:
> > Not sure if this was mentioned before, but you can also add a definition
> > "W_Temp1   EQU 0xFB" so that it's easier to see later that that spot is
> > taken.
> >
> > Cheers,
> > -Neil.
>
> Thanks Neil, someone mentioned it.
>
> I still have a problem with the PAGE selection in the interrupt routine...
>
>    Org     0x04
>
>    movwf   savedW
>    swapf   STATUS, w
>    bcf  STATUS,RP0
>    movwf   savedSTAT
>

I think you need a "pagesel INT_handler" in here before the goto.

{Quote hidden}

Here is the interrupt enty/exit code from the 877A manual... You NEED to
use it ALL !!!!  Note the comment about saving PCLATH if using other
pages.


MOVWF W_TEMP ;Copy W to TEMP register
SWAPF STATUS,W ;Swap status to be saved into W
CLRF STATUS ;bank 0, regardless of current bank, Clears IRP,RP1,RP0
MOVWF STATUS_TEMP ;Save status to bank zero STATUS_TEMP register
MOVF PCLATH, W ;Only required if using pages 1, 2 and/or 3
MOVWF PCLATH_TEMP ;Save PCLATH into W
CLRF PCLATH ;Page zero, regardless of current page
:
:(ISR) ;(Insert user code here)
:
MOVF PCLATH_TEMP, W ;Restore PCLATH
MOVWF PCLATH ;Move W into PCLATH
SWAPF STATUS_TEMP,W ;Swap STATUS_TEMP register into W
;(sets bank to original state)
MOVWF STATUS ;Move W into STATUS register
SWAPF W_TEMP,F ;Swap W_TEMP
SWAPF W_TEMP,W ;Swap W_TEMP into W



>
> According to me, the STATUS register (including the Page Selection Bits) is
> save at the beginning of the Interrupt and it is restored just before the
> retfie.

Program Page selection bits are in PCLATH NOT STATUS.. BANK selection
bits are in STATUS..  You need to save them BOTH!  (see code above).

Peter

2005\06\17@072659 by Jan-Erik Soderholm

face picon face
Francois Robbertze wrote :

> I still have a problem with the PAGE
selection in the
> interrupt routine...
>
>    Org     0x04
>
>    
movwf   savedW
>    swapf   STATUS, w
>    bcf  STATUS,RP0

OK, so know
we are in bank 0...

>    movwf   savedSTAT

Saved in bank 0...

>
>    goto INT_handler
>
>
> INT_handler        ;Located in Page 0...
>    ...
>    #page_1

What is "#page_1" ??

>
EndInterupt                         ;Located in Page1 Program Memory
>    swapf   savedSTAT, w

Are you sure you are in bank 0 ?

>    
movwf   STATUS
>    swapf   savedW, f
>    swapf   savedW, w
>    
#page_0                           ;????????????????????????????
>    
retfie
>
> If I omit the #page_0 before the retfie, then the program
> don't function correctly.

What does "don't function correctly" mean
???

> (THIS IS NOT RIGHT, BECAUSE MY MAIN PROGRAM
> MIGHT BE IN PAGE1
IN THE EVENT OF A INTERRUPT TRIGGER)

Which shouldn't matter, the full
return address is on the stack,
and your code will return to the right
spot anyway.

>
> According to me, the STATUS register (including the
Page
> Selection Bits)

There are no "page selection bits" in the
STATUS reg.

> is save at the beginning of the Interrupt and it is
restored
> just before the retfie.
>
> If the Interrupt is triggered
when the program was
> running in page1 then Page Selection Bits should
be
> according to page1 and the same with interrups
> from page0...
after the retfie command.

Again, there are no "page selection bits" in
STATUS.

Regards,
Jan-Erik.



2005\06\17@074421 by Francois Robbertze

flavicon
face
> Program Page selection bits are in PCLATH NOT STATUS.. BANK selection
> bits are in STATUS..  You need to save them BOTH!  (see code above).
>
> Peter

Thanks Peter

Got confused AGAIN between BANK and PAGE. Should get rid of these macros so
that I can be reminded what Registers is envolved.



2005\06\17@080050 by Francois Robbertze

flavicon
face
Sorry Jan-Eric

> There are no "page selection bits" in the
> STATUS reg.

I almost bank my pages - lol

I will save the PCLACH register as well!

> What is "#page_1" ??

It is a bad practice....a Macro Setting PCLACH, 3

#page_0 macro  ;For program memory paging
       bcf     PCLATH,3
       endm

#page_1 macro  ;For program memory paging
       bsf     PCLATH,3
       endm


> What does "don't function correctly" mean ???
Running around somewhere in Page1


> > (THIS IS NOT RIGHT, BECAUSE MY MAIN PROGRAM
> > MIGHT BE IN PAGE1
> IN THE EVENT OF A INTERRUPT TRIGGER)
>
> Which shouldn't matter, the full
> return address is on the stack,
> and your code will return to the right
> spot anyway.

It will return to the right spot allright, but the Page Select Bits might
not be correctly set for the next call or goto.


Francois

2005\06\17@081830 by Jan-Erik Soderholm

face picon face
Francois Robbertze wrote :


> > Which shouldn't matter, the full
> >
return address is on the stack,
> > and your code will return to the
right
> > spot anyway.
>
> It will return to the right spot allright,
but the Page
> Select Bits might not be correctly set for the next
>
call or goto.

As expected of course. :-)

Have you checked the LCALL
and LGOTO
psuedo instructions ?

Jan-Erik.



2005\06\17@101700 by Francois Robbertze

flavicon
face
> Have you checked the LCALL
> and LGOTO
> psuedo instructions ?
>
> Jan-Erik.

Not jet...

Still learning the basics ;{}

2005\06\17@112922 by Jan-Erik Soderholm

face picon face
Francois Robbertze wrote :

> > Have you checked the LCALL
> > and
LGOTO
> > psuedo instructions ?
> >
> > Jan-Erik.
>
> Not jet...
>
>
Still learning the basics ;{}

OK. In short, they set the PCLATH bit 3
and
4 to match the target of the GOTO and CALL,
and then execute the
GOTO or CALL.

Note that they will always BCF/BSF the and
the PCLATH
bits even if not needed (as when
they are already corrctly set)...

Note2, be carefull and don't put any of the
SKIP instructions directly
before the Lxxxx
pseudo instructions. Only the first BCF/BSF
will be
skipped with some realy "interesting"
results... :-)

Jan-Erik.



2005\06\17@152912 by Dwayne Reid

flavicon
face
At 04:19 AM 6/17/2005, Francois Robbertze wrote:

>I still have a problem with the PAGE selection in the interrupt routine...
>
>    Org     0x04
>
>    movwf   savedW
>    swapf   STATUS, w

change the following line from

>    bcf  STATUS,RP0

to
    clrf  STATUS   ;clears both RAM bank bits on those PICs that have them

>    movwf   savedSTAT

Add the following lines:
    movfw  PCLATH
    movwf  savedPCLATH  ;RAM bank 0


{Quote hidden}

Add the following lines:
    movfw  savedPCLATH
    movwf  PCLATH

>    swapf   savedSTAT, w
>    movwf   STATUS
>    swapf   savedW, f
>    swapf   savedW, w
>    retfie

dwayne

--
Dwayne Reid   <spam_OUTdwaynerTakeThisOuTspamplanet.eon.net>
Trinity Electronics Systems Ltd    Edmonton, AB, CANADA
(780) 489-3199 voice          (780) 487-6397 fax

Celebrating 21 years of Engineering Innovation (1984 - 2005)
 .-.   .-.   .-.   .-.   .-.   .-.   .-.   .-.   .-.   .-
    `-'   `-'   `-'   `-'   `-'   `-'   `-'   `-'   `-'
Do NOT send unsolicited commercial email to this email address.
This message neither grants consent to receive unsolicited
commercial email nor is intended to solicit commercial email.

2005\06\18@074100 by Gerhard Fiedler

picon face
Francois Robbertze wrote:

>> What is "#page_1" ??
>
> It is a bad practice....a Macro Setting PCLACH, 3
>
> #page_0 macro  ;For program memory paging
>         bcf     PCLATH,3
>         endm

Not necessarily "bad practice"... I think it's good practice, for two
reasons. One is that it's better readable (IMO). The other is that it makes
it easier to port the code to a processor with four pages: you just modify
the macro to set/clear both bits as required. Try that with code that sets
the bits explicitly...

Of course it's also good practice to be aware of what's going on in the
macros :)

Gerhard

2005\06\18@092848 by olin piclist

face picon face
Gerhard Fiedler wrote:
> Not necessarily "bad practice"... I think it's good practice, for two
> reasons. One is that it's better readable (IMO). The other is that it
> makes it easier to port the code to a processor with four pages: you
> just modify the macro to set/clear both bits as required. Try that
> with code that sets the bits explicitly...

But manually allocating code to fixed pages is a bad practise in itself.
Also, I believe PAGESEL will emit only a single BCF/BSF on processors with
two pages.


*****************************************************************
Embed Inc, embedded system specialists in Littleton Massachusetts
(978) 742-9014, http://www.embedinc.com

2005\06\18@115154 by John J. McDonough

flavicon
face
----- Original Message -----
From: "Olin Lathrop" <.....olin_piclistKILLspamspam@spam@embedinc.com>
Subject: Re: [PIC] Context Saving


> But manually allocating code to fixed pages is a bad practise in itself.
> Also, I believe PAGESEL will emit only a single BCF/BSF on processors with
> two pages.

You made me look.

PAGESEL does, in fact, only emit a single BCF/BSF on processors with two
pages, and for processors with one page, it emits a message saying it is not
needed.

However, LCALL sets both bits whether or not it is needed.

--McD

2005\06\18@120846 by olin piclist

face picon face
John J. McDonough wrote:
> PAGESEL does, in fact, only emit a single BCF/BSF on processors with
> two pages, and for processors with one page, it emits a message
> saying it is not needed.
>
> However, LCALL sets both bits whether or not it is needed.

So don't do that.  It's easy enough to wrap PAGESEL and CALL into a macro.
In fact, I've already done that.  See the GCALL macro in STD.INS.ASPIC.  In
addition it restores PCLATH to the current page after the return.


*****************************************************************
Embed Inc, embedded system specialists in Littleton Massachusetts
(978) 742-9014, http://www.embedinc.com

2005\06\19@233647 by PicDude

flavicon
face
Speaking of context saving and paging, I found this doc
(ww1.microchip.com/downloads/en/DeviceDoc/ramrom.pdf) yesterday, which
indicates on slide 12, how to "correctly execute GOTO instructions", but it
is wrong.  In the 4 bytes that is sort of allocated to the interrupt vector,
they load W with the high bits of the ISR routine address, then put it into
PCLATH, then call the goto instruction.  Problem is that W is destroyed
before getting to the interrupt.  I can't think of any practical instance
where an ISR will not need to restore W.  I ended up putting the context-save
routine right at address 0x0004 (the interrupt vector), calling the ISR
routine, and restoring it after coming back from the interrupt routine.  
Works well, but any better way of doing this?

Cheers,
-Neil.



On Saturday 18 June 2005 10:51 am, John J. McDonough scribbled:
> {Original Message removed}

2005\06\20@071156 by Gerhard Fiedler

picon face
PicDude wrote:

> I ended up putting the context-save routine right at address 0x0004 (the
> interrupt vector), calling the ISR routine, and restoring it after
> coming back from the interrupt routine. Works well, but any better way
> of doing this?

In what way better?

You need to do some minimal context saving before you execute the first
goto (status, w, pclath). This must be done before you goto somewhere. If
you need to save more context, that may come after the goto.

Gerhard

2005\06\20@074221 by olin piclist

face picon face
PicDude wrote:
> I ended up putting the context-save routine right at
> address 0x0004 (the interrupt vector), calling the ISR routine, and
> restoring it after coming back from the interrupt routine. Works well,
> but any better way of doing this?

Yes.  Put the whole ISR starting at the interrupt vector.  No need for a
GOTO at all.


*****************************************************************
Embed Inc, embedded system specialists in Littleton Massachusetts
(978) 742-9014, http://www.embedinc.com

More... (looser matching)
- Last day of these posts
- In 2005 , 2006 only
- Today
- New search...