RabbitizerInstruction_isValid

This commit is contained in:
Angie 2022-07-03 19:28:13 -04:00
parent a725e0281a
commit bed5d928dd
11 changed files with 336 additions and 121 deletions

View File

@ -37,6 +37,7 @@
#define ARRAY_COUNT(arr) (sizeof(arr) / sizeof(arr[0]))
#define MASK(v, w) ((v) & ((1 << (w)) - 1))
/*
* the SHIFT macros take a value, a shift amount, and a width.
@ -53,7 +54,8 @@
#define SHIFTL(v, s, w) (((v) & ((1 << (w)) - 1)) << (s))
#define SHIFTR(v, s, w) (((v) >> (s)) & ((1 << (w)) - 1))
#define BITREPACK(fullword, v, s, w) (SHIFTL((self)->word, (s)+(w), 32-((s)+(w))) | SHIFTL((v), (s), (w)) | SHIFTL((self)->word, 0, (s)))
#define BITREPACK(fullword, v, s, w) ((SHIFTR((fullword), (s)+(w), 32-((s)+(w))) << ((s)+(w))) | SHIFTL((v), (s), (w)) | MASK((fullword), (s)))
#define BITREPACK_RIGHT(fullword, v, s, w) (SHIFTL((v), (s), (w)) | MASK((fullword), (s)))
int32_t RabbitizerUtils_From2Complement(uint32_t number, int bits);

View File

@ -28,6 +28,7 @@ typedef enum RabbitizerInstrCategory {
typedef struct RabbitizerInstruction {
uint32_t word;
uint32_t _mandatorybits;
RabbitizerInstrId uniqueId;
const RabbitizerInstrDescriptor *descriptor;
@ -69,22 +70,35 @@ typedef struct RabbitizerInstruction {
#define RAB_INSTR_GET_cop2t(self) (SHIFTR((self)->word, 16, 5))
#define RAB_INSTR_SET_opcode(self, value) ((self)->word = BITREPACK((self)->word, value, 26, 6))
#define RAB_INSTR_SET_rs(self, value) ((self)->word = BITREPACK((self)->word, value, 21, 5))
#define RAB_INSTR_SET_rt(self, value) ((self)->word = BITREPACK((self)->word, value, 16, 5))
#define RAB_INSTR_SET_rd(self, value) ((self)->word = BITREPACK((self)->word, value, 11, 5))
#define RAB_INSTR_SET_sa(self, value) ((self)->word = BITREPACK((self)->word, value, 6, 5))
#define RAB_INSTR_SET_function(self, value) ((self)->word = BITREPACK((self)->word, value, 0, 6))
#define RAB_INSTR_PACK_opcode(word, value) (BITREPACK_RIGHT((word), (value), 26, 6))
#define RAB_INSTR_PACK_rs(word, value) (BITREPACK((word), (value), 21, 5))
#define RAB_INSTR_PACK_rt(word, value) (BITREPACK((word), (value), 16, 5))
#define RAB_INSTR_PACK_rd(word, value) (BITREPACK((word), (value), 11, 5))
#define RAB_INSTR_PACK_sa(word, value) (BITREPACK((word), (value), 6, 5))
#define RAB_INSTR_PACK_function(word, value) (BITREPACK((word), (value), 0, 6))
#define RAB_INSTR_SET_instr_index(self, value) ((self)->word = BITREPACK((self)->word, value, 0, 26))
#define RAB_INSTR_SET_immediate(self, value) ((self)->word = BITREPACK((self)->word, value, 0, 16))
#define RAB_INSTR_PACK_cop0d(word, value) (BITREPACK((word), (value), 11, 5))
#define RAB_INSTR_SET_code(self, value) ((self)->word = BITREPACK((self)->word, value, 6, 20))
#define RAB_INSTR_PACK_instr_index(word, value) (BITREPACK((word), (value), 0, 26))
#define RAB_INSTR_PACK_immediate(word, value) (BITREPACK((word), (value), 0, 16))
#define RAB_INSTR_SET_fs(self, value) ((self)->word = BITREPACK((self)->word, value, 11, 5))
#define RAB_INSTR_SET_ft(self, value) ((self)->word = BITREPACK((self)->word, value, 16, 5))
#define RAB_INSTR_SET_fd(self, value) ((self)->word = BITREPACK((self)->word, value, 6, 5))
#define RAB_INSTR_SET_cop1cs(self, value) ((self)->word = BITREPACK((self)->word, value, 11, 5))
#define RAB_INSTR_PACK_code(word, value) (BITREPACK((word), (value), 6, 20))
#define RAB_INSTR_PACK_fmt(word, value) (BITREPACK((word), (value), 21, 5))
#define RAB_INSTR_PACK_fc(word, value) (BITREPACK((word), (value), 4, 2))
#define RAB_INSTR_PACK_cond(word, value) (BITREPACK((word), (value), 0, 4))
#define RAB_INSTR_PACK_fs(word, value) (BITREPACK((word), (value), 11, 5))
#define RAB_INSTR_PACK_ft(word, value) (BITREPACK((word), (value), 16, 5))
#define RAB_INSTR_PACK_fd(word, value) (BITREPACK((word), (value), 6, 5))
#define RAB_INSTR_PACK_cop1cs(word, value) (BITREPACK((word), (value), 11, 5))
#define RAB_INSTR_PACK_op(word, value) (BITREPACK((word), (value), 16, 5))
#define RAB_INSTR_PACK_cop2t(word, value) (BITREPACK((word), (value), 16, 5))
#define RAB_INSTR_PACK_tf(word, value) (BITREPACK((word), (value), 16, 1))
#define RAB_INSTR_PACK_nd(word, value) (BITREPACK((word), (value), 17, 1))
void RabbitizerInstruction_init(RabbitizerInstruction *self, uint32_t word);
@ -157,6 +171,8 @@ bool RabbitizerInstruction_sameOpcodeButDifferentArguments(const RabbitizerInstr
bool RabbitizerInstruction_hasOperand(const RabbitizerInstruction *self, RabbitizerOperandType operand);
bool RabbitizerInstruction_isValid(const RabbitizerInstruction *self);
/* Instruction examination */

View File

@ -19,15 +19,15 @@
#define RAB_INSTR_RSP_GET_index(self) (SHIFTR((self)->word, 7, 4))
#define RAB_INSTR_RSP_SET_vs(self, value) ((self)->word = BITREPACK((self)->word, value, 11, 5))
#define RAB_INSTR_RSP_SET_vt(self, value) ((self)->word = BITREPACK((self)->word, value, 16, 5))
#define RAB_INSTR_RSP_SET_vd(self, value) ((self)->word = BITREPACK((self)->word, value, 6, 5))
#define RAB_INSTR_RSP_PACK_vs(word, value) (BITREPACK((word), value, 11, 5))
#define RAB_INSTR_RSP_PACK_vt(word, value) (BITREPACK((word), value, 16, 5))
#define RAB_INSTR_RSP_PACK_vd(word, value) (BITREPACK((word), value, 6, 5))
#define RAB_INSTR_RSP_SET_elementhigh(self, value) ((self)->word = BITREPACK((self)->word, value, 16, 4))
#define RAB_INSTR_RSP_SET_elementlow(self, value) ((self)->word = BITREPACK((self)->word, value, 7, 4))
#define RAB_INSTR_RSP_PACK_elementhigh(word, value) (BITREPACK((word), value, 16, 4))
#define RAB_INSTR_RSP_PACK_elementlow(word, value) (BITREPACK((word), value, 7, 4))
#define RAB_INSTR_RSP_SET_index(self, value) ((self)->word = BITREPACK((self)->word, value, 7, 4))
#define RAB_INSTR_RSP_SET_offset(self, value) ((self)->word = BITREPACK((self)->word, value, 0, 7))
#define RAB_INSTR_RSP_PACK_index(word, value) (BITREPACK((word), value, 7, 4))
#define RAB_INSTR_RSP_PACK_offset(word, value) (BITREPACK((word), value, 0, 7))
void RabbitizerInstructionRsp_init(RabbitizerInstruction *self, uint32_t word);

View File

@ -42,6 +42,8 @@ class Instruction:
def sameOpcode(self, other: Instruction) -> bool: ...
def sameOpcodeButDifferentArguments(self, other: Instruction) -> bool: ...
def isValid(self) -> bool: ...
def isUnknownType(self) -> bool: ...
def isJType(self) -> bool: ...
def isIType(self) -> bool: ...
@ -61,6 +63,8 @@ class Instruction:
def isLoPair(self) -> bool: ...
def doesLink(self) -> bool: ...
def doesDereference(self) -> bool: ...
def maybeIsMove(self) -> bool: ...
def isPseudo(self) -> bool: ...
def disassemble(self, immOverride: str|None=None, extraLJust: int=0) -> str: ...

View File

@ -181,6 +181,8 @@ static PyObject *rabbitizer_type_Instruction_sameOpcodeButDifferentArguments(PyR
Py_RETURN_FALSE;
}
DEF_METHOD_BOOL(isValid)
#define DEF_DESCRIPTOR_METHOD_BOOL(name) \
static PyObject *rabbitizer_type_Instruction_##name(PyRabbitizerInstruction *self, PyObject *Py_UNUSED(ignored)) { \
if (RabbitizerInstrDescriptor_##name(self->instr.descriptor)) { \
@ -271,6 +273,8 @@ static PyMethodDef Instr_methods[] = {
METHOD_ARGS(sameOpcode, "description"),
METHOD_ARGS(sameOpcodeButDifferentArguments, "description"),
METHOD_NO_ARGS(isValid, ""),
METHOD_NO_ARGS(isUnknownType, ""),
METHOD_NO_ARGS(isJType, ""),
METHOD_NO_ARGS(isIType, ""),

View File

@ -12,6 +12,7 @@
void RabbitizerInstruction_init(RabbitizerInstruction *self, uint32_t word) {
self->word = word;
self->_mandatorybits = 0;
self->uniqueId = RABBITIZER_INSTR_ID_cpu_INVALID;
self->descriptor = &RabbitizerInstrDescriptor_Descriptors[self->uniqueId];
@ -114,7 +115,7 @@ void RabbitizerInstruction_blankOut(RabbitizerInstruction *self) {
case RABBITIZER_OPERAND_TYPE_rs:
case RABBITIZER_OPERAND_TYPE_RSP_rs:
case RABBITIZER_OPERAND_TYPE_RSP_vs:
RAB_INSTR_SET_rs(self, 0);
self->word = RAB_INSTR_PACK_rs(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_rt:
@ -122,7 +123,7 @@ void RabbitizerInstruction_blankOut(RabbitizerInstruction *self) {
case RABBITIZER_OPERAND_TYPE_op:
case RABBITIZER_OPERAND_TYPE_RSP_rt:
case RABBITIZER_OPERAND_TYPE_RSP_vt:
RAB_INSTR_SET_rt(self, 0);
self->word = RAB_INSTR_PACK_rt(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_rd:
@ -131,64 +132,64 @@ void RabbitizerInstruction_blankOut(RabbitizerInstruction *self) {
case RABBITIZER_OPERAND_TYPE_RSP_rd:
case RABBITIZER_OPERAND_TYPE_RSP_vd:
case RABBITIZER_OPERAND_TYPE_RSP_cop0d:
RAB_INSTR_SET_rd(self, 0);
self->word = RAB_INSTR_PACK_rd(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_sa:
RAB_INSTR_SET_sa(self, 0);
self->word = RAB_INSTR_PACK_sa(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_fs:
RAB_INSTR_SET_fs(self, 0);
self->word = RAB_INSTR_PACK_fs(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_ft:
RAB_INSTR_SET_ft(self, 0);
self->word = RAB_INSTR_PACK_ft(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_fd:
RAB_INSTR_SET_fd(self, 0);
self->word = RAB_INSTR_PACK_fd(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_LABEL:
RAB_INSTR_SET_instr_index(self, 0);
self->word = RAB_INSTR_PACK_instr_index(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_code:
RAB_INSTR_SET_code(self, 0);
self->word = RAB_INSTR_PACK_code(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_IMM_base:
// rs imm
RAB_INSTR_SET_rs(self, 0);
self->word = RAB_INSTR_PACK_rs(self->word, 0);
FALLTHROUGH;
case RABBITIZER_OPERAND_TYPE_IMM:
RAB_INSTR_SET_immediate(self, 0);
self->word = RAB_INSTR_PACK_immediate(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vt_elementhigh:
RAB_INSTR_RSP_SET_vt(self, 0);
RAB_INSTR_RSP_SET_elementhigh(self, 0);
self->word = RAB_INSTR_RSP_PACK_vt(self->word, 0);
self->word = RAB_INSTR_RSP_PACK_elementhigh(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vt_elementlow:
RAB_INSTR_RSP_SET_vt(self, 0);
RAB_INSTR_RSP_SET_elementlow(self, 0);
self->word = RAB_INSTR_RSP_PACK_vt(self->word, 0);
self->word = RAB_INSTR_RSP_PACK_elementlow(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vd_vs:
RAB_INSTR_RSP_SET_vd(self, 0);
RAB_INSTR_RSP_SET_vs(self, 0);
self->word = RAB_INSTR_RSP_PACK_vd(self->word, 0);
self->word = RAB_INSTR_RSP_PACK_vs(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vd_index:
RAB_INSTR_RSP_SET_vd(self, 0);
RAB_INSTR_RSP_SET_index(self, 0);
self->word = RAB_INSTR_RSP_PACK_vd(self->word, 0);
self->word = RAB_INSTR_RSP_PACK_index(self->word, 0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_offset_rs:
RAB_INSTR_RSP_SET_offset(self, 0);
RAB_INSTR_SET_rs(self, 0);
self->word = RAB_INSTR_RSP_PACK_offset(self->word, 0);
self->word = RAB_INSTR_PACK_rs(self->word, 0);;
break;
case RABBITIZER_OPERAND_TYPE_INVALID:

View File

@ -432,55 +432,8 @@ bool RabbitizerInstruction_mustDisasmAsData(const RabbitizerInstruction *self) {
}
}
if (self->descriptor->instrType == RABBITIZER_INSTR_TYPE_R) {
bool hasCode = false;
bool hasRs = false;
bool hasRt = false;
bool hasRd = false;
bool hasSa = false;
for (size_t i = 0; i < ARRAY_COUNT(self->descriptor->operands) && self->descriptor->operands[i] != RABBITIZER_OPERAND_TYPE_INVALID; i++) {
RabbitizerOperandType operand = self->descriptor->operands[i];
if (operand == RABBITIZER_OPERAND_TYPE_code) {
hasCode = true;
}
if (operand == RABBITIZER_OPERAND_TYPE_rs) {
hasRs = true;
}
if (operand == RABBITIZER_OPERAND_TYPE_rt) {
hasRt = true;
}
if (operand == RABBITIZER_OPERAND_TYPE_rd) {
hasRd = true;
}
if (operand == RABBITIZER_OPERAND_TYPE_sa) {
hasSa = true;
}
}
if (!hasCode) {
if (!hasRs) {
if (RAB_INSTR_GET_rs(self) != 0) {
return true;
}
}
if (!hasRt) {
if (RAB_INSTR_GET_rt(self) != 0) {
return true;
}
}
if (!hasRd) {
if (RAB_INSTR_GET_rd(self) != 0 && self->uniqueId != RABBITIZER_INSTR_ID_cpu_jalr) {
return true;
}
}
if (!hasSa) {
if (RAB_INSTR_GET_sa(self) != 0) {
return true;
}
}
}
if (!RabbitizerInstruction_isValid(self)) {
return true;
}
return false;
}

View File

@ -3,7 +3,10 @@
#include "instructions/RabbitizerInstruction.h"
#include <assert.h>
#include "common/RabbitizerConfig.h"
#include "instructions/RabbitizerInstructionRsp.h"
#include "instructions/RabbitizerRegister.h"
@ -117,3 +120,150 @@ bool RabbitizerInstruction_sameOpcodeButDifferentArguments(const RabbitizerInstr
}
return RabbitizerInstruction_getRaw(self) != RabbitizerInstruction_getRaw(other);
}
bool RabbitizerInstruction_hasOperand(const RabbitizerInstruction *self, RabbitizerOperandType operand) {
size_t i;
for (i = 0; i < ARRAY_COUNT(self->descriptor->operands) && self->descriptor->operands[i] != RABBITIZER_OPERAND_TYPE_INVALID; i++) {
if (self->descriptor->operands[i] == operand) {
return true;
}
}
return false;
}
bool RabbitizerInstruction_isValid(const RabbitizerInstruction *self) {
size_t i;
uint32_t validbits;
validbits = self->_mandatorybits;
for (i = 0; i < ARRAY_COUNT(self->descriptor->operands) && self->descriptor->operands[i] != RABBITIZER_OPERAND_TYPE_INVALID; i++) {
switch (self->descriptor->operands[i]) {
case RABBITIZER_OPERAND_TYPE_rs:
validbits = RAB_INSTR_PACK_rs(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_rt:
validbits = RAB_INSTR_PACK_rt(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_rd:
validbits = RAB_INSTR_PACK_rd(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_sa:
validbits = RAB_INSTR_PACK_sa(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_cop0d:
validbits = RAB_INSTR_PACK_cop0d(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_fs:
validbits = RAB_INSTR_PACK_fs(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_ft:
validbits = RAB_INSTR_PACK_ft(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_fd:
validbits = RAB_INSTR_PACK_fd(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_cop1cs:
validbits = RAB_INSTR_PACK_cop1cs(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_cop2t:
validbits = RAB_INSTR_PACK_cop2t(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_op:
validbits = RAB_INSTR_PACK_op(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_code:
validbits = RAB_INSTR_PACK_code(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_LABEL:
validbits = RAB_INSTR_PACK_instr_index(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_IMM:
validbits = RAB_INSTR_PACK_immediate(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_IMM_base:
validbits = RAB_INSTR_PACK_immediate(validbits, ~0);
validbits = RAB_INSTR_PACK_rs(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_rs:
validbits = RAB_INSTR_PACK_rs(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_rt:
validbits = RAB_INSTR_PACK_rt(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_rd:
validbits = RAB_INSTR_PACK_rd(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_cop0d:
validbits = RAB_INSTR_PACK_cop0d(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vs:
validbits = RAB_INSTR_RSP_PACK_vs(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vt:
validbits = RAB_INSTR_RSP_PACK_vt(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vd:
validbits = RAB_INSTR_RSP_PACK_vd(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vt_elementhigh:
validbits = RAB_INSTR_RSP_PACK_vt(validbits, ~0);
validbits = RAB_INSTR_RSP_PACK_elementhigh(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vt_elementlow:
validbits = RAB_INSTR_RSP_PACK_vt(validbits, ~0);
validbits = RAB_INSTR_RSP_PACK_elementlow(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vd_vs:
validbits = RAB_INSTR_RSP_PACK_vd(validbits, ~0);
validbits = RAB_INSTR_RSP_PACK_vs(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_vd_index:
validbits = RAB_INSTR_RSP_PACK_vd(validbits, ~0);
validbits = RAB_INSTR_RSP_PACK_index(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_RSP_offset_rs:
validbits = RAB_INSTR_RSP_PACK_offset(validbits, ~0);
validbits = RAB_INSTR_PACK_rs(validbits, ~0);
break;
case RABBITIZER_OPERAND_TYPE_INVALID:
case RABBITIZER_OPERAND_TYPE_MAX:
assert(self->descriptor->operands[i] != RABBITIZER_OPERAND_TYPE_INVALID && self->descriptor->operands[i] != RABBITIZER_OPERAND_TYPE_MAX);
break;
}
}
return ((~validbits) & self->word) == 0;
}

View File

@ -8,7 +8,11 @@
void RabbitizerInstruction_processUniqueId_Normal(RabbitizerInstruction *self) {
switch (RAB_INSTR_GET_opcode(self)) {
uint32_t opcode = RAB_INSTR_GET_opcode(self);
self->_mandatorybits = RAB_INSTR_PACK_opcode(self->_mandatorybits, opcode);
switch (opcode) {
// 0b000000: "SPECIAL",
// 0b000001: "REGIMM",
case 0b000010:
@ -222,7 +226,11 @@ void RabbitizerInstruction_processUniqueId_Normal(RabbitizerInstruction *self) {
void RabbitizerInstruction_processUniqueId_Special(RabbitizerInstruction *self) {
switch (RAB_INSTR_GET_function(self)) {
uint32_t function = RAB_INSTR_GET_function(self);
self->_mandatorybits = RAB_INSTR_PACK_function(self->_mandatorybits, function);
switch (function) {
case 0b000000:
self->uniqueId = RABBITIZER_INSTR_ID_cpu_sll;
break;
@ -249,6 +257,7 @@ void RabbitizerInstruction_processUniqueId_Special(RabbitizerInstruction *self)
break;
case 0b001001:
self->uniqueId = RABBITIZER_INSTR_ID_cpu_jalr;
self->_mandatorybits = RAB_INSTR_PACK_rd(self->_mandatorybits, RAB_INSTR_GET_rd(self));
break;
case 0b001010:
self->uniqueId = RABBITIZER_INSTR_ID_cpu_movz;
@ -476,7 +485,11 @@ void RabbitizerInstruction_processUniqueId_Special(RabbitizerInstruction *self)
void RabbitizerInstruction_processUniqueId_Regimm(RabbitizerInstruction *self) {
switch (RAB_INSTR_GET_rt(self)) {
uint32_t rt = RAB_INSTR_GET_rt(self);
self->_mandatorybits = RAB_INSTR_PACK_rt(self->_mandatorybits, rt);
switch (rt) {
case 0b00000:
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bltz;
break;
@ -533,9 +546,15 @@ void RabbitizerInstruction_processUniqueId_Regimm(RabbitizerInstruction *self) {
void RabbitizerInstruction_processUniqueId_Coprocessor0(RabbitizerInstruction *self) {
self->_handwrittenCategory = true;
uint32_t fmt = RabbitizerInstruction_getFmt(self);
uint32_t tf;
uint32_t nd;
uint32_t function;
switch (RabbitizerInstruction_getFmt(self)) {
self->_handwrittenCategory = true;
self->_mandatorybits = RAB_INSTR_PACK_fmt(self->_mandatorybits, fmt);
switch (fmt) {
case 0b00000:
self->uniqueId = RABBITIZER_INSTR_ID_cpu_mfc0;
break;
@ -558,14 +577,18 @@ void RabbitizerInstruction_processUniqueId_Coprocessor0(RabbitizerInstruction *s
// 0b00_111: "",
case 0b01000:
if (RabbitizerInstruction_getTf(self)) {
if (RabbitizerInstruction_getNd(self)) {
tf = RabbitizerInstruction_getTf(self);
nd = RabbitizerInstruction_getNd(self);
self->_mandatorybits = RAB_INSTR_PACK_tf(self->_mandatorybits, tf);
self->_mandatorybits = RAB_INSTR_PACK_nd(self->_mandatorybits, nd);
if (tf) {
if (nd) {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bc0tl;
} else {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bc0t;
}
} else {
if (RabbitizerInstruction_getNd(self)) {
if (nd) {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bc0fl;
} else {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bc0f;
@ -574,7 +597,9 @@ void RabbitizerInstruction_processUniqueId_Coprocessor0(RabbitizerInstruction *s
break;
default:
switch (RAB_INSTR_GET_function(self)) {
function = RAB_INSTR_GET_function(self);
self->_mandatorybits = RAB_INSTR_PACK_function(self->_mandatorybits, function);
switch (function) {
case 0b000001:
self->uniqueId = RABBITIZER_INSTR_ID_cpu_tlbr;
break;
@ -605,8 +630,13 @@ void RabbitizerInstruction_processUniqueId_Coprocessor0(RabbitizerInstruction *s
void RabbitizerInstruction_processUniqueId_Coprocessor1(RabbitizerInstruction *self) {
uint8_t fmt = RabbitizerInstruction_getFmt(self);
uint8_t fc;
uint32_t tf;
uint32_t nd;
uint32_t function;
uint32_t cond;
self->uniqueId = RABBITIZER_INSTR_ID_cpu_INVALID;
self->_mandatorybits = RAB_INSTR_PACK_fmt(self->_mandatorybits, fmt);
// TODO
switch (fmt) {
case 0b00000:
@ -630,14 +660,18 @@ void RabbitizerInstruction_processUniqueId_Coprocessor1(RabbitizerInstruction *s
break;
case 0b01000: // fmt = BC
if (RabbitizerInstruction_getTf(self)) {
if (RabbitizerInstruction_getNd(self)) {
tf = RabbitizerInstruction_getTf(self);
nd = RabbitizerInstruction_getNd(self);
self->_mandatorybits = RAB_INSTR_PACK_tf(self->_mandatorybits, tf);
self->_mandatorybits = RAB_INSTR_PACK_nd(self->_mandatorybits, nd);
if (tf) {
if (nd) {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bc1tl;
} else {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bc1t;
}
} else {
if (RabbitizerInstruction_getNd(self)) {
if (nd) {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bc1fl;
} else {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_bc1f;
@ -647,7 +681,9 @@ void RabbitizerInstruction_processUniqueId_Coprocessor1(RabbitizerInstruction *s
default:
fmt = fmt & 0x07;
switch (RAB_INSTR_GET_function(self)) {
function = RAB_INSTR_GET_function(self);
self->_mandatorybits = RAB_INSTR_PACK_function(self->_mandatorybits, function);
switch (function) {
case 0b000000:
if (fmt == 0) {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_add_s;
@ -766,9 +802,12 @@ void RabbitizerInstruction_processUniqueId_Coprocessor1(RabbitizerInstruction *s
default:
fc = RabbitizerInstruction_getFc(self);
self->_mandatorybits = RAB_INSTR_PACK_fc(self->_mandatorybits, fc);
if (fc == 0b11) {
// Compare conditions codes
switch (RabbitizerInstruction_getCond(self)) {
cond = RabbitizerInstruction_getCond(self);
self->_mandatorybits = RAB_INSTR_PACK_cond(self->_mandatorybits, cond);
switch (cond) {
case 0b0000:
if (fmt == 0) {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_c_f_s;
@ -886,7 +925,7 @@ void RabbitizerInstruction_processUniqueId_Coprocessor1(RabbitizerInstruction *s
} else if (fc == 0b10) {
// Convert codes
switch (RAB_INSTR_GET_function(self) & 0x07) {
switch (function & 0x07) {
case 0b000:
if (fmt == 0b001) {
self->uniqueId = RABBITIZER_INSTR_ID_cpu_cvt_s_d;
@ -938,7 +977,11 @@ void RabbitizerInstruction_processUniqueId_Coprocessor2(RabbitizerInstruction *s
void RabbitizerInstruction_processUniqueId(RabbitizerInstruction *self) {
switch (RAB_INSTR_GET_opcode(self)) {
uint32_t opcode = RAB_INSTR_GET_opcode(self);
self->_mandatorybits = RAB_INSTR_PACK_opcode(self->_mandatorybits, opcode);
switch (opcode) {
default:
RabbitizerInstruction_processUniqueId_Normal(self);
break;

View File

@ -7,7 +7,13 @@
void RabbitizerInstructionRsp_processUniqueId_Normal(RabbitizerInstruction *self) {
switch (RAB_INSTR_GET_opcode(self)) {
uint32_t opcode = RAB_INSTR_GET_opcode(self);
uint32_t rd;
uint32_t elementlow;
self->_mandatorybits = RAB_INSTR_PACK_opcode(self->_mandatorybits, opcode);
switch (opcode) {
case 0b000010:
self->uniqueId = RABBITIZER_INSTR_ID_rsp_j;
break;
@ -98,7 +104,9 @@ void RabbitizerInstructionRsp_processUniqueId_Normal(RabbitizerInstruction *self
// new rsp stuff
case 0b111010:
switch (RAB_INSTR_GET_rd(self)) {
rd = RAB_INSTR_GET_rd(self);
self->_mandatorybits = RAB_INSTR_PACK_rd(self->_mandatorybits, rd);
switch (rd) {
case 0b00000:
self->uniqueId = RABBITIZER_INSTR_ID_rsp_sbv;
break;
@ -121,7 +129,9 @@ void RabbitizerInstructionRsp_processUniqueId_Normal(RabbitizerInstruction *self
self->uniqueId = RABBITIZER_INSTR_ID_rsp_spv;
break;
case 0b00111:
if (RAB_INSTR_RSP_GET_elementlow(self) == 0) {
elementlow = RAB_INSTR_RSP_GET_elementlow(self);
self->_mandatorybits = RAB_INSTR_RSP_PACK_elementlow(self->_mandatorybits, elementlow);
if (elementlow == 0) {
self->uniqueId = RABBITIZER_INSTR_ID_rsp_suv;
} else {
self->uniqueId = RABBITIZER_INSTR_ID_rsp_swv;
@ -144,7 +154,9 @@ void RabbitizerInstructionRsp_processUniqueId_Normal(RabbitizerInstruction *self
break;
case 0b110010:
switch (RAB_INSTR_GET_rd(self)) {
rd = RAB_INSTR_GET_rd(self);
self->_mandatorybits = RAB_INSTR_PACK_rd(self->_mandatorybits, rd);
switch (rd) {
case 0b00000:
self->uniqueId = RABBITIZER_INSTR_ID_rsp_lbv;
break;
@ -211,7 +223,11 @@ void RabbitizerInstructionRsp_processUniqueId_Normal(RabbitizerInstruction *self
void RabbitizerInstructionRsp_processUniqueId_Special(RabbitizerInstruction *self) {
switch (RAB_INSTR_GET_function(self)) {
uint32_t function = RAB_INSTR_GET_function(self);
self->_mandatorybits = RAB_INSTR_PACK_function(self->_mandatorybits, function);
switch (function) {
case 0b000000:
self->uniqueId = RABBITIZER_INSTR_ID_rsp_sll;
break;
@ -319,7 +335,11 @@ void RabbitizerInstructionRsp_processUniqueId_Special(RabbitizerInstruction *sel
void RabbitizerInstructionRsp_processUniqueId_Regimm(RabbitizerInstruction *self) {
switch (RAB_INSTR_GET_rt(self)) {
uint32_t rt = RAB_INSTR_GET_rt(self);
self->_mandatorybits = RAB_INSTR_PACK_rt(self->_mandatorybits, rt);
switch (rt) {
case 0b00000:
self->uniqueId = RABBITIZER_INSTR_ID_rsp_bltz;
break;
@ -344,7 +364,11 @@ void RabbitizerInstructionRsp_processUniqueId_Regimm(RabbitizerInstruction *self
void RabbitizerInstructionRsp_processUniqueId_Coprocessor0(RabbitizerInstruction *self) {
switch (RabbitizerInstruction_getFmt(self)) {
uint32_t fmt = RabbitizerInstruction_getFmt(self);
self->_mandatorybits = RAB_INSTR_PACK_fmt(self->_mandatorybits, fmt);
switch (fmt) {
case 0b00000:
self->uniqueId = RABBITIZER_INSTR_ID_rsp_mfc0;
break;
@ -363,8 +387,17 @@ void RabbitizerInstructionRsp_processUniqueId_Coprocessor0(RabbitizerInstruction
void RabbitizerInstructionRsp_processUniqueId_Coprocessor2(RabbitizerInstruction *self) {
if (((RAB_INSTR_GET_rs(self) >> 4) & 0x1) == 0) {
switch (RAB_INSTR_RSP_GET_elementhigh(self)) {
uint32_t aux = SHIFTR(self->word, 25, 1);
uint32_t elementhigh;
uint32_t function;
// TODO: name this bit range
self->_mandatorybits = BITREPACK(self->_mandatorybits, aux, 25, 1);
if (aux == 0) {
elementhigh = RAB_INSTR_RSP_GET_elementhigh(self);
self->_mandatorybits = RAB_INSTR_RSP_PACK_elementhigh(self->_mandatorybits, elementhigh);
switch (elementhigh) {
case 0b00000:
self->uniqueId = RABBITIZER_INSTR_ID_rsp_mfc2;
break;
@ -386,7 +419,9 @@ void RabbitizerInstructionRsp_processUniqueId_Coprocessor2(RabbitizerInstruction
break;
}
} else {
switch (RAB_INSTR_GET_function(self)) {
function = RAB_INSTR_GET_function(self);
self->_mandatorybits = RAB_INSTR_PACK_function(self->_mandatorybits, function);
switch (function) {
case 0x00:
self->uniqueId = RABBITIZER_INSTR_ID_rsp_vmulf;
break;
@ -533,7 +568,11 @@ void RabbitizerInstructionRsp_processUniqueId_Coprocessor2(RabbitizerInstruction
void RabbitizerInstructionRsp_processUniqueId(RabbitizerInstruction *self) {
switch (RAB_INSTR_GET_opcode(self)) {
uint32_t opcode = RAB_INSTR_GET_opcode(self);
self->_mandatorybits = RAB_INSTR_PACK_opcode(self->_mandatorybits, opcode);
switch (opcode) {
default:
RabbitizerInstructionRsp_processUniqueId_Normal(self);
break;

7
test.c
View File

@ -9,10 +9,13 @@
int main() {
uint32_t word = 0x8D4A7E18;
uint32_t word;
RabbitizerInstruction instr;
char *buffer;
int extraLJust = 10;
int extraLJust = 5;
// word = 0x8D4A7E18; // lw
word = 0x00004010; // mfhi
RabbitizerInstruction_init(&instr, word);