Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

MIPS -- add fp register; support for lwl, beqz and sltiu instructions #4513

Open
wants to merge 7 commits into
base: dev
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 22 additions & 7 deletions librz/arch/isa/mips/mips_assembler.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,12 @@
#include <rz_types.h>
#include <rz_util.h>

static const char *const regs[33] = {
static const char *const regs[34] = {
"zero", "at", "v0", "v1", "a0", "a1", "a2", "a3",
"t0", "t1", "t2", "t3", "t4", "t5", "t6", "t7",
"s0", "s1", "s2", "s3", "s4", "s5", "s6", "s7",
"t8", "t9", "k0", "k1", "gp", "sp", "s8", "ra",
NULL
"fp", NULL
};

static struct {
Expand All @@ -25,6 +25,7 @@ static struct {
{ "sh", 'I', 3, 41, 0 },
{ "sb", 'I', 3, 40, 0 },
{ "lw", 'I', 3, 35, 0 },
{ "lwl", 'I', 3, 34, 0 },
{ "lh", 'I', 3, 33, 0 },
{ "lb", 'I', 3, 32, 0 },
{ "ori", 'I', 3, 13, 0 },
Expand All @@ -37,6 +38,7 @@ static struct {
{ "bal", 'B', -1, -1, 17 },
{ "bne", 'B', 3, 5, 0 },
{ "beq", 'B', 3, 4, 0 },
{ "beqz", 'B', 2, 1, 4 },
{ "bgez", 'B', -2, -1, 1 },
{ "bgezal", 'B', -2, -1, 17 },
{ "bltzal", 'B', -2, -1, 16 },
Expand All @@ -53,6 +55,7 @@ static struct {
{ "sllv", 'R', 3, 4, 0 },
{ "slt", 'R', 3, 42, 0 },
{ "slti", 'I', 3, 10, 0 },
{ "sltiu", 'I', 3, 11, 0 },
{ "sltu", 'R', 3, 43, 0 },
{ "sra", 'R', -3, 3, 0 },
{ "srl", 'R', -3, 2, 0 },
Expand Down Expand Up @@ -128,7 +131,7 @@ static int getreg(const char *p) {
}
/* check if it's a register */
for (n = 0; regs[n]; n++) {
if (!strcmp(p, regs[n])) {
if (!strcmp(p, regs[n]) || (p[0] == '$' && !strcmp(p + 1, regs[n]))) {
return n;
}
}
Expand Down Expand Up @@ -182,7 +185,12 @@ RZ_IPI int mips_assemble_opcode(const char *str, ut64 pc, ut8 *out) {
for (i = 0; ops[i].name; i++) {
if (!strcmp(ops[i].name, w0)) {
switch (ops[i].args) {
case 3: sscanf(s, "%31s %31s %31s %31s", w0, w1, w2, w3); break;
case 3:
if (sscanf(s, "%31s %31s %31s %31s", w0, w1, w2, w3) == 3) {
// Assume offset is 0 if not provided
strcpy(w3, "0");
}
break;
case -3: sscanf(s, "%31s %31s %31s %31s", w0, w1, w2, w3); break;
case 2: sscanf(s, "%31s %31s %31s", w0, w1, w2); break;
case -2: sscanf(s, "%31s %31s %31s", w0, w1, w2); break;
Expand Down Expand Up @@ -258,9 +266,16 @@ RZ_IPI int mips_assemble_opcode(const char *str, ut64 pc, ut8 *out) {
int op = 0, rs = 0, rt = 0, imm = 0, is_branch = ops[i].type == 'B';
switch (ops[i].args) {
case 2:
op = ops[i].n;
rt = getreg(w1);
imm = getreg(w2);
if (!strcmp(w0, "beqz")) {
op = 4; // op code for beq
rs = getreg(w1);
rt = 0; // zero register
imm = (int)strtol(w2, NULL, 0);
} else {
op = ops[i].n;
rt = getreg(w1);
imm = getreg(w2);
}
break;
case 3:
op = ops[i].n;
Expand Down
121 changes: 121 additions & 0 deletions test/db/asm/mips_32
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
# Big Endian Instructions (please add both forms to this test)
aE "nop" 00000000 0x4
aE "lui t0, 0x1234" 3c081234 0x4
aE "sw t0, 0(t1)" ad280000 0x4
aE "sh t0, 0(t1)" a5280000 0x4
aE "sb t0, 0(t1)" a0280000 0x4
aE "lw t0, 0(t1)" 8d280000 0x4
aE "lwl t0, 0(t1)" 88280000 0x4
aE "lh t0, 0(t1)" 85280000 0x4
aE "lb t0, 0(t1)" 80280000 0x4
aE "ori t0, t1, 0x1234" 35281234 0x4
aE "andi t0, t1, 0x1234" 31281234 0x4
aE "xori t0, t1, 0x1234" 38281234 0x4
aE "addi t0, t1, 0x1234" 21281234 0x4
aE "addiu t0, t1, 0x1234" 25281234 0x4
aE "b 8" 10000002 0x4
aE "bnez t0, 8" 15000002 0x4
aE "bal 0x10000" 04100004 0x4
aE "bne t0, t1, 8" 15090002 0x4
aE "beq t0, t1, 8" 11090002 0x4
aE "beqz t0, 8" 11000002 0x4
aE "bgez t0, 8" 05010002 0x4
aE "bgezal t0, 8" 04110002 0x4
aE "bltzal t0, 8" 04100002 0x4
aE "bgtz t0, 8" 1d000002 0x4
aE "blez t0, 8" 19000002 0x4
aE "bltz t0, 8" 04000002 0x4
aE "syscall" 0000000c 0x4
aE "break" 0000000d 0x4
aE "nor t0, t1, t2" 014b4827 0x4
aE "or t0, t1, t2" 012b4825 0x4
aE "xor t0, t1, t2" 012b4826 0x4
aE "and t0, t1, t2" 012b4824 0x4
aE "sll t0, t1, 2" 00094980 0x4
aE "sllv t0, t1, t2" 01495004 0x4
aE "slt t0, t1, t2" 012b482a 0x4
aE "slti t0, t1, 0x1234" 29281234 0x4
aE "sltiu t0, t1, 0x1234" 2d281234 0x4
aE "sltu t0, t1, t2" 012b482b 0x4
aE "sra t0, t1, 2" 00094983 0x4
aE "srl t0, t1, 2" 00094982 0x4
aE "srlv t0, t1, t2" 01495006 0x4
aE "srav t0, t1, t2" 01495007 0x4
aE "add t0, t1, t2" 012b4820 0x4
aE "move t0, t1" 01204020 0x4
aE "addu t0, t1, t2" 012b4821 0x4
aE "sub t0, t1, t2" 012b4822 0x4
aE "subu t0, t1, t2" 012b4823 0x4
aE "mult t0, t1" 01290018 0x4
aE "multu t0, t1" 01290019 0x4
aE "div t0, t1" 0129001a 0x4
aE "divu t0, t1" 0129001b 0x4
aE "mfhi t0" 00004010 0x4
aE "mflo t0" 00004012 0x4
aE "mthi t0" 01000011 0x4
aE "mtlo t0" 01000013 0x4
aE "jalr t0, t1" 0120f809 0x4
aE "jr t0" 01000008 0x4
aE "jal 0x123456" 0c123456 0x4
aE "j 0x123456" 08123456 0x4

# Little Endian instructions
a "nop" 00000000 0x4
a "lui t0, 0x1234" 3412083c 0x4
a "sw t0, 0(t1)" 000028ad 0x4
a "sh t0, 0(t1)" 000028a5 0x4
a "sb t0, 0(t1)" 000028a0 0x4
a "lw t0, 0(t1)" 0000288d 0x4
a "lwl t0, 0(t1)" 00002888 0x4
a "lh t0, 0(t1)" 00002885 0x4
a "lb t0, 0(t1)" 00002880 0x4
a "ori t0, t1, 0x1234" 34122835 0x4
a "andi t0, t1, 0x1234" 34122831 0x4
a "xori t0, t1, 0x1234" 34122838 0x4
a "addi t0, t1, 0x1234" 34122821 0x4
a "addiu t0, t1, 0x1234" 34122825 0x4
a "b 8" 02000010 0x4
a "bnez t0, 8" 02000015 0x4
a "bal 0x10000" 04001004 0x4
a "bne t0, t1, 8" 02000915 0x4
a "beq t0, t1, 8" 02000911 0x4
a "beqz t0, 8" 02000011 0x4
a "bgez t0, 8" 02000105 0x4
a "bgezal t0, 8" 02001104 0x4
a "bltzal t0, 8" 02001004 0x4
a "bgtz t0, 8" 0200001d 0x4
a "blez t0, 8" 02000019 0x4
a "bltz t0, 8" 02000004 0x4
a "syscall" 0c000000 0x4
a "break" 0d000000 0x4
a "nor t0, t1, t2" 27484b01 0x4
a "or t0, t1, t2" 25482b01 0x4
a "xor t0, t1, t2" 26482b01 0x4
a "and t0, t1, t2" 24482b01 0x4
a "sll t0, t1, 2" 80494900 0x4
a "sllv t0, t1, t2" 04505001 0x4
a "slt t0, t1, t2" 2a482b01 0x4
a "slti t0, t1, 0x1234" 34122829 0x4
a "sltiu t0, t1, 0x1234" 3412282d 0x4
a "sltu t0, t1, t2" 2b482b01 0x4
a "sra t0, t1, 2" 83494900 0x4
a "srl t0, t1, 2" 82494900 0x4
a "srlv t0, t1, t2" 06505001 0x4
a "srav t0, t1, t2" 07505001 0x4
a "add t0, t1, t2" 20482b01 0x4
a "move t0, t1" 20402001 0x4
a "addu t0, t1, t2" 21482b01 0x4
a "sub t0, t1, t2" 22482b01 0x4
a "subu t0, t1, t2" 23482b01 0x4
a "mult t0, t1" 18002901 0x4
a "multu t0, t1" 19002901 0x4
a "div t0, t1" 1a002901 0x4
a "divu t0, t1" 1b002901 0x4
a "mfhi t0" 10400000 0x4
a "mflo t0" 12400000 0x4
a "mthi t0" 11000001 0x4
a "mtlo t0" 13000001 0x4
a "jalr t0, t1" 09f82001 0x4
a "jr t0" 08000001 0x4
a "jal 0x123456" 5634120c 0x4
a "j 0x123456" 56341208 0x4
Loading