diff options
| author | Andrew Kelley <andrew@ziglang.org> | 2020-08-04 15:32:41 -0700 |
|---|---|---|
| committer | Andrew Kelley <andrew@ziglang.org> | 2020-08-04 15:32:41 -0700 |
| commit | e4eb4396c27010d8d07b6fc73e7c7557170f06ad (patch) | |
| tree | d6c5691ec7c7d0d73c918672e905c43ae9f897e2 /src-self-hosted/codegen | |
| parent | 952a397b0e006444e770e51d32cce93186959bdb (diff) | |
| parent | c594f8dc26cebbcd371c0136da5ee7bb0eaca2b3 (diff) | |
| download | zig-e4eb4396c27010d8d07b6fc73e7c7557170f06ad.tar.gz zig-e4eb4396c27010d8d07b6fc73e7c7557170f06ad.zip | |
Merge branch 'pfgithub-stage2-testing-Copy-2'
Diffstat (limited to 'src-self-hosted/codegen')
| -rw-r--r-- | src-self-hosted/codegen/riscv64.zig | 92 |
1 files changed, 92 insertions, 0 deletions
diff --git a/src-self-hosted/codegen/riscv64.zig b/src-self-hosted/codegen/riscv64.zig new file mode 100644 index 0000000000..c5c762709a --- /dev/null +++ b/src-self-hosted/codegen/riscv64.zig @@ -0,0 +1,92 @@ +const std = @import("std"); + +pub const instructions = struct { + pub const CallBreak = packed struct { + pub const Mode = packed enum(u12) { ecall, ebreak }; + opcode: u7 = 0b1110011, + unused1: u5 = 0, + unused2: u3 = 0, + unused3: u5 = 0, + mode: u12, //: Mode + }; + // I-type + pub const Addi = packed struct { + pub const Mode = packed enum(u3) { addi = 0b000, slti = 0b010, sltiu = 0b011, xori = 0b100, ori = 0b110, andi = 0b111 }; + opcode: u7 = 0b0010011, + rd: u5, + mode: u3, //: Mode + rs1: u5, + imm: i12, + }; + pub const Lui = packed struct { + opcode: u7 = 0b0110111, + rd: u5, + imm: i20, + }; + // I_type + pub const Load = packed struct { + pub const Mode = packed enum(u3) { ld = 0b011, lwu = 0b110 }; + opcode: u7 = 0b0000011, + rd: u5, + mode: u3, //: Mode + rs1: u5, + offset: i12, + }; + // I-type + pub const Jalr = packed struct { + opcode: u7 = 0b1100111, + rd: u5, + mode: u3 = 0, + rs1: u5, + offset: i12, + }; +}; + +// zig fmt: off +pub const RawRegister = enum(u8) { + x0, x1, x2, x3, x4, x5, x6, x7, + x8, x9, x10, x11, x12, x13, x14, x15, + x16, x17, x18, x19, x20, x21, x22, x23, + x24, x25, x26, x27, x28, x29, x30, x31, +}; + +pub const Register = enum(u8) { + // 64 bit registers + zero, // zero + ra, // return address. caller saved + sp, // stack pointer. callee saved. + gp, // global pointer + tp, // thread pointer + t0, t1, t2, // temporaries. caller saved. + s0, // s0/fp, callee saved. + s1, // callee saved. + a0, a1, // fn args/return values. caller saved. + a2, a3, a4, a5, a6, a7, // fn args. caller saved. + s2, s3, s4, s5, s6, s7, s8, s9, s10, s11, // saved registers. callee saved. + t3, t4, t5, t6, // caller saved + + pub fn parseRegName(name: []const u8) ?Register { + if(std.meta.stringToEnum(Register, name)) |reg| return reg; + if(std.meta.stringToEnum(RawRegister, name)) |rawreg| return @intToEnum(Register, @enumToInt(rawreg)); + return null; + } + + /// Returns the register's id. + pub fn id(self: @This()) u5 { + return @truncate(u5, @enumToInt(self)); + } + + /// Returns the index into `callee_preserved_regs`. + pub fn allocIndex(self: Register) ?u4 { + inline for(callee_preserved_regs) |cpreg, i| { + if(self == cpreg) return i; + } + return null; + } +}; + +// zig fmt: on + +pub const callee_preserved_regs = [_]Register{ + .s0, .s1, .s2, .s3, .s4, .s5, .s6, .s7, .s8, .s9, .s10, .s11, +}; |
