[net.micro.cbm] c64 floating point, part 3

miller@uiucdcs.UUCP (miller ) (02/07/84)

#N:uiucdcs:36100036:000:2719
uiucdcs!miller    Feb  6 13:00:00 1984


     This is the third in the series of how to use the Basic floating point
subroutines from machine language on the c64.  This time, we'll begin to look
at what subroutines are out there for us to use.  (Note: as before, most of
what I say applies to the vic20 too (or any future major revisions of the c64).
The only real changes are the addresses specified.)  Also, it has come to my
attention that info on the floating point routines is in the book "The VIC
Revealed".  I did not know this when I started this series.  At any rate, since
I'm sure there are others like me who do not have this book, I'll continue this
series.
     Here are the first 15 subroutines:

Integer to F1 $B391 (45969)
A two byte integer value in SF is converted to a floating point number.  The
results are stored into F1.

F1 to integer $B1AA (45482)
F1 is converted into a two byte integer which is stored into $64-65 (100-101).
F1 is trashed.

Memory to F1 $BBA2 (48034)
A 5 byte floating pt. no. anywhere in mem is loaded into F1.  The address is in
SF.  The sign flag of F1 is set if the high order bit of the mantissa is set;
otherwise it is reset.  The exponent is returned in the A register.

ASCII to F1 $B7B5 (47029)
An ASCII string is converted to floating pt format and stored in F1.  The
length of the string is loaded into A; the starting location into the "utility
string pointer" $22-23 (34-35).

F1 to ASCII $BDDD (48605)
F1 is converted into an ASCII string and stored starting at $0100 (256).  A $00
terminates the string.

Memory to F2 $BA8C (47756)
Like above except F2 is used and the sign comparison flag is set.  The exponent
of F1 is returned in A.

F1 to memory $BBD7 (48087)
F1 is stored into any 5 byte location (X holds the MSB; Y the LSB of that loca-
tion).  The high order bit of the mantissa is forced to the F1 sign flag.

F2 to F1 $BBFC (48124)
Copy F2 to F1.

F1 to F2 $BC0F (48143)
Copy F1 to F2.

Logical AND of F1 and F2 $AFE9 (45033)
The results are placed into F1.

Logical OR of F1 and F2 $AFE6 (45030)
The results are placed into F1.

F1 = F1 - F2 $B853 (47187)
Subtraction.

F1 = F1 + F2 $B86A (47210)
Addition.  You must set the sign comparison flag first.  Do this by EORing lo-
cations $66 and $6E and store the results in $6F.  Also, load A with the value
found in $61.  Both of the functions can be done by the memory to F2 routine.

F1 = F1 * F2 $BA30 (47664)
Multiplication.  Same notes apply as in addition.  However, if you call $BA28
(47656) instead, the memory to F2 will be executed first and then this one
automatically.

F1 = LOG (F1) $B9EA (47954)
Natural logarithm (base e).

     Next time I'll complete this series with the final 13 subroutines.

A. Ray Miller
Univ Illinois

al@genrad.UUCP (Al Gudaitis) (02/09/84)

I am not positive but I think there is a minor error in the reported addresses
for two of the routines mentioned by Ray Miller.  The F1 to memory routine is
at $BBD4 not $BBD7 and the F1 to F2 routine is at $BC0C, not $BCOF.  The rest
of the routines look correct.

miller@uiucdcs.UUCP (miller ) (02/15/84)

#R:genrad:-381600:uiucdcs:36100043:000:1123
uiucdcs!miller    Feb 14 23:10:00 1984


     Sorry, but I if I've done this correctly, I have to differ with you on the
addresses for the c64 floating point routines.  You claimed that two of the
addresses I gave in part 3 of my series were incorrect, i.e., "F1 to memory"
and "F1 to F2".  I have copied one of the routines below so that you can verify
it works.  The comments are of course mine, but the rest comes straight from my
disassembler.

; F1 to F2 subroutine
;
    ORG  $BC0F  ;where I started disassembling
    LDX# 6      ;six bytes to copy
    LDA  96,X   ;F1 (97-102)
    STA  104,X  ;F2 (105-110)
    DEX
    BNE  *-5    ;done?
    STX  112
    RTS

     The other routine begins:

; F1 to memory
;
    ORG  $BBD7
    STX  34     ;save MSB memory location
    STY  35     ;save LSB
     .
     .
     .

     If you jump to the locations you suggested ($BC0C and $BBD4) rather than
the ones I gave in my four part series, then in both cases you will first
execute a JSR $BC1B which is an internal round off F1 subroutine.  After the
RTS you will wind up right back where I suggested you branch to in the first
place.

A. Ray Miller
Univ Illinois

al@genrad.UUCP (Al Gudaitis) (02/16/84)

In regards to the accuracy of addresses $BBD4 vs $BBD7 for moving F1 to memory
and $BC0C vs $BC0F for moving F1 to F2, I still think I'm right that the lower
addresses are correct.  First of all, the extra byte at $70 is very important
and should not be ignored.  BASIC obtains extra accuracy by using one more bit
of mantissa for arithmetic operations on the main floating point accumulator
(F1) and then rounding off before sending F1 to any place else (the storage
format in memory is different and so needs conversion and the secondary FPA
(F2) doesn't have room to store the extra bit).  But in addition, $BBD0 is the
entry point for the routine that stores the FPA into the memory occupied by
the current variable (as in a LET statement) and it loads X and Y with the
correct address and then falls through to $BBD4.  In fact, I found no routine
within BASIC that calls $BBD7.  By analogy, I assume that $BC0C is actually
the correct entry point for most F1 to F2 operations though I agree with you
that the only difference between your entry points and mine is that call to
$BC1B.

miller@uiucdcs.UUCP (miller ) (02/22/84)

#R:genrad:-385700:uiucdcs:36100048:000:415
uiucdcs!miller    Feb 21 17:12:00 1984

     Your analysis is interesting.  OK, I'll double check against my Basic ROM
listing.  (Currently, a friend of mine in Florida has it so there will be a
delay.)  In the meantime, perhaps Jeff Goodenough can shed some light on the 3
byte difference for these two routines?  How about it, Jeff, do we want to JSR
to the "round off F1" before the "F1 to memory" or "F1 to F2" rountines?

A. Ray Miller
Univ Illinois

miller@uiucdcs.UUCP (miller ) (03/25/84)

#R:genrad:-385700:uiucdcs:36100064:000:237
uiucdcs!miller    Mar 24 21:47:00 1984

     Yes, I thought I had already acknowledged this correction.  This reply
also got contained in the final summary of the floating point routines that I
posted (look towards the end if you still have that).

A. Ray Miller
Univ Illinois