Orange Pi5 kernel

Deprecated Linux kernel 5.10.110 for OrangePi 5/5B/5+ boards

3 Commits   0 Branches   0 Tags
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   1) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   2) MOTOROLA MICROPROCESSOR & MEMORY TECHNOLOGY GROUP
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   3) M68000 Hi-Performance Microprocessor Division
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   4) M68060 Software Package
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   5) Production Release P1.00 -- October 10, 1994
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   6) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   7) M68060 Software Package Copyright © 1993, 1994 Motorola Inc.  All rights reserved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   8) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300   9) THE SOFTWARE is provided on an "AS IS" basis and without warranty.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  10) To the maximum extent permitted by applicable law,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  11) MOTOROLA DISCLAIMS ALL WARRANTIES WHETHER EXPRESS OR IMPLIED,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  12) INCLUDING IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  13) and any warranty against infringement with regard to the SOFTWARE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  14) (INCLUDING ANY MODIFIED VERSIONS THEREOF) and any accompanying written materials.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  15) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  16) To the maximum extent permitted by applicable law,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  17) IN NO EVENT SHALL MOTOROLA BE LIABLE FOR ANY DAMAGES WHATSOEVER
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  18) (INCLUDING WITHOUT LIMITATION, DAMAGES FOR LOSS OF BUSINESS PROFITS,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  19) BUSINESS INTERRUPTION, LOSS OF BUSINESS INFORMATION, OR OTHER PECUNIARY LOSS)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  20) ARISING OF THE USE OR INABILITY TO USE THE SOFTWARE.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  21) Motorola assumes no responsibility for the maintenance and support of the SOFTWARE.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  22) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  23) You are hereby granted a copyright license to use, modify, and distribute the SOFTWARE
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  24) so long as this entire notice is retained without alteration in any modified and/or
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  25) redistributed versions, and that such modified versions are clearly identified as such.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  26) No licenses are granted by implication, estoppel or otherwise under any patents
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  27) or trademarks of Motorola, Inc.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  28) ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  29) # litop.s:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  30) #	This file is appended to the top of the 060FPLSP package
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  31) # and contains the entry points into the package. The user, in
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  32) # effect, branches to one of the branch table entries located here.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  33) #
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  34) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  35) 	bra.l	_060LSP__idivs64_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  36) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  37) 	bra.l	_060LSP__idivu64_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  38) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  39) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  40) 	bra.l	_060LSP__imuls64_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  41) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  42) 	bra.l	_060LSP__imulu64_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  43) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  44) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  45) 	bra.l	_060LSP__cmp2_Ab_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  46) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  47) 	bra.l	_060LSP__cmp2_Aw_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  48) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  49) 	bra.l	_060LSP__cmp2_Al_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  50) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  51) 	bra.l	_060LSP__cmp2_Db_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  52) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  53) 	bra.l	_060LSP__cmp2_Dw_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  54) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  55) 	bra.l	_060LSP__cmp2_Dl_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  56) 	short	0x0000
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  57) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  58) # leave room for future possible aditions.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  59) 	align	0x200
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  60) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  61) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  62) # XDEF ****************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  63) #	_060LSP__idivu64_(): Emulate 64-bit unsigned div instruction.	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  64) #	_060LSP__idivs64_(): Emulate 64-bit signed div instruction.	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  65) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  66) #	This is the library version which is accessed as a subroutine	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  67) #	and therefore does not work exactly like the 680X0 div{s,u}.l	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  68) #	64-bit divide instruction.					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  69) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  70) # XREF ****************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  71) #	None.								#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  72) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  73) # INPUT ***************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  74) #	0x4(sp)  = divisor						#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  75) #	0x8(sp)  = hi(dividend)						#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  76) #	0xc(sp)  = lo(dividend)						#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  77) #	0x10(sp) = pointer to location to place quotient/remainder	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  78) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  79) # OUTPUT **************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  80) #	0x10(sp) = points to location of remainder/quotient.		#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  81) #		   remainder is in first longword, quotient is in 2nd.	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  82) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  83) # ALGORITHM ***********************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  84) #	If the operands are signed, make them unsigned and save the	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  85) # sign info for later. Separate out special cases like divide-by-zero	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  86) # or 32-bit divides if possible. Else, use a special math algorithm	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  87) # to calculate the result.						#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  88) #	Restore sign info if signed instruction. Set the condition	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  89) # codes before performing the final "rts". If the divisor was equal to	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  90) # zero, then perform a divide-by-zero using a 16-bit implemented	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  91) # divide instruction. This way, the operating system can record that	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  92) # the event occurred even though it may not point to the correct place.	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  93) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  94) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  95) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  96) set	POSNEG,		-1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  97) set	NDIVISOR,	-2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  98) set	NDIVIDEND,	-3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300  99) set	DDSECOND,	-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100) set	DDNORMAL,	-8
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) set	DDQUOTIENT,	-12
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) set	DIV64_CC,	-16
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) ##########
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) # divs.l #
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) ##########
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) 	global		_060LSP__idivs64_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) _060LSP__idivs64_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) 	link.w		%a6,&-16
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) 	movm.l		&0x3f00,-(%sp)		# save d2-d7
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) 	mov.w		%cc,DIV64_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) 	st		POSNEG(%a6)		# signed operation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) 	bra.b		ldiv64_cont
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) ##########
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) # divu.l #
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) ##########
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122) 	global		_060LSP__idivu64_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) _060LSP__idivu64_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) 	link.w		%a6,&-16
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) 	movm.l		&0x3f00,-(%sp)		# save d2-d7
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) 	mov.w		%cc,DIV64_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) 	sf		POSNEG(%a6)		# unsigned operation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) ldiv64_cont:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) 	mov.l		0x8(%a6),%d7		# fetch divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) 	beq.w		ldiv64eq0		# divisor is = 0!!!
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138) 	mov.l		0xc(%a6), %d5		# get dividend hi
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) 	mov.l		0x10(%a6), %d6		# get dividend lo
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) # separate signed and unsigned divide
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) 	tst.b		POSNEG(%a6)		# signed or unsigned?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) 	beq.b		ldspecialcases		# use positive divide
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) # save the sign of the divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) # make divisor unsigned if it's negative
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147) 	tst.l		%d7			# chk sign of divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) 	slt		NDIVISOR(%a6)		# save sign of divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) 	bpl.b		ldsgndividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 150) 	neg.l		%d7			# complement negative divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 151) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 152) # save the sign of the dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 153) # make dividend unsigned if it's negative
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 154) ldsgndividend:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 155) 	tst.l		%d5			# chk sign of hi(dividend)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 156) 	slt		NDIVIDEND(%a6)		# save sign of dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 157) 	bpl.b		ldspecialcases
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 158) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 159) 	mov.w		&0x0, %cc		# clear 'X' cc bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 160) 	negx.l		%d6			# complement signed dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 161) 	negx.l		%d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 162) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 163) # extract some special cases:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 164) #	- is (dividend == 0) ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 165) #	- is (hi(dividend) == 0 && (divisor <= lo(dividend))) ? (32-bit div)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 166) ldspecialcases:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 167) 	tst.l		%d5			# is (hi(dividend) == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 168) 	bne.b		ldnormaldivide		# no, so try it the long way
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 169) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 170) 	tst.l		%d6			# is (lo(dividend) == 0), too
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 171) 	beq.w		lddone			# yes, so (dividend == 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 172) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 173) 	cmp.l		%d7,%d6			# is (divisor <= lo(dividend))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 174) 	bls.b		ld32bitdivide		# yes, so use 32 bit divide
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 175) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 176) 	exg		%d5,%d6			# q = 0, r = dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 177) 	bra.w		ldivfinish		# can't divide, we're done.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 178) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 179) ld32bitdivide:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 180) 	tdivu.l		%d7, %d5:%d6		# it's only a 32/32 bit div!
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 181) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 182) 	bra.b		ldivfinish
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 183) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 184) ldnormaldivide:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 185) # last special case:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 186) #	- is hi(dividend) >= divisor ? if yes, then overflow
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 187) 	cmp.l		%d7,%d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 188) 	bls.b		lddovf			# answer won't fit in 32 bits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 189) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 190) # perform the divide algorithm:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 191) 	bsr.l		ldclassical		# do int divide
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 192) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 193) # separate into signed and unsigned finishes.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 194) ldivfinish:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 195) 	tst.b		POSNEG(%a6)		# do divs, divu separately
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 196) 	beq.b		lddone			# divu has no processing!!!
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 197) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 198) # it was a divs.l, so ccode setting is a little more complicated...
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 199) 	tst.b		NDIVIDEND(%a6)		# remainder has same sign
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 200) 	beq.b		ldcc			# as dividend.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 201) 	neg.l		%d5			# sgn(rem) = sgn(dividend)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 202) ldcc:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 203) 	mov.b		NDIVISOR(%a6), %d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 204) 	eor.b		%d0, NDIVIDEND(%a6)	# chk if quotient is negative
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 205) 	beq.b		ldqpos			# branch to quot positive
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 206) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 207) # 0x80000000 is the largest number representable as a 32-bit negative
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 208) # number. the negative of 0x80000000 is 0x80000000.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 209) 	cmpi.l		%d6, &0x80000000	# will (-quot) fit in 32 bits?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 210) 	bhi.b		lddovf
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 211) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 212) 	neg.l		%d6			# make (-quot) 2's comp
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 213) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 214) 	bra.b		lddone
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 215) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 216) ldqpos:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 217) 	btst		&0x1f, %d6		# will (+quot) fit in 32 bits?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 218) 	bne.b		lddovf
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 219) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 220) lddone:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 221) # if the register numbers are the same, only the quotient gets saved.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 222) # so, if we always save the quotient second, we save ourselves a cmp&beq
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 223) 	andi.w		&0x10,DIV64_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 224) 	mov.w		DIV64_CC(%a6),%cc
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 225) 	tst.l		%d6			# may set 'N' ccode bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 226) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 227) # here, the result is in d1 and d0. the current strategy is to save
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 228) # the values at the location pointed to by a0.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 229) # use movm here to not disturb the condition codes.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 230) ldexit:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 231) 	movm.l		&0x0060,([0x14,%a6])	# save result
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 232) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 233) # EPILOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 234) #	fmovm.l		(%sp)+,&0x0		# restore no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 235) 	movm.l		(%sp)+,&0x00fc		# restore d2-d7
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 236) 	unlk		%a6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 237) # EPILOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 238) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 239) 	rts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 240) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 241) # the result should be the unchanged dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 242) lddovf:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 243) 	mov.l		0xc(%a6), %d5		# get dividend hi
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 244) 	mov.l		0x10(%a6), %d6		# get dividend lo
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 245) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 246) 	andi.w		&0x1c,DIV64_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 247) 	ori.w		&0x02,DIV64_CC(%a6)	# set 'V' ccode bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 248) 	mov.w		DIV64_CC(%a6),%cc
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 249) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 250) 	bra.b		ldexit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 251) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 252) ldiv64eq0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 253) 	mov.l		0xc(%a6),([0x14,%a6])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 254) 	mov.l		0x10(%a6),([0x14,%a6],0x4)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 255) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 256) 	mov.w		DIV64_CC(%a6),%cc
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 257) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 258) # EPILOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 259) #	fmovm.l		(%sp)+,&0x0		# restore no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 260) 	movm.l		(%sp)+,&0x00fc		# restore d2-d7
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 261) 	unlk		%a6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 262) # EPILOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 263) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 264) 	divu.w		&0x0,%d0		# force a divbyzero exception
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 265) 	rts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 266) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 267) ###########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 268) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 269) # This routine uses the 'classical' Algorithm D from Donald Knuth's	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 270) # Art of Computer Programming, vol II, Seminumerical Algorithms.	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 271) # For this implementation b=2**16, and the target is U1U2U3U4/V1V2,	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 272) # where U,V are words of the quadword dividend and longword divisor,	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 273) # and U1, V1 are the most significant words.				#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 274) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 275) # The most sig. longword of the 64 bit dividend must be in %d5, least	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 276) # in %d6. The divisor must be in the variable ddivisor, and the		#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 277) # signed/unsigned flag ddusign must be set (0=unsigned,1=signed).	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 278) # The quotient is returned in %d6, remainder in %d5, unless the		#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 279) # v (overflow) bit is set in the saved %ccr. If overflow, the dividend	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 280) # is unchanged.								#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 281) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 282) ldclassical:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 283) # if the divisor msw is 0, use simpler algorithm then the full blown
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 284) # one at ddknuth:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 285) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 286) 	cmpi.l		%d7, &0xffff
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 287) 	bhi.b		lddknuth		# go use D. Knuth algorithm
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 288) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 289) # Since the divisor is only a word (and larger than the mslw of the dividend),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 290) # a simpler algorithm may be used :
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 291) # In the general case, four quotient words would be created by
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 292) # dividing the divisor word into each dividend word. In this case,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 293) # the first two quotient words must be zero, or overflow would occur.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 294) # Since we already checked this case above, we can treat the most significant
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 295) # longword of the dividend as (0) remainder (see Knuth) and merely complete
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 296) # the last two divisions to get a quotient longword and word remainder:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 297) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 298) 	clr.l		%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 299) 	swap		%d5			# same as r*b if previous step rqd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 300) 	swap		%d6			# get u3 to lsw position
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 301) 	mov.w		%d6, %d5		# rb + u3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 302) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 303) 	divu.w		%d7, %d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 304) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 305) 	mov.w		%d5, %d1		# first quotient word
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 306) 	swap		%d6			# get u4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 307) 	mov.w		%d6, %d5		# rb + u4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 308) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 309) 	divu.w		%d7, %d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 310) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 311) 	swap		%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 312) 	mov.w		%d5, %d1		# 2nd quotient 'digit'
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 313) 	clr.w		%d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 314) 	swap		%d5			# now remainder
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 315) 	mov.l		%d1, %d6		# and quotient
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 316) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 317) 	rts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 318) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 319) lddknuth:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 320) # In this algorithm, the divisor is treated as a 2 digit (word) number
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 321) # which is divided into a 3 digit (word) dividend to get one quotient
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 322) # digit (word). After subtraction, the dividend is shifted and the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 323) # process repeated. Before beginning, the divisor and quotient are
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 324) # 'normalized' so that the process of estimating the quotient digit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 325) # will yield verifiably correct results..
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 326) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 327) 	clr.l		DDNORMAL(%a6)		# count of shifts for normalization
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 328) 	clr.b		DDSECOND(%a6)		# clear flag for quotient digits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 329) 	clr.l		%d1			# %d1 will hold trial quotient
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 330) lddnchk:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 331) 	btst		&31, %d7		# must we normalize? first word of
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 332) 	bne.b		lddnormalized		# divisor (V1) must be >= 65536/2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 333) 	addq.l		&0x1, DDNORMAL(%a6)	# count normalization shifts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 334) 	lsl.l		&0x1, %d7		# shift the divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 335) 	lsl.l		&0x1, %d6		# shift u4,u3 with overflow to u2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 336) 	roxl.l		&0x1, %d5		# shift u1,u2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 337) 	bra.w		lddnchk
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 338) lddnormalized:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 339) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 340) # Now calculate an estimate of the quotient words (msw first, then lsw).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 341) # The comments use subscripts for the first quotient digit determination.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 342) 	mov.l		%d7, %d3		# divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 343) 	mov.l		%d5, %d2		# dividend mslw
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 344) 	swap		%d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 345) 	swap		%d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 346) 	cmp.w		%d2, %d3		# V1 = U1 ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 347) 	bne.b		lddqcalc1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 348) 	mov.w		&0xffff, %d1		# use max trial quotient word
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 349) 	bra.b		lddadj0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 350) lddqcalc1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 351) 	mov.l		%d5, %d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 352) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 353) 	divu.w		%d3, %d1		# use quotient of mslw/msw
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 354) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 355) 	andi.l		&0x0000ffff, %d1	# zero any remainder
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 356) lddadj0:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 357) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 358) # now test the trial quotient and adjust. This step plus the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 359) # normalization assures (according to Knuth) that the trial
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 360) # quotient will be at worst 1 too large.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 361) 	mov.l		%d6, -(%sp)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 362) 	clr.w		%d6			# word u3 left
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 363) 	swap		%d6			# in lsw position
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 364) lddadj1: mov.l		%d7, %d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 365) 	mov.l		%d1, %d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 366) 	mulu.w		%d7, %d2		# V2q
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 367) 	swap		%d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 368) 	mulu.w		%d1, %d3		# V1q
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 369) 	mov.l		%d5, %d4		# U1U2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 370) 	sub.l		%d3, %d4		# U1U2 - V1q
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 371) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 372) 	swap		%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 373) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 374) 	mov.w		%d4,%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 375) 	mov.w		%d6,%d4			# insert lower word (U3)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 376) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 377) 	tst.w		%d0			# is upper word set?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 378) 	bne.w		lddadjd1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 379) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 380) #	add.l		%d6, %d4		# (U1U2 - V1q) + U3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 381) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 382) 	cmp.l		%d2, %d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 383) 	bls.b		lddadjd1		# is V2q > (U1U2-V1q) + U3 ?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 384) 	subq.l		&0x1, %d1		# yes, decrement and recheck
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 385) 	bra.b		lddadj1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 386) lddadjd1:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 387) # now test the word by multiplying it by the divisor (V1V2) and comparing
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 388) # the 3 digit (word) result with the current dividend words
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 389) 	mov.l		%d5, -(%sp)		# save %d5 (%d6 already saved)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 390) 	mov.l		%d1, %d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 391) 	swap		%d6			# shift answer to ms 3 words
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 392) 	mov.l		%d7, %d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 393) 	bsr.l		ldmm2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 394) 	mov.l		%d5, %d2		# now %d2,%d3 are trial*divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 395) 	mov.l		%d6, %d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 396) 	mov.l		(%sp)+, %d5		# restore dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 397) 	mov.l		(%sp)+, %d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 398) 	sub.l		%d3, %d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 399) 	subx.l		%d2, %d5		# subtract double precision
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 400) 	bcc		ldd2nd			# no carry, do next quotient digit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 401) 	subq.l		&0x1, %d1		# q is one too large
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 402) # need to add back divisor longword to current ms 3 digits of dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 403) # - according to Knuth, this is done only 2 out of 65536 times for random
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 404) # divisor, dividend selection.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 405) 	clr.l		%d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 406) 	mov.l		%d7, %d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 407) 	swap		%d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 408) 	clr.w		%d3			# %d3 now ls word of divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 409) 	add.l		%d3, %d6		# aligned with 3rd word of dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 410) 	addx.l		%d2, %d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 411) 	mov.l		%d7, %d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 412) 	clr.w		%d3			# %d3 now ms word of divisor
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 413) 	swap		%d3			# aligned with 2nd word of dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 414) 	add.l		%d3, %d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 415) ldd2nd:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 416) 	tst.b		DDSECOND(%a6)	# both q words done?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 417) 	bne.b		lddremain
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 418) # first quotient digit now correct. store digit and shift the
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 419) # (subtracted) dividend
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 420) 	mov.w		%d1, DDQUOTIENT(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 421) 	clr.l		%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 422) 	swap		%d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 423) 	swap		%d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 424) 	mov.w		%d6, %d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 425) 	clr.w		%d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 426) 	st		DDSECOND(%a6)		# second digit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 427) 	bra.w		lddnormalized
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 428) lddremain:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 429) # add 2nd word to quotient, get the remainder.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 430) 	mov.w		%d1, DDQUOTIENT+2(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 431) # shift down one word/digit to renormalize remainder.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 432) 	mov.w		%d5, %d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 433) 	swap		%d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 434) 	swap		%d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 435) 	mov.l		DDNORMAL(%a6), %d7	# get norm shift count
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 436) 	beq.b		lddrn
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 437) 	subq.l		&0x1, %d7		# set for loop count
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 438) lddnlp:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 439) 	lsr.l		&0x1, %d5		# shift into %d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 440) 	roxr.l		&0x1, %d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 441) 	dbf		%d7, lddnlp
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 442) lddrn:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 443) 	mov.l		%d6, %d5		# remainder
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 444) 	mov.l		DDQUOTIENT(%a6), %d6	# quotient
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 445) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 446) 	rts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 447) ldmm2:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 448) # factors for the 32X32->64 multiplication are in %d5 and %d6.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 449) # returns 64 bit result in %d5 (hi) %d6(lo).
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 450) # destroys %d2,%d3,%d4.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 451) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 452) # multiply hi,lo words of each factor to get 4 intermediate products
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 453) 	mov.l		%d6, %d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 454) 	mov.l		%d6, %d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 455) 	mov.l		%d5, %d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 456) 	swap		%d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 457) 	swap		%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 458) 	mulu.w		%d5, %d6		# %d6 <- lsw*lsw
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 459) 	mulu.w		%d3, %d5		# %d5 <- msw-dest*lsw-source
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 460) 	mulu.w		%d4, %d2		# %d2 <- msw-source*lsw-dest
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 461) 	mulu.w		%d4, %d3		# %d3 <- msw*msw
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 462) # now use swap and addx to consolidate to two longwords
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 463) 	clr.l		%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 464) 	swap		%d6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 465) 	add.w		%d5, %d6		# add msw of l*l to lsw of m*l product
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 466) 	addx.w		%d4, %d3		# add any carry to m*m product
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 467) 	add.w		%d2, %d6		# add in lsw of other m*l product
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 468) 	addx.w		%d4, %d3		# add any carry to m*m product
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 469) 	swap		%d6			# %d6 is low 32 bits of final product
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 470) 	clr.w		%d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 471) 	clr.w		%d2			# lsw of two mixed products used,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 472) 	swap		%d5			# now use msws of longwords
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 473) 	swap		%d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 474) 	add.l		%d2, %d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 475) 	add.l		%d3, %d5	# %d5 now ms 32 bits of final product
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 476) 	rts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 477) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 478) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 479) # XDEF ****************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 480) #	_060LSP__imulu64_(): Emulate 64-bit unsigned mul instruction	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 481) #	_060LSP__imuls64_(): Emulate 64-bit signed mul instruction.	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 482) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 483) #	This is the library version which is accessed as a subroutine	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 484) #	and therefore does not work exactly like the 680X0 mul{s,u}.l	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 485) #	64-bit multiply instruction.					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 486) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 487) # XREF ****************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 488) #	None								#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 489) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 490) # INPUT ***************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 491) #	0x4(sp) = multiplier						#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 492) #	0x8(sp) = multiplicand						#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 493) #	0xc(sp) = pointer to location to place 64-bit result		#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 494) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 495) # OUTPUT **************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 496) #	0xc(sp) = points to location of 64-bit result			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 497) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 498) # ALGORITHM ***********************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 499) #	Perform the multiply in pieces using 16x16->32 unsigned		#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 500) # multiplies and "add" instructions.					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 501) #	Set the condition codes as appropriate before performing an	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 502) # "rts".								#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 503) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 504) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 505) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 506) set MUL64_CC, -4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 507) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 508) 	global		_060LSP__imulu64_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 509) _060LSP__imulu64_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 510) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 511) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 512) 	link.w		%a6,&-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 513) 	movm.l		&0x3800,-(%sp)		# save d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 514) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 515) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 516) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 517) 	mov.w		%cc,MUL64_CC(%a6)	# save incoming ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 518) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 519) 	mov.l		0x8(%a6),%d0		# store multiplier in d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 520) 	beq.w		mulu64_zero		# handle zero separately
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 521) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 522) 	mov.l		0xc(%a6),%d1		# get multiplicand in d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 523) 	beq.w		mulu64_zero		# handle zero separately
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 524) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 525) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 526) #	63			   32				0	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 527) #	----------------------------					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 528) #	| hi(mplier) * hi(mplicand)|					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 529) #	----------------------------					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 530) #		     -----------------------------			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 531) #		     | hi(mplier) * lo(mplicand) |			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 532) #		     -----------------------------			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 533) #		     -----------------------------			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 534) #		     | lo(mplier) * hi(mplicand) |			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 535) #		     -----------------------------			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 536) #	  |			   -----------------------------	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 537) #	--|--			   | lo(mplier) * lo(mplicand) |	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 538) #	  |			   -----------------------------	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 539) #	========================================================	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 540) #	--------------------------------------------------------	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 541) #	|	hi(result)	   |	    lo(result)         |	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 542) #	--------------------------------------------------------	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 543) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 544) mulu64_alg:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 545) # load temp registers with operands
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 546) 	mov.l		%d0,%d2			# mr in d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 547) 	mov.l		%d0,%d3			# mr in d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 548) 	mov.l		%d1,%d4			# md in d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 549) 	swap		%d3			# hi(mr) in lo d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 550) 	swap		%d4			# hi(md) in lo d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 551) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 552) # complete necessary multiplies:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 553) 	mulu.w		%d1,%d0			# [1] lo(mr) * lo(md)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 554) 	mulu.w		%d3,%d1			# [2] hi(mr) * lo(md)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 555) 	mulu.w		%d4,%d2			# [3] lo(mr) * hi(md)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 556) 	mulu.w		%d4,%d3			# [4] hi(mr) * hi(md)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 557) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 558) # add lo portions of [2],[3] to hi portion of [1].
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 559) # add carries produced from these adds to [4].
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 560) # lo([1]) is the final lo 16 bits of the result.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 561) 	clr.l		%d4			# load d4 w/ zero value
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 562) 	swap		%d0			# hi([1]) <==> lo([1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 563) 	add.w		%d1,%d0			# hi([1]) + lo([2])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 564) 	addx.l		%d4,%d3			#    [4]  + carry
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 565) 	add.w		%d2,%d0			# hi([1]) + lo([3])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 566) 	addx.l		%d4,%d3			#    [4]  + carry
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 567) 	swap		%d0			# lo([1]) <==> hi([1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 568) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 569) # lo portions of [2],[3] have been added in to final result.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 570) # now, clear lo, put hi in lo reg, and add to [4]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 571) 	clr.w		%d1			# clear lo([2])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 572) 	clr.w		%d2			# clear hi([3])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 573) 	swap		%d1			# hi([2]) in lo d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 574) 	swap		%d2			# hi([3]) in lo d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 575) 	add.l		%d2,%d1			#    [4]  + hi([2])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 576) 	add.l		%d3,%d1			#    [4]  + hi([3])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 577) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 578) # now, grab the condition codes. only one that can be set is 'N'.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 579) # 'N' CAN be set if the operation is unsigned if bit 63 is set.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 580) 	mov.w		MUL64_CC(%a6),%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 581) 	andi.b		&0x10,%d4		# keep old 'X' bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 582) 	tst.l		%d1			# may set 'N' bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 583) 	bpl.b		mulu64_ddone
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 584) 	ori.b		&0x8,%d4		# set 'N' bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 585) mulu64_ddone:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 586) 	mov.w		%d4,%cc
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 587) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 588) # here, the result is in d1 and d0. the current strategy is to save
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 589) # the values at the location pointed to by a0.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 590) # use movm here to not disturb the condition codes.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 591) mulu64_end:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 592) 	exg		%d1,%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 593) 	movm.l		&0x0003,([0x10,%a6])		# save result
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 594) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 595) # EPILOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 596) #	fmovm.l		(%sp)+,&0x0		# restore no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 597) 	movm.l		(%sp)+,&0x001c		# restore d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 598) 	unlk		%a6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 599) # EPILOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 600) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 601) 	rts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 602) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 603) # one or both of the operands is zero so the result is also zero.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 604) # save the zero result to the register file and set the 'Z' ccode bit.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 605) mulu64_zero:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 606) 	clr.l		%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 607) 	clr.l		%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 608) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 609) 	mov.w		MUL64_CC(%a6),%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 610) 	andi.b		&0x10,%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 611) 	ori.b		&0x4,%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 612) 	mov.w		%d4,%cc			# set 'Z' ccode bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 613) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 614) 	bra.b		mulu64_end
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 615) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 616) ##########
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 617) # muls.l #
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 618) ##########
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 619) 	global		_060LSP__imuls64_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 620) _060LSP__imuls64_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 621) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 622) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 623) 	link.w		%a6,&-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 624) 	movm.l		&0x3c00,-(%sp)		# save d2-d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 625) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 626) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 627) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 628) 	mov.w		%cc,MUL64_CC(%a6)	# save incoming ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 629) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 630) 	mov.l		0x8(%a6),%d0		# store multiplier in d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 631) 	beq.b		mulu64_zero		# handle zero separately
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 632) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 633) 	mov.l		0xc(%a6),%d1		# get multiplicand in d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 634) 	beq.b		mulu64_zero		# handle zero separately
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 635) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 636) 	clr.b		%d5			# clear sign tag
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 637) 	tst.l		%d0			# is multiplier negative?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 638) 	bge.b		muls64_chk_md_sgn	# no
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 639) 	neg.l		%d0			# make multiplier positive
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 640) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 641) 	ori.b		&0x1,%d5		# save multiplier sgn
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 642) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 643) # the result sign is the exclusive or of the operand sign bits.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 644) muls64_chk_md_sgn:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 645) 	tst.l		%d1			# is multiplicand negative?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 646) 	bge.b		muls64_alg		# no
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 647) 	neg.l		%d1			# make multiplicand positive
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 648) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 649) 	eori.b		&0x1,%d5		# calculate correct sign
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 650) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 651) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 652) #	63			   32				0	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 653) #	----------------------------					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 654) #	| hi(mplier) * hi(mplicand)|					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 655) #	----------------------------					#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 656) #		     -----------------------------			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 657) #		     | hi(mplier) * lo(mplicand) |			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 658) #		     -----------------------------			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 659) #		     -----------------------------			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 660) #		     | lo(mplier) * hi(mplicand) |			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 661) #		     -----------------------------			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 662) #	  |			   -----------------------------	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 663) #	--|--			   | lo(mplier) * lo(mplicand) |	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 664) #	  |			   -----------------------------	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 665) #	========================================================	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 666) #	--------------------------------------------------------	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 667) #	|	hi(result)	   |	    lo(result)         |	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 668) #	--------------------------------------------------------	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 669) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 670) muls64_alg:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 671) # load temp registers with operands
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 672) 	mov.l		%d0,%d2			# mr in d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 673) 	mov.l		%d0,%d3			# mr in d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 674) 	mov.l		%d1,%d4			# md in d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 675) 	swap		%d3			# hi(mr) in lo d3
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 676) 	swap		%d4			# hi(md) in lo d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 677) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 678) # complete necessary multiplies:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 679) 	mulu.w		%d1,%d0			# [1] lo(mr) * lo(md)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 680) 	mulu.w		%d3,%d1			# [2] hi(mr) * lo(md)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 681) 	mulu.w		%d4,%d2			# [3] lo(mr) * hi(md)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 682) 	mulu.w		%d4,%d3			# [4] hi(mr) * hi(md)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 683) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 684) # add lo portions of [2],[3] to hi portion of [1].
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 685) # add carries produced from these adds to [4].
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 686) # lo([1]) is the final lo 16 bits of the result.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 687) 	clr.l		%d4			# load d4 w/ zero value
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 688) 	swap		%d0			# hi([1]) <==> lo([1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 689) 	add.w		%d1,%d0			# hi([1]) + lo([2])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 690) 	addx.l		%d4,%d3			#    [4]  + carry
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 691) 	add.w		%d2,%d0			# hi([1]) + lo([3])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 692) 	addx.l		%d4,%d3			#    [4]  + carry
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 693) 	swap		%d0			# lo([1]) <==> hi([1])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 694) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 695) # lo portions of [2],[3] have been added in to final result.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 696) # now, clear lo, put hi in lo reg, and add to [4]
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 697) 	clr.w		%d1			# clear lo([2])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 698) 	clr.w		%d2			# clear hi([3])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 699) 	swap		%d1			# hi([2]) in lo d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 700) 	swap		%d2			# hi([3]) in lo d2
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 701) 	add.l		%d2,%d1			#    [4]  + hi([2])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 702) 	add.l		%d3,%d1			#    [4]  + hi([3])
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 703) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 704) 	tst.b		%d5			# should result be signed?
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 705) 	beq.b		muls64_done		# no
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 706) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 707) # result should be a signed negative number.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 708) # compute 2's complement of the unsigned number:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 709) #   -negate all bits and add 1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 710) muls64_neg:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 711) 	not.l		%d0			# negate lo(result) bits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 712) 	not.l		%d1			# negate hi(result) bits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 713) 	addq.l		&1,%d0			# add 1 to lo(result)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 714) 	addx.l		%d4,%d1			# add carry to hi(result)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 715) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 716) muls64_done:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 717) 	mov.w		MUL64_CC(%a6),%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 718) 	andi.b		&0x10,%d4		# keep old 'X' bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 719) 	tst.l		%d1			# may set 'N' bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 720) 	bpl.b		muls64_ddone
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 721) 	ori.b		&0x8,%d4		# set 'N' bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 722) muls64_ddone:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 723) 	mov.w		%d4,%cc
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 724) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 725) # here, the result is in d1 and d0. the current strategy is to save
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 726) # the values at the location pointed to by a0.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 727) # use movm here to not disturb the condition codes.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 728) muls64_end:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 729) 	exg		%d1,%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 730) 	movm.l		&0x0003,([0x10,%a6])	# save result at (a0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 731) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 732) # EPILOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 733) #	fmovm.l		(%sp)+,&0x0		# restore no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 734) 	movm.l		(%sp)+,&0x003c		# restore d2-d5
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 735) 	unlk		%a6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 736) # EPILOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 737) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 738) 	rts
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 739) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 740) # one or both of the operands is zero so the result is also zero.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 741) # save the zero result to the register file and set the 'Z' ccode bit.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 742) muls64_zero:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 743) 	clr.l		%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 744) 	clr.l		%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 745) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 746) 	mov.w		MUL64_CC(%a6),%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 747) 	andi.b		&0x10,%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 748) 	ori.b		&0x4,%d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 749) 	mov.w		%d4,%cc			# set 'Z' ccode bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 750) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 751) 	bra.b		muls64_end
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 752) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 753) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 754) # XDEF ****************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 755) #	_060LSP__cmp2_Ab_(): Emulate "cmp2.b An,<ea>".			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 756) #	_060LSP__cmp2_Aw_(): Emulate "cmp2.w An,<ea>".			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 757) #	_060LSP__cmp2_Al_(): Emulate "cmp2.l An,<ea>".			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 758) #	_060LSP__cmp2_Db_(): Emulate "cmp2.b Dn,<ea>".			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 759) #	_060LSP__cmp2_Dw_(): Emulate "cmp2.w Dn,<ea>".			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 760) #	_060LSP__cmp2_Dl_(): Emulate "cmp2.l Dn,<ea>".			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 761) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 762) #	This is the library version which is accessed as a subroutine	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 763) #	and therefore does not work exactly like the 680X0 "cmp2"	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 764) #	instruction.							#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 765) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 766) # XREF ****************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 767) #	None								#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 768) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 769) # INPUT ***************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 770) #	0x4(sp) = Rn							#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 771) #	0x8(sp) = pointer to boundary pair				#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 772) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 773) # OUTPUT **************************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 774) #	cc = condition codes are set correctly				#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 775) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 776) # ALGORITHM ***********************************************************	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 777) #	In the interest of simplicity, all operands are converted to	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 778) # longword size whether the operation is byte, word, or long. The	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 779) # bounds are sign extended accordingly. If Rn is a data register, Rn is #
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 780) # also sign extended. If Rn is an address register, it need not be sign #
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 781) # extended since the full register is always used.			#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 782) #	The condition codes are set correctly before the final "rts".	#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 783) #									#
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 784) #########################################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 785) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 786) set	CMP2_CC,	-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 787) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 788) 	global		_060LSP__cmp2_Ab_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 789) _060LSP__cmp2_Ab_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 790) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 791) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 792) 	link.w		%a6,&-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 793) 	movm.l		&0x3800,-(%sp)		# save d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 794) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 795) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 796) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 797) 	mov.w		%cc,CMP2_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 798) 	mov.l		0x8(%a6), %d2		# get regval
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 799) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 800) 	mov.b		([0xc,%a6],0x0),%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 801) 	mov.b		([0xc,%a6],0x1),%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 802) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 803) 	extb.l		%d0			# sign extend lo bnd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 804) 	extb.l		%d1			# sign extend hi bnd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 805) 	bra.w		l_cmp2_cmp		# go do the compare emulation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 806) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 807) 	global		_060LSP__cmp2_Aw_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 808) _060LSP__cmp2_Aw_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 809) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 810) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 811) 	link.w		%a6,&-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 812) 	movm.l		&0x3800,-(%sp)		# save d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 813) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 814) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 815) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 816) 	mov.w		%cc,CMP2_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 817) 	mov.l		0x8(%a6), %d2		# get regval
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 818) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 819) 	mov.w		([0xc,%a6],0x0),%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 820) 	mov.w		([0xc,%a6],0x2),%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 821) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 822) 	ext.l		%d0			# sign extend lo bnd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 823) 	ext.l		%d1			# sign extend hi bnd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 824) 	bra.w		l_cmp2_cmp		# go do the compare emulation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 825) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 826) 	global		_060LSP__cmp2_Al_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 827) _060LSP__cmp2_Al_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 828) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 829) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 830) 	link.w		%a6,&-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 831) 	movm.l		&0x3800,-(%sp)		# save d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 832) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 833) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 834) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 835) 	mov.w		%cc,CMP2_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 836) 	mov.l		0x8(%a6), %d2		# get regval
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 837) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 838) 	mov.l		([0xc,%a6],0x0),%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 839) 	mov.l		([0xc,%a6],0x4),%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 840) 	bra.w		l_cmp2_cmp		# go do the compare emulation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 841) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 842) 	global		_060LSP__cmp2_Db_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 843) _060LSP__cmp2_Db_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 844) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 845) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 846) 	link.w		%a6,&-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 847) 	movm.l		&0x3800,-(%sp)		# save d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 848) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 849) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 850) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 851) 	mov.w		%cc,CMP2_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 852) 	mov.l		0x8(%a6), %d2		# get regval
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 853) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 854) 	mov.b		([0xc,%a6],0x0),%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 855) 	mov.b		([0xc,%a6],0x1),%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 856) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 857) 	extb.l		%d0			# sign extend lo bnd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 858) 	extb.l		%d1			# sign extend hi bnd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 859) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 860) # operation is a data register compare.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 861) # sign extend byte to long so we can do simple longword compares.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 862) 	extb.l		%d2			# sign extend data byte
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 863) 	bra.w		l_cmp2_cmp		# go do the compare emulation
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 864) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 865) 	global		_060LSP__cmp2_Dw_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 866) _060LSP__cmp2_Dw_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 867) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 868) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 869) 	link.w		%a6,&-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 870) 	movm.l		&0x3800,-(%sp)		# save d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 871) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 872) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 873) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 874) 	mov.w		%cc,CMP2_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 875) 	mov.l		0x8(%a6), %d2		# get regval
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 876) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 877) 	mov.w		([0xc,%a6],0x0),%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 878) 	mov.w		([0xc,%a6],0x2),%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 879) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 880) 	ext.l		%d0			# sign extend lo bnd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 881) 	ext.l		%d1			# sign extend hi bnd
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 882) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 883) # operation is a data register compare.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 884) # sign extend word to long so we can do simple longword compares.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 885) 	ext.l		%d2			# sign extend data word
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 886) 	bra.w		l_cmp2_cmp		# go emulate compare
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 887) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 888) 	global		_060LSP__cmp2_Dl_
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 889) _060LSP__cmp2_Dl_:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 890) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 891) # PROLOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 892) 	link.w		%a6,&-4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 893) 	movm.l		&0x3800,-(%sp)		# save d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 894) #	fmovm.l		&0x0,-(%sp)		# save no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 895) # PROLOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 896) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 897) 	mov.w		%cc,CMP2_CC(%a6)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 898) 	mov.l		0x8(%a6), %d2		# get regval
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 899) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 900) 	mov.l		([0xc,%a6],0x0),%d0
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 901) 	mov.l		([0xc,%a6],0x4),%d1
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 902) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 903) #
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 904) # To set the ccodes correctly:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 905) #	(1) save 'Z' bit from (Rn - lo)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 906) #	(2) save 'Z' and 'N' bits from ((hi - lo) - (Rn - hi))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 907) #	(3) keep 'X', 'N', and 'V' from before instruction
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 908) #	(4) combine ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 909) #
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 910) l_cmp2_cmp:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 911) 	sub.l		%d0, %d2		# (Rn - lo)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 912) 	mov.w		%cc, %d3		# fetch resulting ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 913) 	andi.b		&0x4, %d3		# keep 'Z' bit
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 914) 	sub.l		%d0, %d1		# (hi - lo)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 915) 	cmp.l		%d1,%d2			# ((hi - lo) - (Rn - hi))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 916) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 917) 	mov.w		%cc, %d4		# fetch resulting ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 918) 	or.b		%d4, %d3		# combine w/ earlier ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 919) 	andi.b		&0x5, %d3		# keep 'Z' and 'N'
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 920) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 921) 	mov.w		CMP2_CC(%a6), %d4	# fetch old ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 922) 	andi.b		&0x1a, %d4		# keep 'X','N','V' bits
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 923) 	or.b		%d3, %d4		# insert new ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 924) 	mov.w		%d4,%cc			# save new ccodes
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 925) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 926) # EPILOGUE BEGIN ########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 927) #	fmovm.l		(%sp)+,&0x0		# restore no fpregs
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 928) 	movm.l		(%sp)+,&0x001c		# restore d2-d4
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 929) 	unlk		%a6
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 930) # EPILOGUE END ##########################################################
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 931) 
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 932) 	rts