| @@ -0,0 +1,4 @@ | |||||
| -Xms512M | |||||
| -Xmx4096M | |||||
| -Xss32M | |||||
| -XX:MaxMetaspaceSize=1024M | |||||
| @@ -1,4 +1,4 @@ | |||||
| * Exercise 1 | |||||
| * Exercise description | |||||
| The task in this exercise is to implement a 5-stage pipelined processor for | The task in this exercise is to implement a 5-stage pipelined processor for | ||||
| the [[./instructions.org][RISCV32I instruction set]]. | the [[./instructions.org][RISCV32I instruction set]]. | ||||
| @@ -6,14 +6,27 @@ | |||||
| at a time, whereas in exercise 2 your design will handle multiple instructions | at a time, whereas in exercise 2 your design will handle multiple instructions | ||||
| at a time. | at a time. | ||||
| This is done by inserting 4 NOP instructions inbetween each source instruction, | This is done by inserting 4 NOP instructions inbetween each source instruction, | ||||
| enabling us to use the same tests for both exercise 1 and 2. | |||||
| enabling us to use the same tests and harness for both exercise 1 and 2. | |||||
| Once you are done with exercise 1, you can up the difficulty by setting nopPad | |||||
| to false and start reading the [[exercise2.org][ex2 guide]]. | |||||
| In the project skeleton files ([[./src/main/scala/][Found here]]) you can see that a lot of code has | In the project skeleton files ([[./src/main/scala/][Found here]]) you can see that a lot of code has | ||||
| already been provided. | |||||
| already been provided, which can make it difficult to get started. | |||||
| Hopefully this document can help clear up at least some of the confusion. | |||||
| First an overview of what you are designing is presented, followed by a walk-through | |||||
| for getting the most basic instructions to work. | |||||
| In order to orient yourself you first need a map, thus a high level overview of the | |||||
| processor you're going to design is showed underneath: | |||||
| Keep in mind that this is just a high level sketch, omitting many details as well | |||||
| entire features (for instance branch logic) | |||||
| #+CAPTION: A very high level processor schematic. Registers, Instruction and data memory are already implemented. | |||||
| [[./Images/FiveStage.png]] | |||||
| Before going further it is useful to get an overview of what is provided out | |||||
| of the box. | |||||
| Now that you have an idea of what you're building it is time to take inventory of | |||||
| the files included in the skeleton, and what, if anything should be added. | |||||
| + [[./src/main/scala/Tile.scala]] | + [[./src/main/scala/Tile.scala]] | ||||
| This is the top level module for the system as a whole. This is where the test | This is the top level module for the system as a whole. This is where the test | ||||
| @@ -26,7 +39,11 @@ | |||||
| should be declared and wired together. | should be declared and wired together. | ||||
| Some of these modules have already been declared in order to wire up the | Some of these modules have already been declared in order to wire up the | ||||
| debugging logic for your test harness. | debugging logic for your test harness. | ||||
| This file corresponds to the high-level overview in its entirety. | |||||
| *This module is intended to be further fleshed out by you.* | *This module is intended to be further fleshed out by you.* | ||||
| As you work with this module, try keeping logic to a minimum to help readability. | |||||
| If you end up with a lot of signal select logic, consider moving that to a separate | |||||
| module. | |||||
| + [[./src/main/scala/IF.scala]] | + [[./src/main/scala/IF.scala]] | ||||
| This is the instruction fetch stage. | This is the instruction fetch stage. | ||||
| @@ -94,10 +111,11 @@ | |||||
| of these settings can be quite useful to alter. | of these settings can be quite useful to alter. | ||||
| The main attraction is the test options. By altering the verbosity settings you | The main attraction is the test options. By altering the verbosity settings you | ||||
| may change what is output. | may change what is output. | ||||
| The settings are | |||||
| The settings are: | |||||
| + printIfSuccessful | + printIfSuccessful | ||||
| Enables logging on tests that succeed | |||||
| Enables logging on tests that succeed. | |||||
| You typically want this turned off, at least for the full test runner. | |||||
| + printErrors | + printErrors | ||||
| Enables logging of errors. You obviously want this one on, at least on the single | Enables logging of errors. You obviously want this one on, at least on the single | ||||
| @@ -147,6 +165,12 @@ | |||||
| In your sketch you will eventually add a box for registers, IMEM and DMEM, which | In your sketch you will eventually add a box for registers, IMEM and DMEM, which | ||||
| should make it clear how the already finished modules fit into the grander design, | should make it clear how the already finished modules fit into the grander design, | ||||
| making the skeleton-code less mysterious. | making the skeleton-code less mysterious. | ||||
| To give you an idea of how a drill down looks like, here is my sketch of the ID stage: | |||||
| #+CAPTION: Instruction decode stage, showing the various signals. | |||||
| [[./Images/IDstage.png]] | |||||
| I would generally advice to do these on paper, but don't half-ass them. | |||||
| ** Adding numbers | ** Adding numbers | ||||
| @@ -174,11 +198,11 @@ | |||||
| **** Step ¾: | **** Step ¾: | ||||
| In your console, type ~testOnly FiveStage.SingleTest~ to run only the tests that you | In your console, type ~testOnly FiveStage.SingleTest~ to run only the tests that you | ||||
| have defined in the [[./src/test/scala/Manifest.scala][test manifest]] (currently set to ~"forward2.s"~). | |||||
| have defined in the [[./src/test/scala/Manifest.scala][test manifest]] (currently set to ~forward2.s~). | |||||
| As you will first implement addition you should change this to the [[./src/test/resources/tests/basic/immediate/addi.s][add immediate test]]. | As you will first implement addition you should change this to the [[./src/test/resources/tests/basic/immediate/addi.s][add immediate test]]. | ||||
| Luckily you do not have to deal with file paths, simply changing ~"forward2.s"~ to | |||||
| ~"addi.s"~ suffices. | |||||
| Luckily you do not have to deal with file paths, simply changing ~forward2.s~ to | |||||
| ~addi.s~ suffices. | |||||
| Ensure that the addi test is run by repeating the ~testOnly FiveStage.SingleTest~ | Ensure that the addi test is run by repeating the ~testOnly FiveStage.SingleTest~ | ||||
| command. | command. | ||||
| @@ -188,7 +212,7 @@ | |||||
| In [[./src/test/main/IF.scala]] you can see that the IMEM module is already set to fetch | In [[./src/test/main/IF.scala]] you can see that the IMEM module is already set to fetch | ||||
| the current program counter address (line 41), however since the current PC is stuck | the current program counter address (line 41), however since the current PC is stuck | ||||
| at 0 it will fetch the same instruction over and over. Rectify this by commenting in | at 0 it will fetch the same instruction over and over. Rectify this by commenting in | ||||
| ~// PC := PC + 4.U~ at line 43. | |||||
| ~// PC := PC + 4.U~ at line 48. | |||||
| You can now verify that your design fetches new instructions each cycle by running | You can now verify that your design fetches new instructions each cycle by running | ||||
| the test as in the previous step. | the test as in the previous step. | ||||
| @@ -207,10 +231,10 @@ | |||||
| Next you need to ensure that the registers and decoder gets the relevant data from the | Next you need to ensure that the registers and decoder gets the relevant data from the | ||||
| instruction. | instruction. | ||||
| This is made more convenient by the fact that `Instruction` is a class, allowing you | |||||
| This is made more convenient by the fact that ~Instruction~ is a class, allowing you | |||||
| to access methods defined on it. | to access methods defined on it. | ||||
| Keep in mind that it is only a class at compile and synthesis time, it will be | |||||
| indistinguishable from a regular ~UIint(32.W)~ in your finished circuit. | |||||
| Keep in mind that it is only a class during compile and build time, it will be | |||||
| indistinguishable from a regular ~UInt(32.W)~ in your finished circuit. | |||||
| The methods can be accessed like this: | The methods can be accessed like this: | ||||
| #+BEGIN_SRC scala | #+BEGIN_SRC scala | ||||
| // Drive funct6 of myModule with the 26th to 31st bit of instruction | // Drive funct6 of myModule with the 26th to 31st bit of instruction | ||||
| @@ -221,9 +245,27 @@ | |||||
| Your IF should now have an instruction as an OUTPUT, and your ID as an INPUT, however | Your IF should now have an instruction as an OUTPUT, and your ID as an INPUT, however | ||||
| they are not connected. This must be done in the CPU class where both the ID and IF are | they are not connected. This must be done in the CPU class where both the ID and IF are | ||||
| instantiated. | instantiated. | ||||
| In the overview sketch you probably noticed the barriers between IF and ID. | |||||
| In accordance with the overview, it is incorrect to directly connect the two modules, | |||||
| instead you must connect them using a *barrier*. | |||||
| A barrier is responsible for keeping a value inbetween cycles, facilitating pipelining. | |||||
| There is however one complicating matter: It takes a cycle to get the instruction from the | |||||
| instruction memory, thus we don't want to delay it in the barrier! | |||||
| In order to make code readable I suggest adding a new file for your barriers, containing | |||||
| four different modules for the barriers your design will need. | |||||
| Start with implementing your IF barrier module, which should contain the following: | |||||
| + An input and output for PC where the output is delayed by a single cycle. | |||||
| + An input and output for instruction where the output is wired directly to the input with | |||||
| no delay. | |||||
| The sketch for your barrier looks like this | |||||
| #+CAPTION: The barrier between IF and ID. Note the passthrough for the instruction | |||||
| [[./Images/IFID.png]] | |||||
| **** Step 4½: | **** Step 4½: | ||||
| You should now verify that the correct control signals are produced. Using printf, ensure | |||||
| You can now verify that the correct control signals are produced. Using printf, ensure | |||||
| that: | that: | ||||
| + The program counter is increasing in increments of 4 | + The program counter is increasing in increments of 4 | ||||
| + The instruction in ID is as expected | + The instruction in ID is as expected | ||||
| @@ -231,7 +273,8 @@ | |||||
| + The correct operands are fetched from the registers | + The correct operands are fetched from the registers | ||||
| Keep in mind that printf might not always be cycle accurate, the point is to ensure that | Keep in mind that printf might not always be cycle accurate, the point is to ensure that | ||||
| your processor design at least does something! | |||||
| your processor design at least does something! In general it is better to use debug signals | |||||
| and println, but for quick and dirty debugging printf is passable. | |||||
| *** Step 5: | *** Step 5: | ||||
| You will now have to create the EX stage. Use the structure of the IF and ID modules to | You will now have to create the EX stage. Use the structure of the IF and ID modules to | ||||
| @@ -247,12 +290,24 @@ | |||||
| ... | ... | ||||
| ) | ) | ||||
| io.aluResult := MuxLookup(0.U(32.W), io.aluOp, ALUopMap) | |||||
| // MuxLookup API: https://github.com/freechipsproject/chisel3/wiki/Muxes-and-Input-Selection#muxlookup | |||||
| io.aluResult := MuxLookup(io.aluOp, 0.U(32.W), ALUopMap) | |||||
| #+END_SRC | #+END_SRC | ||||
| As with the ID stage, you will need a barrier between ID and EX stage. | |||||
| In this case, as the overview sketch indicates, all values should be delayed one cycle. | |||||
| When you have finished the barrier, instantiate it and wire ID and EX together with the barrier in the | |||||
| same fashion as IF and ID. | |||||
| You don't need to add every single signal for your barrier, rather you should add them as they | |||||
| become needed. | |||||
| *** Step 6: | *** Step 6: | ||||
| Your MEM stage does very little when an ADDI instruction is executed, so implementing it should | Your MEM stage does very little when an ADDI instruction is executed, so implementing it should | ||||
| be easy. All you have to do is forward signals | |||||
| be easy. All you have to do is forward signals. | |||||
| From the overview sketch you can see that the same trick used in the IF/ID barrier is utilized | |||||
| here, bypassing the data memory read value since it is already delayed by a cycle. | |||||
| *** Step 7: | *** Step 7: | ||||
| You now need to actually write the result back to your register bank. | You now need to actually write the result back to your register bank. | ||||
| @@ -0,0 +1,109 @@ | |||||
| * Exercise 2 | |||||
| Safety wheels are now officially off. | |||||
| To verify this, set nopPadded to false in Manifest.scala and observe as all hell | |||||
| breaks loose. | |||||
| Let's break down what's going wrong and what we can do about it. | |||||
| ** RAW Hazards | |||||
| Consider the following program: | |||||
| #+begin_src asm | |||||
| main: | |||||
| add x1, x1, x2 | |||||
| add x1, x1, x1 | |||||
| add x1, x1, x2 | |||||
| #+end_src | |||||
| In your implementation this will give you wrong results since the results | |||||
| of the first add operation will not be available in the registers before | |||||
| x1 is fetched for the second and third operation. | |||||
| Your first task should therefore be to implement a forwarding unit | |||||
| The forwarding unit is located in the EX stage and is responsible for selecting | |||||
| the ALU input from three possible sources. | |||||
| These sources are: | |||||
| + The value received from the register bank | |||||
| + The ALU result currently in MEM | |||||
| + The writeback result | |||||
| The forwarder prioritizes as follows: | |||||
| + If the input register address is not the destination in either MEM or WB, select the | |||||
| register. | |||||
| + If the input register address is the destination register in WB, but not in MEM, select | |||||
| the writeback signal. | |||||
| + If the input register address is the destination register for the operation currently | |||||
| in MEM, select that operation. | |||||
| There is a special case you need take into account, namely load operations. | |||||
| Considering the following program: | |||||
| #+begin_src asm | |||||
| main: | |||||
| lw x1, 0(x2) | |||||
| add x1, x1, x1 | |||||
| add x1, x1, x1 | |||||
| #+end_src | |||||
| When the second operation (~add x1, x1, x1~) is in EX, the third clause in the forwarder | |||||
| is triggered, however the result is not yet ready since fetching memory costs a cycle. | |||||
| In order to fix this the forwarder must issue a signal that freezes the pipeline. | |||||
| This is done by issuing a signal to the barrier registers, telling them to _not_ update | |||||
| their contents, essentially repeating the last instruction. | |||||
| There are many subtleties to consider here. | |||||
| For instance: What should happen to the instruction currently | |||||
| in MEM? If it too is repeated the hazard detector will trigger next cycle, effectively | |||||
| deadlocking your processor. | |||||
| What about when the write address and read address are similar in the ID stage? | |||||
| Designing a forwarder can take very long, or it can be done very quickly, all depending | |||||
| on how *methodical* you are. My advice is to design the algorithm first, then when you're | |||||
| satisfied implement it on hardware. | |||||
| ** Control hazards | |||||
| Consider the following code | |||||
| #+begin_src asm | |||||
| main: | |||||
| beq zero, zero, target | |||||
| add x1, x1, x1 | |||||
| add x1, x1, x1 | |||||
| j main | |||||
| target: | |||||
| sub x1, x2, x2 | |||||
| sub x2, x2, x2 | |||||
| #+end_src | |||||
| Depending on your design the two add instructions will be fetched before the beq jump happens. | |||||
| Whenever a branch happens it is necessary to flush the spurious instructions that were fetched | |||||
| before the branch was noticed. | |||||
| However, simply waiting until the branch has been decided is not acceptable since that guarantees | |||||
| lost cycles. | |||||
| In your first iteration, simply assume branches will not be taken, and if they are taken issue | |||||
| a warning to the barriers that hold spurious instructions telling them to render them impotent | |||||
| by setting the control signals to do nothing. | |||||
| * Putting the pedal to the metal | |||||
| Once you have a design that RAW and control hazards you're ready to up the ante and add some | |||||
| improvements to your design. | |||||
| Some suggestions: | |||||
| ** Branch predictor | |||||
| Instead of assuming branch not taken, use a branch predictor. There are many different schemes, | |||||
| but I advice you to stick to a simple one, such as 1-bit or 2-bit. | |||||
| ** Fast branch handling | |||||
| Certaing branches like BEQ and BNE can be calculated very quickly, wheras size comparison branches | |||||
| (BGE, BLE and friends) take longer. It is therefore feasible to do these checks in the ID stage. | |||||
| ** Adding a data cache | |||||
| Unless you have already done the two suggested improvements, do not attempt to create a cache. | |||||
| The first thing you need to do is to add a latency for memory fetching, if not you will have | |||||
| nothing to improve upon. | |||||
| If you still insist, start with the BTreeManyO3.s program and analyze the memory access pattern. | |||||
| What sort of eviction policy and cache size would you choose for this pattern? | |||||
| You should try writing additional benchmarking programs, it is important to have something measurable, | |||||
| and the current programs are not made to test cache performance!! | |||||
| @@ -2,6 +2,8 @@ | |||||
| 4.2. Register-Register Arithmetic Instructions | 4.2. Register-Register Arithmetic Instructions | ||||
| -------------------------------------------------------------------------- | -------------------------------------------------------------------------- | ||||
| These do not render well on github, try using your text editor. | |||||
| * ADD | * ADD | ||||
| - Summary : Addition with 3 GPRs, no overflow exception | - Summary : Addition with 3 GPRs, no overflow exception | ||||
| @@ -8,13 +8,18 @@ class InstructionFetch extends MultiIOModule { | |||||
| val testHarness = IO( | val testHarness = IO( | ||||
| new Bundle { | new Bundle { | ||||
| val IMEMsetup = Input(new IMEMsetupSignals) | val IMEMsetup = Input(new IMEMsetupSignals) | ||||
| val PC = Output(UInt()) | |||||
| val PC = Output(UInt()) | |||||
| } | } | ||||
| ) | ) | ||||
| /** | /** | ||||
| * TODO: Add signals for handling events such as jumps | |||||
| * TODO: Add input signals for handling events such as jumps | |||||
| * TODO: Add output signal for the instruction. | |||||
| * The instruction is of type Bundle, which means that you must | |||||
| * use the same syntax used in the testHarness for IMEM setup signals | |||||
| * further up. | |||||
| */ | */ | ||||
| val io = IO( | val io = IO( | ||||
| new Bundle { | new Bundle { | ||||
| @@ -35,7 +40,7 @@ class InstructionFetch extends MultiIOModule { | |||||
| /** | /** | ||||
| * TODO: Your code here. | * TODO: Your code here. | ||||
| * | |||||
| * | |||||
| * You should expand on or rewrite the code below. | * You should expand on or rewrite the code below. | ||||
| */ | */ | ||||
| IMEM.io.instructionAddress := PC | IMEM.io.instructionAddress := PC | ||||
| @@ -47,11 +52,10 @@ class InstructionFetch extends MultiIOModule { | |||||
| /** | /** | ||||
| * Setup. You should not change this code | |||||
| * Setup. You should not change this code. | |||||
| */ | */ | ||||
| when(testHarness.IMEMsetup.setup) { | when(testHarness.IMEMsetup.setup) { | ||||
| PC := 0.U | PC := 0.U | ||||
| // TODO: You must set the instruction to Instruction.NOP here. | |||||
| // throw new Exception("Just making sure you're seeing the line above") | |||||
| io.instruction := Instruction.NOP | |||||
| } | } | ||||
| } | } | ||||
| @@ -22,14 +22,17 @@ class Instruction extends Bundle(){ | |||||
| def immediateJType = Cat(instruction(31), instruction(19, 12), instruction(20), instruction(30, 25), instruction(24, 21), 0.U(1.W)).asSInt | def immediateJType = Cat(instruction(31), instruction(19, 12), instruction(20), instruction(30, 25), instruction(24, 21), 0.U(1.W)).asSInt | ||||
| def immediateZType = instruction(19, 15).zext | def immediateZType = instruction(19, 15).zext | ||||
| def bubble(): Instruction = { | |||||
| val bubbled = Wire(new Instruction) | |||||
| bubbled.instruction := instruction | |||||
| bubbled.instruction(6, 0) := BitPat.bitPatToUInt(BitPat("b0010011")) | |||||
| bubbled | |||||
| } | |||||
| } | } | ||||
| object Instruction { | object Instruction { | ||||
| def bubble(i: Instruction) = | |||||
| i.opcode := BitPat.bitPatToUInt(BitPat("b0010011")) | |||||
| def default: Instruction = { | |||||
| def NOP: Instruction = { | |||||
| val w = Wire(new Instruction) | val w = Wire(new Instruction) | ||||
| w.instruction := 0.U | |||||
| w.instruction := BitPat.bitPatToUInt(BitPat("b00000000000000000000000000010011")) | |||||
| w | w | ||||
| } | } | ||||
| } | } | ||||
| @@ -1,204 +1,204 @@ | |||||
| main: | main: | ||||
| ori gp, gp, 0xFFFFFE09 | |||||
| and gp, gp, ra | |||||
| xor ra, ra, sp | |||||
| sra ra, sp, sp | |||||
| sltiu gp, ra, 0x01AE | |||||
| srli sp, sp, 0x0005 | |||||
| addi ra, sp, 0x0177 | |||||
| srai sp, ra, 0x0003 | |||||
| sub sp, ra, sp | |||||
| slli sp, ra, 0x000B | |||||
| add sp, gp, ra | |||||
| slli gp, sp, 0x0006 | |||||
| ori sp, ra, 0xFFFFFF64 | |||||
| and gp, gp, gp | |||||
| andi gp, gp, 0x0084 | |||||
| xori ra, ra, 0xFFFFFEB4 | |||||
| or sp, ra, ra | or sp, ra, ra | ||||
| xori ra, sp, 0x003D | |||||
| srli sp, sp, 0xFFFFFFF2 | |||||
| addi ra, sp, 0x0012 | |||||
| add ra, gp, sp | |||||
| ori gp, ra, 0xFFFFFFB8 | |||||
| sll ra, ra, ra | |||||
| sll sp, gp, ra | |||||
| slt ra, gp, ra | |||||
| srai gp, gp, 0xFFFFFFFB | |||||
| slli ra, ra, 0x0007 | |||||
| sub sp, gp, sp | |||||
| andi ra, gp, 0x002D | |||||
| sub gp, gp, sp | |||||
| srai ra, gp, 0x0005 | |||||
| or sp, ra, sp | |||||
| xori ra, gp, 0xFFFFFF54 | |||||
| sll ra, sp, ra | |||||
| sub gp, gp, sp | |||||
| add ra, sp, sp | |||||
| sll ra, gp, ra | |||||
| add gp, sp, sp | |||||
| ori gp, sp, 0xFFFFFE68 | |||||
| srli sp, gp, 0xFFFFFFF1 | |||||
| sltui ra, ra, 0xFFFFFE5D | |||||
| srli ra, gp, 0x0006 | |||||
| srai sp, sp, 0x0005 | |||||
| andi sp, sp, 0x0129 | |||||
| and sp, sp, sp | |||||
| slli gp, ra, 0x0001 | |||||
| or gp, gp, gp | |||||
| or sp, gp, gp | |||||
| slli gp, gp, 0x0006 | |||||
| srl sp, ra, gp | |||||
| sltui gp, ra, 0xFFFFFEC3 | |||||
| add sp, gp, sp | |||||
| xori ra, ra, 0xFFFFFFA2 | |||||
| or gp, gp, sp | |||||
| and sp, gp, gp | |||||
| srai gp, sp, 0x0008 | |||||
| add sp, sp, ra | |||||
| slti sp, ra, 0xFFFFFFF7 | |||||
| srli gp, ra, 0xFFFFFFFD | |||||
| sll gp, ra, gp | |||||
| sltu sp, sp, gp | |||||
| srli gp, ra, 0x0002 | |||||
| ori gp, sp, 0xFFFFFF28 | |||||
| srl ra, gp, ra | |||||
| slti gp, ra, 0x0054 | |||||
| or gp, ra, ra | |||||
| ori sp, gp, 0x01D9 | |||||
| addi sp, ra, 0x0078 | |||||
| sltiu sp, sp, 0xFFFFFF1E | |||||
| srli gp, sp, 0x0000 | |||||
| slti sp, ra, 0xFFFFFEF7 | |||||
| srai ra, ra, 0x0001 | |||||
| or sp, ra, gp | |||||
| xor sp, sp, ra | |||||
| sub sp, ra, sp | |||||
| sub ra, gp, ra | |||||
| sltiu gp, sp, 0xFFFFFE85 | |||||
| addi sp, gp, 0x017C | |||||
| sltiu ra, gp, 0xFFFFFF64 | |||||
| xori sp, gp, 0x00A1 | |||||
| xor ra, sp, gp | |||||
| ori gp, ra, 0x00B6 | |||||
| add ra, ra, sp | |||||
| sltiu gp, ra, 0xFFFFFFEC | |||||
| sltu gp, sp, ra | |||||
| sll sp, ra, gp | |||||
| add gp, ra, ra | |||||
| or gp, ra, gp | |||||
| xor sp, ra, sp | |||||
| addi sp, gp, 0xFFFFFF4C | |||||
| xor ra, sp, gp | |||||
| xori ra, sp, 0xFFFFFF72 | |||||
| xori gp, sp, 0xFFFFFE95 | |||||
| or ra, ra, ra | |||||
| slti ra, gp, 0xFFFFFE75 | |||||
| slli sp, sp, 0x0004 | |||||
| sltiu ra, ra, 0xFFFFFE25 | |||||
| add sp, ra, gp | |||||
| sltiu gp, gp, 0xFFFFFFDB | |||||
| addi sp, sp, 0x003D | |||||
| sll ra, ra, sp | |||||
| ori ra, ra, 0x012C | |||||
| add gp, ra, gp | |||||
| xori sp, sp, 0x0157 | |||||
| slti gp, sp, 0xFFFFFF2A | |||||
| and sp, ra, ra | and sp, ra, ra | ||||
| addi sp, gp, 0x0054 | |||||
| slli gp, ra, 0xFFFFFFF2 | |||||
| ori sp, sp, 0x0093 | |||||
| add gp, gp, gp | |||||
| and gp, gp, gp | |||||
| sltui gp, ra, 0x00DE | |||||
| slli sp, gp, 0x000D | |||||
| slli sp, ra, 0xFFFFFFF5 | |||||
| sltui sp, ra, 0xFFFFFF0E | |||||
| and ra, gp, ra | |||||
| add gp, sp, sp | |||||
| slti ra, sp, 0x008C | |||||
| srli ra, sp, 0x0000 | |||||
| addi sp, sp, 0x0168 | |||||
| slli ra, ra, 0xFFFFFFF3 | |||||
| addi ra, gp, 0x012A | |||||
| or sp, gp, ra | |||||
| add ra, sp, gp | |||||
| and gp, ra, ra | |||||
| slli ra, gp, 0xFFFFFFF6 | |||||
| or sp, gp, sp | |||||
| or gp, ra, ra | |||||
| ori gp, ra, 0x00EB | |||||
| or sp, gp, ra | |||||
| ori gp, sp, 0x01DA | |||||
| andi ra, ra, 0xFFFFFFE9 | |||||
| addi gp, sp, 0x00C9 | |||||
| sltui ra, ra, 0xFFFFFF13 | |||||
| sltui ra, ra, 0xFFFFFF3A | |||||
| sltui sp, gp, 0xFFFFFE5A | |||||
| ori sp, sp, 0xFFFFFFFE | |||||
| and gp, sp, gp | |||||
| sltui sp, ra, 0x0034 | |||||
| srl gp, gp, ra | |||||
| sll gp, sp, ra | |||||
| ori ra, gp, 0xFFFFFEB6 | |||||
| sll ra, sp, ra | |||||
| sra ra, gp, sp | |||||
| sub ra, sp, gp | |||||
| xor gp, gp, sp | |||||
| sub ra, ra, sp | |||||
| srl gp, gp, sp | |||||
| andi ra, ra, 0xFFFFFFCB | |||||
| ori ra, ra, 0xFFFFFE1B | |||||
| andi ra, ra, 0xFFFFFEC8 | |||||
| sltui sp, gp, 0x0108 | |||||
| add gp, ra, ra | |||||
| sltiu ra, gp, 0xFFFFFE56 | |||||
| sra gp, gp, ra | |||||
| xori sp, gp, 0xFFFFFF0D | |||||
| sub sp, gp, ra | sub sp, gp, ra | ||||
| slti ra, sp, 0x015D | |||||
| slli sp, sp, 0x0004 | |||||
| xor gp, sp, ra | |||||
| srl ra, gp, ra | |||||
| sltui ra, ra, 0xFFFFFF3C | |||||
| add sp, sp, sp | |||||
| add gp, gp, ra | |||||
| andi sp, sp, 0xFFFFFF3A | |||||
| srli ra, sp, 0x0004 | |||||
| ori sp, gp, 0xFFFFFEAB | |||||
| ori sp, ra, 0xFFFFFE95 | |||||
| slli sp, sp, 0xFFFFFFF2 | |||||
| xori gp, sp, 0x0040 | |||||
| slti gp, sp, 0xFFFFFED1 | |||||
| or sp, sp, sp | |||||
| sltui sp, gp, 0x01B4 | |||||
| addi ra, gp, 0x002D | |||||
| and sp, gp, gp | |||||
| or ra, ra, ra | |||||
| or ra, gp, ra | |||||
| or ra, gp, ra | |||||
| sra ra, ra, gp | |||||
| sra gp, ra, sp | |||||
| sub ra, sp, ra | |||||
| slti ra, ra, 0x0154 | |||||
| slli ra, ra, 0x000A | |||||
| ori ra, gp, 0xFFFFFEC2 | |||||
| ori ra, sp, 0x0075 | |||||
| addi gp, sp, 0x0079 | |||||
| xor gp, ra, sp | |||||
| srli ra, sp, 0x0008 | |||||
| srai ra, ra, 0x000F | srai ra, ra, 0x000F | ||||
| sltu sp, sp, ra | |||||
| slli ra, gp, 0xFFFFFFF5 | |||||
| slti gp, gp, 0x00E0 | |||||
| addi gp, ra, 0xFFFFFF72 | |||||
| srl ra, ra, gp | |||||
| sltui gp, sp, 0xFFFFFEAA | |||||
| xor sp, ra, gp | |||||
| and gp, sp, ra | |||||
| srli gp, gp, 0x0003 | |||||
| xori ra, ra, 0x01BD | |||||
| sub ra, gp, sp | |||||
| slli gp, gp, 0x0006 | |||||
| sra sp, gp, gp | |||||
| add sp, sp, sp | |||||
| srai ra, sp, 0x0001 | |||||
| slli gp, ra, 0x0010 | |||||
| andi ra, ra, 0xFFFFFFA8 | |||||
| add sp, ra, sp | |||||
| srai ra, gp, 0x000E | |||||
| srai ra, sp, 0x0005 | |||||
| addi ra, gp, 0xFFFFFF83 | |||||
| xor gp, sp, ra | |||||
| srai sp, gp, 0x0004 | |||||
| srli ra, ra, 0x0007 | |||||
| sll gp, ra, gp | sll gp, ra, gp | ||||
| xori ra, sp, 0x0065 | |||||
| or ra, sp, ra | |||||
| slt sp, gp, ra | |||||
| addi ra, sp, 0xFFFFFE34 | |||||
| slli gp, sp, 0x0007 | |||||
| sll ra, sp, gp | |||||
| sltui gp, gp, 0xFFFFFE62 | |||||
| slti sp, sp, 0x0019 | |||||
| xori ra, gp, 0x0092 | |||||
| sltui gp, sp, 0xFFFFFF29 | |||||
| srl sp, ra, gp | |||||
| xori sp, gp, 0xFFFFFF4C | |||||
| add sp, ra, gp | |||||
| add sp, gp, ra | |||||
| xori gp, gp, 0x0163 | |||||
| add ra, gp, gp | |||||
| srli gp, gp, 0x000B | |||||
| add sp, ra, ra | |||||
| sltu ra, ra, sp | |||||
| sll sp, ra, ra | |||||
| ori sp, sp, 0xFFFFFF6B | |||||
| slli gp, gp, 0x0006 | |||||
| xori sp, ra, 0x00A7 | |||||
| add sp, ra, ra | |||||
| add ra, gp, gp | |||||
| addi gp, gp, 0xFFFFFFE9 | |||||
| sra sp, ra, gp | |||||
| add gp, ra, ra | |||||
| ori gp, gp, 0x0002 | |||||
| addi gp, gp, 0x002F | |||||
| sll sp, sp, ra | |||||
| srli sp, ra, 0x000E | |||||
| ori gp, sp, 0x00EB | |||||
| sra gp, ra, sp | |||||
| sra sp, sp, gp | sra sp, sp, gp | ||||
| slli sp, ra, 0x0008 | |||||
| srl sp, sp, sp | |||||
| and gp, ra, ra | |||||
| sra ra, ra, gp | |||||
| add sp, gp, ra | add sp, gp, ra | ||||
| andi sp, sp, 0x0039 | |||||
| sll ra, gp, sp | |||||
| andi gp, ra, 0xFFFFFECC | |||||
| sll sp, sp, sp | |||||
| sub sp, sp, ra | |||||
| srai ra, sp, 0x0008 | |||||
| xor gp, ra, sp | |||||
| add sp, sp, sp | |||||
| sub gp, ra, gp | |||||
| xori gp, sp, 0x01EE | |||||
| and ra, ra, ra | |||||
| ori gp, ra, 0xFFFFFE96 | |||||
| slli ra, gp, 0x0002 | |||||
| srli gp, ra, 0x000D | |||||
| add ra, sp, sp | |||||
| andi sp, gp, 0xFFFFFEC0 | |||||
| andi sp, gp, 0xFFFFFE7A | |||||
| xori ra, sp, 0x0169 | |||||
| xori gp, sp, 0xFFFFFE02 | |||||
| andi ra, ra, 0xFFFFFFD1 | |||||
| xor ra, sp, gp | |||||
| xori gp, gp, 0x00AB | |||||
| srl ra, ra, gp | |||||
| and ra, ra, sp | |||||
| xori gp, sp, 0x005D | |||||
| srai sp, sp, 0x000A | |||||
| addi ra, sp, 0xFFFFFE19 | |||||
| srl gp, sp, gp | |||||
| add ra, ra, sp | |||||
| srai gp, ra, 0x000E | |||||
| sltu gp, gp, sp | |||||
| srli sp, ra, 0x0004 | |||||
| ori gp, sp, 0xFFFFFE6E | |||||
| and gp, ra, ra | |||||
| ori gp, ra, 0xFFFFFFAF | |||||
| srl ra, ra, ra | |||||
| or sp, ra, ra | or sp, ra, ra | ||||
| addi ra, gp, 0x0084 | |||||
| ori sp, sp, 0xFFFFFF3D | |||||
| xor gp, ra, gp | |||||
| sra ra, ra, gp | |||||
| xori ra, sp, 0x0040 | |||||
| srai gp, gp, 0x0002 | |||||
| xori ra, ra, 0xFFFFFE9A | |||||
| sra ra, sp, sp | |||||
| ori gp, sp, 0xFFFFFFB8 | |||||
| sll sp, ra, ra | |||||
| sll sp, ra, gp | |||||
| sll gp, sp, sp | |||||
| sra gp, ra, ra | |||||
| srli gp, gp, 0x0001 | |||||
| ori gp, sp, 0x0018 | |||||
| and gp, gp, gp | |||||
| sll gp, sp, gp | |||||
| srli gp, sp, 0x0006 | |||||
| add gp, ra, ra | |||||
| add gp, ra, sp | |||||
| sra sp, ra, ra | |||||
| ori sp, ra, 0x0022 | |||||
| and gp, gp, gp | |||||
| add ra, sp, ra | |||||
| sll sp, gp, gp | |||||
| ori gp, sp, 0x008E | |||||
| add sp, ra, sp | |||||
| and sp, gp, gp | |||||
| addi ra, sp, 0x0145 | |||||
| and sp, gp, gp | |||||
| sll gp, ra, sp | |||||
| addi sp, sp, 0xFFFFFFAF | |||||
| xori sp, ra, 0xFFFFFE2C | |||||
| srl gp, ra, gp | |||||
| sub ra, sp, gp | |||||
| add sp, ra, ra | |||||
| slli sp, sp, 0x0006 | |||||
| sltu gp, sp, ra | |||||
| sub gp, ra, sp | |||||
| xori ra, ra, 0xFFFFFF9A | |||||
| addi sp, sp, 0xFFFFFE12 | |||||
| slli ra, ra, 0x0003 | |||||
| slli gp, ra, 0x0004 | |||||
| add gp, gp, gp | |||||
| xori ra, ra, 0xFFFFFED7 | |||||
| andi gp, gp, 0xFFFFFE05 | |||||
| and gp, gp, sp | |||||
| addi gp, gp, 0xFFFFFEE5 | |||||
| slli ra, gp, 0x000A | |||||
| sll sp, gp, gp | |||||
| and ra, gp, sp | |||||
| ori ra, gp, 0xFFFFFE22 | |||||
| srl sp, sp, gp | |||||
| srli ra, sp, 0x0005 | |||||
| slli ra, ra, 0x0005 | |||||
| srai ra, ra, 0x0007 | |||||
| srli ra, gp, 0x000F | |||||
| andi gp, gp, 0xFFFFFF96 | |||||
| sra sp, gp, gp | |||||
| srai gp, gp, 0x000F | |||||
| sub sp, sp, gp | |||||
| sltiu ra, ra, 0xFFFFFF41 | |||||
| and sp, sp, sp | |||||
| xor gp, sp, ra | |||||
| srai gp, sp, 0x000A | |||||
| xori gp, gp, 0x00D3 | |||||
| or gp, sp, sp | |||||
| sltu gp, ra, gp | |||||
| slli ra, gp, 0x0002 | |||||
| or sp, gp, ra | |||||
| addi ra, ra, 0x002B | |||||
| addi gp, ra, 0x0035 | |||||
| slli sp, gp, 0x0008 | |||||
| addi gp, sp, 0x015E | |||||
| xor ra, gp, sp | |||||
| or ra, gp, ra | |||||
| sll ra, gp, ra | |||||
| sll gp, gp, ra | |||||
| srli gp, ra, 0x000C | |||||
| slt sp, ra, sp | |||||
| sltiu sp, sp, 0xFFFFFE1C | |||||
| ori sp, ra, 0xFFFFFE83 | |||||
| andi sp, sp, 0xFFFFFEFC | |||||
| addi ra, ra, 0xFFFFFF85 | |||||
| ori gp, ra, 0x0084 | |||||
| sll gp, gp, ra | |||||
| xori gp, sp, 0xFFFFFF6D | |||||
| sll gp, sp, gp | |||||
| sra ra, sp, ra | |||||
| xor ra, gp, sp | |||||
| srl ra, ra, sp | |||||
| srl ra, ra, sp | |||||
| andi gp, ra, 0xFFFFFE7B | |||||
| srai ra, sp, 0x000F | |||||
| sub sp, sp, ra | |||||
| or sp, gp, gp | |||||
| slt ra, ra, gp | |||||
| or gp, gp, sp | |||||
| srli ra, sp, 0x000B | |||||
| andi ra, gp, 0xFFFFFFD4 | |||||
| slli ra, gp, 0x0009 | |||||
| done | done | ||||
| #regset x1, 123 | #regset x1, 123 | ||||
| #regset x2, -40 | #regset x2, -40 | ||||
| @@ -1,205 +1,205 @@ | |||||
| main: | main: | ||||
| sltui gp, ra, 0x01AE | |||||
| srli sp, sp, 0xFFFFFFFB | |||||
| addi ra, sp, 0x0177 | |||||
| sub sp, ra, sp | |||||
| slli sp, ra, 0x000B | |||||
| add sp, gp, ra | |||||
| slli gp, sp, 0x0006 | |||||
| ori sp, ra, 0xFFFFFF64 | |||||
| and gp, gp, gp | |||||
| andi gp, gp, 0x0084 | |||||
| xori ra, ra, 0xFFFFFEB4 | |||||
| or sp, ra, ra | |||||
| addi sp, ra, 0x0078 | |||||
| srli gp, sp, 0x0000 | |||||
| srl sp, gp, sp | |||||
| andi ra, gp, 0xFFFFFFF4 | |||||
| srai ra, ra, 0xFFFFFFFF | |||||
| sltu gp, sp, gp | |||||
| or sp, ra, gp | |||||
| sub ra, gp, ra | |||||
| addi sp, gp, 0x017C | |||||
| sltui ra, gp, 0xFFFFFF64 | |||||
| xori sp, gp, 0x00A1 | |||||
| xor ra, sp, gp | |||||
| ori gp, ra, 0x00B6 | |||||
| add ra, ra, sp | |||||
| sltui gp, ra, 0xFFFFFFEC | |||||
| sltu gp, sp, ra | |||||
| sll sp, ra, gp | |||||
| add gp, ra, ra | |||||
| or gp, ra, gp | |||||
| xor sp, ra, sp | |||||
| addi sp, gp, 0xFFFFFF4C | |||||
| xor ra, sp, gp | |||||
| xori ra, sp, 0xFFFFFF72 | |||||
| xori gp, sp, 0xFFFFFE95 | |||||
| or ra, ra, ra | |||||
| slti ra, gp, 0xFFFFFE75 | |||||
| slli sp, sp, 0xFFFFFFFC | |||||
| sltui ra, ra, 0xFFFFFE25 | |||||
| add sp, ra, gp | |||||
| sltui gp, gp, 0xFFFFFFDB | |||||
| addi sp, sp, 0x003D | |||||
| sll ra, ra, sp | |||||
| ori ra, ra, 0x012C | |||||
| add gp, ra, gp | |||||
| xori sp, sp, 0x0157 | |||||
| slti gp, sp, 0xFFFFFF2A | |||||
| and sp, ra, ra | |||||
| add gp, ra, ra | |||||
| sltui ra, gp, 0xFFFFFE56 | |||||
| sra gp, gp, ra | |||||
| xori sp, gp, 0xFFFFFF0D | |||||
| sub sp, gp, ra | |||||
| slti ra, ra, 0x0154 | |||||
| slli ra, ra, 0x000A | |||||
| ori ra, gp, 0xFFFFFEC2 | |||||
| ori ra, sp, 0x0075 | |||||
| addi gp, sp, 0x0079 | |||||
| xor gp, ra, sp | |||||
| srli ra, sp, 0xFFFFFFF8 | |||||
| slli gp, gp, 0x0006 | |||||
| sra sp, gp, gp | |||||
| add sp, sp, sp | |||||
| slli gp, ra, 0xFFFFFFF0 | |||||
| add sp, ra, sp | |||||
| srai ra, sp, 0x0005 | |||||
| addi ra, gp, 0xFFFFFF83 | |||||
| xor gp, sp, ra | |||||
| srli ra, ra, 0x0007 | |||||
| sll gp, ra, gp | |||||
| xori gp, gp, 0x0163 | |||||
| add ra, gp, gp | |||||
| add sp, ra, ra | |||||
| sltu ra, ra, sp | |||||
| sll sp, ra, ra | |||||
| ori sp, sp, 0xFFFFFF6B | |||||
| slli gp, gp, 0xFFFFFFFA | |||||
| xori sp, ra, 0x00A7 | |||||
| add sp, ra, ra | |||||
| add ra, gp, gp | |||||
| addi gp, gp, 0xFFFFFFE9 | |||||
| sra sp, ra, gp | |||||
| add gp, ra, ra | |||||
| ori gp, gp, 0x0002 | |||||
| addi gp, gp, 0x002F | |||||
| sll sp, sp, ra | |||||
| srli sp, ra, 0xFFFFFFF2 | |||||
| ori gp, sp, 0x00EB | |||||
| sra gp, ra, sp | |||||
| sra sp, sp, gp | |||||
| and gp, ra, ra | |||||
| sra ra, ra, gp | |||||
| add sp, gp, ra | |||||
| srl gp, sp, gp | |||||
| add ra, ra, sp | |||||
| srai gp, ra, 0xFFFFFFF2 | |||||
| srli sp, ra, 0xFFFFFFFC | |||||
| ori gp, sp, 0xFFFFFE6E | |||||
| and gp, ra, ra | |||||
| ori gp, ra, 0xFFFFFFAF | |||||
| srl ra, ra, ra | |||||
| or sp, ra, ra | |||||
| ori gp, sp, 0x0018 | |||||
| and gp, gp, gp | |||||
| slti gp, ra, 0x00C6 | |||||
| sll gp, sp, gp | |||||
| srli gp, sp, 0xFFFFFFFA | |||||
| add gp, ra, ra | |||||
| add gp, ra, sp | |||||
| sra sp, ra, ra | |||||
| ori sp, ra, 0x0022 | |||||
| and gp, gp, gp | |||||
| add ra, sp, ra | |||||
| sll sp, gp, gp | |||||
| ori gp, sp, 0x008E | |||||
| slti ra, gp, 0x00B5 | |||||
| add sp, ra, sp | |||||
| and sp, gp, gp | |||||
| addi ra, sp, 0x0145 | |||||
| and sp, gp, gp | |||||
| sll gp, ra, sp | |||||
| addi sp, sp, 0xFFFFFFAF | |||||
| xori sp, ra, 0xFFFFFE2C | |||||
| srl gp, ra, gp | |||||
| sub ra, sp, gp | |||||
| add sp, ra, ra | |||||
| slli sp, sp, 0x0006 | |||||
| sub gp, ra, sp | |||||
| sltu sp, ra, gp | |||||
| xori ra, ra, 0xFFFFFF9A | |||||
| addi sp, sp, 0xFFFFFE12 | |||||
| slli ra, ra, 0xFFFFFFFD | |||||
| add gp, gp, gp | |||||
| xori ra, ra, 0xFFFFFED7 | |||||
| andi gp, gp, 0xFFFFFE05 | |||||
| and gp, gp, sp | |||||
| addi gp, gp, 0xFFFFFEE5 | |||||
| slli ra, gp, 0xFFFFFFF6 | |||||
| sll sp, gp, gp | |||||
| and ra, gp, sp | |||||
| ori ra, gp, 0xFFFFFE22 | |||||
| srl sp, sp, gp | |||||
| srli ra, sp, 0x0005 | |||||
| slli ra, ra, 0xFFFFFFFB | |||||
| srai ra, ra, 0xFFFFFFF9 | |||||
| srli ra, gp, 0xFFFFFFF1 | |||||
| andi gp, gp, 0xFFFFFF96 | |||||
| sra sp, gp, gp | |||||
| srai gp, gp, 0x000F | |||||
| sub sp, sp, gp | |||||
| sltui ra, ra, 0xFFFFFF41 | |||||
| and sp, sp, sp | |||||
| xor gp, sp, ra | |||||
| srai gp, sp, 0xFFFFFFF6 | |||||
| xori gp, gp, 0x00D3 | |||||
| or gp, sp, sp | |||||
| sltu gp, ra, gp | |||||
| slli ra, gp, 0x0002 | |||||
| or sp, gp, ra | |||||
| addi ra, ra, 0x002B | |||||
| addi gp, ra, 0x0035 | |||||
| slli sp, gp, 0x0008 | |||||
| addi gp, sp, 0x015E | |||||
| xor ra, gp, sp | |||||
| or ra, gp, ra | |||||
| sll ra, gp, ra | |||||
| sll gp, gp, ra | |||||
| srli gp, ra, 0xFFFFFFF4 | |||||
| slt sp, ra, sp | |||||
| sltui sp, sp, 0xFFFFFE1C | |||||
| ori sp, ra, 0xFFFFFE83 | |||||
| andi sp, sp, 0xFFFFFEFC | |||||
| addi ra, ra, 0xFFFFFF85 | |||||
| ori gp, ra, 0x0084 | |||||
| sll gp, gp, ra | |||||
| xori gp, sp, 0xFFFFFF6D | |||||
| sll gp, sp, gp | |||||
| sra ra, sp, ra | |||||
| xor ra, gp, sp | |||||
| srl ra, ra, sp | |||||
| srl ra, ra, sp | |||||
| andi gp, ra, 0xFFFFFE7B | |||||
| srai ra, sp, 0xFFFFFFF1 | |||||
| sub sp, sp, ra | |||||
| or sp, gp, gp | |||||
| slt ra, ra, gp | |||||
| or gp, gp, sp | |||||
| srli ra, sp, 0xFFFFFFF5 | |||||
| andi ra, gp, 0xFFFFFFD4 | |||||
| sra sp, sp, sp | |||||
| add sp, ra, sp | |||||
| sub gp, ra, sp | |||||
| xori ra, gp, 0x0131 | |||||
| add sp, sp, ra | |||||
| addi sp, gp, 0x0003 | |||||
| sll ra, ra, ra | |||||
| slli gp, ra, 0x000E | |||||
| andi ra, gp, 0xFFFFFE88 | |||||
| srai ra, gp, 0xFFFFFFFA | |||||
| done | |||||
| ori gp, gp, 0xFFFFFE09 | |||||
| and gp, gp, ra | |||||
| srli sp, ra, 0x0002 | |||||
| xor ra, ra, sp | |||||
| or sp, ra, ra | |||||
| xori ra, sp, 0x003D | |||||
| addi ra, sp, 0x0012 | |||||
| add ra, gp, sp | |||||
| ori gp, ra, 0xFFFFFFB8 | |||||
| sll ra, ra, ra | |||||
| sll sp, gp, ra | |||||
| slt ra, gp, ra | |||||
| srai gp, gp, 0x0005 | |||||
| slli ra, ra, 0x0007 | |||||
| sub sp, gp, sp | |||||
| andi ra, gp, 0x002D | |||||
| sub gp, gp, sp | |||||
| srai ra, gp, 0x0005 | |||||
| or sp, ra, sp | |||||
| xori ra, gp, 0xFFFFFF54 | |||||
| sll ra, sp, ra | |||||
| sub gp, gp, sp | |||||
| add ra, sp, sp | |||||
| sll ra, gp, ra | |||||
| add gp, sp, sp | |||||
| ori gp, sp, 0xFFFFFE68 | |||||
| srli sp, gp, 0x000F | |||||
| sltiu ra, ra, 0xFFFFFE5D | |||||
| srli ra, gp, 0x0006 | |||||
| srai sp, sp, 0x0005 | |||||
| andi sp, sp, 0x0129 | |||||
| and sp, sp, sp | |||||
| slli gp, ra, 0x0001 | |||||
| or gp, gp, gp | |||||
| or sp, gp, gp | |||||
| slli gp, gp, 0x0006 | |||||
| srl sp, ra, gp | |||||
| sltiu gp, ra, 0xFFFFFEC3 | |||||
| add sp, gp, sp | |||||
| srli ra, sp, 0x0001 | |||||
| xori ra, ra, 0xFFFFFFA2 | |||||
| or gp, gp, sp | |||||
| and sp, gp, gp | |||||
| srai gp, sp, 0x0008 | |||||
| add sp, sp, ra | |||||
| slti sp, ra, 0xFFFFFFF7 | |||||
| srli gp, ra, 0x0003 | |||||
| sll gp, ra, gp | |||||
| sltu sp, sp, gp | |||||
| srli gp, ra, 0x0002 | |||||
| ori gp, sp, 0xFFFFFF28 | |||||
| srl ra, gp, ra | |||||
| or gp, ra, ra | |||||
| ori sp, gp, 0x01D9 | |||||
| and sp, ra, ra | |||||
| addi sp, gp, 0x0054 | |||||
| slli gp, ra, 0x000E | |||||
| ori sp, sp, 0x0093 | |||||
| srai sp, ra, 0x000F | |||||
| slti ra, gp, 0xFFFFFFCB | |||||
| add gp, gp, gp | |||||
| and gp, gp, gp | |||||
| sltiu gp, ra, 0x00DE | |||||
| slli sp, gp, 0x000D | |||||
| slli sp, ra, 0x000B | |||||
| sltiu sp, ra, 0xFFFFFF0E | |||||
| and ra, gp, ra | |||||
| add gp, sp, sp | |||||
| slti ra, sp, 0x008C | |||||
| srli ra, sp, 0x0000 | |||||
| addi sp, sp, 0x0168 | |||||
| slli ra, ra, 0x000D | |||||
| addi ra, gp, 0x012A | |||||
| or sp, gp, ra | |||||
| add ra, sp, gp | |||||
| and gp, ra, ra | |||||
| slli ra, gp, 0x000A | |||||
| or sp, gp, sp | |||||
| or gp, ra, ra | |||||
| srli ra, sp, 0x0002 | |||||
| ori gp, ra, 0x00EB | |||||
| or sp, gp, ra | |||||
| ori gp, sp, 0x01DA | |||||
| andi ra, ra, 0xFFFFFFE9 | |||||
| addi gp, sp, 0x00C9 | |||||
| sltiu ra, ra, 0xFFFFFF13 | |||||
| sltiu ra, ra, 0xFFFFFF3A | |||||
| sltiu sp, gp, 0xFFFFFE5A | |||||
| ori sp, sp, 0xFFFFFFFE | |||||
| and gp, sp, gp | |||||
| sltiu sp, ra, 0x0034 | |||||
| srl gp, gp, ra | |||||
| sll gp, sp, ra | |||||
| ori ra, gp, 0xFFFFFEB6 | |||||
| sll ra, sp, ra | |||||
| sra ra, gp, sp | |||||
| sub ra, sp, gp | |||||
| xor gp, gp, sp | |||||
| sub ra, ra, sp | |||||
| srl gp, gp, sp | |||||
| andi ra, ra, 0xFFFFFFCB | |||||
| ori ra, ra, 0xFFFFFE1B | |||||
| andi ra, ra, 0xFFFFFEC8 | |||||
| sltiu sp, gp, 0x0108 | |||||
| sub sp, gp, ra | |||||
| slti ra, sp, 0x015D | |||||
| slli sp, sp, 0x0004 | |||||
| xor gp, sp, ra | |||||
| srl ra, gp, ra | |||||
| sltiu ra, ra, 0xFFFFFF3C | |||||
| add sp, sp, sp | |||||
| add gp, gp, ra | |||||
| slli gp, gp, 0x0001 | |||||
| andi sp, sp, 0xFFFFFF3A | |||||
| slt gp, sp, gp | |||||
| srli ra, sp, 0x0004 | |||||
| ori sp, gp, 0xFFFFFEAB | |||||
| ori sp, ra, 0xFFFFFE95 | |||||
| slli sp, sp, 0x000E | |||||
| xori gp, sp, 0x0040 | |||||
| slti gp, sp, 0xFFFFFED1 | |||||
| or sp, sp, sp | |||||
| sltiu sp, gp, 0x01B4 | |||||
| addi ra, gp, 0x002D | |||||
| and sp, gp, gp | |||||
| or ra, ra, ra | |||||
| or ra, gp, ra | |||||
| srli ra, ra, 0x0004 | |||||
| or ra, gp, ra | |||||
| sra ra, ra, gp | |||||
| slli ra, gp, 0x000B | |||||
| slti gp, gp, 0x00E0 | |||||
| addi gp, ra, 0xFFFFFF72 | |||||
| sltiu gp, sp, 0xFFFFFEAA | |||||
| xor sp, ra, gp | |||||
| and gp, sp, ra | |||||
| srli gp, gp, 0x0003 | |||||
| xori ra, ra, 0x01BD | |||||
| srl ra, ra, gp | |||||
| srai ra, gp, 0x0006 | |||||
| sub ra, gp, sp | |||||
| sll gp, ra, gp | |||||
| xori ra, sp, 0x0065 | |||||
| and ra, gp, ra | |||||
| or ra, sp, ra | |||||
| slt sp, gp, ra | |||||
| addi ra, sp, 0xFFFFFE34 | |||||
| slli gp, sp, 0x0007 | |||||
| sll ra, sp, gp | |||||
| sltiu gp, gp, 0xFFFFFE62 | |||||
| slti sp, sp, 0x0019 | |||||
| xori ra, gp, 0x0092 | |||||
| sltiu gp, sp, 0xFFFFFF29 | |||||
| srl sp, ra, gp | |||||
| xori sp, gp, 0xFFFFFF4C | |||||
| add sp, ra, gp | |||||
| add sp, gp, ra | |||||
| sra sp, sp, gp | |||||
| slli sp, ra, 0x0008 | |||||
| srl sp, sp, sp | |||||
| add sp, gp, ra | |||||
| andi sp, sp, 0x0039 | |||||
| sll ra, gp, sp | |||||
| andi gp, ra, 0xFFFFFECC | |||||
| sll sp, sp, sp | |||||
| sub sp, sp, ra | |||||
| srai ra, sp, 0x0008 | |||||
| xor gp, ra, sp | |||||
| add sp, sp, sp | |||||
| sub gp, ra, gp | |||||
| xori gp, sp, 0x01EE | |||||
| and ra, ra, ra | |||||
| ori gp, ra, 0xFFFFFE96 | |||||
| slli ra, gp, 0x0002 | |||||
| srli gp, ra, 0x000D | |||||
| srli sp, gp, 0x0005 | |||||
| add ra, sp, sp | |||||
| andi sp, gp, 0xFFFFFEC0 | |||||
| andi sp, gp, 0xFFFFFE7A | |||||
| xori ra, sp, 0x0169 | |||||
| xori gp, sp, 0xFFFFFE02 | |||||
| andi ra, ra, 0xFFFFFFD1 | |||||
| xor ra, sp, gp | |||||
| xori gp, gp, 0x00AB | |||||
| srl ra, ra, gp | |||||
| and ra, ra, sp | |||||
| xori gp, sp, 0x005D | |||||
| srai sp, sp, 0x000A | |||||
| addi ra, sp, 0xFFFFFE19 | |||||
| or sp, ra, ra | |||||
| addi ra, gp, 0x0084 | |||||
| ori sp, sp, 0xFFFFFF3D | |||||
| xor gp, ra, gp | |||||
| sra ra, ra, gp | |||||
| xori ra, sp, 0x0040 | |||||
| srai gp, gp, 0x0002 | |||||
| xori ra, ra, 0xFFFFFE9A | |||||
| sra ra, sp, sp | |||||
| ori gp, sp, 0xFFFFFFB8 | |||||
| sll sp, ra, ra | |||||
| done | |||||
| #regset x1, 123 | #regset x1, 123 | ||||
| #regset x2, -40 | #regset x2, -40 | ||||
| #regset x3, 0xFFEE | #regset x3, 0xFFEE | ||||
| @@ -158,12 +158,13 @@ object Data { | |||||
| rightShifted | rightShifted | ||||
| } | } | ||||
| def splitLoHi(loBits: Int): (Int, Int) = { | |||||
| val hiBits = 32 - loBits | |||||
| val sep = 31 - loBits | |||||
| val lo = i.field(31, loBits) | |||||
| val hi = i.field(sep, hiBits) | |||||
| (lo, hi) | |||||
| def splitHiLo(hiBits: Int): (Int, Int) = { | |||||
| val loBits = 32 - hiBits | |||||
| val sep = 31 - hiBits | |||||
| val hi = i.field(31, hiBits) | |||||
| val lo = i.field(sep, loBits) | |||||
| say(s"split lo hi for $i with $hiBits high bits and got low: $lo, high: $hi") | |||||
| (hi, lo) | |||||
| } | } | ||||
| def log2: Int = math.ceil(math.log(i.toDouble)/math.log(2.0)).toInt | def log2: Int = math.ceil(math.log(i.toDouble)/math.log(2.0)).toInt | ||||
| @@ -93,14 +93,17 @@ object Ops { | |||||
| def or( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), OR) | def or( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), OR) | ||||
| def xor( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), XOR) | def xor( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), XOR) | ||||
| def and( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), AND) | def and( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), AND) | ||||
| def sll( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), SLL) | |||||
| def srl( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), SRL) | |||||
| def sra( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), SRA) | |||||
| def slt( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), SLT) | def slt( rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), SLT) | ||||
| def sltu(rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), SLTU) | def sltu(rd: Int, rs1: Int, imm: Int) = ArithImm(Reg(rd), Reg(rs1), Imm(imm), SLTU) | ||||
| def nop = add(0, 0, 0) | def nop = add(0, 0, 0) | ||||
| } | } | ||||
| case class ArithImmShift(rd: Reg, rs1: Reg, shamt: Imm, op: ArithOp) extends Op with IType | |||||
| object ArithImmShift { | |||||
| def sll( rd: Int, rs1: Int, imm: Int) = ArithImmShift(Reg(rd), Reg(rs1), Imm(imm), SLL) | |||||
| def srl( rd: Int, rs1: Int, imm: Int) = ArithImmShift(Reg(rd), Reg(rs1), Imm(imm), SRL) | |||||
| def sra( rd: Int, rs1: Int, imm: Int) = ArithImmShift(Reg(rd), Reg(rs1), Imm(imm), SRA) | |||||
| } | |||||
| case class LUI(rd: Reg, imm: Imm) extends Op with UType | case class LUI(rd: Reg, imm: Imm) extends Op with UType | ||||
| case class AUIPC(rd: Reg, imm: Imm) extends Op with UType | case class AUIPC(rd: Reg, imm: Imm) extends Op with UType | ||||
| @@ -84,12 +84,12 @@ object Parser { | |||||
| stringWs("xori") ~> arithImm.mapN{ArithImm.xor}, | stringWs("xori") ~> arithImm.mapN{ArithImm.xor}, | ||||
| stringWs("andi") ~> arithImm.mapN{ArithImm.and}, | stringWs("andi") ~> arithImm.mapN{ArithImm.and}, | ||||
| stringWs("slli") ~> arithImm.mapN{ArithImm.sll}, | |||||
| stringWs("srli") ~> arithImm.mapN{ArithImm.srl}, | |||||
| stringWs("srai") ~> arithImm.mapN{ArithImm.sra}, | |||||
| stringWs("slli") ~> arithImm.mapN{ArithImmShift.sll}, | |||||
| stringWs("srli") ~> arithImm.mapN{ArithImmShift.srl}, | |||||
| stringWs("srai") ~> arithImm.mapN{ArithImmShift.sra}, | |||||
| stringWs("slti") ~> arithImm.mapN{ArithImm.slt}, | stringWs("slti") ~> arithImm.mapN{ArithImm.slt}, | ||||
| stringWs("sltui") ~> arithImm.mapN{ArithImm.sltu}, | |||||
| stringWs("sltiu") ~> arithImm.mapN{ArithImm.sltu}, | |||||
| // pseudos | // pseudos | ||||
| stringWs("not") ~> (reg <~ sep, reg, ok(-1)).mapN{ArithImm.xor}, | stringWs("not") ~> (reg <~ sep, reg, ok(-1)).mapN{ArithImm.xor}, | ||||
| @@ -98,8 +98,11 @@ object Parser { | |||||
| // seqz rd, rs1 => sltiu rd, rs1, 1 | // seqz rd, rs1 => sltiu rd, rs1, 1 | ||||
| stringWs("seqz") ~> (reg <~ sep, reg, ok(1)).mapN{ArithImm.sltu}, | stringWs("seqz") ~> (reg <~ sep, reg, ok(1)).mapN{ArithImm.sltu}, | ||||
| stringWs("li") ~> (reg ~ sep ~ int).collect{ | |||||
| case((a, b), c) if (c.nBitsS <= 12) => ArithImm.add(a, 0, c) | |||||
| stringWs("li") ~> (reg ~ sep ~ (hex | int)).collect{ | |||||
| case((a, b), c) if (c.nBitsS <= 12) => { | |||||
| say(s"for c: $c, nBitsS was ${c.nBitsS}") | |||||
| ArithImm.add(a, 0, c) | |||||
| } | |||||
| }, | }, | ||||
| @@ -122,16 +125,16 @@ object Parser { | |||||
| //////////////////////////////////////////// | //////////////////////////////////////////// | ||||
| //// load/store | //// load/store | ||||
| stringWs("sw") ~> (reg <~ sep, int <~ char('('), reg <~ char(')')).mapN{case (rs2, offset, rs1) => SW(rs2, rs1, offset)}, | |||||
| stringWs("lw") ~> (reg <~ sep, int <~ char('('), reg <~ char(')')).mapN{case (rd, offset, rs1) => LW(rd, rs1, offset)}, | |||||
| stringWs("sw") ~> (reg <~ sep, (hex | int) <~ char('('), reg <~ char(')')).mapN{case (rs2, offset, rs1) => SW(rs2, rs1, offset)}, | |||||
| stringWs("lw") ~> (reg <~ sep, (hex | int) <~ char('('), reg <~ char(')')).mapN{case (rd, offset, rs1) => LW(rd, rs1, offset)}, | |||||
| //////////////////////////////////////////// | //////////////////////////////////////////// | ||||
| //// others | //// others | ||||
| stringWs("auipc") ~> (reg <~ sep, int).mapN{AUIPC.apply}, | |||||
| stringWs("lui") ~> (reg <~ sep, int).mapN{LUI.apply}, | |||||
| stringWs("auipc") ~> (reg <~ sep, (hex | int)).mapN{AUIPC.apply}, | |||||
| stringWs("lui") ~> (reg <~ sep, (hex | int)).mapN{LUI.apply}, | |||||
| many(whitespace) ~> string("nop") ~> ok(Arith.add(0, 0, 0)), | many(whitespace) ~> string("nop") ~> ok(Arith.add(0, 0, 0)), | ||||
| many(whitespace) ~> string("done") ~> ok(DONE), | many(whitespace) ~> string("done") ~> ok(DONE), | ||||
| @@ -140,19 +143,18 @@ object Parser { | |||||
| ).map(_.widen[Op]).reduce(_|_) | ).map(_.widen[Op]).reduce(_|_) | ||||
| // def getShiftsHalfWord(offset: Int): (Int, Int) = (offset % 4) match { | |||||
| // case 0 => (16, 16) | |||||
| // case 1 => ( | |||||
| // } | |||||
| val multipleInstructions: Parser[List[Op]] = List( | val multipleInstructions: Parser[List[Op]] = List( | ||||
| stringWs("li") ~> (reg <~ sep, int.map(_.splitLoHi(12))).mapN{ case(rd, (lo, hi)) => List( | |||||
| // stringWs("li") ~> (reg <~ sep, (hex | int).map(_.splitLoHi(20))).mapN{ case(rd, (hi, lo)) => { | |||||
| stringWs("li") ~> (reg <~ sep, (hex | int).map(_.splitHiLo(20))).mapN{ case(rd, (hi, lo)) => { | |||||
| say("hello?") | |||||
| List( | |||||
| ArithImm.add(rd, rd, lo), | |||||
| LUI(rd, hi), | LUI(rd, hi), | ||||
| ArithImm.add(rd, 0, lo) | |||||
| )}.map(_.widen[Op]), | |||||
| )}}.map(_.widen[Op]), | |||||
| // NOTE: THESE ARE NOT PSEUDO-OPS IN RISV32I! | |||||
| // NOTE: THESE ARE NOT PSEUDO-OPS IN RISC-V32I! | |||||
| // NOTE: USES A SPECIAL REGISTER | // NOTE: USES A SPECIAL REGISTER | ||||
| // NOTE: PROBABLY BROKEN, NOT EXHAUSTIVELY TESTED!!! | |||||
| stringWs("lh") ~> (reg <~ sep, int <~ char('('), reg <~ char(')')).mapN{ | stringWs("lh") ~> (reg <~ sep, int <~ char('('), reg <~ char(')')).mapN{ | ||||
| case (rd, offset, rs1) if (offset % 4 == 3) => { | case (rd, offset, rs1) if (offset % 4 == 3) => { | ||||
| val placeHolder = if(rd == Reg("a0").value) Reg("a1").value else Reg("a0").value | val placeHolder = if(rd == Reg("a0").value) Reg("a1").value else Reg("a0").value | ||||
| @@ -160,16 +162,16 @@ object Parser { | |||||
| SW(placeHolder, 0, 2048), | SW(placeHolder, 0, 2048), | ||||
| LW(placeHolder, rs1.value, (offset & 0xFFFFFF1C)), | LW(placeHolder, rs1.value, (offset & 0xFFFFFF1C)), | ||||
| LW(rd.value, rs1.value, (offset & 0xFFFFFF1C) + 4), | LW(rd.value, rs1.value, (offset & 0xFFFFFF1C) + 4), | ||||
| ArithImm.sra(placeHolder, placeHolder, 24), | |||||
| ArithImm.sll(rd.value, rd.value, 24), | |||||
| ArithImm.sra(rd.value, rd.value, 16), | |||||
| ArithImmShift.sra(placeHolder, placeHolder, 24), | |||||
| ArithImmShift.sll(rd.value, rd.value, 24), | |||||
| ArithImmShift.sra(rd.value, rd.value, 16), | |||||
| Arith.add(rd, rd, placeHolder), | Arith.add(rd, rd, placeHolder), | ||||
| LW(placeHolder, 0, 2048)).reverse | LW(placeHolder, 0, 2048)).reverse | ||||
| } | } | ||||
| case (rd, offset, rs1) if (offset % 4 == 2) => { | case (rd, offset, rs1) if (offset % 4 == 2) => { | ||||
| List( | List( | ||||
| LW(rd, rs1, (offset & 0xFFFFFF1C)), | LW(rd, rs1, (offset & 0xFFFFFF1C)), | ||||
| ArithImm.sra(rd, rd, 16) | |||||
| ArithImmShift.sra(rd, rd, 16) | |||||
| ).reverse | ).reverse | ||||
| } | } | ||||
| @@ -177,8 +179,8 @@ object Parser { | |||||
| val leftShift = if((offset % 4) == 0) 16 else 8 | val leftShift = if((offset % 4) == 0) 16 else 8 | ||||
| List( | List( | ||||
| LW(rd, rs1, (offset & 0xFFFFFF1C)), | LW(rd, rs1, (offset & 0xFFFFFF1C)), | ||||
| ArithImm.sll(rd, rd, leftShift), | |||||
| ArithImm.sra(rd, rd, 16), | |||||
| ArithImmShift.sll(rd, rd, leftShift), | |||||
| ArithImmShift.sra(rd, rd, 16), | |||||
| ).reverse | ).reverse | ||||
| } | } | ||||
| }.map(_.widen[Op]), | }.map(_.widen[Op]), | ||||
| @@ -23,16 +23,17 @@ case class VM( | |||||
| def stepInstruction: Either[Finished, ExecutionTrace[VM]] = { | def stepInstruction: Either[Finished, ExecutionTrace[VM]] = { | ||||
| if (pc.value == 0xEB1CEB1C) Left(Success) | if (pc.value == 0xEB1CEB1C) Left(Success) | ||||
| else getOp flatMap { | else getOp flatMap { | ||||
| case op: Branch => executeBranch(op) | |||||
| case op: Arith => executeArith(op) | |||||
| case op: ArithImm => executeArithImm(op) | |||||
| case op: AUIPC => executeAUIPC(op) | |||||
| case op: LUI => executeLUI(op) | |||||
| case op: JALR => executeJALR(op) | |||||
| case op: JAL => executeJAL(op) | |||||
| case op: LW => executeLW(op) | |||||
| case op: SW => executeSW(op) | |||||
| case DONE => Left(Success) | |||||
| case op: Branch => executeBranch(op) | |||||
| case op: Arith => executeArith(op) | |||||
| case op: ArithImm => executeArithImm(op) | |||||
| case op: ArithImmShift => executeArithImmShift(op) | |||||
| case op: AUIPC => executeAUIPC(op) | |||||
| case op: LUI => executeLUI(op) | |||||
| case op: JALR => executeJALR(op) | |||||
| case op: JAL => executeJAL(op) | |||||
| case op: LW => executeLW(op) | |||||
| case op: SW => executeSW(op) | |||||
| case DONE => Left(Success) | |||||
| } | } | ||||
| } | } | ||||
| @@ -75,6 +76,13 @@ case class VM( | |||||
| } | } | ||||
| private def executeArithImmShift(op: ArithImmShift) = { | |||||
| val (regUpdate, nextRegs) = regs.arithImm(op.rd, op.rs1, op.shamt, op.op.run) | |||||
| val nextVM = this.copy(regs = nextRegs) | |||||
| Right(step(nextVM, regUpdate.toList:_*)) | |||||
| } | |||||
| private def executeLUI(op: LUI) = { | private def executeLUI(op: LUI) = { | ||||
| val (regUpdate, nextRegs) = regs + (op.rd -> (op.imm.value << 12)) | val (regUpdate, nextRegs) = regs + (op.rd -> (op.imm.value << 12)) | ||||
| val nextVM = this.copy(regs = nextRegs) | val nextVM = this.copy(regs = nextRegs) | ||||
| @@ -125,12 +125,11 @@ object assembler { | |||||
| } | } | ||||
| /** | /** | ||||
| * Currently not used, thus we allow too larg shifts. | |||||
| * Used by SRI, SRAI, SLLI | |||||
| */ | */ | ||||
| def setShiftTypeImmediate(instruction: Int, immediate: Int): Int = { | |||||
| def setShiftTypeImmediate(shamt: Int, addr: Addr): Int => InstructionFragment = { | |||||
| val points = List((24, 5)) | val points = List((24, 5)) | ||||
| val withField = applyImmediate(5, immediate, points)(instruction) | |||||
| withField | |||||
| applyImmediateU(shamt, points, addr) | |||||
| } | } | ||||
| def setOpCode(opcode: Int): Int => Int = setField(0, 7, opcode) | def setOpCode(opcode: Int): Int => Int = setField(0, 7, opcode) | ||||
| @@ -142,16 +141,17 @@ object assembler { | |||||
| def setOpCode(op: Op): Int => Int = op match { | def setOpCode(op: Op): Int => Int = op match { | ||||
| case x: Branch => setOpCode("1100011".binary) | |||||
| case x: Arith => setOpCode("0110011".binary) | |||||
| case x: ArithImm => setOpCode("0010011".binary) | |||||
| case x: LW => setOpCode("0000011".binary) | |||||
| case x: SW => setOpCode("0100011".binary) | |||||
| case x: JALR => setOpCode("1100111".binary) | |||||
| case x: JAL => setOpCode("1101111".binary) | |||||
| case x: AUIPC => setOpCode("0110111".binary) | |||||
| case x: LUI => setOpCode("0010111".binary) | |||||
| case DONE => setOpCode("0010011".binary) // done is turned into a NOP in the assembler. | |||||
| case x: Branch => setOpCode("1100011".binary) | |||||
| case x: Arith => setOpCode("0110011".binary) | |||||
| case x: ArithImm => setOpCode("0010011".binary) | |||||
| case x: ArithImmShift => setOpCode("0010011".binary) | |||||
| case x: LW => setOpCode("0000011".binary) | |||||
| case x: SW => setOpCode("0100011".binary) | |||||
| case x: JALR => setOpCode("1100111".binary) | |||||
| case x: JAL => setOpCode("1101111".binary) | |||||
| case x: AUIPC => setOpCode("0010111".binary) | |||||
| case x: LUI => setOpCode("0110111".binary) | |||||
| case DONE => setOpCode("0010011".binary) // done is turned into a NOP in the assembler. | |||||
| } | } | ||||
| def setComparisonFunct(cmp: Comparison): Int => Int = cmp match { | def setComparisonFunct(cmp: Comparison): Int => Int = cmp match { | ||||
| @@ -195,7 +195,6 @@ object assembler { | |||||
| setRs1(op.rs1.value) | setRs1(op.rs1.value) | ||||
| def assembleSType(op: SType): Int => Int = { | def assembleSType(op: SType): Int => Int = { | ||||
| // say("stype") | |||||
| instruction => | instruction => | ||||
| (setRs1(op.rs1.value) andThen | (setRs1(op.rs1.value) andThen | ||||
| setRs2(op.rs2.value))(instruction) | setRs2(op.rs2.value))(instruction) | ||||
| @@ -214,16 +213,17 @@ object assembler { | |||||
| def assembleImmediate(op: Op, addr: Addr, labelMap: Map[Label, Addr]): Int => Either[(String, Addr), Int] = op match { | def assembleImmediate(op: Op, addr: Addr, labelMap: Map[Label, Addr]): Int => Either[(String, Addr), Int] = op match { | ||||
| case DONE => instruction => Right(instruction) | |||||
| case op: Arith => instruction => Right(instruction) | |||||
| case op: ArithImm => setItypeImmediate(op.imm.value, addr) | |||||
| case op: Branch => setBranchDestination(labelMap, op, addr) | |||||
| case op: JALR => instruction => labelMap.lift(op.dst).toRight(s"label ${op.dst} not found", addr).flatMap(addr => setItypeImmediate(addr.value, addr)(instruction)) | |||||
| case op: AUIPC => setUtypeImmediate(op.imm.value, addr) | |||||
| case op: LUI => setUtypeImmediate(op.imm.value, addr) | |||||
| case op: LW => setItypeImmediate(op.offset.value, addr) | |||||
| case op: SW => setStypeImmediate(op.offset.value, addr) | |||||
| case op: JAL => instruction => { | |||||
| case DONE => instruction => Right(instruction) | |||||
| case op: Arith => instruction => Right(instruction) | |||||
| case op: ArithImm => setItypeImmediate(op.imm.value, addr) | |||||
| case op: ArithImmShift => setShiftTypeImmediate(op.shamt.value, addr) | |||||
| case op: Branch => setBranchDestination(labelMap, op, addr) | |||||
| case op: JALR => instruction => labelMap.lift(op.dst).toRight(s"label ${op.dst} not found", addr).flatMap(addr => setItypeImmediate(addr.value, addr)(instruction)) | |||||
| case op: AUIPC => setUtypeImmediate(op.imm.value, addr) | |||||
| case op: LUI => setUtypeImmediate(op.imm.value, addr) | |||||
| case op: LW => setItypeImmediate(op.offset.value, addr) | |||||
| case op: SW => setStypeImmediate(op.offset.value, addr) | |||||
| case op: JAL => instruction => { | |||||
| val addressDistance = labelMap | val addressDistance = labelMap | ||||
| .lift(op.dst).toRight(s"label ${op.dst} not found", addr) | .lift(op.dst).toRight(s"label ${op.dst} not found", addr) | ||||
| .map(absoluteAddr => absoluteAddr - addr) | .map(absoluteAddr => absoluteAddr - addr) | ||||
| @@ -246,14 +246,18 @@ object assembler { | |||||
| val opcode = setOpCode(op) | val opcode = setOpCode(op) | ||||
| val extras: Int => Int = (instruction: Int) => op match { | val extras: Int => Int = (instruction: Int) => op match { | ||||
| case op: Branch => setComparisonFunct(op.comp)(instruction) | |||||
| case op: ArithImm => setArithFunct(op.op)(instruction) | |||||
| case op: Arith => setArithFunct(op.op)(instruction) | |||||
| case op: JALR => setFunct3("000".binary)(instruction) | |||||
| case op: LW => setFunct3("010".binary)(instruction) | |||||
| case op: SW => setFunct3("010".binary)(instruction) | |||||
| case DONE => (setFunct3("000".binary) andThen setFunct7("0000000".binary))(instruction) | |||||
| case _ => instruction | |||||
| case op: Branch => setComparisonFunct(op.comp)(instruction) | |||||
| case op: ArithImm => setArithFunct(op.op)(instruction) | |||||
| case op: ArithImmShift => setArithFunct(op.op)(instruction) | |||||
| case op: Arith => setArithFunct(op.op)(instruction) | |||||
| case op: JALR => setFunct3("000".binary)(instruction) | |||||
| case op: LW => setFunct3("010".binary)(instruction) | |||||
| case op: SW => setFunct3("010".binary)(instruction) | |||||
| case DONE => (setFunct3("000".binary) andThen setFunct7("0000000".binary))(instruction) | |||||
| case op: AUIPC => instruction | |||||
| case op: JAL => instruction | |||||
| case op: LUI => instruction | |||||
| } | } | ||||
| val withOp = opcode(0) | val withOp = opcode(0) | ||||
| @@ -1,178 +0,0 @@ | |||||
| package FiveStage | |||||
| import cats.data.Writer | |||||
| import cats._ | |||||
| import cats.data.{ Op => _ } | |||||
| import cats.implicits._ | |||||
| object DTree { | |||||
| // opaques WHEN | |||||
| type Feature = String | |||||
| type Value = String | |||||
| type Cls = String | |||||
| case class TrainingData(values: Map[Feature, Value], cls: Cls) | |||||
| type TestData = Map[Feature, Value] | |||||
| // Base | |||||
| // def predict(data: TestData): Cls = "Died" | |||||
| // Gendered | |||||
| def predictStatic(data: TestData): Cls = | |||||
| if(data("gender") == "female") | |||||
| "survived" | |||||
| else "died" | |||||
| sealed trait Tree | |||||
| case class Node(feature: Feature, children: Map[Value, Tree]) extends Tree | |||||
| case class Leaf(cls: Cls) extends Tree | |||||
| val genderBased: Tree = Node( | |||||
| "gender", Map( | |||||
| "female" -> Leaf("survived"), | |||||
| "male" -> Leaf("died"), | |||||
| )) | |||||
| def predict(data: TestData)(tree: Tree): Cls = | |||||
| tree match { | |||||
| case Leaf(cls) => cls | |||||
| case Node(feature, children) => predict(data)(children(data(feature))) | |||||
| } | |||||
| val data = Map("gender" -> "female", "family size" -> "0", "ticket" -> "1") | |||||
| predict(data)(genderBased) // true | |||||
| def entropy(classes: List[Cls]): Double = { | |||||
| val total = classes.size | |||||
| classes.groupBy(identity) | |||||
| .mapValues { group => | |||||
| val prop = group.size / total | |||||
| prop * math.log(1.0 / prop) | |||||
| }.values.sum | |||||
| } | |||||
| def bucketedEntropy(data: List[TrainingData], feature: Feature): Double = { | |||||
| val total = data.size | |||||
| val bucketed = data.groupBy(_.values(feature)) | |||||
| .mapValues(_.map(_.cls)) | |||||
| .toMap | |||||
| bucketed.values.map { classes => | |||||
| val prop = classes.size / total | |||||
| prop * entropy(classes) | |||||
| }.sum | |||||
| } | |||||
| def best(data: List[TrainingData], features: Set[Feature]): Feature = features.minBy(bucketedEntropy(data, _)) | |||||
| def mostCommonCls(data: List[TrainingData]): Cls = ??? | |||||
| def build(data: List[TrainingData], features: Set[Feature]): Tree = { | |||||
| if(features.nonEmpty) { | |||||
| val feature = best(data, features) | |||||
| val buckets = data.groupBy(_.values(feature)) | |||||
| Node(feature, buckets.mapValues(build(_, features - feature))) | |||||
| } else { | |||||
| Leaf(mostCommonCls(data)) | |||||
| } | |||||
| } | |||||
| def withHKT { | |||||
| sealed trait Tree[A] | |||||
| case class Node[A](feature: Feature, children: Map[Value, A]) extends Tree[A] | |||||
| case class Leaf[A](cls: Cls) extends Tree[A] | |||||
| // import matryoshka._ | |||||
| // import matryoshka.data.Fix | |||||
| // import matryoshka.implicits._ | |||||
| case class Fix[F[_]](unfix: F[Fix[F]]) | |||||
| case class Cofree[F[_], A](head: A, tail: F[Cofree[F, A]]){ | |||||
| def counit: A = head | |||||
| def map[B](f: A => B)(implicit ev: Functor[F]): Cofree[F, B] = Cofree(f(head), tail.map(_.map(f))) | |||||
| /** | |||||
| * Coflatmap alters the value of the node based on its context, then recursively | |||||
| * alters its tail independently (which makes sense as it's the only thing Cofree[F, A] => B can do. | |||||
| */ | |||||
| def coflatMap[B](fa: Cofree[F, A] => B)(implicit ev: Functor[F]): Cofree[F, B] = { | |||||
| val b = fa(this) | |||||
| val fb = tail.map(_.coflatMap(fa)) | |||||
| Cofree(b, fb) | |||||
| } | |||||
| } | |||||
| implicit val treeFunctor: Functor[Tree] = new Functor[Tree] { | |||||
| def map[A, B](fa: Tree[A])(f: A => B): Tree[B] = fa match { | |||||
| case Node(name, children) => Node(name, children.mapValues(f)) | |||||
| case Leaf(cls) => Leaf(cls) | |||||
| } | |||||
| } | |||||
| val genderBased: Fix[Tree] = | |||||
| Fix(Node( | |||||
| "gender", | |||||
| Map( | |||||
| "female" -> Fix(Leaf[Fix[Tree]]("survived")), | |||||
| "male" -> Fix(Leaf[Fix[Tree]]("died")) | |||||
| ))) | |||||
| def build: ((List[TrainingData], Set[Feature])) => Tree[(List[TrainingData], Set[Feature])] = { | |||||
| case (data, features) => | |||||
| if(features.nonEmpty) { | |||||
| val feature = best(data, features) | |||||
| val buckets = data.groupBy(_.values(feature)) | |||||
| val next = buckets.mapValues { subset => (subset, features - feature) } | |||||
| Node(feature, next) | |||||
| } else { | |||||
| Leaf(mostCommonCls(data)) | |||||
| } | |||||
| } | |||||
| def explore(testData: TestData): Fix[Tree] => Cls Either Fix[Tree] = | |||||
| fix => fix.unfix match { | |||||
| case Leaf(cls) => Left(cls) | |||||
| case Node(feature, children) => Right(children.get(testData(feature)).get) | |||||
| } | |||||
| // Anamorphism: Generalized unfold, builds structures | |||||
| def ana[F[_]: Functor, A](f: A => F[A])(a: A): Fix[F] = | |||||
| Fix( (f(a)).map(ana(f)) ) | |||||
| // Catamorphism: Generalized fold, tears structures down. | |||||
| def cata[F[_]: Functor, A](fa: F[A] => A)(f: Fix[F]): A = { | |||||
| fa(f.unfix.map(cata(fa))) | |||||
| } | |||||
| // def hyloSimple[F[_] : Functor, A, B](f: F[B] => B)(g: A => F[A]): A => B | |||||
| def hyloSimple[F[_]: Functor, A, B](f: F[B] => B)(g: A => F[A])(a: A): B = | |||||
| cata(f)(ana(g)(a)) | |||||
| // A more powerful cata | |||||
| def para[F[_]: Functor, A](f: F[(Fix[F], A)] => A)(fa: Fix[F]): A = | |||||
| f(fa.unfix.map(x => (x, para(f)(x)))) | |||||
| // A more powerful ana | |||||
| def apo[F[_]: Functor, A](f: A => F[Either[Fix[F], A]])(a: A): Fix[F] = { | |||||
| Fix(f(a).map{ | |||||
| case Right(a) => apo(f)(a) | |||||
| case Left(fix) => fix | |||||
| }) | |||||
| } | |||||
| // When we have cofree | |||||
| def histo[F[_]: Functor, A](f: F[Cofree[F, A]] => A)(fix: Fix[F]): A = { | |||||
| def toCofree(fix: Fix[F]): Cofree[F, A] = | |||||
| Cofree(histo(f)(fix), fix.unfix.map(toCofree)) | |||||
| f(fix.unfix.map(toCofree)) | |||||
| } | |||||
| } | |||||
| } | |||||
| @@ -1,164 +0,0 @@ | |||||
| package FiveStage | |||||
| import cats.data.Writer | |||||
| import cats._ | |||||
| import cats.data.{ Op => _ } | |||||
| import cats.implicits._ | |||||
| import fileUtils.say | |||||
| object DeletDis { | |||||
| def delet = { | |||||
| case class Fix[F[_]](unfix: F[Fix[F]]) | |||||
| case class Cofree[F[_], A](head: A, tail: F[Cofree[F, A]]){ | |||||
| def counit: A = head | |||||
| def map[B](f: A => B)(implicit ev: Functor[F]): Cofree[F, B] = Cofree(f(head), tail.map(_.map(f))) | |||||
| /** | |||||
| * Coflatmap alters the value of the node based on its context, then recursively | |||||
| * alters its tail independently (which makes sense as it's the only thing Cofree[F, A] => B can do. | |||||
| */ | |||||
| def coflatMap[B](fa: Cofree[F, A] => B)(implicit ev: Functor[F]): Cofree[F, B] = { | |||||
| val b = fa(this) | |||||
| val fb = tail.map(_.coflatMap(fa)) | |||||
| Cofree(b, fb) | |||||
| } | |||||
| } | |||||
| // Anamorphism: Generalized unfold, builds structures | |||||
| def ana[F[_]: Functor, A](f: A => F[A])(a: A): Fix[F] = | |||||
| Fix( (f(a)).map(ana(f)) ) | |||||
| // Catamorphism: Generalized fold, tears structures down. | |||||
| def cata[F[_]: Functor, A](fa: F[A] => A)(f: Fix[F]): A = { | |||||
| fa(f.unfix.map(cata(fa))) | |||||
| } | |||||
| // def hyloSimple[F[_] : Functor, A, B](f: F[B] => B)(g: A => F[A]): A => B | |||||
| def hylo[F[_]: Functor, A, B](f: F[B] => B)(g: A => F[A])(a: A): B = | |||||
| cata(f)(ana(g)(a)) | |||||
| // A more powerful cata | |||||
| def para[F[_]: Functor, A](f: F[(Fix[F], A)] => A)(fa: Fix[F]): A = | |||||
| f(fa.unfix.map(x => (x, para(f)(x)))) | |||||
| // A more powerful ana | |||||
| def apo[F[_]: Functor, A](f: A => F[Either[Fix[F], A]])(a: A): Fix[F] = { | |||||
| Fix(f(a).map{ | |||||
| case Right(a) => apo(f)(a) | |||||
| case Left(fix) => fix | |||||
| }) | |||||
| } | |||||
| // When we have cofree | |||||
| def histo[F[_]: Functor, A](f: F[Cofree[F, A]] => A)(fix: Fix[F]): A = { | |||||
| def toCofree(fix: Fix[F]): Cofree[F, A] = | |||||
| Cofree(histo(f)(fix), fix.unfix.map(toCofree)) | |||||
| f(fix.unfix.map(toCofree)) | |||||
| } | |||||
| sealed trait StackR | |||||
| final case class DoneR(result: Int = 1) extends StackR | |||||
| final case class MoreR(stack: StackR, next: Int) extends StackR | |||||
| def unfoldStackR(n: Int): StackR = | |||||
| if(n > 0) MoreR(unfoldStackR(n-1), n) else DoneR() | |||||
| say(unfoldStackR(5)) | |||||
| sealed trait Stack[A] | |||||
| final case class Done[A](result: Int) extends Stack[A] | |||||
| final case class More[A](a: A, next: Int) extends Stack[A] | |||||
| object Stack { | |||||
| implicit val stackFunctor: Functor[Stack] = new Functor[Stack] { | |||||
| def map[A, B](fa: Stack[A])(f: A => B): Stack[B] = fa match { | |||||
| case Done(result) => Done(result) | |||||
| case More(a, next) => More(f(a), next) | |||||
| } | |||||
| } | |||||
| def done[A](result: Int = 1): Stack[A] = Done(result) | |||||
| def more[A](a: A, next: Int): Stack[A] = More(a, next) | |||||
| } | |||||
| import Stack._ | |||||
| val stackCoalgebra: Int => Stack[Int] = | |||||
| n => if(n > 0) more(n - 1, n) else done() | |||||
| say(ana(stackCoalgebra)(5)) | |||||
| val stackAlgebra: Stack[Int] => Int = { | |||||
| case Done(result) => result | |||||
| case More(acc, next) => acc * next | |||||
| } | |||||
| say(cata(stackAlgebra)(ana(stackCoalgebra)(5))) | |||||
| say(hylo(stackAlgebra)(stackCoalgebra)(5)) | |||||
| sealed trait Nat[A] | |||||
| final case class Zero[A]() extends Nat[A] | |||||
| final case class Succ[A](prev: A) extends Nat[A] | |||||
| object Nat { | |||||
| implicit val natFunctor: Functor[Nat] = new Functor[Nat] { | |||||
| override def map[A, B](na: Nat[A])(f: A => B): Nat[B] = | |||||
| na match { | |||||
| case Zero() => Zero() | |||||
| case Succ(a) => Succ(f(a)) | |||||
| } | |||||
| } | |||||
| } | |||||
| val natAlgebra: Nat[Int] => Int = { | |||||
| case Zero() => 1 | |||||
| case Succ(n) => { | |||||
| say(s"nat alg succ $n") | |||||
| n + 1 | |||||
| } | |||||
| } | |||||
| val natAlgebraS: Nat[String] => String = { | |||||
| case Zero() => "N" | |||||
| case Succ(n) => n match { | |||||
| case "N" => "NI" | |||||
| case "NI" => "NIG" | |||||
| case "NIG" => "NIGG" | |||||
| case "NIGG" => "NIGGE" | |||||
| case "NIGGE" => "NIGGER :-" | |||||
| case s => s + "D" | |||||
| } | |||||
| } | |||||
| val natCoalgebra: Int => Nat[Int] = | |||||
| n => if (n == 0) Zero() else Succ(n - 1) | |||||
| val b = ana(natCoalgebra)(9) | |||||
| val c = cata(natAlgebraS)(b) | |||||
| say(c) | |||||
| val natAlgebraPara: Nat[(Fix[Nat], Int)] => Int = { | |||||
| case Zero() => 1 | |||||
| case Succ((fix, acc)) => { | |||||
| say(s"nat para alg succ $fix, $acc") | |||||
| cata(natAlgebra)(fix) * acc | |||||
| } | |||||
| } | |||||
| val build = ana(natCoalgebra)(_) | |||||
| say("built") | |||||
| val tear = para(natAlgebraPara)(_) | |||||
| say(tear(build(5))) | |||||
| // say(ana(natCoalgebra)(5)) | |||||
| val lastThreeSteps: Fix[Stack] = Fix(More(Fix(More(Fix(More(Fix(Done(1)),1)),2)),3)) | |||||
| val stackCoalgebraApo: Int => Stack[Either[Fix[Stack], Int]] = | |||||
| n => if(n > 3) more(n - 1, n).map(_.asRight) else lastThreeSteps.unfix.map(_.asLeft) | |||||
| } | |||||
| } | |||||
| @@ -81,16 +81,17 @@ object PrintUtils { | |||||
| val UNKNOWN = "UNKNOWN" | val UNKNOWN = "UNKNOWN" | ||||
| def printInstruction(op: Ops.Op, labelMap: Map[Label, Addr]): fansi.Str = op match { | def printInstruction(op: Ops.Op, labelMap: Map[Label, Addr]): fansi.Str = op match { | ||||
| case op: Branch => fansi.Color.Red(s"B${op.comp}\t${op.rs1.show}, ${op.rs2.show}, ${op.dst.show}\t[${labelMap.lift(op.dst).getOrElse(UNKNOWN)}]") | |||||
| case op: Arith => s"${op.op}\t${op.rd.show}, ${op.rs1.show}, ${op.rs2.show}" | |||||
| case op: ArithImm => s"${op.op}I\t${op.rd.show}, ${op.rs1.show}, ${op.imm.show}" | |||||
| case op: JALR => fansi.Color.Green(s"JALR\t${op.rd.show}, ${op.rs1.show}, ${op.dst.show}\t[${labelMap.lift(op.dst).getOrElse(UNKNOWN)}]") | |||||
| case op: JAL => fansi.Color.Magenta(s"JAL\t${op.rd.show}, ${op.dst.show} [${labelMap.lift(op.dst).getOrElse(UNKNOWN)}]") | |||||
| case op: LW => s"LW\t${op.rd.show}, ${op.offset.show}(${op.rs1.show})" | |||||
| case op: SW => s"SW\t${op.rs2.show}, ${op.offset.show}(${op.rs1.show})" | |||||
| case op: LUI => s"LUI\t${op.rd.show}, ${op.imm.show}" | |||||
| case op: AUIPC => s"AUIPC\t${op.rd.show}, ${op.imm.show}" | |||||
| case DONE => s"DONE" | |||||
| case op: Branch => fansi.Color.Red(s"B${op.comp}\t${op.rs1.show}, ${op.rs2.show}, ${op.dst.show}\t[${labelMap.lift(op.dst).getOrElse(UNKNOWN)}]") | |||||
| case op: Arith => s"${op.op}\t${op.rd.show}, ${op.rs1.show}, ${op.rs2.show}" | |||||
| case op: ArithImm => s"${op.op}I\t${op.rd.show}, ${op.rs1.show}, ${op.imm.show}" | |||||
| case op: ArithImmShift => s"${op.op}I\t${op.rd.show}, ${op.rs1.show}, ${op.shamt.show}" | |||||
| case op: JALR => fansi.Color.Green(s"JALR\t${op.rd.show}, ${op.rs1.show}, ${op.dst.show}\t[${labelMap.lift(op.dst).getOrElse(UNKNOWN)}]") | |||||
| case op: JAL => fansi.Color.Magenta(s"JAL\t${op.rd.show}, ${op.dst.show} [${labelMap.lift(op.dst).getOrElse(UNKNOWN)}]") | |||||
| case op: LW => s"LW\t${op.rd.show}, ${op.offset.show}(${op.rs1.show})" | |||||
| case op: SW => s"SW\t${op.rs2.show}, ${op.offset.show}(${op.rs1.show})" | |||||
| case op: LUI => s"LUI\t${op.rd.show}, ${op.imm.show}" | |||||
| case op: AUIPC => s"AUIPC\t${op.rd.show}, ${op.imm.show}" | |||||
| case DONE => s"DONE" | |||||
| } | } | ||||
| @@ -118,7 +119,7 @@ object PrintUtils { | |||||
| def printBinary(bin: Map[Addr, Int]): String = { | def printBinary(bin: Map[Addr, Int]): String = { | ||||
| bin.toList.sortBy(_._1.value).map{ case(addr, op) => s"$addr: ${op.hs}" }.mkString("\n","\n","\n") | |||||
| bin.toList.sortBy(_._1.value).map{ case(addr, op) => s"$addr: ${op.hs}\t--\t${op.binary}" }.mkString("\n","\n","\n") | |||||
| } | } | ||||
| @@ -346,7 +347,8 @@ object PrintUtils { | |||||
| def printLogSideBySide(trace: List[ExecutionTraceEvent], chiselTrace: List[CircuitTrace], program: Program): String = { | def printLogSideBySide(trace: List[ExecutionTraceEvent], chiselTrace: List[CircuitTrace], program: Program): String = { | ||||
| import LogParser._ | import LogParser._ | ||||
| val header = "ADDRESS -- VM UPDATES --- DEVICE UNDER TEST UPDATES --- CORRESPONDING SOURCE LINE\n" | |||||
| val traces = mergeTraces(trace, chiselTrace).map(x => printMergedTraces((x), program)) | val traces = mergeTraces(trace, chiselTrace).map(x => printMergedTraces((x), program)) | ||||
| traces.map(_.mkString("\n")).mkString("\n", "\n--------------------------------------------------------------------------+------------------------------------------------------+-------------------------------\n", "\n") | |||||
| "\n" + header + (traces.map(_.mkString("\n")).mkString("\n", "\n--------------------------------------------------------------------------+------------------------------------------------------+-------------------------------\n", "\n")) | |||||
| } | } | ||||
| } | } | ||||
| @@ -75,7 +75,7 @@ object TestUtils { | |||||
| val entry = hasLeft + (leftIndex << 1) + (hasRight << 8) + (rightIndex << 9) + (root.value << 16) | val entry = hasLeft + (leftIndex << 1) + (hasRight << 8) + (rightIndex << 9) + (root.value << 16) | ||||
| say(s"with leftIndex: ${leftIndex.hs}, rightIndex: ${rightIndex.hs}, value: ${root.value.hs} we got ${entry.hs}") | |||||
| // say(s"with leftIndex: ${leftIndex.hs}, rightIndex: ${rightIndex.hs}, value: ${root.value.hs} we got ${entry.hs}") | |||||
| entry :: foldAnno(root.left) ::: foldAnno(root.right) | entry :: foldAnno(root.left) ::: foldAnno(root.right) | ||||
| }.getOrElse(Nil) | }.getOrElse(Nil) | ||||
| @@ -98,8 +98,8 @@ object TestUtils { | |||||
| */ | */ | ||||
| def generateHazardsForward(steps: Int) : Unit = { | def generateHazardsForward(steps: Int) : Unit = { | ||||
| // val r = new scala.util.Random(0xF01D1EF7) | |||||
| val r = new scala.util.Random(0xF01D1EF8) | |||||
| val r = new scala.util.Random(0xF01D1EF7) | |||||
| // val r = new scala.util.Random(0xF01D1EF8) | |||||
| import Ops._ | import Ops._ | ||||
| val active = List(1, 2, 3) | val active = List(1, 2, 3) | ||||
| @@ -136,9 +136,9 @@ object TestUtils { | |||||
| (s"ori ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.or(rd, rs1, imm)), | (s"ori ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.or(rd, rs1, imm)), | ||||
| (s"xori ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.xor(rd, rs1, imm)), | (s"xori ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.xor(rd, rs1, imm)), | ||||
| (s"andi ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.and(rd, rs1, imm)), | (s"andi ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.and(rd, rs1, imm)), | ||||
| (s"slli ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(shift).show}", ArithImm.sll(rd, rs1, shift)), | |||||
| (s"srli ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(shift).show}", ArithImm.srl(rd, rs1, shift)), | |||||
| (s"srai ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(shift).show}", ArithImm.sra(rd, rs1, shift)), | |||||
| (s"slli ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(math.abs(shift).toInt % 32).show}", ArithImmShift.sll(rd, rs1, math.abs(shift).toInt % 32)), | |||||
| (s"srli ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(math.abs(shift).toInt % 32).show}", ArithImmShift.srl(rd, rs1, math.abs(shift).toInt % 32)), | |||||
| (s"srai ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(math.abs(shift).toInt % 32).show}", ArithImmShift.sra(rd, rs1, math.abs(shift).toInt % 32)), | |||||
| (s"slti ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.slt(rd, rs1, imm)), | (s"slti ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.slt(rd, rs1, imm)), | ||||
| (s"sltiu ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.sltu(rd, rs1, imm))) | (s"sltiu ${Reg(rd).show}, ${Reg(rs1).show}, ${Imm(imm).show}", ArithImm.sltu(rd, rs1, imm))) | ||||
| (rd, choices.shuffle(r).head) | (rd, choices.shuffle(r).head) | ||||
| @@ -1,43 +0,0 @@ | |||||
| // package FiveStage | |||||
| // import chisel3._ | |||||
| // import chisel3.iotesters._ | |||||
| // import org.scalatest.{Matchers, FlatSpec} | |||||
| // import spire.math.{UInt => Uint} | |||||
| // import fileUtils._ | |||||
| // import cats.implicits._ | |||||
| // import RISCVutils._ | |||||
| // import RISCVasm._ | |||||
| // import riscala._ | |||||
| // import utilz._ | |||||
| // class AllTests extends FlatSpec with Matchers { | |||||
| // val results = fileUtils.getAllTests.map{f => | |||||
| // val result = TestRunner.runTest(f.getPath, false) | |||||
| // (f.getName, result) | |||||
| // } | |||||
| // makeReport(results) | |||||
| // } | |||||
| // /** | |||||
| // This is for you to run more verbose testing. | |||||
| // */ | |||||
| // class SelectedTests extends FlatSpec with Matchers { | |||||
| // val tests = List( | |||||
| // "matMul.s" | |||||
| // ) | |||||
| // if(!tests.isEmpty){ | |||||
| // val results = fileUtils.getAllTests.filter(f => tests.contains(f.getName)).map{ f => | |||||
| // val result = TestRunner.runTest(f.getPath, true) | |||||
| // (f.getName, result) | |||||
| // } | |||||
| // makeReport(results) | |||||
| // } | |||||
| // } | |||||