[Coco] Divide by 10 on a Motorola MC6809(E)
mdj at bds-soft.com
mdj at bds-soft.com
Thu Mar 21 12:10:28 EDT 2024
Rather than just make a special routine for Divide By 10, I decided a more general 16 x 16 Divide would be more useful for my purposes. Adjust the "ORG $4325" to suit your own needs. For what it's worth:
*****
*
* DU1616.ASM
* MDJ 2023/02/02
*
* 16-BIT BY 16-BIT
* UNSIGNED DIVIDE
*
* ENTRY CONDITIONS:
* X = DIVIDEND
* Y = DIVISOR
*
* EXIT CONDITIONS:
* X = QUOTIENT
* Y = REMAINDER
*
* ON EXIT, IF
* DIVIDE BY ZERO
* ERROR:
* X = #$FFFF
* Y = #$FFFF
* AN IMPOSSIBLE RESULT
*
*****
*
* THIS FUNCTION WAS
* ADAPTED FROM:
* BARROW, DAVID (1984).
* 6809 MACHINE CODE
* PROGRAMMING.
* LONDON: GRANADA
* TECHNICAL BOOKS,
* PAGES 29-33.
*
*****
ORG $4325
DU1616 PSHS A,B,X,Y,CC
CMPY #0 IS IT DIVIDE-BY-ZERO?
BEQ LBL003 GO IF YES (ERROR)
LDB #16 NUMBER OF 16-BIT SHIFTS
PSHS B SAVE THE COUNT
CLRA CLEAR ACCUMULATOR D
CLRB
* 16 SHIFTS - TRY TO SUBTRACT DIVISOR AT EACH SHIFT,
* FORMING QUOTIENT ONE BIT AT A TIME.
* QUOTIENT SHIFTS IN AS DIVIDEND SHIFTS OUT.
LBL001 ASL 5,S SHIFT NEXT DIVIDEND BIT THROUGH
ROL 4,S INTO REMAINDER (D), CLEARING
ROLB NEXT QUOTIENT BIT AT BIT 0 5,S
ROLA
CMPD 6,S CAN DIVISOR BE SUBTRACTED?
BLO LBL002 GO IF NO
SUBD 6,S SUBTRACT AND SET QUOTIENT BIT
INC 5,S AT CORRESPONDING BIT LOCATION
LBL002 DEC ,S REPEAT TIL ENTIRE DIVIDEND SHIFTED
BNE LBL001 (D IS NOW THE REMAINDER)
* PUT REMAINDER INTO STACKED Y.
* CLEAR COUNT BYTE OFF STACK.
* PULL RESULTS (X AND Y) AND CLEAN THE STACK
STD 6,S REMAINDER TO STACKED Y
LEAS 1,S REMOVE COUNT FROM STACK
PULS A,B,X,Y,CC
BRA LBL004 GO TO EXIT
* ERROR HANDLING
LBL003 PULS A,B,X,Y,CC
LDX #$FFFF SET ERROR CODING
LDY #$FFFF
* EXIT
LBL004 RTS
END
--
M. David Johnson
mdj at bds-soft.com
-----Original Message-----
From: Coco <coco-bounces at maltedmedia.com> On Behalf Of Don Barber via Coco
Sent: Wednesday, March 20, 2024 5:02 PM
To: CoCoList for Color Computer Enthusiasts <coco at maltedmedia.com>
Cc: Don Barber <don at dgb3.net>
Subject: Re: [Coco] Divide by 10 on a Motorola MC6809(E)
Sorry yes arithmetic shift was incorrect, my bad. Should clear the carry bit with the right ANDCC and then do LSRA instead.
Don
Sent from my iPhone
> On Mar 20, 2024, at 3:48 PM, Sean Conner via Coco <coco at maltedmedia.com> wrote:
>
> It was thus said that the Great Don Barber via Coco once stated:
>> A trick I use to divide 8 bit integers by 10 is to MUL by 205, then
>> shift the A register down by 3 bits (ASRA three times). This works
>> out to
>> 205/2048 which is close enough precision to 1/10 for 8 bit integers.
>
> Nice, although when I tried it, it gave very ... odd ... results for
> higher values of A. Up through 150 it gave the right answers, but
> starting with 160, it started returning (mostly incorrect) negative answers:
>
> 160 -16
> 170 -15
> 180 -14
> 190 -13
> ...
> 240 -8
> 250 -9
>
> change the ASRA to LSRA and the results are what you would expect for
> unsigned division. Also, after the sequence:
>
> ldb #205
> mul
> lsra
> lsra
> lsra
>
> the C flag is 1 for remainders of 5 through 9; clear otherwise. I
> found that interesting.
>
> -spc
>
>
> --
> Coco mailing list
> Coco at maltedmedia.com
> https://pairlist5.pair.net/mailman/listinfo/coco
--
Coco mailing list
Coco at maltedmedia.com
https://pairlist5.pair.net/mailman/listinfo/coco
More information about the Coco
mailing list