⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 softfp.s

📁 <B>Digital的Unix操作系统VAX 4.2源码</B>
💻 S
📖 第 1 页 / 共 5 页
字号:
	bne	t6,zero,2f	# then the high part of the fraction	bne	t7,zero,2f	# then the low part of the fraction	# Now RT is known to be zero so return the properly signed zero	move	t2,t0	move	t3,zero	move	v0,zero	b	rd_2w2:	/*	 * Now that all the NaN, infinity and zero cases have been taken care	 * of what is left are values that can be added.  So get all values	 * into a format that can be added.  For normalized numbers set the	 * implied one and remove the exponent bias.  For denormalized numbers	 * convert to normalized numbers with the correct exponent.	 */	bne	t1,zero,1f	# check for RS being denormalized	li	t1,-DEXP_BIAS+1	# set denorm's exponent	jal	rs_renorm_d	# normalize it	b	2f1:	subu	t1,DEXP_BIAS	# if RS is not denormalized then remove the	or	t2,DIMP_1BIT	#  exponent bias, and set the implied 1 bit2:	bne	t5,zero,3f	# check for RT being denormalized	li	t5,-DEXP_BIAS+1	# set denorm's exponent	jal	rt_renorm_d	# normalize it	b	4f3:	subu	t5,DEXP_BIAS	# if RT is not denormalized then remove the	or	t6,DIMP_1BIT	#  exponent bias, and set the implied 1 bit4:	/*	 * Calculate the exponent of the result to be used by the norm_d:	 * code to figure the final exponent.	 */	addu	t1,t5	addu	t1,12	/*	 * Since the norm_d: code expects the fraction to be in t2,t3,t8	 * RS's fraction is moved to t4,t5 so to free up t2,t3 to hold	 * the accululated result of the partal products.	 */	move	t4,t2	move	t5,t3	multu	t5,t7		# multiply RS(low) * RT(low) fractions	mflo	ra		# all the low 32 bits (ra) go into the sticky	sne	ra,ra,zero	#  bit so set it if there are any one bits	mfhi	t8		# get the high 32 bits (t8)	multu	t5,t6		# multiply RS(low) * RT(high) fractions	mflo	v1		# the low 32 bits will be added to t8	mfhi	t3		# the high 32 bits will go into t3	move	t2,zero		# the highest accumulator word is zero'ed	not	v0,v1		# set the carry out of t8 and low 32 bits	sltu	t9,v0,t8	#  of the mult (v1)	addu	t8,v1		# do the add of t8 and the low 32 bits (v1)	beq	t9,zero,1f	# if no carry out continue	addu	t3,1		# add the carry in	seq	t2,t3,zero	# set the carry out into t31:	multu	t4,t7		# multiply RS(high) * RT(low) fractions	mflo	v1		# the low 32 bits will be added to t8	mfhi	t5		# the high 32 bits will be added to t3	not	v0,v1		# set the carry out of t8 and low 32 bits	sltu	t9,v0,t8	#  of the mult (v1)	addu	t8,v1		# do the add of t8 and the low 32 bits (v1)	beq	t9,zero,2f	# branch if no carry out	# add t3 and the high 32 bits of the mult (t5) and the carry in	not	v0,t5		# set the carry out of t3 and high 32 bits	sltu	t9,v0,t3	#  of the mult (t5)	addu	t3,t5		# do the add of t3 and the high 32 bits (t5)	addu	t3,1		# add the carry in	seq	v0,t3,zero	# set the carry out of the carry in	or	t9,v0		# set the final carry out	b	3f2:	# add t3 and the high 32 bits of the mult (t5) and no carry in	not	v0,t5		# set the carry out of t3 and high 32 bits	sltu	t9,v0,t3	#  of the mult (t5)	addu	t3,t5		# do the add of t3 and the high 32 bits (t5)3:	addu	t2,t9		# add the carry out to t2	multu	t4,t6		# multiply RS(high) * RT(high) fractions	mflo	v1		# the low 32 bits will be added to t3	mfhi	t5		# the high 32 bits will be added to t2	not	v0,v1		# set the carry out of t3 and low 32 bits	sltu	t9,v0,t3	#  of the mult (v1)	addu	t3,v1		# do the add of t3 and the low 32 bits (v1)	beq	t9,zero,4f	# branch if no carry out	# add t2 and the high 32 bits of the mult (t5) and the carry in	addu	t2,1		# add the carry in4:	addu	t2,t5		# do the add of t2 and the high 32 bits (t5)	or	t8,ra	b	norm_dmul_e:mul_q:	b	illfpinstfunc_div:	lw	v1,div_fmt_tab(v0)	j	v1	.rdatadiv_fmt_tab:	.word	div_s:1, div_d:1, div_e:1, div_q:1, illfpinst:1	.text/* * Division single RD = RS / RT */.globl div_sdiv_s:	/*	 * Break out the operands into their fields (sign,exp,fraction) and	 * handle NaN operands by calling {rs,rt}breakout_s() .	 */	li	t9,C1_FMT_SINGLE*4	li	v1,1	jal	rs_breakout_s	jal	rt_breakout_s	/*	 * With the NaN cases taken care of the sign of the result for all	 * other operands is just the exclusive or of the signs of the	 * operands.	 */	xor	t0,t4	/*	 * Check for division of infinities, and produce the correct	 * action if so.	 */	bne	t1,SEXP_INF,3f	# is RS an infinity?	bne	t5,SEXP_INF,2f	# is RT also an infinity?	/*	 * The operation is infinity / infinity which is an invalid operation.	 * So set the invalid exception in the fpc_csr (a3) and setup the	 * result depending if the enable for the invalid exception is set.	 */	or	a3,INVALID_EXC	and	v0,a3,INVALID_ENABLE	beq	v0,zero,1f	/*	 * The invalid trap was enabled so signal a SIGFPE and leave the	 * result register unmodified.	 */	li	v0,SIGFPE	jal	post_signal	li	v0,1	b	store_fpc_csr	/*	 * The invalid trap was NOT enabled so the result is a quiet NaN.	 * So use the default quiet NaN and exit softfp().	 */1:	li	t2,SQUIETNAN_LEAST	move	v0,zero	b	rd_1w	/*	 * RS is an infinity and RT is NOT an infinity so the result is just a	 * a properly signed infinity (even if RT is zero).	 */2:	or	t2,t0	sll	t1,SEXP_SHIFT	or	t2,t1	move	v0,zero	b	rd_1w	/*	 * RS is known NOT to be an infinity so now check RT for an infinity	 */3:	bne	t5,SEXP_INF,4f	# is RT an infinity?	/*	 * RT is an infinity and RS is NOT an infinity so the result is just a	 * a properly signed zero.	 */	move	t2,t0	move	v0,zero	b	rd_1w4:	/*	 * Check for the division with zeros and produce the correct action	 * if so.	 */	bne	t5,zero,4f	# check RT for a zero value (first the exp)	bne	t6,zero,4f	# then the fraction	/*	 * Now RT is known to be zero, if RS is zero it is an invalid operation	 * if not it is a divide by zero.	 */	bne	t1,zero,2f	# check RS for a zero value (first the exp)	bne	t2,zero,2f	# then the fraction	/*	 * The operation is 0 / 0 which is an invalid operation.	 * So set the invalid exception in the fpc_csr (a3) and setup the	 * result depending if the enable for the invalid exception is set.	 */	or	a3,INVALID_EXC	and	v0,a3,INVALID_ENABLE	beq	v0,zero,1f	/*	 * The invalid trap was enabled so signal a SIGFPE and leave the	 * result register unmodified.	 */	li	v0,SIGFPE	jal	post_signal	li	v0,1	b	store_fpc_csr	/*	 * The invalid trap was NOT enabled so the result is a quiet NaN.	 * So use the default quiet NaN and exit softfp().	 */1:	li	t2,SQUIETNAN_LEAST	move	v0,zero	b	rd_1w	/*	 * The operation is x / 0 which is a divide by zero excrption.  So set	 * the divide by zero exception in the fpc_csr (a3) and setup the	 * result depending if the enable for the divide by zero exception	 * is set.	 */2:	or	a3,DIVIDE0_EXC	and	v0,a3,DIVIDE0_ENABLE	beq	v0,zero,3f	/*	 * The divide by zero trap was enabled so signal a SIGFPE and leave the	 * result register unmodified.	 */	li	v0,SIGFPE	jal	post_signal	li	v0,1	b	store_fpc_csr	/*	 * The divide by zero trap was NOT enabled so the result is a properly	 * signed infinity.	 */3:	or	t2,t0,SEXP_INF<<SEXP_SHIFT	move	v0,zero	b	rd_1w	/*	 * Now RT is known NOT to be zero, if RS is zero the result is just	 * a properly signed zero.	 */4:	bne	t1,zero,5f	# check RS for a zero value (first the exp)	bne	t2,zero,5f	# then the fraction	move	t2,t0	move	v0,zero	b	rd_1w5:	/*	 * Now that all the NaN, infinity and zero cases have been taken care	 * of what is left are values that can be divded.  So get all values	 * into a format that can be divded.  For normalized numbers set the	 * implied one and remove the exponent bias.  For denormalized numbers	 * convert to normalized numbers with the correct exponent.	 */	bne	t1,zero,1f	# check for RS being denormalized	li	t1,-SEXP_BIAS+1	# set denorm's exponent	jal	rs_renorm_s	# normalize it	b	2f1:	subu	t1,SEXP_BIAS	# if RS is not denormalized then remove the	or	t2,SIMP_1BIT	#  exponent bias, and set the implied 1 bit2:	bne	t5,zero,3f	# check for RT being denormalized	li	t5,-SEXP_BIAS+1	# set denorm's exponent	jal	rt_renorm_s	# normalize it	b	4f3:	subu	t5,SEXP_BIAS	# if RT is not denormalized then remove the	or	t6,SIMP_1BIT	#  exponent bias, and set the implied 1 bit4:	/*	 * Calculate the exponent of the result to be used by the norm_s:	 * code to figure the final exponent.	 */	subu	t1,t5	subu	t1,8	/*	 * Since the norm_s: code expects the fraction to be in t2,t8	 * RS's fraction is moved to t4 so to free up t2 to hold	 * the final quotient of the division.	 */	move	t4,t2	move	v0,zero		# set the number of quotient bits calculated				#  to zero	move	t2,zero		# clear the quotient accumulator1:	bltu	t4,t6,3f	# check if dividend (RS) >= divisor (RT)2:	# subtract divisor (RT) from dividend (RS)	subu	t4,t6		# subtract the fraction words	addu	t2,1		# add one to the quotient accumulator	bne	t4,zero,3f	# see if division is done (remainder of zero)	move	t8,zero		# clear the sticky register (no remainder)	negu	v0		# shift the quotient accumulator into it's	addu	v0,31		#  final possition and goto norm_s:	sll	t2,v0	b	norm_s3:	sll	t4,1		# shift the dividend (RS) left one bit	addu	v0,1		# add one to the number of quotient bits				#  calculated	sll	t2,1		# shift the quotient accumulator left one bit	# see if enough quotient bits have been calculated if not continue	blt	v0,SFRAC_BITS+3,1b	negu	v0		# shift the quoient accumulator into it's	addu	v0,31		#  final possition	sll	t2,v0	move	t8,t4		# set the sticky register with all the bits of				#  remainder	b	norm_s/* * Division double RD = RS / RT */.globl div_ddiv_d:	/*	 * Break out the operands into their fields (sign,exp,fraction) and	 * handle NaN operands by calling {rs,rt}breakout_d() .	 */	li	t9,C1_FMT_DOUBLE*4	li	v1,1	jal	rs_breakout_d	jal	rt_breakout_d	/*	 * With the NaN cases taken care of the sign of the result for all	 * other operands is just the exclusive or of the signs of the	 * operands.	 */	xor	t0,t4	/*	 * Check for division of infinities, and produce the correct	 * action if so.	 */	bne	t1,DEXP_INF,3f	# is RS an infinity?	bne	t5,DEXP_INF,2f	# is RT also an infinity?	/*	 * The operation is infinity / infinity which is an invalid operation.	 * So set the invalid exception in the fpc_csr (a3) and setup the	 * result depending if the enable for the invalid exception is set.	 */	or	a3,INVALID_EXC	and	v0,a3,INVALID_ENABLE	beq	v0,zero,1f	/*	 * The invalid trap was enabled so signal a SIGFPE and leave the	 * result register unmodified.	 */	li	v0,SIGFPE	jal	post_signal	li	v0,1	b	store_fpc_csr	/*	 * The invalid trap was NOT enabled so the result is a quiet NaN.	 * So use the default quiet NaN and exit softfp().	 */1:	li	t2,DQUIETNAN_LESS	li	t3,DQUIETNAN_LEAST	move	v0,zero	b	rd_2w	/*	 * RS is an infinity and RT is NOT an infinity so the result is just a	 * a properly signed infinity (even if RT is zero).	 */2:	or	t2,t0	sll	t1,DEXP_SHIFT	or	t2,t1	move	v0,zero	b	rd_2w	/*	 * RS is known NOT to be an infinity so now check RT for an infinity	 */3:	bne	t5,DEXP_INF,4f	# is RT an infinity?	/*	 * RT is an infinity and RS is NOT an infinity so the result is just a	 * a properly signed zero.	 */	move	t2,t0	move	t3,zero	move	v0,zero	b	rd_2w4:	/*	 * Check for the division with zeros and produce the correct action	 * if so.	 */	bne	t5,zero,4f	# check RT for a zero value (first the exp)	bne	t6,zero,4f	# then the high part of the fraction	bne	t7,zero,4f	# then the low part of the fraction	/*	 * Now RT is known to be zero, if RS is zero it is an invalid operation	 * if not it is a divide by zero.	 */	bne	t1,zero,2f	# check RS for a zero value (first the exp)	bne	t2,zero,2f	# then the high part of the fraction	bne	t3,zero,2f	# then the low part of the fraction	/*	 * The operation is 0 / 0 which is an invalid operation.	 * So set the invalid exception in the fpc_csr (a3) and setup the	 * result depending if the enable for the invalid exception is set.	 */	or	a3,INVALID_EXC	and	v0,a3,INVALID_ENABLE	beq	v0,zero,1f	/*	 * The invalid trap was enabled so signal a SIGFPE and leave the	 * result register unmodified.	 */	li	v0,SIGFPE	jal	post_signal	li	v0,1	b	store_fpc_csr	/*	 * The invalid trap was NOT enabled so the result is a quiet NaN.	 * So use the default quiet NaN and exit softfp().	 */1:	li	t2,DQUIETNAN_LESS	li	t3,DQUIETNAN_LEAST	move	v0,zero	b	rd_2w	/*	 * The operation is x / 0 which is a divide by zero excrption.  So set	 * the divide by zero exception in the fpc_csr (a3) and setup the	 * result depending if the enable for the divide by zero exception	 * is set.	 */2:	or	a3,DIVIDE0_EXC	and	v0,a3,DIVIDE0_ENABLE	beq	v0,zero,3f	/*	 * The divide by zero trap was enabled so signal a SIGFPE and leave the	 * result register unmodified.	 */	li	v0,SIGFPE	jal	post_signal	li	v0,1	b	store_fpc_csr	/*	 * The divide by zero trap was NOT enabled so the result is a properly	 * signed infinity.	 */3:	or	t2,t0,DEXP_INF<<DEXP_SHIFT	move	t3,zero	move	v0,zero	b	rd_2w	/*	 * Now RT is known NOT to be zero, if RS is zero the result is just	 * a properly signed zero.	 */4:	bne	t1,zero,5f	# check RS for a zero value (first the exp)	bne	t2,zero,5f	# then the high part of the fraction	bne	t3,zero,5f	# then the low part of the fraction	move	t2,t0	move	v0,zero	b	rd_2w5:	/*	 * Now that all the NaN, infinity and zero c

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -