Also: PIC Microcontoller Radix Math Methods
; BIN_ASC 16-bit value ; This routine converts a 16-bit number into a counted string of ; ASCII characters compatible with Serout. It suppresses ; leading zeros so that numbers like 17 are sent as "17" not "00017". buffer = 31 ; String buffer at end of memory. ASC_0 = '0' ; ASCII numbers: 30h thru 39h. ASC_dp = '.' ; ASCII char for decimal point (period). fix = 3 ; Position for fixed decimal point. org 8 dec_no Res 1 ; Decade (1,10,100...) to work on. tempH Res 1 ; 16-bit temporary variable used by tempL Res 1 ; the BIN_ASC routine. hiB Res 1 ; MSB of number to convert. lowB Res 1 ; LSB of number to convert. flags ds 1 zs = flags.0 ; Leading-zero suppression flag. P = pic16c55 ; device pic16c55,xt_osc,wdt_off,protect_off reset start org 0 ; Table consisting of values 10,000, 1000, 100, 10, and 1. decade ADDWF 02, _W RETLW 39 RETLW 16 RETLW 3 RETLW 232 RETLW 0 RETLW 100 RETLW 0 RETLW 10 RETLW 0 RETLW 1 start MOVLW $FF ; To see routines output, either MOVWF hiB MOVLW $FF ; use the PSIM PIC simulator, or MOVWF lowB CALL BIN_ASC ; merge with Serout. GOTO $ ; Endless loop ; This routine accepts a 16-bit number in hiB, lowB and converts it into ; a counted ASCII text string located at the address "buffer." The buffer ; grows downward in memory. The first (0th) item in buffer is the number ; of characters in the string. The routine destroys the contents of ; hiB, lowB. If this value is required elsewhere, make a copy. BIN_ASC CLRF buffer ; Clear char count (item 0 in buf). CLRF flags ; Clear zs flag. CLRF dec_no ; Clear decade no. MOVLW buffer-1 ; Reserve 0th byte of buffer for count. MOVWF fsr BIN_ASC_loop MOVF dec_no ,_w CALL decade ; from the lookup table. MOVWF tempH INCF dec_no ,F ; Get 2nd digit of decade no. MOVF dec_no ,_w CALL decade MOVWF tempL CALL d_point ; Insert decimal point. CALL sub_it ; Divide hiB,lowB by tempH,tempL MOVF indirect ,_w BTFSC flags, 0 ; If zs = 0 AND digit = 0 then GOTO BIN_ASC_no_zs BTFSC 3,2 ; digit is a leading zero to be GOTO BIN_ASC_no_zed BIN_ASC_no_zs MOVWF indirect ADD indirect,#ASC_0 ; an included zero (as in 7501) INCF buffer, F ; or a non-zero digit. DECF fsr, F ; Point to next memory location. BSF flags, 0 ; First non-zero digit sets zs bit. BIN_ASC_no_zed INCF dec_no,F ; Next decade. MOVLW 8 ; If dec_no = 8, we're down to ones. SUBWF dec_no ,_w BTFSS 3,2 GOTO BIN_ASC ; Otherwise, do next decade. INCF dec_no ,F ; Update decade number for d_point. CALL d_point ; Decimal point here? MOVF lowB ,_w MOVWF indirect ADD indirect,#ASC_0 ; Add offset for conversion to ASCII. INCF buffer, F ; Add 1 to character count. RETLW 0h ; This routine performs division by iterated subtraction. It is efficient ; in this application because the dividend and divisor keep getting smaller ; as BIN_ASC runs, so the quotient is never larger than nine. A general- ; purpose division routine would be slower (and longer). sub_it CLRF indirect ; Clear to track no. of subtractions. sub_it_loop MOVF tempL,_w ; Subtract LSB. SUBWF lowB, F BTFSC 3,0 ; If no borrow, continue w/MSB. GOTO sub_it_skip MOVLW 1 ; Otherwise borrow from MSB. SUBWF hiB, F BTFSC 3,0 ; If borrow causes a carry, then GOTO sub_it_skip INCF hiB, F ; add numbers back and return. MOVF tempL,_w ADDWF lowB, F RETLW 0h sub_it_skip MOVF tempH,_w ; Subtract MSB. SUBWF hiB, F BTFSC 3,0 ; If no borrow, subtract again. GOTO sub_it_skip2 ADD lowB,tempL ; Otherwise, undo the subtraction BTFSC 3,0 ; by adding entire 16-bit no. INCF hiB, F ; back together and return. ADD hiB,tempH RETLW 0 sub_it_skip2 INCF indirect, F ; No borrow, so do it again. GOTO sub_it_loop ; This routine adds a decimal point in the location set by "fix" in the ; equates at the beginning of the program. The location of the decimal point ; is in front of the "fix"ed digit, numbered starting with 0. If you fix the ; point at 0, the first (0th) character in the string produced by BIN_ASC ; will be a decimal point. If you don't want a decimal point, either move ; it out of range (fix = 6), or delete this routine and the "call d_point" ; in the body of BIN_ASC above. d_point MOVLW fix*2+1 SUBWF dec_no ,_w BTFSS 3,2 RETLW 0h BSF flags, 0 MOVLW ASC_dp MOVWF indirect INCF buffer, F DECF fsr, F RETLW 0h
Questions:
dear,+
I look for a converter code (binary to ASCII) and i think that the code of Dontronics and Scott Edwards is good for me.
But the instruction "ADD indirect,#ASC_0" & "ADD lowB,tempL" are used. I don't uderstand and i don't find this instruction in the data sheet of Microchip...
I use a PIC17C756, could you help me, please?
Sébastien Desmet
Comments:
; This routine accepts a 16-bit number in hiB, lowB and converts it into ; a null terminated ASCII text string located at the address "buffer." ; The routine destroys the contents of hiB, lowB. PRDEC: clrf flags ; Clear zs flag. clrf dec_no ; Clear decade no. movlw buffer ; get buffer addr movwf FSR ; set-up indirect adressing prdeclp: movf dec_no,w call decade ; table lookup movwf tempH ; save it incf dec_no,f ; Get 2nd digit of decade no. movf dec_no,w ; incremented decade counter call decade ; table lookup movwf tempL ; save it ; call d_point ; Insert decimal point. call sub_it ; Divide hiB,lowB by tempH,tempL movf INDF,w ; get the result btfsc flags,0 ; If zs = 0 AND digit = 0 then goto prdecnzs btfsc STATUS,2 ; digit is a leading zero to be goto prdecnz prdecnzs: ;no leading 0 supression movwf INDF movlw a'0' addwf INDF,f ; add ascii '0' incf FSR,f ; Point to next memory location. bsf flags,0 ; First non-zero digit sets zs bit. prdecnz: incf dec_no,f ; Next decade. movlw 0x08 ; If dec_no = 8, we're down to ones. subwf dec_no,w btfss STATUS,2 goto prdeclp ; Otherwise, do next decade. incf dec_no,f ; Update decade number for d_point. ; call d_point ; Decimal point here? movf lowB,w movwf INDF movlw a'0' addwf INDF,f ; add ascii '0' incf FSR,f movlw 0x00 movwf INDF ; null terminated call PRLINE retlw 0x00 ; This routine performs division by iterated subtraction. It is efficient ; in this application because the dividend and divisor keep getting smaller ; as BIN_ASC runs, so the quotient is never larger than nine. A general- ; purpose division routine would be slower (and longer). sub_it: clrf INDF ; Clear to track no. of subtractions. sub_it_loop: movf tempL,w ; Subtract LSB. subwf lowB,f btfsc STATUS,0 ; If no borrow, continue w/MSB. goto sub_it_skip movlw 0x01 ; Otherwise borrow from MSB. subwf hiB,f btfsc STATUS,0 ; If borrow causes a carry, then goto sub_it_skip incf hiB,f ; add numbers back and return. movf tempL,w addwf lowB,f retlw 0x00 sub_it_skip: movf tempH,w ; Subtract MSB. subwf hiB,f btfsc STATUS,0 ; If no borrow, subtract again. goto sub_it_skip2 movf tempL,w addwf lowB,f ; Otherwise, undo the subtraction btfsc STATUS,0 ; by adding entire 16-bit no. incf hiB,f ; back together and return. movf tempH,w addwf hiB,f retlw 0x00 sub_it_skip2 incf INDF,f ; No borrow, so do it again. goto sub_it_loop ; This routine adds a decimal point in the location set by "fix" in the ; equates at the beginning of the program. The location of the decimal point ; is in front of the "fix"ed digit, numbered starting with 0. If you fix the ; point at 0, the first (0th) character in the string produced by BIN_ASC ; will be a decimal point. If you don't want a decimal point, either move ; it out of range (fix = 6), or delete this routine and the "call d_point" ; in the body of BIN_ASC above. d_point movlw fix*2+1 subwf dec_no,w btfss STATUS,2 retlw 0x00 bsf flags,0 movlw a'.' movwf INDF incf FSR,f retlw 0x00 ; Table consisting of values 10,000, 1000, 100, 10, and 1. decade addwf PCL,f retlw d'39' ; 10,000 retlw d'16' retlw d'3' ; 1,000 retlw d'232' retlw d'0' ; 100 retlw d'100' retlw d'0' ; 10 retlw d'10' retlw d'0' ; 1 retlw d'1'
file: /Techref/microchip/math/radix/b2a-16b5dlzd.htm, 12KB, , updated: 2009/11/23 15:43, local time: 2024/12/22 19:50,
owner: JMN-EFP-786,
18.116.37.200:LOG IN
|
©2024 These pages are served without commercial sponsorship. (No popup ads, etc...).Bandwidth abuse increases hosting cost forcing sponsorship or shutdown. This server aggressively defends against automated copying for any reason including offline viewing, duplication, etc... Please respect this requirement and DO NOT RIP THIS SITE. Questions? <A HREF="http://massmind.ecomorder.com/Techref/microchip/math/radix/b2a-16b5dlzd.htm"> PIC Microcontoller Radix Math Method Binary to ASCII, 16 bit to 5 digits </A> |
Did you find what you needed? |
Welcome to ecomorder.com! |
Ashley Roll has put together a really nice little unit here. Leave off the MAX232 and keep these handy for the few times you need true RS232! |
.