×   Main Menu ALL The 8BS News Manuals (New menu) Links Worth a Look Tools Disc and Basic Webring Site Map 8BS Guestbook Old Guest Book Me The Barnsley Rovers   
8-Bit Software

The BBC and Master Computer Public Domain Library

Integer Multiplication Routine

Submitted by Steve Fewell

Routine: imult
Name: Integer Multiplication
Starting Address: &9F64
Entry criteria: IWA contains the first Integer number. Y contains the Most Significant Byte of this Integer number (?&2D). ?&4 and ?&5 point to the second Integer variable. ?&27 = 4, X = &4.
Notes: If the IWA > &FFFF, it is truncated to 16 bits.
Exit: IWA contains the result of [Integer variable * IWA]

Description:
Exclusive-OR the Most significant bytes of both integers together, this determines the sign of the result (if only one of the MSBs is negative then the result is negative, otherwise it is positive).

Make both integers positive [using ipos] (so that we only have to do positive multiplication).

Store the multiplier in zero-page locations (&39 to &3C) and put the multiplicand into the IWA [popi].

Initialise the result to zero (The result is stored in Y [&3D], X [&3E], &3F and &40).

Keep repeating the following loop until the multiplier is zero [only the least significant two bytes of the multiplier are used]:

(1) Divide the multiplier by 2 (and make the result integer)

(2) If an integer result was not obtained, (i.e. Multiplier was an odd number before division) then add the multiplicand to the result. [Dividing the multiplier lost 0.5 of its value, so we add on the multiplicand (which at this stage is worth 0.5 * the actual multiplicand) before it is multiplied to perform the multiplication of the lost 0.5 of the multiplier].

(3) Multiply the multiplicand by 2

Until multiplier is zero ((&39 OR &3A) = zero).

Retrieve the result from the zero page locations (&3D to &40) and make it negative if the sign [at the beginning] was determined to be negative.

Jump to &9FCA to test the value of X [the next operator] when the routine was entered. If X contains the operator code for '*', '/', 'MOD' or 'DIV' then send the result to the appropriate routine, for further calculation, otherwise exit the multiplication routine.

Disassembly for the integer multiplication routine

9F64 Z 90 5A PHY
9F65   032 190 172 20 BE AC JSR &ACBE Make IWA value positive [ipos]
9F68 ' 134 039 86 27 STX &27
9F6A 9 162 057 A2 39 LDX#&39
9F6C   032 198 189 20 C6 BD JSR &BDC6 Save Integer (IWA) to zero page location [izpout]
9F6F   032 230 188 20 E6 BC JSR &BCE6 Retrieve IWA value from Stack[popi]
9F72 h 104 68 PLA
9F73 E- 069 045 45 2D EOR &2D
9F75 7 133 055 85 37 STA &37
9F77   032 190 172 20 BE AC JSR &ACBE Make the IWA value positive [ipos]
9F7A   160 000 A0 00 LDY#&00
9F7C   162 000 A2 00 LDX#&00
9F7E d? 100 063 64 3F STZ &3F
9F80 d@ 100 064 64 40 STZ &40
9F82 F: 070 058 46 3A LSR &3A
9F84 f9 102 057 66 39 ROR &39
9F86   144 021 90 15 BCC 21 --> &9F9D
9F88   24 18 CLC
9F89   152 98 TYA
9F8A e* 101 042 65 2A ADC &2A
9F8C   168 A8 TAY
9F8D   138 8A TXA
9F8E e+ 101 043 65 2B ADC &2B
9F90   170 AA TAX
9F91 ? 165 063 A5 3F LDA &3F
9F93 e, 101 044 65 2C ADC &2C
9F95 ? 133 063 85 3F STA &3F
9F97 @ 165 064 A5 40 LDA &40
9F99 e- 101 045 65 2D ADC &2D
9F9B @ 133 064 85 40 STA &40
9F9D * 006 042 06 2A ASL &2A
9F9F &+ 038 043 26 2B ROL &2B
9FA1 &, 038 044 26 2C ROL &2C
9FA3 &- 038 045 26 2D ROL &2D
9FA5 9 165 057 A5 39 LDA &39
9FA7 : 005 058 05 3A ORA &3A
9FA9   208 215 D0 D7 BNE -41 --> &9F82
9FAB = 132 061 84 3D STY &3D
9FAD > 134 062 86 3E STX &3E
9FAF 7 165 055 A5 37 LDA &37
9FB1   8 8 PHP
9FB2 = 162 061 A2 3D LDX#&3D
9FB4   032 128 170 20 80 AA JSR &AA80 Set the IWA to an Integer value at a zero-page location [izpin]
9FB7 ( 40 28 PLP
9FB8   016 003 10 03 BPL 3 --> &9FBD
9FBA   032 222 172 20 DE AC JSR &ACDE icomp
9FBD ' 166 039 A6 27 LDX &27
9FBF   128 009 80 09 BRA 9 --> &9FCA
9FC1 L; 076 059 159 4C 3B 9F JMP &9F3B '*' Operator
9FC4 & 032 038 188 20 26 BC JSR &BC26 Push IWA value to the BASIC Stack [pushi]
9FC7   032 018 160 20 12 A0 JSR &A012
9FCA * 224 042 E0 2A CPX#&2A
9FCC   240 243 F0 F3 BEQ -13 --> &9FC1
9FCE / 224 047 E0 2F CPX#&2F
9FD0   240 009 F0 09 BEQ 9 --> &9FDB '/' Operator
9FD2   224 131 E0 83 CPX#&83
9FD4   240 031 F0 1F BEQ 31 --> &9FF5 Integer MOD routine
9FD6   224 129 E0 81 CPX#&81
9FD8 # 240 035 F0 23 BEQ 35 --> &9FFD Integer DIV routine
9FDA ` 96 60 RTS


 Back to 8BS
Or