使用RISC-V实现斐波那契函数,使得f(0)= 0,f(1)= 1,...,直到f(47)。我的输出匹配到46的所有内容。但是当我尝试计算f(47)时,我得到:-1323752223.
下面是输出:Output from Code below with n=47
是否有某种溢出,因为我得到一个负整数值?我应该在哪里查看并修复错误?
.data
n: .word 47
.text
.globl main
main:
li x2, 0 # Used to determine if n (x7) equals 0
li x3, 1 # Used to determine if n (x7) equals 1
li x5, 0 # First number
li x6, 1 # Second number
lw x7, n # Limit
li x8, 1 # Counter
beq x7, x2, DO # If n == 0 then jump to DO (Which shoud print 0). Implements f(0) = 0
beq x7, x3, WRITE # if n == 1 then jump to WRITE (Which should print 1). Implements f(1) = 1
LOOP: beq x8, x7, EXIT # Comparse the counter x8 which starts with 1 to n (limit). If x8 == x7 jump to EXIT
add x4, x5, x6 # Add x5 to x6 and store in x4
ori x5, x6, 0 # Assign the second number to my first number
ori x6, x4, 0 # Assign the sum of x5 and x6 to my second number
addi x8, x8, 1 # Add 1 to my counter
j LOOP # Jump to loop
EXIT:
li x17, 1 # Load constant 1 to x17
add x10,x4,x0 # Add x4 (which contains the result after the above coe) to x10
ecall # Issue an SystemCall which prints an integer (Because of the 1 in x17)
li x17, 5
ecall
li x17, 10
ecall # Reads an int from input console (Because of the 10 in x17)
DO:
li x4, 0 # load 0 in x10 (x10 will be used by the SysCall to print) and print
add x10,x4,x0
li x17, 1
ecall
li x17, 5
ecall
li x17, 10
ecall
WRITE: li x4, 1 # load 1 in x10 and print
add x10,x4,x0
li x17,1
ecall
li x17, 5
ecall
li x17, 10
ecall
2条答案
按热度按时间fnx2tebb1#
是的,您已经找到了有符号32位整数可以容纳的范围。
fib(47)
= 2971215073不适合有符号的32位整数,但适合无符号的-然而,RARS没有“unsigned int”打印函数。fib(48)
= 4807526976不适合32位格式,即使是无符号格式。斐波那契数列列表:https://www.math.net/list-of-fibonacci-numbers
如果你想表示更大的数字,你需要一个策略。
fib(92)
= 7540113804746346429。最后,您可以检测并发出所选算术数据类型溢出的错误。RISC V上的溢出检测有点简单,但并不明显。
从技术上讲,将2个任意的32位数字相加会得到一个33位的答案,但不会超过33位,因此我们可以使用数学知识来检测溢出。
首先,在32位数中,最高位是符号位(当有符号数据类型时)或幅度位(当无符号数据类型时)。
如果您添加两个正数(就像
fib
的情况一样)并且设置了符号位,那么您就有符号溢出-但如果解释为无符号,则是正确的位模式。但是,使用ecall #1将无法正确打印数字,因为它会将数字打印为有符号并解释为负数。你可以自己写无符号数字打印;您也可以查找这种情况,并简单地停止打印程序,并发出一个错误。除此之外,您还可以通过查看结果值是否小于输入操作数之一来检查32位无符号加法是否溢出。
最后一种方法也用于多字加法,以进行从低位字到高位字的进位。
nr7wwzry2#
下面是在RISC-V汇编中计算Fibonacci的简单代码: