Doug Manzer wrote: > I started working on an algorithm to convert the floating point > binary to decimal; for instance > > 111.111 binary > > means 1 + 2 + 4 + 0.5 + 0.25 + 0.125 decimal. The method would > deal with the integer and fractional parts separately, generating > the BCD equivalent of each power of 2 and adding it to a running > total if the bit was 1. Naturally, I'd rather use code (or even an > algorithm) that was already available. > Doug, I think you'll find for the simple example of 111.111 binary that the routines I posted will do the job for you. In general, if you have a fixed point binary representation: ... b3 b2 b1 b0. b-1 b-2 b-3 b-4 ... you can break these into two integers: b3 b2 b1 b0 and b-1 b-2 b-3 b-4 (the notation, bn means the nth bit of the binary number. Typically, the n's are written as subscripts. However, that's a luxury we sacrifice with simple ASCII word processing). The first integer can be converted using standard binary to BCD translation routines. The routines I posted to you, "write_byte_as_dec" and "write_word_as_dec", will perform this translation for bytes and words. The second integer can be converted using the "scale_hex2dec" (perhaps a blatant misnomer in this context). Originally, I wrote this routine to display percentages. In other words, the byte to be "scaled" ranges from 0 to 255 and I want that expressed as a percentage from 0 to 99. However, it turns out that this routine is in fact converting an 8-bit binary fraction to a two digit decimal fraction. To be used in your application, the binary fraction only needs to be shifted the appropriate number of positions so that b-1 occupies the most significant bit. The theory behind the algorithm is summarized by the comments of the program: ;******************************************************************* ;scale_hex2dec ; The purpose of this routine is to scale a hexadecimal byte to a ;decimal byte. In other words, if 'h' is a hexadecimal byte then ;the scaled decimal equivalent 'd' is: ; d = h * 100/256. ;Note that this can be simplified: ; d = h * 25 / 64 = h * 0x19 / 0x40 ;Multiplication and division can be expressed in terms of shift lefts ;and shift rights: ; d = [ (h<<4) + (h<<3) + h ] >> 6 ;The program divides the shifting as follows so that carries are automatically ;taken care of: ; d = (h + (h + (h>>3)) >> 1) >> 2 ; ;Inputs: W - should contain 'h', the hexadecimal value to be scaled ;Outputs: W - The scaled hexadecimal value is returned in W ;Memory: temp ;Calls: none scale_hex2dec MOVWF temp ;Hex value is in W. CLRC ;Clear the Carry bit so it doesn't affect RRF RRF temp,F CLRC RRF temp,F CLRC RRF temp,F ;temp = h>>3 ADDWF temp,F ;temp = h + (h>>3) RRF temp,F ;temp = (h + (h>>3)) >> 1 ADDWF temp,F ;temp = h + ((h + (h>>3)) >> 1) RRF temp,F CLRC RRF temp,W ;d = W = (h + (h + (h>>3)) >> 1) >> 2 RETURN When the routine is complete, W will contain a number between 0 and 99. It is then a simple matter to call the binary to BCD routine to display this as a two digit decimal number. If more than two decimal digits are needed, then the concepts behind this algorithm can be extended. For example, to get a three digit decimal fraction from a word you could perform the analogous computations: d = h * 1000 / 65536 For four digits: d = h * 10000 / 65536 Although I haven't coded it, the last formula is efficiently expressed as: d = ((((h>>4 - h)>>3 + h)>>2) + h)>>3 I realize that your original question was directed more towards a general purpose floating point conversion. You probably would've been elated had someone posted C's printf function. However as I expressed in my original message to you, speed has almost always been my concern when I use a microcontroller. Consequently, I advoid general purpose floating point processing in favor of fixed point and/or integer processing. Scott P.S. There is another totally different way to do the binary to decimal conversions that I will post later (if someone else doesn't first).