update mld,msim with new headers
This commit is contained in:
parent
b773ef9709
commit
e470009a16
4 changed files with 109 additions and 136 deletions
|
@ -8,9 +8,9 @@
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
#include <melf.h>
|
#include <melf.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
|
#include <mips32.h>
|
||||||
|
|
||||||
#include "link.h"
|
#include "link.h"
|
||||||
#include "mips.h"
|
|
||||||
|
|
||||||
static int load_objects(struct linker *linker)
|
static int load_objects(struct linker *linker)
|
||||||
{
|
{
|
||||||
|
@ -443,7 +443,7 @@ static int relocate_instruction_rela(struct linker *linker,
|
||||||
uint32_t sym_vaddr = B32(new_sym->st_value);
|
uint32_t sym_vaddr = B32(new_sym->st_value);
|
||||||
uint32_t *ins_raw = (uint32_t *) &seg->bytes[off];
|
uint32_t *ins_raw = (uint32_t *) &seg->bytes[off];
|
||||||
|
|
||||||
union mips_instruction_data ins;
|
union mips32_instruction ins;
|
||||||
ins.raw = B32(*ins_raw);
|
ins.raw = B32(*ins_raw);
|
||||||
|
|
||||||
uint32_t ins_vaddr = seg->new_vaddr + off;
|
uint32_t ins_vaddr = seg->new_vaddr + off;
|
||||||
|
|
|
@ -5,7 +5,6 @@
|
||||||
|
|
||||||
#include <linux/limits.h>
|
#include <linux/limits.h>
|
||||||
#include <mlimits.h>
|
#include <mlimits.h>
|
||||||
#include <mips.h>
|
|
||||||
#include <merror.h>
|
#include <merror.h>
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <elf.h>
|
#include <elf.h>
|
||||||
|
@ -224,7 +223,6 @@ struct object {
|
||||||
// program table
|
// program table
|
||||||
Elf32_Phdr *phdr;
|
Elf32_Phdr *phdr;
|
||||||
size_t phdr_len;
|
size_t phdr_len;
|
||||||
bool phdr_local; // if phdr was created though malloc
|
|
||||||
|
|
||||||
// phdr <=> shdr mappings
|
// phdr <=> shdr mappings
|
||||||
uint32_t *phdr_to_shdr_mapping;
|
uint32_t *phdr_to_shdr_mapping;
|
||||||
|
|
29
mld/obj.c
29
mld/obj.c
|
@ -105,7 +105,6 @@ static int create_phdr(struct object *object)
|
||||||
|
|
||||||
object->phdr = phdr;
|
object->phdr = phdr;
|
||||||
object->phdr_len = entries;
|
object->phdr_len = entries;
|
||||||
object->phdr_local = true;
|
|
||||||
|
|
||||||
uint32_t *mapping = malloc(entries * sizeof(uint32_t));
|
uint32_t *mapping = malloc(entries * sizeof(uint32_t));
|
||||||
if (mapping == NULL) {
|
if (mapping == NULL) {
|
||||||
|
@ -148,29 +147,6 @@ static int create_phdr(struct object *object)
|
||||||
return M_SUCCESS;
|
return M_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Map the phdr
|
|
||||||
*/
|
|
||||||
static int load_phdr(struct object *object)
|
|
||||||
{
|
|
||||||
//size_t phdr_len = B16(object->ehdr->e_phentsize) *
|
|
||||||
// B16(object->ehdr->e_phnum);
|
|
||||||
|
|
||||||
//if (phdr_len < 1)
|
|
||||||
return create_phdr(object);
|
|
||||||
|
|
||||||
//size_t phdr_off = B32(object->ehdr->e_phoff);
|
|
||||||
//object->phdr = (Elf32_Phdr *) (object->mapped + phdr_off);
|
|
||||||
//object->phdr_len = B16(object->ehdr->e_phnum);
|
|
||||||
|
|
||||||
//if (BOUND_CHK(object, phdr_len, phdr_off)) {
|
|
||||||
// ERROR("cannot read phdr");
|
|
||||||
// return M_ERROR;
|
|
||||||
//}
|
|
||||||
|
|
||||||
//return M_SUCCESS;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Load the strtabs
|
* Load the strtabs
|
||||||
*/
|
*/
|
||||||
|
@ -358,7 +334,6 @@ int object_load(struct object *object, char *path, uint32_t index)
|
||||||
object->mapped = NULL;
|
object->mapped = NULL;
|
||||||
object->name = path;
|
object->name = path;
|
||||||
object->index = index;
|
object->index = index;
|
||||||
object->phdr_local = false;
|
|
||||||
object->phdr_to_shdr_mapping = NULL;
|
object->phdr_to_shdr_mapping = NULL;
|
||||||
|
|
||||||
/** load the file */
|
/** load the file */
|
||||||
|
@ -374,7 +349,7 @@ int object_load(struct object *object, char *path, uint32_t index)
|
||||||
return M_ERROR;
|
return M_ERROR;
|
||||||
|
|
||||||
/* phdr */
|
/* phdr */
|
||||||
if (load_phdr(object))
|
if (create_phdr(object))
|
||||||
return M_ERROR;
|
return M_ERROR;
|
||||||
|
|
||||||
/* strtabs */
|
/* strtabs */
|
||||||
|
@ -404,7 +379,7 @@ void object_free(struct object *obj)
|
||||||
free(obj->strtabs);
|
free(obj->strtabs);
|
||||||
if (obj->segments != NULL)
|
if (obj->segments != NULL)
|
||||||
free(obj->segments);
|
free(obj->segments);
|
||||||
if (obj->phdr_local)
|
if (obj->phdr != NULL)
|
||||||
free(obj->phdr);
|
free(obj->phdr);
|
||||||
if (obj->phdr_to_shdr_mapping)
|
if (obj->phdr_to_shdr_mapping)
|
||||||
free(obj->phdr_to_shdr_mapping);
|
free(obj->phdr_to_shdr_mapping);
|
||||||
|
|
210
msim/ins.c
210
msim/ins.c
|
@ -1,8 +1,8 @@
|
||||||
#include <mips.h>
|
|
||||||
#include <melf.h>
|
#include <melf.h>
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <merror.h>
|
#include <merror.h>
|
||||||
|
#include <mips32r6.h>
|
||||||
#include "sim.h"
|
#include "sim.h"
|
||||||
|
|
||||||
/* sign extension */
|
/* sign extension */
|
||||||
|
@ -33,22 +33,22 @@ static void sim_delay_slot(struct simulator *sim)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
uint32_t ins = * (uint32_t *) (uintptr_t) sim->pc;
|
uint32_t ins = * (uint32_t *) (uintptr_t) sim->pc;
|
||||||
union mips_instruction_data data = { .raw = B32(ins) };
|
union mips32_instruction data = { .raw = B32(ins) };
|
||||||
sim->pc += 4;
|
sim->pc += 4;
|
||||||
|
|
||||||
switch (data.op) {
|
switch (data.op) {
|
||||||
case MIPS_OP_REGIMM:
|
case MIPS32R6_OP_REGIMM:
|
||||||
case MIPS_OP_J:
|
case MIPS32R6_OP_J:
|
||||||
case MIPS_OP_JAL:
|
case MIPS32R6_OP_JAL:
|
||||||
case MIPS_OP_JALX:
|
case MIPS32R6_OP_JALX:
|
||||||
case MIPS_OP_BEQ:
|
case MIPS32R6_OP_BEQ:
|
||||||
case MIPS_OP_BEQL:
|
case MIPS32R6_OP_BEQL:
|
||||||
case MIPS_OP_BNE:
|
case MIPS32R6_OP_BNE:
|
||||||
case MIPS_OP_BNEL:
|
case MIPS32R6_OP_BNEL:
|
||||||
case MIPS_OP_BGTZ:
|
case MIPS32R6_OP_BGTZ:
|
||||||
case MIPS_OP_BGTZL:
|
case MIPS32R6_OP_BGTZL:
|
||||||
case MIPS_OP_BLEZ:
|
case MIPS32R6_OP_BLEZ:
|
||||||
case MIPS_OP_BLEZL:
|
case MIPS32R6_OP_BLEZL:
|
||||||
sim_dump(sim, "attempted to execute jump instruction in delay"
|
sim_dump(sim, "attempted to execute jump instruction in delay"
|
||||||
"slot (0b%05b)", data.op);
|
"slot (0b%05b)", data.op);
|
||||||
default:
|
default:
|
||||||
|
@ -58,15 +58,15 @@ static void sim_delay_slot(struct simulator *sim)
|
||||||
}
|
}
|
||||||
|
|
||||||
static void sim_ins_special_sop30(struct simulator *sim,
|
static void sim_ins_special_sop30(struct simulator *sim,
|
||||||
union mips_instruction_data ins)
|
union mips32_instruction ins)
|
||||||
{
|
{
|
||||||
switch (ins.shamt) {
|
switch (ins.shamt) {
|
||||||
case MIPS_SOP30_MUL:
|
case MIPS32R6_SOP30_MUL:
|
||||||
sim->reg[ins.rd] = (SSE64(sim->reg[ins.rs]) *
|
sim->reg[ins.rd] = (SSE64(sim->reg[ins.rs]) *
|
||||||
SSE64(sim->reg[ins.rt])) >> 0;
|
SSE64(sim->reg[ins.rt])) >> 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_SOP30_MUH:
|
case MIPS32R6_SOP30_MUH:
|
||||||
sim->reg[ins.rd] = (SSE64(sim->reg[ins.rs]) *
|
sim->reg[ins.rd] = (SSE64(sim->reg[ins.rs]) *
|
||||||
SSE64(sim->reg[ins.rt])) >> 32;
|
SSE64(sim->reg[ins.rt])) >> 32;
|
||||||
break;
|
break;
|
||||||
|
@ -77,15 +77,15 @@ static void sim_ins_special_sop30(struct simulator *sim,
|
||||||
}
|
}
|
||||||
|
|
||||||
static void sim_ins_special_sop31(struct simulator *sim,
|
static void sim_ins_special_sop31(struct simulator *sim,
|
||||||
union mips_instruction_data ins)
|
union mips32_instruction ins)
|
||||||
{
|
{
|
||||||
switch (ins.shamt) {
|
switch (ins.shamt) {
|
||||||
case MIPS_SOP31_MULU:
|
case MIPS32R6_SOP31_MULU:
|
||||||
sim->reg[ins.rd] = (SE64(sim->reg[ins.rs]) *
|
sim->reg[ins.rd] = (SE64(sim->reg[ins.rs]) *
|
||||||
SE64(sim->reg[ins.rt])) >> 0;
|
SE64(sim->reg[ins.rt])) >> 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_SOP31_MUHU:
|
case MIPS32R6_SOP31_MUHU:
|
||||||
sim->reg[ins.rd] = (SE64(sim->reg[ins.rs]) *
|
sim->reg[ins.rd] = (SE64(sim->reg[ins.rs]) *
|
||||||
SE64(sim->reg[ins.rt])) >> 32;
|
SE64(sim->reg[ins.rt])) >> 32;
|
||||||
break;
|
break;
|
||||||
|
@ -96,15 +96,15 @@ static void sim_ins_special_sop31(struct simulator *sim,
|
||||||
}
|
}
|
||||||
|
|
||||||
static void sim_ins_special_sop32(struct simulator *sim,
|
static void sim_ins_special_sop32(struct simulator *sim,
|
||||||
union mips_instruction_data ins)
|
union mips32_instruction ins)
|
||||||
{
|
{
|
||||||
switch (ins.shamt) {
|
switch (ins.shamt) {
|
||||||
case MIPS_SOP32_DIV:
|
case MIPS32R6_SOP32_DIV:
|
||||||
sim->reg[ins.rd] = (signed) sim->reg[ins.rs] /
|
sim->reg[ins.rd] = (signed) sim->reg[ins.rs] /
|
||||||
(signed) sim->reg[ins.rt];
|
(signed) sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_SOP32_MOD:
|
case MIPS32R6_SOP32_MOD:
|
||||||
sim->reg[ins.rd] = (signed) sim->reg[ins.rs] %
|
sim->reg[ins.rd] = (signed) sim->reg[ins.rs] %
|
||||||
(signed) sim->reg[ins.rt];
|
(signed) sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
@ -115,14 +115,14 @@ static void sim_ins_special_sop32(struct simulator *sim,
|
||||||
}
|
}
|
||||||
|
|
||||||
static void sim_ins_special_sop33(struct simulator *sim,
|
static void sim_ins_special_sop33(struct simulator *sim,
|
||||||
union mips_instruction_data ins)
|
union mips32_instruction ins)
|
||||||
{
|
{
|
||||||
switch (ins.shamt) {
|
switch (ins.shamt) {
|
||||||
case MIPS_SOP33_DIVU:
|
case MIPS32R6_SOP33_DIVU:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] / sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] / sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_SOP33_MODU:
|
case MIPS32R6_SOP33_MODU:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] % sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] % sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -132,124 +132,124 @@ static void sim_ins_special_sop33(struct simulator *sim,
|
||||||
}
|
}
|
||||||
|
|
||||||
static void sim_ins_special(struct simulator *sim,
|
static void sim_ins_special(struct simulator *sim,
|
||||||
union mips_instruction_data ins)
|
union mips32_instruction ins)
|
||||||
{
|
{
|
||||||
switch (ins.funct) {
|
switch (ins.funct) {
|
||||||
case MIPS_FUNCT_ADD:
|
case MIPS32R6_FUNCT_ADD:
|
||||||
// TODO: trap on overflow
|
// TODO: trap on overflow
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] + sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] + sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_ADDU:
|
case MIPS32R6_FUNCT_ADDU:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] + sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] + sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_AND:
|
case MIPS32R6_FUNCT_AND:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] & sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] & sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SOP30:
|
case MIPS32R6_FUNCT_SOP30:
|
||||||
sim_ins_special_sop30(sim, ins);
|
sim_ins_special_sop30(sim, ins);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SOP31:
|
case MIPS32R6_FUNCT_SOP31:
|
||||||
sim_ins_special_sop31(sim, ins);
|
sim_ins_special_sop31(sim, ins);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SOP32:
|
case MIPS32R6_FUNCT_SOP32:
|
||||||
sim_ins_special_sop32(sim, ins);
|
sim_ins_special_sop32(sim, ins);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SOP33:
|
case MIPS32R6_FUNCT_SOP33:
|
||||||
sim_ins_special_sop33(sim, ins);
|
sim_ins_special_sop33(sim, ins);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_JALR:
|
case MIPS32R6_FUNCT_JALR:
|
||||||
sim->reg[ins.rd] = sim->pc + 4;
|
sim->reg[ins.rd] = sim->pc + 4;
|
||||||
/* fall through */
|
/* fall through */
|
||||||
case MIPS_FUNCT_JR:
|
case MIPS32R6_FUNCT_JR:
|
||||||
sim_delay_slot(sim);
|
sim_delay_slot(sim);
|
||||||
sim->pc = sim->reg[ins.rs];
|
sim->pc = sim->reg[ins.rs];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_MFHI:
|
case MIPS32R6_FUNCT_MFHI:
|
||||||
sim->reg[ins.rd] = sim->hi;
|
sim->reg[ins.rd] = sim->hi;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_MFLO:
|
case MIPS32R6_FUNCT_MFLO:
|
||||||
sim->reg[ins.rd] = sim->low;
|
sim->reg[ins.rd] = sim->low;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_MTHI:
|
case MIPS32R6_FUNCT_MTHI:
|
||||||
sim->hi = sim->reg[ins.rd];
|
sim->hi = sim->reg[ins.rd];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_MTLO:
|
case MIPS32R6_FUNCT_MTLO:
|
||||||
sim->low = sim->reg[ins.rd];
|
sim->low = sim->reg[ins.rd];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SLL:
|
case MIPS32R6_FUNCT_SLL:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rt] << ins.shamt;
|
sim->reg[ins.rd] = sim->reg[ins.rt] << ins.shamt;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SLLV:
|
case MIPS32R6_FUNCT_SLLV:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rt] << sim->reg[ins.rs];
|
sim->reg[ins.rd] = sim->reg[ins.rt] << sim->reg[ins.rs];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SLT:
|
case MIPS32R6_FUNCT_SLT:
|
||||||
sim->reg[ins.rd] = (signed) sim->reg[ins.rs] <
|
sim->reg[ins.rd] = (signed) sim->reg[ins.rs] <
|
||||||
(signed) sim->reg[ins.rt] ? 1 : 0;
|
(signed) sim->reg[ins.rt] ? 1 : 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SLTU:
|
case MIPS32R6_FUNCT_SLTU:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] < sim->reg[ins.rt] ? 1 : 0;
|
sim->reg[ins.rd] = sim->reg[ins.rs] < sim->reg[ins.rt] ? 1 : 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SRA:
|
case MIPS32R6_FUNCT_SRA:
|
||||||
sim->reg[ins.rd] = (signed) sim->reg[ins.rt] >> ins.shamt;
|
sim->reg[ins.rd] = (signed) sim->reg[ins.rt] >> ins.shamt;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SRAV:
|
case MIPS32R6_FUNCT_SRAV:
|
||||||
sim->reg[ins.rd] = (signed) sim->reg[ins.rt] >>
|
sim->reg[ins.rd] = (signed) sim->reg[ins.rt] >>
|
||||||
sim->reg[ins.rs];
|
sim->reg[ins.rs];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SRL:
|
case MIPS32R6_FUNCT_SRL:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rt] >> ins.shamt;
|
sim->reg[ins.rd] = sim->reg[ins.rt] >> ins.shamt;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SRLV:
|
case MIPS32R6_FUNCT_SRLV:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rt] >> sim->reg[ins.rs];
|
sim->reg[ins.rd] = sim->reg[ins.rt] >> sim->reg[ins.rs];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SUB:
|
case MIPS32R6_FUNCT_SUB:
|
||||||
// TODO: trap on overflow
|
// TODO: trap on overflow
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] - sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] - sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SUBU:
|
case MIPS32R6_FUNCT_SUBU:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] - sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] - sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_SYSCALL:
|
case MIPS32R6_FUNCT_SYSCALL:
|
||||||
sim->reg[MIPS_REG_V0] = syscall(
|
sim->reg[MIPS32_REG_V0] = syscall(
|
||||||
sim->reg[MIPS_REG_V0],
|
sim->reg[MIPS32_REG_V0],
|
||||||
sim->reg[MIPS_REG_A0],
|
sim->reg[MIPS32_REG_A0],
|
||||||
sim->reg[MIPS_REG_A1],
|
sim->reg[MIPS32_REG_A1],
|
||||||
sim->reg[MIPS_REG_A2],
|
sim->reg[MIPS32_REG_A2],
|
||||||
sim->reg[MIPS_REG_A3]
|
sim->reg[MIPS32_REG_A3]
|
||||||
);
|
);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_OR:
|
case MIPS32R6_FUNCT_OR:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] | sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] | sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_NOR:
|
case MIPS32R6_FUNCT_NOR:
|
||||||
sim->reg[ins.rd] = !(sim->reg[ins.rs] | sim->reg[ins.rt]);
|
sim->reg[ins.rd] = !(sim->reg[ins.rs] | sim->reg[ins.rt]);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_XOR:
|
case MIPS32R6_FUNCT_XOR:
|
||||||
sim->reg[ins.rd] = sim->reg[ins.rs] ^ sim->reg[ins.rt];
|
sim->reg[ins.rd] = sim->reg[ins.rs] ^ sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
@ -259,28 +259,28 @@ static void sim_ins_special(struct simulator *sim,
|
||||||
}
|
}
|
||||||
|
|
||||||
static void sim_ins_regimm(struct simulator *sim,
|
static void sim_ins_regimm(struct simulator *sim,
|
||||||
union mips_instruction_data ins)
|
union mips32_instruction ins)
|
||||||
{
|
{
|
||||||
uint32_t pc = sim->pc;
|
uint32_t pc = sim->pc;
|
||||||
|
|
||||||
switch (ins.bfunct) {
|
switch (ins.bfunct) {
|
||||||
case MIPS_FUNCT_BGEZAL:
|
case MIPS32R6_FUNCT_BGEZAL:
|
||||||
case MIPS_FUNCT_BGEZALL:
|
case MIPS32R6_FUNCT_BGEZALL:
|
||||||
sim->reg[MIPS_REG_RA] = sim->pc + 4;
|
sim->reg[MIPS32_REG_RA] = sim->pc + 4;
|
||||||
/* fall through */
|
/* fall through */
|
||||||
case MIPS_FUNCT_BGEZ:
|
case MIPS32R6_FUNCT_BGEZ:
|
||||||
case MIPS_FUNCT_BGEZL:
|
case MIPS32R6_FUNCT_BGEZL:
|
||||||
sim_delay_slot(sim);
|
sim_delay_slot(sim);
|
||||||
if ((signed) sim->reg[ins.rs] >= 0)
|
if ((signed) sim->reg[ins.rs] >= 0)
|
||||||
sim->pc = pc + SSE(ins.offset, 2);
|
sim->pc = pc + SSE(ins.offset, 2);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_FUNCT_BLTZAL:
|
case MIPS32R6_FUNCT_BLTZAL:
|
||||||
case MIPS_FUNCT_BLTZALL:
|
case MIPS32R6_FUNCT_BLTZALL:
|
||||||
sim->reg[MIPS_REG_RA] = sim->pc + 4;
|
sim->reg[MIPS32_REG_RA] = sim->pc + 4;
|
||||||
/* fall through */
|
/* fall through */
|
||||||
case MIPS_FUNCT_BLTZ:
|
case MIPS32R6_FUNCT_BLTZ:
|
||||||
case MIPS_FUNCT_BLTZL:
|
case MIPS32R6_FUNCT_BLTZL:
|
||||||
sim_delay_slot(sim);
|
sim_delay_slot(sim);
|
||||||
if ((signed) sim->reg[ins.rs] < 0)
|
if ((signed) sim->reg[ins.rs] < 0)
|
||||||
sim->pc = pc + SSE(ins.offset, 2);
|
sim->pc = pc + SSE(ins.offset, 2);
|
||||||
|
@ -294,130 +294,130 @@ static void sim_ins_regimm(struct simulator *sim,
|
||||||
void sim_ins(struct simulator *sim, uint32_t raw)
|
void sim_ins(struct simulator *sim, uint32_t raw)
|
||||||
{
|
{
|
||||||
// get ins parts
|
// get ins parts
|
||||||
union mips_instruction_data ins = {
|
union mips32_instruction ins = {
|
||||||
.raw = B32(raw)
|
.raw = B32(raw)
|
||||||
};
|
};
|
||||||
uint32_t pc = sim->pc;
|
uint32_t pc = sim->pc;
|
||||||
|
|
||||||
// reset zero reg
|
// reset zero reg
|
||||||
sim->reg[MIPS_REG_ZERO] = 0;
|
sim->reg[MIPS32_REG_ZERO] = 0;
|
||||||
|
|
||||||
switch (ins.op) {
|
switch (ins.op) {
|
||||||
case MIPS_OP_SPECIAL:
|
case MIPS32R6_OP_SPECIAL:
|
||||||
sim_ins_special(sim, ins);
|
sim_ins_special(sim, ins);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_REGIMM:
|
case MIPS32R6_OP_REGIMM:
|
||||||
sim_ins_regimm(sim, ins);
|
sim_ins_regimm(sim, ins);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_ADDI:
|
case MIPS32R6_OP_ADDI:
|
||||||
sim->reg[ins.rt] = (int32_t)sim->reg[ins.rs] +
|
sim->reg[ins.rt] = (int32_t)sim->reg[ins.rs] +
|
||||||
SE(ins.immd);
|
SE(ins.immd);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_ADDIU:
|
case MIPS32R6_OP_ADDIU:
|
||||||
sim->reg[ins.rt] = sim->reg[ins.rs] + SE(ins.immd);
|
sim->reg[ins.rt] = sim->reg[ins.rs] + SE(ins.immd);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_ANDI:
|
case MIPS32R6_OP_ANDI:
|
||||||
sim->reg[ins.rt] = sim->reg[ins.rs] & ZE(ins.immd);
|
sim->reg[ins.rt] = sim->reg[ins.rs] & ZE(ins.immd);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_BALC:
|
case MIPS32R6_OP_BALC:
|
||||||
sim->reg[MIPS_REG_RA] = sim->pc;
|
sim->reg[MIPS32_REG_RA] = sim->pc;
|
||||||
/* fall through */
|
/* fall through */
|
||||||
case MIPS_OP_BC:
|
case MIPS32R6_OP_BC:
|
||||||
sim->pc += SSE(ins.offs26, 2);
|
sim->pc += SSE(ins.offs26, 2);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_BEQ:
|
case MIPS32R6_OP_BEQ:
|
||||||
case MIPS_OP_BEQL:
|
case MIPS32R6_OP_BEQL:
|
||||||
sim_delay_slot(sim);
|
sim_delay_slot(sim);
|
||||||
if (sim->reg[ins.rs] == sim->reg[ins.rt])
|
if (sim->reg[ins.rs] == sim->reg[ins.rt])
|
||||||
sim->pc = pc + SSE(ins.offset, 2);
|
sim->pc = pc + SSE(ins.offset, 2);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_BGTZ:
|
case MIPS32R6_OP_BGTZ:
|
||||||
case MIPS_OP_BGTZL:
|
case MIPS32R6_OP_BGTZL:
|
||||||
sim_delay_slot(sim);
|
sim_delay_slot(sim);
|
||||||
if ((signed) sim->reg[ins.rs] <= 0)
|
if ((signed) sim->reg[ins.rs] <= 0)
|
||||||
sim->pc = pc + SSE(ins.offset, 2);
|
sim->pc = pc + SSE(ins.offset, 2);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_BLEZ:
|
case MIPS32R6_OP_BLEZ:
|
||||||
case MIPS_OP_BLEZL:
|
case MIPS32R6_OP_BLEZL:
|
||||||
sim_delay_slot(sim);
|
sim_delay_slot(sim);
|
||||||
if ((signed) sim->reg[ins.rs] <= 0)
|
if ((signed) sim->reg[ins.rs] <= 0)
|
||||||
sim->pc = pc + SSE(ins.offset, 2);
|
sim->pc = pc + SSE(ins.offset, 2);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_BNE:
|
case MIPS32R6_OP_BNE:
|
||||||
case MIPS_OP_BNEL:
|
case MIPS32R6_OP_BNEL:
|
||||||
sim_delay_slot(sim);
|
sim_delay_slot(sim);
|
||||||
if (sim->reg[ins.rs] != sim->reg[ins.rt])
|
if (sim->reg[ins.rs] != sim->reg[ins.rt])
|
||||||
sim->pc = pc + SSE(ins.offset, 2);
|
sim->pc = pc + SSE(ins.offset, 2);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_JAL:
|
case MIPS32R6_OP_JAL:
|
||||||
sim->reg[MIPS_REG_RA] = sim->pc + 4;
|
sim->reg[MIPS32_REG_RA] = sim->pc + 4;
|
||||||
/* fall through */
|
/* fall through */
|
||||||
case MIPS_OP_J:
|
case MIPS32R6_OP_J:
|
||||||
sim_delay_slot(sim);
|
sim_delay_slot(sim);
|
||||||
sim->pc &= 0xF0000000;
|
sim->pc &= 0xF0000000;
|
||||||
sim->pc |= ins.target << 2;
|
sim->pc |= ins.target << 2;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_LB:
|
case MIPS32R6_OP_LB:
|
||||||
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), int8_t);
|
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), int8_t);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_LBU:
|
case MIPS32R6_OP_LBU:
|
||||||
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), uint8_t);
|
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), uint8_t);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_LH:
|
case MIPS32R6_OP_LH:
|
||||||
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), int16_t);
|
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), int16_t);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_LHU:
|
case MIPS32R6_OP_LHU:
|
||||||
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), uint16_t);
|
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), uint16_t);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_LUI:
|
case MIPS32R6_OP_LUI:
|
||||||
sim->reg[ins.rt] = ins.immd << 16;
|
sim->reg[ins.rt] = ins.immd << 16;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_LW:
|
case MIPS32R6_OP_LW:
|
||||||
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), uint32_t);
|
sim->reg[ins.rt] = *PTR(VADDR(sim, ins), uint32_t);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_SB:
|
case MIPS32R6_OP_SB:
|
||||||
*PTR(VADDR(sim, ins), uint8_t) = sim->reg[ins.rt];
|
*PTR(VADDR(sim, ins), uint8_t) = sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_SH:
|
case MIPS32R6_OP_SH:
|
||||||
*PTR(VADDR(sim, ins), uint16_t) = sim->reg[ins.rt];
|
*PTR(VADDR(sim, ins), uint16_t) = sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_SW:
|
case MIPS32R6_OP_SW:
|
||||||
*PTR(VADDR(sim, ins), uint32_t) = sim->reg[ins.rt];
|
*PTR(VADDR(sim, ins), uint32_t) = sim->reg[ins.rt];
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_SLTI:
|
case MIPS32R6_OP_SLTI:
|
||||||
sim->reg[ins.rt] = (signed) sim->reg[ins.rs] <
|
sim->reg[ins.rt] = (signed) sim->reg[ins.rs] <
|
||||||
(signed) SE(ins.immd) ? 1 : 0;
|
(signed) SE(ins.immd) ? 1 : 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_SLTIU:
|
case MIPS32R6_OP_SLTIU:
|
||||||
sim->reg[ins.rt] = sim->reg[ins.rs] < SE(ins.immd) ? 1 : 0;
|
sim->reg[ins.rt] = sim->reg[ins.rs] < SE(ins.immd) ? 1 : 0;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_ORI:
|
case MIPS32R6_OP_ORI:
|
||||||
sim->reg[ins.rt] = sim->reg[ins.rs] | ins.immd;
|
sim->reg[ins.rt] = sim->reg[ins.rs] | ins.immd;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case MIPS_OP_XORI:
|
case MIPS32R6_OP_XORI:
|
||||||
sim->reg[ins.rt] = sim->reg[ins.rs] ^ ins.immd;
|
sim->reg[ins.rt] = sim->reg[ins.rs] ^ ins.immd;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue