addi

addi

Asembler RISC-V Referencja

lyszt.net obejmuje addi i inne instrukcje RISC-V w większych szczegółach.

Format kodowania

R
31–25funct7
24–20rs2
19–15rs1
14–12funct3
11–7rd
6–0opcode
I
31–20imm[11:0]
19–15rs1
14–12funct3
11–7rd
6–0opcode
S
31–25imm[11:5]
24–20rs2
19–15rs1
14–12funct3
11–7imm[4:0]
6–0opcode
B
31–25imm[12,10:5]
24–20rs2
19–15rs1
14–12funct3
11–7imm[4:1,11]
6–0opcode
U
31–12imm[31:12]
11–7rd
6–0opcode
J
31–12imm[20,10:1,11,19:12]
11–7rd
6–0opcode

Opis

addi dodaje stałą do rejestru. Nazwa oznacza add immediate (dodaj natychmiastowe). Wartość natychmiastowa to stała zapisana w samej instrukcji, a nie odczytana z rejestru. Użyj jej, gdy jedna z liczb jest ustalona podczas pisania programu, na przykład przy dodawaniu 1 do licznika.

Postać addi pokazano poniżej. Odczytuje wartość z rejestru źródłowego rs1, dodaje stałą imm i zapisuje wynik do rejestru docelowego rd.

addi rd, rs1, imm

Następna linia odczytuje t0, dodaje jeden i zapisuje wynik z powrotem, więc t0 = t0 + 1.

addi t0, t0, 1

Stała zajmuje 12 bitów i jest ze znakiem, co daje zakres od -2048 do 2047. Asembler odrzuca większe wartości. W przypadku większej stałej najpierw załaduj ją do rejestru za pomocą li. Ujemna stała sprawia, że addi również odejmuje, dlatego RISC-V nie ma osobnej instrukcji odejmowania wartości natychmiastowej. Następna linia odlicza w dół.

addi t0, t0, -1

Podręcznik RISC-V nazywa tę stałą 12-bitową wartością natychmiastową ze znakiem rozszerzonym. Stwierdza, że przepełnienie arytmetyczne jest ignorowane, więc wynik zachowuje tylko swoje dolne bity XLEN, gdzie XLEN to szerokość rejestru w bitach, tutaj 32. Gdy znak stałej jest znany, jedno rozgałęzienie po dodaniu sprawdza przepełnienie ze znakiem. Dwie poniższe linie obsługują typowy przypadek dodawania dodatniej stałej.

addi t0, t1, +imm
blt t0, t1, overflow

Programy używają addi do liczników, do przesuwania wskaźnika na następny element i do rezerwowania miejsca na stosie. Przykład dodaje 1, aby zwiększyć licznik, i dodaje -16, aby zarezerwować 16 bajtów pamięci roboczej, co jest typowym początkiem funkcji potrzebującej miejsca roboczego.

Przykład

addi t0, t0, 1     # t0++
addi sp, sp, -16   # reserve 16 bytes of stack