Searching \ for '[PIC] tables in 18F452' 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/memory.htm?key=table
Search entire site for: 'tables in 18F452'.

Exact match. Not showing close matches.
PICList Thread
'[PIC] tables in 18F452'
2005\03\09@183602 by Roland

flavicon
face
Hi

I've been looking at the table command of the 18F, and am trying to figure
out the syntax.

On the 16F, it was simply....



d_user                   ;default code
       addwf  PCL,f
       dt     "6781234",0D

readit
       call   d_user    ;get table value of user code
       movwf  gotit     ;stick it in
       return

----------------------
The 16F to 18F migration example shows....


RdStr   movlw  HIGH(string)
       movwf  TBLPTRH         ; load high byte of pointer (0x12)
       movlw  LOW(string)
       movwf  TBLPTRL         ; load low byte of pointer (0x34)

read    tblrd*+                ; read byte from program memory,
                              ; and increment pointer one byte
       movff  TABLAT,PORTB    ; move byte from table latch to output port B
       tstfsz TABLAT          ; was retrieved byte a null?
goto    read                   ; no, do loop again
       return

ORG 0x1234
String DW "This is a test.",0x00 ; text string

_________________


So do I simply write;

d_user                       ;default code
       dw     "6781234",0D

readit
       movlw  HIGH(d_user)
       movwf  TBLPTRH       ; load high byte of pointer
       movlw  LOW(d_user)
       movwf  TBLPTRL       ; load low byte of pointer

       tblrd*               ; read byte from program memory,
       movff  TABLAT,gotit  ; move byte from table


-The above does work, just not sure how correct it is.
-Is it necessary to ORG each string?
-If so, must it be on an even boundry?
-I suppose I can just 'clrf TBLPTRU' initially instead of setting it each
time?



Regards
Roland Jollivet

2005\03\09@192644 by Jan-Erik Soderholm

face picon face
Roland wrote :

> So do I simply write;
>
> d_user                       ;default code
>         dw     "6781234",0D
>
> readit
>         movlw  HIGH(d_user)
>         movwf  TBLPTRH       ; load high byte of pointer
>         movlw  LOW(d_user)
>         movwf  TBLPTRL       ; load low byte of pointer
>
>         tblrd*               ; read byte from program memory,
>         movff  TABLAT,gotit  ; move byte from table
>
>
> -The above does work, just not sure how correct it is.

You are only reading the first byte, right ?

> -Is it necessary to ORG each string?

Can't be, since ORG isn't even always valid.
A normal label should be enough. But your example
above did work, didn't you say ?

> -If so, must it be on an even boundry?

No, the TBLxxx instructions operates on *bytes*, not words.

> -I suppose I can just 'clrf TBLPTRU' initially instead of
> setting it each time ?

If you are working within the lower 64K bytes of program
memory, yes, I'd guess so.

Jan-Erik.



2005\03\09@221416 by Lee Jones

flavicon
face
> I've been looking at the table command of the 18F, and am
> trying to figure out the syntax.
>
> On the 16F, it was simply....
>
> d_user                   ;default code
>         addwf  PCL,f
>         dt     "6781234",0D

DT generated a series of RETLW instructions in consecutive
program memory locations.  The ADDWF was using the value in
W to offset into your table.  (Code does not deal with the
possible overflow into the next 256 byte memory segment.)

> readit
>         call   d_user    ;get table value of user code
>         movwf  gotit     ;stick it in
>         return
>
> ----------------------
> The 16F to 18F migration example shows....
>
> RdStr

Upper byte (highest 5 bits) of TBLPTR is not being initialized.
You need to have either a

         CLRF TBLPTRU                ; only works with .LE. 64KB of program memory
or
         MOVLW UPPER string
         MOVWF TBLPTRU, ACCESS ; works on any size program memory

{Quote hidden}

GOTO READ is overkill since target of the jump is obviously within
1000 bytes; I'd use a BRA READ which only takes 2 bytes.

{Quote hidden}

I'd use a DB since that defines bytes.  DW is documented as being
equivalent to a DB on the 18 series, but I think DB is clearer.

> readit
>        movlw  HIGH(d_user)
>        movwf  TBLPTRH       ; load high byte of pointer
>        movlw  LOW(d_user)
>        movwf  TBLPTRL       ; load low byte of pointer
>        ;
>        tblrd*               ; read byte from program memory,
>        movff  TABLAT,gotit  ; move byte from table

This code will always loads the first byte from the table into
gotit.  Your original code loaded the Nth byte, where N was
stored in W upon entry to the routine.  This version also only
works if program memory is 64KB or smaller.

I'd write it as (and I believe that the textual description of
routine's functionality is not optional):

; readit - function to return Nth octet from a   d_user   table in
; program memory, where N is an unsigned 8-bit offest contained in
; WREG on entry.  On return, 8-bit value retrieved has been stored
; in  gotit  variable.
;
; routine trashes WREG, STATUS, TBLPTR, & TABLAT
;
readit
       MOVLW UPPER d_user
       MOVWF TBLPTRU, ACCESS   ; load upper byte of pointer
       MOVLW HIGH d_user
       MOVWF TBLPTRH           ; load high byte of pointer
       MOVLW LOW d_user
       MOVWF TBLPTRL           ; load low byte of pointer
       ;
       ADDWF TBLPTRL, F, ACCESS
       CLRF WREG, ACCESS
       ADDWFC TBLPTRH, F, ACCESS
       ADDWFC TBLPTRU, F, ACCESS ; adjust pointer to Nth element (N in WREG)
       ;
       tblrd*                  ; read byte from program memory into TABLAT
       ;
       movff  TABLAT, gotit    ; store byte into specified destination
       ;
       RETURN

This should have the same functionality as your original 16F code.
And work in any size memory version 18 series PIC.

                                               Lee Jones

2005\03\09@233708 by Lee Jones

flavicon
face
I made an error in the sample code I posted earlier tonight.
I forgot to save & restore the value in W.  The corrected
code appears below:

{Quote hidden}

       MOVWF TABLAT, ACCESS      ; save offset value for later (TABLAT is temp)
       ;
>       MOVLW UPPER d_user
>       MOVWF TBLPTRU, ACCESS     ; load upper byte of pointer
>       MOVLW HIGH d_user
>       MOVWF TBLPTRH             ; load high byte of pointer
>       MOVLW LOW d_user
>       MOVWF TBLPTRL             ; load low byte of pointer
       ;
       MOVF TABLAT, W, ACCESS    ; restore offset value
{Quote hidden}

                                               Lee Jones


2005\03\09@235957 by William Chops Westfield

face picon face
On Mar 9, 2005, at 7:21 PM, Lee Jones wrote:

>> On the 16F, it was simply....
>>
>> d_user                   ;default code
>>         addwf  PCL,f
>>         dt     "6781234",0D
>
> DT generated a series of RETLW instructions in consecutive
> program memory locations.

There's nothing wrong with this same scheme on an 18f, although
you'll have to double f first (and therefore the index couldn't
be bigger than 127.)  It's just that this makes the
table twice as big as it needs to be, since program memory is
16 bits wide.  There's a tradeoff between the extra space
needed to implement the code for tblrd vs the extra space used
by the table itself.

BillW

2005\03\10@003324 by Roland

flavicon
face

Thanks guys, questions answered.

The main issue was that 99% of the examples I could find were doing a block
table read from defined memory areas. Then, the only example I found from
uChip using a string, was prefixed with an ORG, so I was unsure about
adressing a string at an arb location in memory.

Regards
Roland




At 07:21 PM 09/03/2005 -0800, you wrote:
{Quote hidden}

port B
{Quote hidden}

Regards
Roland Jollivet

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