Hi,
The routine below for PIC18F in extended mode implements the 'utoa' and
'itoa' functions. It may seem complicated but is indeed very simple.
Most of the complexity is due to the fact that it is reentrant and uses
indexed memory accesses.
The algorithm adds 3 to each nibble of the result only if the resulting
nibble is 8 or higher, then shifts the MSBit of the value to be
converted into the LSBit of the result, until all the bits are done.
<pre>
<code>
;===============================================================================
; Copyright (c) 2008, Isaac Marino Bavaresco
; All rights reserved
; ***@yahoo.com.br
;===============================================================================
#include "P18CXXX.INC"
;===============================================================================
radix decimal
;===============================================================================
STDLIB code
;===============================================================================
s equ 0
v equ 2
Aux equ 6
#define NotZero 0
;===============================================================================
; char *utoa( auto unsigned short v, auto char RAM *s );
global utoa
utoa: bsf STATUS,C,ACCESS ; Unsigned = 1;
bra Common
;===============================================================================
; char *itoa( auto signed short v, auto char RAM *s );
global itoa
itoa: bcf STATUS,C,ACCESS ; Unsigned = 0;
;===============================================================================
Common: movff FSR2L,POSTINC1 ; *(WORD*)FSR1++ = FSR2;
movff FSR2H,POSTINC1
movff FSR1L,FSR2L ; FSR2 = FSR1
movff FSR1H,FSR2H
subfsr 2,6 ; FSR2 -= 4;
addfsr 1,3
;---------------------------------------------------------------
movf [s+0],w ; PROD = FSR0 = s;
movwf FSR0L,ACCESS
movwf PRODL,ACCESS
movf [s+1],w
movwf FSR0H,ACCESS
movwf PRODH,ACCESS
;---------------------------------------------------------------
btfss STATUS,C,ACCESS ; if( !Unsigned && v < 0 )
btfss [v+1],7 ; {
bra Positive
Negative: movlw '-' ; *s++ = '-'
movwf POSTINC0,ACCESS
subwf WREG,f,ACCESS ; v = -v; }
subfwb [v+0],f
subfwb [v+1],f
;
;
;---------------------------------------------------------------
Positive: clrf [Aux+0]
clrf [Aux+1]
clrf [Aux+2]
;
;
movlw 15
movwf TBLPTRL,ACCESS
;----------------------
LessThanEight: rlcf [v+0],f ; 3
rlcf [v+1],f ; 4
;
;
;
;
rlcf [Aux+2],f ; 9
rlcf [Aux+1],f ; 10
rlcf [Aux+0],f ; 11
btfsc [Aux+2],2
bra Loop
decfsz TBLPTRL,f,ACCESS ; 12
bra LessThanEight ; 13/14
;----------------------
LoopStart: incf TBLPTRL,f,ACCESS
Loop: movlw 3 ; 1
movwf TBLPTRH,ACCESS ; 0
DigitLoop: movlw 0x03 ; 1
addwf [Aux+0],w ; 2
btfsc WREG,3,ACCESS ; 3
movwf [Aux+0] ; 4
movlw 0x30 ; 5
addwf [Aux+0],w ; 6
btfsc WREG,7,ACCESS ; 7
movwf [Aux+0] ; 8
addfsr 2,1 ; 9
decfsz TBLPTRH,f,ACCESS ; 10
bra DigitLoop ; 11/12
subfsr 2,3 ; 2
rlcf [v+0],f ; 3
rlcf [v+1],f ; 4
;
;
;
;
rlcf [Aux+2],f ; 9
rlcf [Aux+1],f ; 10
rlcf [Aux+0],f ; 11
decfsz TBLPTRL,f,ACCESS ; 12
bra Loop ; 13/14
;---------------------------------------------------------------
bcf TBLPTRH,NotZero,ACCESS
movlw 3
movwf TBLPTRL ; 0
Tens: swapf [Aux+0],w ; 1
andlw 0x0f ; 2
btfss TBLPTRH,NotZero,ACCESS ; 3
bz Units ; 4
bsf TBLPTRH,NotZero,ACCESS ; 5
addlw '0' ; 6
movwf POSTINC0,ACCESS ; 7
Units: movf [Aux+0],w ; 8
andlw 0x0f ; 9
btfss TBLPTRH,NotZero,ACCESS ; 10
bz Next ; 11
bsf TBLPTRH,NotZero,ACCESS ; 12
addlw '0' ; 13
movwf POSTINC0,ACCESS ; 14
Next: addfsr 2,1 ; 15
decfsz TBLPTRL,f,ACCESS ; 16
bra Tens ; 17/18
movlw '0'
btfss TBLPTRH,NotZero,ACCESS
movwf POSTINC0,ACCESS
clrf INDF0,ACCESS
;---------------------------------------------------------------
Epilog: subfsr 1,4
movff POSTDEC1,FSR2H
movff INDF1,FSR2L
return 0
;===============================================================================
end
;===============================================================================
</code>
</pre>
Post by Dwayne ReidGood day to all.
I'm looking for a small, fast 9-bit binary-to-decimal conversion
routine. Somewhere between Scott Datallo's 8-bit-to-decimal and John
Payson's 16-bit-to-decimal routines.
Input range is [0..511] in binary, output in BCD or
packed-BCD. Actual input range for this project is 0..399 but I
might as well try to get the full 9-bits of range.
Short and fast if possible.
I've been looking at PICLIST.com as well as my old email archives but
haven't seen anything that is both short and fast.
Does anyone have something that they can share?
Many thanks!
dwayne
---
Este email foi escaneado pelo Avast antivírus.
https://www.avast.com/antivirus
--
http://www.piclist.com/techref/piclist PIC/SX FAQ & list archive
View/change your membership options at
http://mailman.mit.edu/mailma