From: CBFalconer - view profile Date: Fri, Mar 23 2001 3:34 pm Email: CBFalconer Groups: comp.os.cpm subject: Falconer FP package part 5 At some point I got that complete package down to under 0800h (2k) bytes, so it would conveniently fit in a single ROM. I think I also generalized the output, much the same as the generalized input system. At any rate, between the source you found and this there is enough for anyone to regenerate and check it against the loadmap. I took the documentation you converted from WS and reformatted it so it will fit. It is unchanged except for my title/address. Herewith: ============================================================ "Falconer Floating Point Arithmetic" by Charles Falconer, formerly Chief Instrumentation Engineer, Yale University http://www.qwikpages.com/backstreets/cbfalconer in DDJ, March 1979, p.4 and April 1979, p.16 This software package provides full floating point arithmetic capability for 8080, 8085, and Z80-based machines, with very little speed penalty over use of integer arithmetic. The system can handle all 16-bit integer values (treated either as positive integers in the range 0 to 65535, or as signed integers in the range -32768 to 32767) without any loss of information, yet the extended range (approximately 10^-38 to 10^+38) convenience of floating point is directly available, together with various mathematical functions (i.e., logarithms, exponentials, etc). I hope that this publication will discourage use of integer arithmetic in various interpreters, compilers, etc. The operand size is such as to allow virtually all inner loops to be performed entirely in registers, with attendant speed benefits. At a 518 nanoseconds clock, most arithmetic operations are performed in one millisecond or less, division in about 1.5 milliseconds. A 4-MHz Z80 system can halve this. This is not far removed from integer execution times. I strongly recommend that any user of this package do so without any alteration (except deletion of routines not needed in the application). This system has been in routine operation since April 1976, and is incorporated in other systems. The least exercised routines are in FLTINPUT and FUNCTION. While the calling convention to IVAL, for example, may appear unusual, it has been specifically designed to allow re-entrant use with various data sources. A calling routine of the form: GETNUM: PUSH B LXI B,(address of char input routine) CALL IVAL ; (or IVALC) POP B RET will customize this as required and will avoid conflict with any other software. The system does not have the awkward range limitation of the EA chip (approximately 10^-18 to 10^+18) and some other systems, which I have found to bite the user all too often. Due to the careful treatment of rounding and over/underflow, the system will usually give the expected results (inversion of large matrices is the only exception noted so far, yet systems of 5 to 10 simultaneous equations, on our typical input data, can be handled adequately), and the error and overflow reporting will provide adequate warnings of runtime misuse. Error analysis is mathematically tractable. The AERC (arithmetic error connector) allows trappings of illegal operands (division by zero, logarithm of negative number, etc). If desired, this can be specified a: AERC: STC RET which will cause all such occurrences to be treated as overflows. In general, any error is signaled by Carry set on routine exit. The individual routine functions are stated in the commentary, and registers disturbed are listed. Notice that the unspecified I/O routines output register C, and return with A set to C on entry. Input routines return characters in A. Also, notice that all routines (except those specifically using I/O devices) are re-entrant, and use only stack-assigned temporary storage. The code is thus inherently suitable for the time sharing or interrupt driven applications. Users who have been using integer arithmetic may find that extra stack space must be allocated. An extra 32 bytes should normally suffice. For the benefit of readers without a macro-assembler, macros used generally depend on the definition of registers as B=0, C=1, D=2, E=3, H=4, L=5, M=SP=PSW=6, A=7. Between the macro definitions and the actual code generated, users should be able to substitute suitable source code. Our assembler permits "@" and "." in names, automatically increments and decrements the global variable ".LVL" on each PUSH and POP instruction, respectively, and can generate relocatable code. Source code between IF and ENDIF statements is assembled only if the IF operand is non-zero, and between IFZ and ENDIF only if the IFZ operand is zero. This listing uses this construct only within macros. The "EXTRN" lists show external addresses required within a module, and the "ENTRY" lists show address required by other modules. Note that some character constants may be in lower case (and are so marked). The printer used translated these to upper case. This should be sufficient to allow the user to customize the source to his assembler. I originally intended to submit listings with all macros fully expanded, but the results were excessively cluttered, no longer held any clarity, and the listing length was virtually doubled. As submitted, all information remains present, but the reader may have to refer to the macro definitions fairly often. The load map below shows the location of all routines when loaded at location 1000H up, in the order shown. The "U" identifies labels undefined in the overall system. Historically, this system replaced an earlier design (published in the Intel User Library) which used 2's complement mantissas and exponents. That system had 1 less bit of resolution, control of negative extremes and rounding had a problem, and was 5 to 10 times slower than the present system. Load Map -------- Code Data Name --------- ---- ---- 1000-115A None INTARITH.ASM 115B-1463 None FLTARITH.ASM 1464-15BB None FLTINPUT.ASM 15BC-17D2 None FLTOUT.ASM 17D3-19FA None FUNCTION.ASM .AND 1986 .EQU 19A6 .GE. 19D7 .GG. 19E0 .GT. 19C5 .LE. 19BC .LT. 19CE .NE. 19AF .OR. 1971 .XOR 1996 U-AERC 0000 BCLC 102B BCLZ 102A BCRA 1032 BCRC 1034 C1BC 1045 C1DE 104D C2BC 1044 C2DE 104C C2DHL 1054 U-COUT 0000 DEBLK 1479 DERA 103B DERC 103D DHLZ 1022 DIV 1114 DQUIK 1082 DTEN 106A EXDG 15FF EXP2 18E1 EXPX 1931 FADD 1303 FCMP 1387 FDIV 1248 FDIVR 12A5 FDIVT 1202 FINT 13DC FIXR 1439 FIXT 1404 FLOAD 11DC FLOT 13E1 FLOTA 13B9 FLOTD 13D7 FLOTP 13CE FMAT 172B FMOD 17EE FMUL 1210 FMULT 11F4 FRACT 17D3 FRCIP 12B1 FSTOR 11E8 FSUB 137A FSUBR 12FF FXCHG 11B5 IDIV 10A7 IMUL 108A IVAL 1482 IVALC 14B5 JBC 1477 LAS 101A LBCS 1011 LDES 1008 LFBIS 11A9 LFBS 119C LFDIS 11B9 LFDS 11BF LFLT 170C LOG2 1B23 LOGB 188C U-LOUT 0000 MUL 10D9 MUL10 1061 MLRD 115B DDZS 15E1 DFLT 171C ONEG 15DC OPT 15D7 DTCBK 15BC DTCCL 15BE POLY 1BAB QMAX 146B QNUM 1464 SFDIS 11C9 STADR 1000 TFLT 1714 -- Chuck F