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

📄 4_1vos

📁 大型risc处理器设计源代码,这是书中的代码 基于流水线的risc cpu设计
💻
📖 第 1 页 / 共 5 页
字号:
         // c0000610             ;
FC780014 // c0000610             Bt     UnImp_OpCd          ; continue with opcode analysis
61D80016 // c0000614             MOV    R27, R22            ; load Op1 to R27
         // c0000618             ;
FC780012 // c0000618             Bt     UnImp_OpCd          ; continue with opcode analysis
61D80017 // c000061c             MOV    R27, R23            ; load Op1 to R27
         // c0000620             ;
FC780010 // c0000620             Bt     UnImp_OpCd          ; continue with opcode analysis
0EDE0018 // c0000624             LD.q   R27, R24, 24*4      ; load Op1 to R27
         // c0000628             ;
FC78000E // c0000628             Bt     UnImp_OpCd          ; continue with opcode analysis
0EDE0019 // c000062c             LD.q   R27, R24, 25*4      ; load Op1 to R27
         // c0000630             ;
FC78000C // c0000630             Bt     UnImp_OpCd          ; continue with opcode analysis
0EDE001A // c0000634             LD.q   R27, R24, 26*4      ; load Op1 to R27
         // c0000638             ;
FC78000A // c0000638             Bt     UnImp_OpCd          ; continue with opcode analysis
0EDE001B // c000063c             LD.q   R27, R24, 27*4      ; load Op1 to R27
         // c0000640             ;
FC780008 // c0000640             Bt     UnImp_OpCd          ; continue with opcode analysis
0EDE001C // c0000644             LD.q   R27, R24, 28*4      ; load Op1 to R27
         // c0000648             ;
FC780006 // c0000648             Bt     UnImp_OpCd          ; continue with opcode analysis
0EDE001D // c000064c             LD.q   R27, R24, 29*4      ; load Op1 to R27
         // c0000650             ;
FC780004 // c0000650             Bt     UnImp_OpCd          ; continue with opcode analysis
0EDE001E // c0000654             LD.q   R27, R24, 30*4      ; load Op1 to R27
         // c0000658             ;
FC780002 // c0000658             Bt     UnImp_OpCd          ; continue with opcode analysis
0EDE001F // c000065c             LD.q   R27, R24, 31*4      ; load Op1 to R27
         // c0000660             ;------------------------------------------------------------------
         // c0000660 
         // c0000660             ; check opcode (only MUL or DIV possible)
         // c0000660 ;DelaySlot  LSR    R25, R26, 26        ; determine opcode
6A06401E // c0000660 UnImp_OpCd: CMP.f  R25, %011110        ; MUL?
FCC00006 // c0000664             Beq.a  UnImp_Mul           ; branch to MUL routine
61C80000 // c0000668             CLR    R25                 ;   sign positive
6ACE401F // c000066c             SUB.f  R25, R25, %011111   ; clear R25, DIV?
FCC00023 // c0000670             Beq.a  UnImp_Div           ; branch to DIV routine
61C80000 // c0000674             CLR    R25                 ;   sign positive
         // c0000678             ; opcode was neither MUL nor DIV: hardware error
FF000000 // c0000678             HALT                       ;
         // c000067c 
         // c000067c 
         // c000067c             ;==================================================================
         // c000067c             ; signed Multiplication of 32-bit operands by addition
         // c000067c             ;
         // c000067c             ; MUL(.f) Rd, Ra, Rb   \{REG[Rd|1],REG[Rd&1E]\} := REG[Ra] * REG[Rb]
         // c000067c             ; MUL(.f) Rd, Ra, IMM  \{REG[Rd|1],REG[Rd&1E]\} := REG[Ra] * IMM
         // c000067c             ;
         // c000067c             ; local registers:
         // c000067c             ; R24: pointer to UserSwapSpace to save changed registers
         // c000067c             ; R25: result sign + manipulations of opcode + SR
         // c000067c             ; R26: opcode of not implemented instruction
         // c000067c             ; R27: factor1 (F1) + operand1 of instruction
         // c000067c             ; R28: high word factor (F2)
         // c000067c             ; R29: low word factor2 (F2) + operand2 of instruction
         // c000067c             ; R30: high word result
         // c000067c             ; R31: low word result
         // c000067c             ;
         // c000067c ;DelaySlot  CLR    R25                 ; result sign positive
         // c000067c             ;
6B06C000 // c000067c UnImp_Mul:  TST.f  R27                 ; op1 positive?
FC100004 // c0000680             Bpl    UnImp_Mul1          ; clear high result register
61F00000 // c0000684             CLR    R30                 ; otherwise, change
48CE7FFF // c0000688             NOT    R25, R25            ;   result sign
69D8001B // c000068c             NEG    R27, R27            ;   op1 positive
         // c0000690             ;
6B074000 // c0000690 UnImp_Mul1: TST.f  R29                 ; op2 positive?
FC100004 // c0000694             Bpl    UnImp_Mul2          ; clear low result register
61F80000 // c0000698             CLR    R31                 ; otherwise, change
48CE7FFF // c000069c             NOT    R25, R25            ;   result sign
69E8001D // c00006a0             NEG    R29, R29            ;   op2 positive
         // c00006a4             ;
         // c00006a4             ; to optimize performance, ensure the smaller value in the
         // c00006a4             ; "shifted" register and F2 > F2
6B07401B // c00006a4 UnImp_Mul2: CMP.f  R29, R27            ;
FC280004 // c00006a8             Bge    UnImp_Mul3          ; Op2 > Op1?
61E0001D // c00006ac             MOV    R28, R29            ; exchange values
61E8001B // c00006b0             MOV    R29, R27            ;
61D8001C // c00006b4             MOV    R27, R28            ;
         // c00006b8             ;
61E00000 // c00006b8 UnImp_Mul3: CLR    R28                 ; clear high F2
         // c00006bc             ;
         // c00006bc             ;  Product := F2 * F1
         // c00006bc             ; \{R30,R31\}:=\{R28,R29\}*R27
56DEC001 // c00006bc             LSR.f  R27, R27, 1         ; if no addition,
FC880005 // c00006c0 UnImp_Mul4: Bcc.a  UnImp_Mul5          ;   shift
52EF4001 // c00006c4             LSL.f  R29, R29, 1         ;   low F2
63FFC01D // c00006c8             ADD.f  R31, R31, R29       ; otherwise, add low
65F7801C // c00006cc             ADDC   R30, R30, R28       ; and high and shift
52EF4001 // c00006d0             LSL.f  R29, R29, 1         ; shift low F2
65E7001C // c00006d4 UnImp_Mul5: ADDC   R28, R28, R28       ; shift high F2 with carry
6B06C000 // c00006d8             TST.f  R27                 ;
FC87FFF9 // c00006dc             Bne.a  UnImp_Mul4          ; add again?
56DEC001 // c00006e0             LSR.f  R27, R27, 1         ;   add next time?
         // c00006e4             ;
         // c00006e4             ; sign correction necessary?
6B064000 // c00006e4             TST.f  R25                 ; sign of product
FC90002C // c00006e8             Bpl.a  UnImP_Flg1          ; 
52068006 // c00006ec             LSL.f  R00, R26, 6         ;
         // c00006f0             ;
6BF8001F // c00006f0             NEG.f  R31, R31            ;
FC780028 // c00006f4             Bt     UnImp_Flg           ; continue with flags
6DF0001E // c00006f8             NEGC   R30, R30            ;
         // c00006fc             ;==================================================================
         // c00006fc 
         // c00006fc 
         // c00006fc             ;==================================================================
         // c00006fc             ; signed division of 32-bit operands by subtraction
         // c00006fc             ; R27 : R29 = R30 remainder R31    with 0<=remainder<dividend
         // c00006fc             ;
         // c00006fc             ; local registers:
         // c00006fc             ; R24: pointer to UserSwapSpace to save changed registers
         // c00006fc             ; R25: sign of result
         // c00006fc             ; R26: opcode of not implemented instruction
         // c00006fc             ; R27: divisor
         // c00006fc             ; R28: position control for shifting
         // c00006fc             ; R29: divisor
         // c00006fc             ; R30: integer quotient
         // c00006fc             ; R31: remainder (and present dividend)
         // c00006fc             ;
         // c00006fc ;DelaySlot  CLR    R25                 ; result sign positive
         // c00006fc             ;
63F8001B // c00006fc UnImp_Div:  MOV.f  R31, R27            ; dividend positive?
FC100004 // c0000700             Bpl    UnImp_Div1          ; clear high result register
63D8001D // c0000704             MOV.f  R27, R29            ;
44CE4002 // c0000708             OR     R25, R25, %10       ; change sign
69F8001F // c000070c             NEG    R31, R31            ; dividend positive
         // c0000710             ;
         // c0000710 ;DelaySlot  MOV.f  R27, R29            ; test divisor
FC47FED4 // c0000710 UnImp_Div1: Beq    DivByZero           ; if 0, branch to exception
61F00000 // c0000714             CLR    R30                 ; if positive:
FC100005 // c0000718             Bpl    UnImp_Div2          ; clear low result register
60E00001 // c000071c             MOV    R28, 1              ;
44CE4001 // c0000720             OR     R25, R25, %01       ;   change sign
69E8001D // c0000724             NEG    R29, R29            ;   divisor positive
61D8001D // c0000728             MOV    R27, R29            ;   save divisor
         // c000072c             ;
         // c000072c             ; shift as required
         // c000072c ;DelaySlot  MOV    R28, 1              ; starting value for position
52EF4001 // c000072c UnImp_Div2: LSL.f  R29, R29, 1         ; is divisor*2
FC500004 // c0000730             Bmi    UnImp_Div3          ;   possible?
6B07C01D // c0000734             CMP.f  R31, R29            ; or < dividend?
FCAFFFFD // c0000738             Bge.a  UnImp_Div2          ;   if yes, continue
50E70001 // c000073c             LSL    R28, R28, 1         ;   and remember new position
54EF4001 // c0000740 UnImp_Div3: LSR    R29, R29, 1         ; if no, correction
         // c0000744             ;
         // c0000744 ;DelaySlot  CLR    R30                 ; initialize quotient
6B07401F // c0000744             CMP.f  R29, R31            ; compare divisor and dividend
FCA80005 // c0000748 UnImp_Div4: Bge.a  UnImp_Div5          ; divisor greater?
56E70001 // c000074c             LSR.f  R28, R28, 1         ; if yes, correct position
69FFC01D // c0000750             SUB    R31, R31, R29       ; if no, subtract divisor
61F7801C // c0000754             ADD    R30, R30, R28       ;   and update quotient
56E70001 // c0000758             LSR.f  R28, R28, 1         ;   and shift position right
54EF4001 // c000075c UnImp_Div5: LSR    R29, R29, 1         ; and divisor
FC87FFFA // c0000760             Bne.a  UnImp_Div4          ; if not done,
6B07401F // c0000764             CMP.f  R29, R31            ;   compare divisor and dividend
         // c0000768             ;
         // c0000768             ; correct result due to sign?
6A064000 // c0000768             CMP.f  R25, %00            ; (+) : (+) ?
FC40000A // c000076c             Beq    UnImP_Flg           ; if yes, no correction
6A064001 // c0000770             CMP.f  R25, %01            ; if no: (+) : (-) ?
FC400007 // c0000774             Beq    UnImp_Div7          ; if yes, negate quotient
6B00001F // c0000778             NEG.f  R00, R31            ; remainder 0 (or "negative")?
FC400003 // c000077c             Beq    UnImp_Div6          ; 0, test if correction
65F78000 // c0000780             ADDC   R30, R30, R00       ; negative, increase quotient
69FEC01F // c0000784             SUB    R31, R27, R31       ; correct remainder
6A064002 // c0000788 UnImp_Div6: CMP.f  R25, %10            ; (-) : (+) ?
FCC00002 // c000078c             Beq.a  UnImP_Flg           ; if yes,
69F0001E // c0000790 UnImp_Div7: NEG    R30, R30            ; negate quotient
         // c0000794             ;==================================================================
         // c0000794 
         // c0000794 
         // c0000794             ; test if flags have to be set
52068006 // c0000794 UnImP_Flg:  LSL.f  R00, R26, 6         ; flag option?
FC10000A // c0000798 UnImP_Flg1: Bpl    UnImp_Rd            ; if no, compute Rd REG no
6B078000 // c000079c             TST.f  R30                 ; otherwise, set flags
FCC00002 // c00007a0             Beq.a  UnImp_Flg2          ; if high=0,
6B07C000 // c00007a4             TST.f  R31                 ;   check low result
EAE0C000 // c00007a8 UnImp_Flg2: LRFS   R28, SR             ; load NZVC flags from SR
40E7000F // c00007ac             AND    R28, R28, %00001111 ;
EAE9C000 // c00007b0             LRFS   R29, ECSR           ; combine status
40EF40F0 // c00007b4             AND    R29, R29, %11110000 ; from ECSR
45EF401C // c00007b8             OR     R29, R29, R28       ; with flags
EB38001D // c00007bc             SRIS   ECSR, R29           ; and transfer
         // c00007c0 
         // c00007c0             ; determine destination
50CE8008 // c00007c0 UnImp_Rd:   LSL    R25, R26, 8         ; compute
54CE401C // c00007c4             LSR    R25, R25, 28        ;   destination
50CE4004 // c00007c8             LSL    R25, R25, 4         ;   and
E0DE0000 // c00007cc             LDH    R27, UnImp_RdTb     ;   add to
44DEC7E0 // c00007d0             OR     R27, R27, UnImp_RdTb & $1FFF ; branch table
61DEC019 // c00007d4             ADD    R27, R27, R25       ; as distance
EB00001B // c00007d8             JMP    R27                 ; store result
EAC8C000 // c00007dc             LRFS   R25, SR             ;
         // c00007e0             ;------------------------------------------------------------------
         // c00007e0             ; branch tab

⌨️ 快捷键说明

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