#include"scf_vm.h"
-#define NAJA_REG_FP 29
-#define NAJA_REG_LR 30
-#define NAJA_REG_SP 31
-
static const char* somaps[][3] =
{
{"x64", "/lib/ld-linux-aarch64.so.1", "/lib64/ld-linux-x86-64.so.2"},
{"x64", "/lib/aarch64-linux-gnu/libc.so.6", "/lib/x86_64-linux-gnu/libc.so.6"},
};
-typedef int64_t (*naja_dyn_func_pt)(uint64_t r0,
+typedef int (*dyn_func_pt)(uint64_t r0,
uint64_t r1,
uint64_t r2,
uint64_t r3,
uint64_t r4,
uint64_t r5,
uint64_t r6,
- uint64_t r7);
+ uint64_t r7,
+ double d0,
+ double d1,
+ double d2,
+ double d3,
+ double d4,
+ double d5,
+ double d6,
+ double d7);
int naja_vm_open(scf_vm_t* vm)
{
static int naja_vm_dynamic_link(scf_vm_t* vm)
{
- naja_dyn_func_pt f = NULL;
- scf_vm_naja_t* naja = vm->priv;
+ scf_vm_naja_t* naja = vm->priv;
+ dyn_func_pt f = NULL;
int64_t sp = naja->regs[NAJA_REG_SP];
if (r16 == vm->jmprel[i].r_offset) {
int j = ELF64_R_SYM(vm->jmprel[i].r_info);
-
char* fname = vm->dynstr + vm->dynsym[j].st_name;
scf_logw("j: %d, %s\n", j, fname);
naja->regs[4],
naja->regs[5],
naja->regs[6],
- naja->regs[7]);
+ naja->regs[7],
+ naja->fvec[0].d[0],
+ naja->fvec[1].d[0],
+ naja->fvec[2].d[0],
+ naja->fvec[3].d[0],
+ naja->fvec[4].d[0],
+ naja->fvec[5].d[0],
+ naja->fvec[6].d[0],
+ naja->fvec[7].d[0]);
naja->regs[NAJA_REG_SP] += 16;
return 0;
naja->regs[rd] = naja->regs[rs0] + uimm15;
- printf("add r%d, r%d, %lu\n", rd, rs0, uimm15);
+ NAJA_PRINTF("add r%d, r%d, %lu\n", rd, rs0, uimm15);
} else {
uint64_t sh = (inst >> 18) & 0x3;
uint64_t uimm8 = (inst >> 10) & 0xff;
if (0 == sh) {
naja->regs[rd] = naja->regs[rs0] + (naja->regs[rs1] << uimm8);
- printf("add r%d, r%d, r%d << %lu\n", rd, rs0, rs1, uimm8);
+ NAJA_PRINTF("add r%d, r%d, r%d << %lu\n", rd, rs0, rs1, uimm8);
} else if (1 == sh) {
naja->regs[rd] = naja->regs[rs0] + (naja->regs[rs1] >> uimm8);
- printf("add r%d, r%d, r%d LSR %lu\n", rd, rs0, rs1, uimm8);
+ NAJA_PRINTF("add r%d, r%d, r%d LSR %lu\n", rd, rs0, rs1, uimm8);
} else {
naja->regs[rd] = naja->regs[rs0] + (((int64_t)naja->regs[rs1]) >> uimm8);
- printf("add r%d, r%d, r%d ASR %lu\n", rd, rs0, rs1, uimm8);
+ NAJA_PRINTF("add r%d, r%d, r%d ASR %lu\n", rd, rs0, rs1, uimm8);
}
}
return 0;
}
+static int __naja_fadd(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+
+ naja->fvec[rd].d[0] = naja->fvec[rs0].d[0] + naja->fvec[rs1].d[0];
+
+ NAJA_PRINTF("fadd d%d, d%d, d%d\n", rd, rs0, rs1);
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fsub(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+
+ naja->fvec[rd].d[0] = naja->fvec[rs0].d[0] - naja->fvec[rs1].d[0];
+
+ NAJA_PRINTF("fsub r%d, r%d, r%d\n", rd, rs0, rs1);
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fcmp(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+
+ double d = naja->fvec[rs0].d[0] - naja->fvec[rs1].d[0];
+
+ NAJA_PRINTF("fcmp d%d, d%d\n", rs0, rs1);
+
+ if (d > 0.0)
+ naja->flags = 0x4;
+ else if (d < 0.0)
+ naja->flags = 0x2;
+ else
+ naja->flags = 0x1;
+
+ naja->ip += 4;
+ return 0;
+}
+
static int __naja_sub(scf_vm_t* vm, uint32_t inst)
{
scf_vm_naja_t* naja = vm->priv;
naja->regs[rd] = naja->regs[rs0] - uimm15;
- printf("sub r%d, r%d, %lu\n", rd, rs0, uimm15);
+ NAJA_PRINTF("sub r%d, r%d, %lu\n", rd, rs0, uimm15);
} else {
uint64_t sh = (inst >> 18) & 0x3;
uint64_t uimm8 = (inst >> 10) & 0xff;
if (0 == sh) {
naja->regs[rd] = naja->regs[rs0] - (naja->regs[rs1] << uimm8);
- printf("sub r%d, r%d, r%d << %lu\n", rd, rs0, rs1, uimm8);
+ NAJA_PRINTF("sub r%d, r%d, r%d << %lu\n", rd, rs0, rs1, uimm8);
} else if (1 == sh) {
naja->regs[rd] = naja->regs[rs0] - (naja->regs[rs1] >> uimm8);
- printf("sub r%d, r%d, r%d LSR %lu\n", rd, rs0, rs1, uimm8);
+ NAJA_PRINTF("sub r%d, r%d, r%d LSR %lu\n", rd, rs0, rs1, uimm8);
} else {
naja->regs[rd] = naja->regs[rs0] - (((int64_t)naja->regs[rs1]) >> uimm8);
- printf("sub r%d, r%d, r%d ASR %lu\n", rd, rs0, rs1, uimm8);
+ NAJA_PRINTF("sub r%d, r%d, r%d ASR %lu\n", rd, rs0, rs1, uimm8);
}
}
scf_vm_naja_t* naja = vm->priv;
int rs0 = inst & 0x1f;
- int rd = (inst >> 21) & 0x1f;
int I = (inst >> 20) & 0x1;
int ret = 0;
ret = naja->regs[rs0] - uimm15;
- printf("cmp r%d, %ld, rs0: %lx, ret: %d\n", rs0, uimm15, naja->regs[rs0], ret);
+ NAJA_PRINTF("cmp r%d, %ld, rs0: %lx, ret: %d\n", rs0, uimm15, naja->regs[rs0], ret);
} else {
uint64_t sh = (inst >> 18) & 0x3;
if (0 == sh) {
ret = naja->regs[rs0] - (naja->regs[rs1] << uimm8);
- printf("cmp r%d, r%d LSL %ld, rs0: %#lx, rs1: %#lx, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
+ NAJA_PRINTF("cmp r%d, r%d LSL %ld, rs0: %#lx, rs1: %#lx, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
} else if (1 == sh) {
ret = naja->regs[rs0] - (naja->regs[rs1] >> uimm8);
- printf("cmp r%d, r%d LSR %ld, rs0: %#lx, rs1: %#lx, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
+ NAJA_PRINTF("cmp r%d, r%d LSR %ld, rs0: %#lx, rs1: %#lx, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
} else {
ret = naja->regs[rs0] - (((int64_t)naja->regs[rs1]) >> uimm8);
- printf("cmp r%d, r%d ASR %ld, rs0: %#lx, rs1: %ld, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
+ NAJA_PRINTF("cmp r%d, r%d ASR %ld, rs0: %#lx, rs1: %ld, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
}
}
int S = (inst >> 20) & 0x1;
int opt = (inst >> 15) & 0x3;
- scf_logw("\n");
if (S)
naja->regs[rd] = (int64_t)naja->regs[rs0] * (int64_t)naja->regs[rs1];
else
naja->regs[rd] = naja->regs[rs0] * naja->regs[rs1];
- if (0 == opt)
+ if (0 == opt) {
naja->regs[rd] += naja->regs[rs2];
- else if (1 == opt)
+
+ NAJA_PRINTF("madd r%d, r%d, r%d, r%d", rd, rs2, rs0, rs1);
+ } else if (1 == opt) {
naja->regs[rd] = naja->regs[rs2] - naja->regs[rd];
+ NAJA_PRINTF("msub r%d, r%d, r%d, r%d", rd, rs2, rs0, rs1);
+ } else {
+ if (S)
+ NAJA_PRINTF("smul r%d, r%d, r%d", rd, rs0, rs1);
+ else
+ NAJA_PRINTF("mul r%d, r%d, r%d", rd, rs0, rs1);
+ }
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fmul(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+ int rs2 = (inst >> 10) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int opt = (inst >> 18) & 0x3;
+
+ naja->fvec[rd].d[0] = naja->fvec[rs0].d[0] * naja->fvec[rs1].d[0];
+
+ if (0 == opt) {
+ naja->fvec[rd].d[0] += naja->fvec[rs2].d[0];
+
+ NAJA_PRINTF("fmadd d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+
+ } else if (1 == opt) {
+ naja->fvec[rd].d[0] = naja->fvec[rs2].d[0] - naja->fvec[rd].d[0];
+
+ NAJA_PRINTF("fmsub d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+ } else
+ NAJA_PRINTF("fmul d%d, d%d, d%d", rd, rs0, rs1);
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fdiv(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+ int rs2 = (inst >> 10) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int opt = (inst >> 18) & 0x3;
+
+ naja->fvec[rd].d[0] = naja->fvec[rs0].d[0] / naja->fvec[rs1].d[0];
+
+ if (0 == opt) {
+ naja->fvec[rd].d[0] += naja->fvec[rs2].d[0];
+
+ NAJA_PRINTF("fdadd d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+
+ } else if (1 == opt) {
+ naja->fvec[rd].d[0] = naja->fvec[rs2].d[0] - naja->fvec[rd].d[0];
+
+ NAJA_PRINTF("fdsub d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+ } else
+ NAJA_PRINTF("fdiv d%d, d%d, d%d", rd, rs0, rs1);
+
naja->ip += 4;
return 0;
}
int S = (inst >> 20) & 0x1;
int opt = (inst >> 15) & 0x3;
- scf_logw("\n");
if (S)
naja->regs[rd] = (int64_t)naja->regs[rs0] / (int64_t)naja->regs[rs1];
else
naja->regs[rd] = naja->regs[rs0] / naja->regs[rs1];
- if (0 == opt)
+ if (0 == opt) {
naja->regs[rd] += naja->regs[rs2];
- else if (1 == opt)
+
+ NAJA_PRINTF("fdadd d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+
+ } else if (1 == opt) {
naja->regs[rd] = naja->regs[rs2] - naja->regs[rd];
+ NAJA_PRINTF("dsub r%d, r%d, r%d, r%d", rd, rs2, rs0, rs1);
+ } else {
+ if (S)
+ NAJA_PRINTF("sdiv r%d, r%d, r%d", rd, rs0, rs1);
+ else
+ NAJA_PRINTF("div r%d, r%d, r%d", rd, rs0, rs1);
+ }
+
naja->ip += 4;
return 0;
}
-static int __naja_ldr_disp(scf_vm_t* vm, uint32_t inst)
+static int __naja_mem(scf_vm_t* vm, int64_t addr, uint8_t** pdata, int64_t* poffset)
{
- scf_vm_naja_t* naja = vm->priv;
-
- int rb = inst & 0x1f;
- int rd = (inst >> 21) & 0x1f;
- int A = (inst >> 20) & 0x1;
- int ext = (inst >> 17) & 0x7;
- int s12 = (inst >> 5) & 0xfff;
-
- if (s12 & 0x800)
- s12 |= 0xfffff000;
-
- scf_logd("rd: %d, rb: %d, s12: %d, ext: %d\n", rd, rb, s12, ext);
-
- int64_t addr = naja->regs[rb];
- int64_t offset = 0;
- uint8_t* data;
+ scf_vm_naja_t* naja = vm->priv;
+ uint8_t* data = NULL;
+ int64_t offset = 0;
if (addr >= (int64_t)vm->data->data) {
data = (uint8_t*)addr;
offset = addr;
}
+ *poffset = offset;
+ *pdata = data;
+ return 0;
+}
+
+static int __naja_fstr_disp(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rb = inst & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int A = (inst >> 20) & 0x1;
+ int ext = (inst >> 17) & 0x7;
+ int s12 = (inst >> 5) & 0xfff;
+
+ if (s12 & 0x800)
+ s12 |= 0xfffff000;
+
+ scf_logd("rd: %d, rb: %d, s12: %d, ext: %d\n", rd, rb, s12, ext);
+
+ int64_t addr = naja->regs[rb];
+ int64_t offset = 0;
+ uint8_t* data = NULL;
+
+ int ret = __naja_mem(vm, addr, &data, &offset);
+ if (ret < 0)
+ return ret;
+
if (!A)
offset += s12 << (ext & 0x3);
}
switch (ext) {
- case 0:
- naja->regs[rd] = *(uint8_t*)(data + offset);
- if (A) {
- naja->regs[rb] += s12;
- printf("ldrb r%d, [r%d, %d]!\n", rd, rb, s12);
- } else
- printf("ldrb r%d, [r%d, %d]\n", rd, rb, s12);
- break;
-
- case 1:
- naja->regs[rd] = *(uint16_t*)(data + offset);
+ case 3:
+ *(double*)(data + offset) = naja->fvec[rd].d[0];
if (A) {
- naja->regs[rb] += s12 << 1;
- printf("ldrw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
+ naja->regs[rb] += s12 << 3;
+ NAJA_PRINTF("fstr d%d, [r%d, %d]!, rd: %lg, rb: %ld, %p\n", rd, rb, s12 << 3, naja->fvec[rd].d[0], naja->regs[rb], data + offset);
} else
- printf("ldrw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
+ NAJA_PRINTF("fstr d%d, [r%d, %d]\n", rd, rb, s12 << 3);
break;
- case 2:
- naja->regs[rd] = *(uint32_t*)(data + offset);
+ case 6:
+ *(float*)(data + offset) = naja->fvec[rd].d[0];
if (A) {
naja->regs[rb] += s12 << 2;
- printf("ldrl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ NAJA_PRINTF("fstrf f%d, [r%d, %d]!\n", rd, rb, s12 << 2);
} else
- printf("ldrl r%d, [r%d, %d], %ld, %p\n", rd, rb, s12 << 2, naja->regs[rd], data + offset);
+ NAJA_PRINTF("fstrf f%d, [r%d, %d]\n", rd, rb, s12 << 2);
break;
-
- case 3:
- naja->regs[rd] = *(uint64_t*)(data + offset);
- if (A) {
- naja->regs[rb] += s12 << 3;
- printf("ldr r%d, [r%d, %d]!, rd: %#lx, rb: %ld, %p\n", rd, rb, s12 << 3, naja->regs[rd], naja->regs[rb], data + offset);
- } else
- printf("ldr r%d, [r%d, %d]\n", rd, rb, s12 << 3);
+ default:
+ scf_loge("ext: %d\n", ext);
+ return -1;
break;
+ };
- case 4:
- naja->regs[rd] = *(int8_t*)(data + offset);
- if (A) {
- naja->regs[rb] += s12;
- printf("ldrsb r%d, [r%d, %d]!\n", rd, rb, s12);
- } else
- printf("ldrsb r%d, [r%d, %d]\n", rd, rb, s12);
- break;
+ naja->ip += 4;
+ return 0;
+}
- case 5:
- naja->regs[rd] = *(int16_t*)(data + offset);
+static int __naja_fldr_disp(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rb = inst & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int A = (inst >> 20) & 0x1;
+ int ext = (inst >> 17) & 0x7;
+ int s12 = (inst >> 5) & 0xfff;
+
+ if (s12 & 0x800)
+ s12 |= 0xfffff000;
+
+ scf_logd("rd: %d, rb: %d, s12: %d, ext: %d\n", rd, rb, s12, ext);
+
+ int64_t addr = naja->regs[rb];
+ int64_t offset = 0;
+ uint8_t* data = NULL;
+
+ int ret = __naja_mem(vm, addr, &data, &offset);
+ if (ret < 0)
+ return ret;
+
+ if (!A)
+ offset += s12 << (ext & 0x3);
+
+ if (data == naja->stack) {
+ offset = -offset;
+
+ scf_logd("offset0: %ld, size: %ld\n", offset, naja->size);
+ assert(offset >= 0);
+
+ if (naja->size < offset) {
+ scf_loge("offset: %ld, size: %ld\n", offset, naja->size);
+ return -EINVAL;
+ }
+
+ offset -= 1 << (ext & 0x3);
+ }
+
+ switch (ext) {
+ case 3:
+ naja->fvec[rd].d[0] = *(double*)(data + offset);
if (A) {
- naja->regs[rb] += s12 << 1;
- printf("ldrsw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
+ naja->regs[rb] += s12 << 3;
+ NAJA_PRINTF("fldr d%d, [r%d, %d]!, rd: %lg, rb: %ld, %p\n", rd, rb, s12 << 3, naja->fvec[rd].d[0], naja->regs[rb], data + offset);
} else
- printf("ldrsw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
+ NAJA_PRINTF("fldr d%d, [r%d, %d], rd: %lg, rb: %ld, %p\n", rd, rb, s12 << 3, naja->fvec[rd].d[0], naja->regs[rb], data + offset);
break;
case 6:
- naja->regs[rd] = *(int32_t*)(data + offset);
+ naja->fvec[rd].d[0] = *(float*)(data + offset);
if (A) {
naja->regs[rb] += s12 << 2;
- printf("ldrsl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ NAJA_PRINTF("fldrf f%d, [r%d, %d]!, rd: %lg, rb: %ld, %p\n", rd, rb, s12 << 2, naja->fvec[rd].d[0], naja->regs[rb], data + offset);
} else
- printf("ldrsl r%d, [r%d, %d]\n", rd, rb, s12 << 2);
+ NAJA_PRINTF("fldrf f%d, [r%d, %d], rd: %lg, rb: %ld, %p\n", rd, rb, s12 << 2, naja->fvec[rd].d[0], naja->regs[rb], data + offset);
break;
default:
- scf_loge("\n");
+ scf_loge("ext: %d\n", ext);
return -1;
break;
};
return 0;
}
-static int __naja_ldr_sib(scf_vm_t* vm, uint32_t inst)
+static int __naja_ldr_disp(scf_vm_t* vm, uint32_t inst)
{
scf_vm_naja_t* naja = vm->priv;
int rb = inst & 0x1f;
- int ri = (inst >> 5) & 0x1f;
int rd = (inst >> 21) & 0x1f;
+ int A = (inst >> 20) & 0x1;
int ext = (inst >> 17) & 0x7;
- int u7 = (inst >> 10) & 0x7f;
+ int s12 = (inst >> 5) & 0xfff;
+
+ if (s12 & 0x800)
+ s12 |= 0xfffff000;
+
+ scf_logd("rd: %d, rb: %d, s12: %d, ext: %d\n", rd, rb, s12, ext);
int64_t addr = naja->regs[rb];
- uint64_t offset;
- uint8_t* data;
+ int64_t offset = 0;
+ uint8_t* data = NULL;
- scf_logd("ldr r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
- scf_logd("rd: %#lx\n", naja->regs[rd]);
- scf_logd("rb: %#lx\n", naja->regs[rb]);
- scf_logd("ri: %#lx\n", naja->regs[ri]);
+ int ret = __naja_mem(vm, addr, &data, &offset);
+ if (ret < 0)
+ return ret;
- if (addr >= (int64_t)vm->data->data) {
- data = (uint8_t*)addr;
+ if (!A)
+ offset += s12 << (ext & 0x3);
- if (addr >= (int64_t)vm->data->data + vm->data->len) {
- scf_loge("addr: %#lx, %#lx\n", addr, (int64_t)vm->data->data + vm->data->len);
- return -1;
- }
+ if (data == naja->stack) {
+ offset = -offset;
- } else if (addr >= (int64_t)vm->rodata->data) {
- data = (uint8_t*)addr;
+ scf_logd("offset0: %ld, size: %ld\n", offset, naja->size);
+ assert(offset >= 0);
- if (addr >= (int64_t)vm->rodata->data + vm->rodata->len) {
- scf_loge("\n");
- return -1;
+ if (naja->size < offset) {
+ scf_loge("offset: %ld, size: %ld\n", offset, naja->size);
+ return -EINVAL;
}
- } else if (addr >= (int64_t)vm->text->data) {
- data = (uint8_t*)addr;
+ offset -= 1 << (ext & 0x3);
+ }
- if (addr >= (int64_t)vm->text->data + vm->text->len) {
- scf_loge("\n");
- return -1;
- }
+ switch (ext) {
+ case 0:
+ naja->regs[rd] = *(uint8_t*)(data + offset);
+ if (A) {
+ naja->regs[rb] += s12;
+ NAJA_PRINTF("ldrb r%d, [r%d, %d]!\n", rd, rb, s12);
+ } else
+ NAJA_PRINTF("ldrb r%d, [r%d, %d]\n", rd, rb, s12);
+ break;
- } else if (addr >= 0x800000) {
- data = vm->data->data;
- offset = addr - vm->data->addr;
+ case 1:
+ naja->regs[rd] = *(uint16_t*)(data + offset);
+ if (A) {
+ naja->regs[rb] += s12 << 1;
+ NAJA_PRINTF("ldrw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
+ } else
+ NAJA_PRINTF("ldrw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
+ break;
- if (offset >= vm->data->len) {
+ case 2:
+ naja->regs[rd] = *(uint32_t*)(data + offset);
+ if (A) {
+ naja->regs[rb] += s12 << 2;
+ NAJA_PRINTF("ldrl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ } else
+ NAJA_PRINTF("ldrl r%d, [r%d, %d], %ld, %p\n", rd, rb, s12 << 2, naja->regs[rd], data + offset);
+ break;
+
+ case 3:
+ naja->regs[rd] = *(uint64_t*)(data + offset);
+ if (A) {
+ naja->regs[rb] += s12 << 3;
+ NAJA_PRINTF("ldr r%d, [r%d, %d]!, rd: %#lx, rb: %ld, %p\n", rd, rb, s12 << 3, naja->regs[rd], naja->regs[rb], data + offset);
+ } else
+ NAJA_PRINTF("ldr r%d, [r%d, %d]\n", rd, rb, s12 << 3);
+ break;
+
+ case 4:
+ naja->regs[rd] = *(int8_t*)(data + offset);
+ if (A) {
+ naja->regs[rb] += s12;
+ NAJA_PRINTF("ldrsb r%d, [r%d, %d]!\n", rd, rb, s12);
+ } else
+ NAJA_PRINTF("ldrsb r%d, [r%d, %d]\n", rd, rb, s12);
+ break;
+
+ case 5:
+ naja->regs[rd] = *(int16_t*)(data + offset);
+ if (A) {
+ naja->regs[rb] += s12 << 1;
+ NAJA_PRINTF("ldrsw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
+ } else
+ NAJA_PRINTF("ldrsw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
+ break;
+
+ case 6:
+ naja->regs[rd] = *(int32_t*)(data + offset);
+ if (A) {
+ naja->regs[rb] += s12 << 2;
+ NAJA_PRINTF("ldrsl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ } else
+ NAJA_PRINTF("ldrsl r%d, [r%d, %d]\n", rd, rb, s12 << 2);
+ break;
+ default:
scf_loge("\n");
return -1;
- }
+ break;
+ };
- } else if (addr >= 0x600000) {
- data = vm->rodata->data;
- offset = addr - vm->rodata->addr;
+ naja->ip += 4;
+ return 0;
+}
- if (offset >= vm->rodata->len) {
- scf_loge("\n");
- return -1;
- }
+static int __naja_ldr_sib(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
- } else if (addr >= 0x400000) {
- data = vm->text->data;
- offset = addr - vm->text->addr;
+ int rb = inst & 0x1f;
+ int ri = (inst >> 5) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int ext = (inst >> 17) & 0x7;
+ int u7 = (inst >> 10) & 0x7f;
- if (offset >= vm->text->len) {
- scf_loge("\n");
- return -1;
- }
+ int64_t addr = naja->regs[rb];
+ int64_t offset = 0;
+ uint8_t* data = NULL;
- } else {
- data = naja->stack;
- offset = addr;
- }
+ int ret = __naja_mem(vm, addr, &data, &offset);
+ if (ret < 0)
+ return ret;
offset += (naja->regs[ri] << u7);
switch (ext) {
case 0:
- printf("ldrb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("ldrb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
naja->regs[rd] = *(uint8_t*)(data + offset);
break;
case 1:
- printf("ldrw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("ldrw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
naja->regs[rd] = *(uint16_t*)(data + offset);
break;
case 2:
- printf("ldrl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("ldrl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
naja->regs[rd] = *(uint32_t*)(data + offset);
break;
case 3:
- printf("ldr r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("ldr r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
naja->regs[rd] = *(uint64_t*)(data + offset);
break;
case 4:
- printf("ldrsb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("ldrsb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
naja->regs[rd] = *(int8_t*)(data + offset);
break;
case 5:
- printf("ldrsw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("ldrsw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
naja->regs[rd] = *(int16_t*)(data + offset);
break;
case 6:
- printf("ldrsl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("ldrsl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
naja->regs[rd] = *(int32_t*)(data + offset);
break;
return 0;
}
-static int __naja_str_disp(scf_vm_t* vm, uint32_t inst)
+static int __naja_fldr_sib(scf_vm_t* vm, uint32_t inst)
{
scf_vm_naja_t* naja = vm->priv;
int rb = inst & 0x1f;
+ int ri = (inst >> 5) & 0x1f;
int rd = (inst >> 21) & 0x1f;
- int A = (inst >> 20) & 0x1;
- int ext = (inst >> 17) & 0x3;
- int s12 = (inst >> 5) & 0xfff;
-
- if (s12 & 0x800)
- s12 |= 0xfffff000;
+ int ext = (inst >> 17) & 0x7;
+ int u7 = (inst >> 10) & 0x7f;
int64_t addr = naja->regs[rb];
int64_t offset = 0;
- uint8_t* data;
+ uint8_t* data = NULL;
- if (addr >= (int64_t)vm->data->data) {
- data = (uint8_t*)addr;
+ int ret = __naja_mem(vm, addr, &data, &offset);
+ if (ret < 0)
+ return ret;
- if (addr >= (int64_t)vm->data->data + vm->data->len) {
- scf_loge("\n");
- return -1;
- }
+ offset += (naja->regs[ri] << u7);
- } else if (addr >= (int64_t)vm->rodata->data) {
- data = (uint8_t*)addr;
+ if (data == naja->stack) {
+ offset = -offset;
- if (addr >= (int64_t)vm->rodata->data + vm->rodata->len) {
+ assert(offset >= 0);
+
+ if (naja->size < offset) {
scf_loge("\n");
return -1;
}
- } else if (addr >= (int64_t)vm->text->data) {
- data = (uint8_t*)addr;
+ offset -= 1 << (ext & 0x3);
+ }
- if (addr >= (int64_t)vm->text->data + vm->text->len) {
- scf_loge("\n");
- return -1;
- }
+ switch (ext) {
+ case 3:
+ NAJA_PRINTF("fldr d%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
- } else if (addr >= 0x800000) {
- data = vm->data->data;
- offset = addr - vm->data->addr;
+ naja->fvec[rd].d[0] = *(double*)(data + offset);
+ break;
- scf_loge("rb: %d, offset: %ld, addr: %#lx, %#lx\n", rb, offset, addr, vm->data->addr);
+ case 6:
+ NAJA_PRINTF("fldrf f%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
- if (offset >= vm->data->len) {
+ naja->fvec[rd].d[0] = *(float*)(data + offset);
+ break;
+ default:
scf_loge("\n");
return -1;
- }
+ break;
+ };
- } else if (addr >= 0x600000) {
- data = vm->rodata->data;
- offset = addr - vm->rodata->addr;
+ naja->ip += 4;
+ return 0;
+}
- if (offset >= vm->rodata->len) {
+static int __naja_fstr_sib(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rb = inst & 0x1f;
+ int ri = (inst >> 5) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int ext = (inst >> 17) & 0x3;
+ int u7 = (inst >> 10) & 0x7f;
+
+ int64_t addr = naja->regs[rb];
+ int64_t offset = 0;
+ uint8_t* data = NULL;
+
+ int ret = __naja_mem(vm, addr, &data, &offset);
+ if (ret < 0)
+ return ret;
+
+ offset += naja->regs[ri] << u7;
+
+ if (data == naja->stack) {
+ offset = -offset;
+
+ assert(offset >= 0);
+
+ if (naja->size < offset) {
scf_loge("\n");
return -1;
}
- } else if (addr >= 0x400000) {
- data = vm->text->data;
- offset = addr - vm->text->addr;
+ offset -= 1 << ext;
+ }
- if (offset >= vm->text->len) {
+ switch (ext) {
+ case 3:
+ NAJA_PRINTF("fstr d%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+
+ *(double*)(data + offset) = naja->fvec[rd].d[0];
+ break;
+
+ case 6:
+ NAJA_PRINTF("fldrf f%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+
+ *(float*)(data + offset) = naja->fvec[rd].d[0];
+ break;
+ default:
scf_loge("\n");
return -1;
- }
+ break;
+ };
- } else {
- data = naja->stack;
- offset = addr;
- }
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_str_disp(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rb = inst & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int A = (inst >> 20) & 0x1;
+ int ext = (inst >> 17) & 0x3;
+ int s12 = (inst >> 5) & 0xfff;
+
+ if (s12 & 0x800)
+ s12 |= 0xfffff000;
+
+ int64_t addr = naja->regs[rb];
+ int64_t offset = 0;
+ uint8_t* data = NULL;
+
+ int ret = __naja_mem(vm, addr, &data, &offset);
+ if (ret < 0)
+ return ret;
offset += s12 << ext;
*(uint8_t*)(data + offset) = naja->regs[rd];
if (A) {
naja->regs[rb] += s12;
- printf("strb r%d, [r%d, %d]!\n", rd, rb, s12);
+ NAJA_PRINTF("strb r%d, [r%d, %d]!\n", rd, rb, s12);
} else
- printf("strb r%d, [r%d, %d]\n", rd, rb, s12);
+ NAJA_PRINTF("strb r%d, [r%d, %d]\n", rd, rb, s12);
break;
case 1:
*(uint16_t*)(data + offset) = naja->regs[rd];
if (A) {
naja->regs[rb] += s12 << 1;
- printf("strw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
+ NAJA_PRINTF("strw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
} else
- printf("strw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
+ NAJA_PRINTF("strw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
break;
case 2:
*(uint32_t*)(data + offset) = naja->regs[rd];
if (A) {
naja->regs[rb] += s12 << 2;
- printf("strl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ NAJA_PRINTF("strl r%d, [r%d, %d]!, s12: %d\n", rd, rb, s12 << 2, s12);
} else
- printf("strl r%d, [r%d, %d], %d, %p\n", rd, rb, s12 << 2, *(uint32_t*)(data + offset), data + offset);
+ NAJA_PRINTF("strl r%d, [r%d, %d], s12: %d, %d, %p\n", rd, rb, s12 << 2, s12, *(uint32_t*)(data + offset), data + offset);
break;
case 3:
*(uint64_t*)(data + offset) = naja->regs[rd];
if (A) {
naja->regs[rb] += s12 << 3;
- printf("str r%d, [r%d, %d]!, rd: %#lx, rb: %ld, %p\n", rd, rb, s12 << 3, naja->regs[rd], naja->regs[rb], data + offset);
+ NAJA_PRINTF("str r%d, [r%d, %d]!, rd: %#lx, rb: %ld, %p\n", rd, rb, s12 << 3, naja->regs[rd], naja->regs[rb], data + offset);
} else
- printf("str r%d, [r%d, %d]\n", rd, rb, s12 << 3);
+ NAJA_PRINTF("str r%d, [r%d, %d]\n", rd, rb, s12 << 3);
break;
default:
int ext = (inst >> 17) & 0x3;
int u7 = (inst >> 10) & 0x7f;
- uint64_t addr = naja->regs[rb];
- uint64_t offset = 0;
- uint8_t* data;
-
- if (addr >= (int64_t)vm->data->data) {
- data = (uint8_t*)addr;
-
- if (addr >= (int64_t)vm->data->data + vm->data->len) {
- scf_loge("\n");
- return -1;
- }
-
- } else if (addr >= (int64_t)vm->rodata->data) {
- data = (uint8_t*)addr;
-
- if (addr >= (int64_t)vm->rodata->data + vm->rodata->len) {
- scf_loge("\n");
- return -1;
- }
-
- } else if (addr >= (int64_t)vm->text->data) {
- data = (uint8_t*)addr;
-
- if (addr >= (int64_t)vm->text->data + vm->text->len) {
- scf_loge("\n");
- return -1;
- }
-
- } else if (addr >= 0x800000) {
- data = vm->data->data;
- offset = addr - vm->data->addr;
-
- if (offset >= vm->data->len) {
- scf_loge("\n");
- return -1;
- }
-
- } else if (addr >= 0x600000) {
- data = vm->rodata->data;
- offset = addr - vm->rodata->addr;
-
- if (offset >= vm->rodata->len) {
- scf_loge("\n");
- return -1;
- }
-
- } else if (addr >= 0x400000) {
- data = vm->text->data;
- offset = addr - vm->text->addr;
-
- if (offset >= vm->text->len) {
- scf_loge("\n");
- return -1;
- }
+ int64_t addr = naja->regs[rb];
+ int64_t offset = 0;
+ uint8_t* data = NULL;
- } else {
- data = naja->stack;
- offset = addr;
- }
+ int ret = __naja_mem(vm, addr, &data, &offset);
+ if (ret < 0)
+ return ret;
offset += naja->regs[ri] << u7;
switch (ext) {
case 0:
- printf("strb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("strb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
*(uint8_t*)(data + offset) = naja->regs[rd];
break;
case 1:
- printf("strw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("strw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
*(uint16_t*)(data + offset) = naja->regs[rd];
break;
case 2:
- printf("strl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("strl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
*(uint32_t*)(data + offset) = naja->regs[rd];
break;
case 3:
- printf("str r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ NAJA_PRINTF("str r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
*(uint64_t*)(data + offset) = naja->regs[rd];
break;
simm26 |= 0xfc000000;
naja->ip += simm26 << 2;
- printf("jmp %#lx\n", naja->ip);
+ NAJA_PRINTF("jmp %#lx\n", naja->ip);
return 0;
}
naja->ip += simm26 << 2;
- printf("call %#lx\n", naja->ip);
+ NAJA_PRINTF("call %#lx\n", naja->ip);
return 0;
}
naja->ip += 4;
if (0 == cc)
- printf("jz %#lx, flags: %#lx\n", naja->ip, naja->flags);
+ NAJA_PRINTF("jz %#lx, flags: %#lx\n", naja->ip, naja->flags);
else if (1 == cc)
- printf("jnz %#lx, flags: %#lx\n", naja->ip, naja->flags);
+ NAJA_PRINTF("jnz %#lx, flags: %#lx\n", naja->ip, naja->flags);
else if (2 == cc)
- printf("jge %#lx, flags: %#lx\n", naja->ip, naja->flags);
+ NAJA_PRINTF("jge %#lx, flags: %#lx\n", naja->ip, naja->flags);
else if (3 == cc)
- printf("jgt %#lx, flags: %#lx\n", naja->ip, naja->flags);
+ NAJA_PRINTF("jgt %#lx, flags: %#lx\n", naja->ip, naja->flags);
else if (4 == cc)
- printf("jle %#lx, flags: %#lx\n", naja->ip, naja->flags);
+ NAJA_PRINTF("jle %#lx, flags: %#lx\n", naja->ip, naja->flags);
else if (5 == cc)
- printf("jlt %#lx, flags: %#lx\n", naja->ip, naja->flags);
+ NAJA_PRINTF("jlt %#lx, flags: %#lx\n", naja->ip, naja->flags);
else {
scf_loge("\n");
return -EINVAL;
if (naja_vm_dynamic_link == (void*)naja->regs[rd]) {
- printf("\033[36mjmp r%d, %#lx@plt\033[0m\n", rd, naja->regs[rd]);
+ NAJA_PRINTF("\033[36mjmp r%d, %#lx@plt\033[0m\n", rd, naja->regs[rd]);
int ret = naja_vm_dynamic_link(vm);
if (ret < 0) {
} else if (naja->regs[rd] < vm->text->addr
|| naja->regs[rd] > vm->text->addr + vm->text->len) {
- printf("\033[36mjmp r%d, %#lx@plt\033[0m\n", rd, naja->regs[rd]);
+ NAJA_PRINTF("\033[36mjmp r%d, %#lx@plt\033[0m\n", rd, naja->regs[rd]);
- naja_dyn_func_pt pt = (naja_dyn_func_pt) naja->regs[rd];
+ dyn_func_pt f = (void*)naja->regs[rd];
- naja->regs[0] = pt(naja->regs[0],
+ naja->regs[0] = f(naja->regs[0],
naja->regs[1],
naja->regs[2],
naja->regs[3],
naja->regs[4],
naja->regs[5],
naja->regs[6],
- naja->regs[7]);
+ naja->regs[7],
+ naja->fvec[0].d[0],
+ naja->fvec[1].d[0],
+ naja->fvec[2].d[0],
+ naja->fvec[3].d[0],
+ naja->fvec[4].d[0],
+ naja->fvec[5].d[0],
+ naja->fvec[6].d[0],
+ naja->fvec[7].d[0]);
naja->ip = naja->regs[NAJA_REG_LR];
} else {
naja->ip = naja->regs[rd];
- printf("jmp r%d, %#lx\n", rd, naja->regs[rd]);
+ NAJA_PRINTF("jmp r%d, %#lx\n", rd, naja->regs[rd]);
}
}
if (naja_vm_dynamic_link == (void*)naja->regs[rd]) {
- printf("\033[36mcall r%d, %#lx@plt\033[0m\n", rd, naja->regs[rd]);
+ NAJA_PRINTF("\033[36mcall r%d, %#lx@plt\033[0m\n", rd, naja->regs[rd]);
int ret = naja_vm_dynamic_link(vm);
if (ret < 0) {
} else if (naja->regs[rd] < vm->text->addr
|| naja->regs[rd] > vm->text->addr + vm->text->len) {
- printf("\033[36mcall r%d, %#lx@plt\033[0m\n", rd, naja->regs[rd]);
-
- naja_dyn_func_pt pt = (naja_dyn_func_pt) naja->regs[rd];
-
- naja->regs[0] = pt(naja->regs[0],
- naja->regs[1],
- naja->regs[2],
- naja->regs[3],
- naja->regs[4],
- naja->regs[5],
- naja->regs[6],
- naja->regs[7]);
+ NAJA_PRINTF("\033[36mcall r%d, %#lx@plt\033[0m\n", rd, naja->regs[rd]);
+
+ dyn_func_pt f = (void*)naja->regs[rd];
+
+ naja->regs[0] = f(naja->regs[0],
+ naja->regs[1],
+ naja->regs[2],
+ naja->regs[3],
+ naja->regs[4],
+ naja->regs[5],
+ naja->regs[6],
+ naja->regs[7],
+ naja->fvec[0].d[0],
+ naja->fvec[1].d[0],
+ naja->fvec[2].d[0],
+ naja->fvec[3].d[0],
+ naja->fvec[4].d[0],
+ naja->fvec[5].d[0],
+ naja->fvec[6].d[0],
+ naja->fvec[7].d[0]);
naja->ip = naja->regs[NAJA_REG_LR];
} else {
- printf("call r%d, %#lx\n", rd, naja->regs[rd]);
+ NAJA_PRINTF("call r%d, %#lx\n", rd, naja->regs[rd]);
naja->ip = naja->regs[rd];
}
else if (naja->regs[rd] >= 0x400000)
naja->regs[rd] = naja->regs[rd] - vm->text->addr + (uint64_t)vm->text->data;
- printf("adrp r%d, [rip, %d], %#lx\n", rd, s21, naja->regs[rd]);
+ NAJA_PRINTF("adrp r%d, [rip, %d], %#lx\n", rd, s21, naja->regs[rd]);
naja->ip += 4;
return 0;
naja->size = sp + STACK_INC;
}
- printf("ret, %#lx, sp: %ld, stack->size: %ld\n", naja->ip, sp, naja->size);
+ NAJA_PRINTF("ret, %#lx, sp: %ld, stack->size: %ld\n", naja->ip, sp, naja->size);
return 0;
}
naja->regs[rd] = 0 == (cc & naja->flags);
if (SCF_VM_Z == cc)
- printf("setz r%d\n", rd);
+ NAJA_PRINTF("setz r%d\n", rd);
else if (SCF_VM_NZ == cc)
- printf("setnz r%d\n", rd);
+ NAJA_PRINTF("setnz r%d\n", rd);
else if (SCF_VM_GE == cc)
- printf("setge r%d\n", rd);
+ NAJA_PRINTF("setge r%d\n", rd);
else if (SCF_VM_GT == cc)
- printf("setgt r%d\n", rd);
+ NAJA_PRINTF("setgt r%d\n", rd);
else if (SCF_VM_LT == cc)
- printf("setlt r%d\n", rd);
+ NAJA_PRINTF("setlt r%d\n", rd);
else if (SCF_VM_LE == cc)
- printf("setle r%d\n", rd);
+ NAJA_PRINTF("setle r%d\n", rd);
else {
scf_loge("inst: %#x\n", inst);
return -EINVAL;
if (X && (inst & 0x8000)) {
naja->regs[rd] |= ~0xffffULL;
- printf("movsb r%d, %d\n", rd, inst & 0xffff);
+ NAJA_PRINTF("movsb r%d, %d\n", rd, inst & 0xffff);
} else {
- printf("mov r%d, %d\n", rd, inst & 0xffff);
+ NAJA_PRINTF("mov r%d, %d\n", rd, inst & 0xffff);
}
} else if (1 == opt) {
naja->regs[rd] |= (inst & 0xffffULL) << 16;
- printf("mov r%d, %d << 16\n", rd, inst & 0xffff);
+ NAJA_PRINTF("mov r%d, %d << 16\n", rd, inst & 0xffff);
} else if (2 == opt) {
naja->regs[rd] |= (inst & 0xffffULL) << 32;
- printf("mov r%d, %d << 32\n", rd, inst & 0xffff);
+ NAJA_PRINTF("mov r%d, %d << 32\n", rd, inst & 0xffff);
} else if (3 == opt) {
naja->regs[rd] |= (inst & 0xffffULL) << 48;
- printf("mov r%d, %d << 48\n", rd, inst & 0xffff);
+ NAJA_PRINTF("mov r%d, %d << 48\n", rd, inst & 0xffff);
} else if (7 == opt) {
naja->regs[rd] = ~(inst & 0xffffULL);
- printf("mvn r%d, %d\n", rd, inst & 0xffff);
+ NAJA_PRINTF("mvn r%d, %d\n", rd, inst & 0xffff);
}
} else {
if (0 == opt) {
if (X) {
- printf("mov r%d, r%d LSL r%d\n", rd, rs, rs1);
+ NAJA_PRINTF("mov r%d, r%d LSL r%d\n", rd, rs, rs1);
naja->regs[rd] = naja->regs[rs] << naja->regs[rs1];
} else {
naja->regs[rd] = naja->regs[rs] << u11;
if (0 == u11)
- printf("mov r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("mov r%d, r%d\n", rd, rs);
else
- printf("mov r%d, r%d LSL %d\n", rd, rs, u11);
+ NAJA_PRINTF("mov r%d, r%d LSL %d\n", rd, rs, u11);
}
} else if (1 == opt) {
if (X) {
- printf("mov r%d, r%d LSR r%d\n", rd, rs, rs1);
+ NAJA_PRINTF("mov r%d, r%d LSR r%d\n", rd, rs, rs1);
naja->regs[rd] = naja->regs[rs] >> naja->regs[rs1];
} else {
naja->regs[rd] = naja->regs[rs] >> u11;
if (0 == u11)
- printf("mov r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("mov r%d, r%d\n", rd, rs);
else
- printf("mov r%d, r%d LSR %d\n", rd, rs, u11);
+ NAJA_PRINTF("mov r%d, r%d LSR %d\n", rd, rs, u11);
}
} else if (2 == opt) {
if (X) {
- printf("mov r%d, r%d ASR r%d\n", rd, rs, rs1);
+ NAJA_PRINTF("mov r%d, r%d ASR r%d\n", rd, rs, rs1);
naja->regs[rd] = (int64_t)naja->regs[rs] >> naja->regs[rs1];
} else {
naja->regs[rd] = (int64_t)naja->regs[rs] >> u11;
if (0 == u11)
- printf("mov r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("mov r%d, r%d\n", rd, rs);
else
- printf("mov r%d, r%d ASR %d\n", rd, rs, u11);
+ NAJA_PRINTF("mov r%d, r%d ASR %d\n", rd, rs, u11);
}
} else if (3 == opt) {
- printf("NOT r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("NOT r%d, r%d\n", rd, rs);
naja->regs[rd] = ~naja->regs[rs];
} else if (4 == opt) {
naja->regs[rd] = -naja->regs[rs];
- printf("NEG r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("NEG r%d, r%d\n", rd, rs);
} else if (5 == opt) {
if (X) {
- printf("movsb r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("movsb r%d, r%d\n", rd, rs);
naja->regs[rd] = (int8_t)naja->regs[rs];
} else {
naja->regs[rd] = (uint8_t)naja->regs[rs];
- printf("movzb r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("movzb r%d, r%d\n", rd, rs);
}
} else if (6 == opt) {
if (X) {
- printf("movsw r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("movsw r%d, r%d\n", rd, rs);
naja->regs[rd] = (int16_t)naja->regs[rs];
} else {
naja->regs[rd] = (uint16_t)naja->regs[rs];
- printf("movzw r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("movzw r%d, r%d\n", rd, rs);
}
} else if (7 == opt) {
if (X) {
- printf("movsl r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("movsl r%d, r%d\n", rd, rs);
naja->regs[rd] = (int32_t)naja->regs[rs];
} else {
naja->regs[rd] = (uint32_t)naja->regs[rs];
- printf("movzl r%d, r%d\n", rd, rs);
+ NAJA_PRINTF("movzl r%d, r%d\n", rd, rs);
}
}
}
return 0;
}
+static int __naja_fmov(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs = inst & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int opt = (inst >> 16) & 0xf;
+
+ if (0 == opt) {
+ naja->fvec[rd].d[0] = naja->fvec[rs].d[0];
+
+ NAJA_PRINTF("fmov d%d, d%d\n", rd, rs);
+
+ } else if (1 == opt) {
+ naja->fvec[rd].d[0] = naja->fvec[rs].d[0];
+
+ NAJA_PRINTF("fss2sd d%d, f%d\n", rd, rs);
+
+ } else if (2 == opt) {
+ naja->fvec[rd].d[0] = naja->fvec[rs].d[0];
+
+ NAJA_PRINTF("fsd2ss d%d, f%d\n", rd, rs);
+
+ } else if (3 == opt) {
+ naja->fvec[rd].d[0] = -naja->fvec[rs].d[0];
+
+ NAJA_PRINTF("fneg d%d, d%d\n", rd, rs);
+
+ } else if (4 == opt) {
+ naja->regs[rd] = (int64_t)naja->fvec[rs].d[0];
+
+ NAJA_PRINTF("cvtss2si r%d, f%d\n", rd, rs);
+
+ } else if (5 == opt) {
+ naja->regs[rd] = (int64_t)naja->fvec[rs].d[0];
+
+ NAJA_PRINTF("cvtsd2si r%d, d%d\n", rd, rs);
+
+ } else if (6 == opt) {
+ naja->regs[rd] = (uint64_t)naja->fvec[rs].d[0];
+
+ NAJA_PRINTF("cvtss2ui r%d, f%d\n", rd, rs);
+
+ } else if (7 == opt) {
+ naja->regs[rd] = (uint64_t)naja->fvec[rs].d[0];
+
+ NAJA_PRINTF("cvtsd2ui r%d, d%d\n", rd, rs);
+
+ } else if (0xc == opt) {
+ naja->fvec[rd].d[0] = (double)naja->regs[rs];
+
+ NAJA_PRINTF("cvtsi2ss f%d, r%d\n", rd, rs);
+
+ } else if (0xd == opt) {
+ naja->fvec[rd].d[0] = (double)naja->regs[rs];
+
+ NAJA_PRINTF("cvtsi2sd d%d, r%d\n", rd, rs);
+
+ } else if (0xe == opt) {
+ naja->fvec[rd].d[0] = (double)naja->regs[rs];
+
+ NAJA_PRINTF("cvtui2ss f%d, r%d\n", rd, rs);
+
+ } else if (0xf == opt) {
+ naja->fvec[rd].d[0] = (double)naja->regs[rs];
+
+ NAJA_PRINTF("cvtui2sd f%d, r%d\n", rd, rs);
+ } else {
+ scf_loge("\n");
+ return -EINVAL;
+ }
+
+ naja->ip += 4;
+ return 0;
+}
+
static naja_opcode_pt naja_opcodes[64] =
{
__naja_add, // 0
__naja_teq, //14
__naja_mov, //15
- NULL, //16
- NULL, //17
- NULL, //18
- NULL, //19
- NULL, //20
- NULL, //21
+ __naja_fadd, //16
+ __naja_fsub, //17
+ __naja_fmul, //18
+ __naja_fdiv, //19
+ __naja_fldr_disp,//20
+ __naja_fstr_disp,//21
NULL, //22
NULL, //23
__naja_call_disp,//24
- NULL, //25
+ __naja_fcmp, //25
__naja_call_reg, //26
NULL, //27
- NULL, //28
- NULL, //29
+ __naja_fldr_sib, //28
+ __naja_fstr_sib, //29
NULL, //30
- NULL, //31
+ __naja_fmov, //31
NULL, //32
NULL, //33
return -EINVAL;
}
- printf("%4d, %#lx: ", n++, naja->ip);
+ NAJA_PRINTF("%4d, %#lx: ", n++, naja->ip);
ret = pt(vm, inst);
if (ret < 0) {
scf_loge("\n");
return ret;
}
- usleep(50 * 1000);
+// usleep(10 * 1000);
}
- scf_logw("r0: %ld\n", naja->regs[0]);
+ scf_logw("r0: %ld, sizeof(fv256_t): %ld\n", naja->regs[0], sizeof(fv256_t));
return naja->regs[0];
}
#include"scf_vm.h"
-#define NAJA_REG_FP 29
-#define NAJA_REG_LR 30
-#define NAJA_REG_SP 31
-
static int __naja_add(scf_vm_t* vm, uint32_t inst)
{
scf_vm_naja_t* naja = vm->priv;
if (I) {
uint64_t uimm15 = (inst >> 5) & 0x7fff;
- printf("add r%d, r%d, %lu\n", rd, rs0, uimm15);
+ printf("add r%d, r%d, %lu\n", rd, rs0, uimm15);
} else {
uint64_t sh = (inst >> 18) & 0x3;
uint64_t uimm8 = (inst >> 10) & 0xff;
int rs1 = (inst >> 5) & 0x1f;
if (0 == sh)
- printf("add r%d, r%d, r%d LSL %lu\n", rd, rs0, rs1, uimm8);
+ printf("add r%d, r%d, r%d LSL %lu\n", rd, rs0, rs1, uimm8);
else if (1 == sh)
- printf("add r%d, r%d, r%d LSR %lu\n", rd, rs0, rs1, uimm8);
+ printf("add r%d, r%d, r%d LSR %lu\n", rd, rs0, rs1, uimm8);
else
- printf("add r%d, r%d, r%d ASR %lu\n", rd, rs0, rs1, uimm8);
+ printf("add r%d, r%d, r%d ASR %lu\n", rd, rs0, rs1, uimm8);
}
return 0;
if (I) {
uint64_t uimm15 = (inst >> 5) & 0x7fff;
- printf("sub r%d, r%d, %lu\n", rd, rs0, uimm15);
+ printf("sub r%d, r%d, %lu\n", rd, rs0, uimm15);
} else {
uint64_t sh = (inst >> 18) & 0x3;
uint64_t uimm8 = (inst >> 10) & 0xff;
int rs1 = (inst >> 5) & 0x1f;
if (0 == sh)
- printf("sub r%d, r%d, r%d << %lu\n", rd, rs0, rs1, uimm8);
+ printf("sub r%d, r%d, r%d << %lu\n", rd, rs0, rs1, uimm8);
else if (1 == sh)
- printf("sub r%d, r%d, r%d LSR %lu\n", rd, rs0, rs1, uimm8);
+ printf("sub r%d, r%d, r%d LSR %lu\n", rd, rs0, rs1, uimm8);
else
- printf("sub r%d, r%d, r%d ASR %lu\n", rd, rs0, rs1, uimm8);
+ printf("sub r%d, r%d, r%d ASR %lu\n", rd, rs0, rs1, uimm8);
}
return 0;
scf_vm_naja_t* naja = vm->priv;
int rs0 = inst & 0x1f;
- int rd = (inst >> 21) & 0x1f;
int I = (inst >> 20) & 0x1;
int ret = 0;
if (I) {
- uint64_t uimm15 = (inst >> 5) & 0x7fff;
- printf("cmp r%d, %ld, rs0: %lx, ret: %d\n", rs0, uimm15, naja->regs[rs0], ret);
+ int uimm15 = (inst >> 5) & 0x7fff;
+ printf("cmp r%d, %d\n", rs0, uimm15);
} else {
- uint64_t sh = (inst >> 18) & 0x3;
- uint64_t uimm8 = (inst >> 10) & 0xff;
- int rs1 = (inst >> 5) & 0x1f;
+ int sh = (inst >> 18) & 0x3;
+ int uimm8 = (inst >> 10) & 0xff;
+ int rs1 = (inst >> 5) & 0x1f;
if (0 == sh)
- printf("cmp r%d, r%d LSL %ld, rs0: %#lx, rs1: %#lx, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
+ printf("cmp r%d, r%d LSL %d\n", rs0, rs1, uimm8);
else if (1 == sh)
- printf("cmp r%d, r%d LSR %ld, rs0: %#lx, rs1: %#lx, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
+ printf("cmp r%d, r%d LSR %d\n", rs0, rs1, uimm8);
else
- printf("cmp r%d, r%d ASR %ld, rs0: %#lx, rs1: %ld, ret: %d\n", rs0, rs1, uimm8, naja->regs[rs0], naja->regs[rs1], ret);
+ printf("cmp r%d, r%d ASR %d\n", rs0, rs1, uimm8);
}
return 0;
if (S) {
if (0 == opt)
- printf("smadd r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
+ printf("smadd r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
else if (1 == opt)
- printf("smsub r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
+ printf("smsub r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
else
- printf("smul r%d, r%d, r%d\n", rd, rs0, rs1);
+ printf("smul r%d, r%d, r%d\n", rd, rs0, rs1);
} else {
if (0 == opt)
- printf("madd r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
+ printf("madd r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
else if (1 == opt)
- printf("msub r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
+ printf("msub r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
else
- printf("mul r%d, r%d, r%d\n", rd, rs0, rs1);
+ printf("mul r%d, r%d, r%d\n", rd, rs0, rs1);
}
return 0;
if (S) {
if (0 == opt)
- printf("sdadd r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
+ printf("sdadd r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
else if (1 == opt)
- printf("sdsub r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
+ printf("sdsub r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
else
- printf("sdiv r%d, r%d, r%d\n", rd, rs0, rs1);
+ printf("sdiv r%d, r%d, r%d\n", rd, rs0, rs1);
} else {
if (0 == opt)
- printf("dadd r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
+ printf("dadd r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
else if (1 == opt)
- printf("dsub r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
+ printf("dsub r%d, r%d, r%d, r%d\n", rd, rs2, rs0, rs1);
else
- printf("div r%d, r%d, r%d\n", rd, rs0, rs1);
+ printf("div r%d, r%d, r%d\n", rd, rs0, rs1);
}
return 0;
switch (ext) {
case 0:
if (A)
- printf("ldrb r%d, [r%d, %d]!\n", rd, rb, s12);
+ printf("ldrb r%d, [r%d, %d]!\n", rd, rb, s12);
else
- printf("ldrb r%d, [r%d, %d]\n", rd, rb, s12);
+ printf("ldrb r%d, [r%d, %d]\n", rd, rb, s12);
break;
case 1:
if (A)
- printf("ldrw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
+ printf("ldrw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
else
- printf("ldrw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
+ printf("ldrw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
break;
case 2:
if (A)
- printf("ldrl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ printf("ldrl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
else
- printf("ldrl r%d, [r%d, %d]\n", rd, rb, s12 << 2);
+ printf("ldrl r%d, [r%d, %d]\n", rd, rb, s12 << 2);
break;
case 3:
if (A)
- printf("ldr r%d, [r%d, %d]!\n", rd, rb, s12 << 3);
+ printf("ldr r%d, [r%d, %d]!\n", rd, rb, s12 << 3);
else
- printf("ldr r%d, [r%d, %d]\n", rd, rb, s12 << 3);
+ printf("ldr r%d, [r%d, %d]\n", rd, rb, s12 << 3);
break;
case 4:
if (A)
- printf("ldrsb r%d, [r%d, %d]!\n", rd, rb, s12);
+ printf("ldrsb r%d, [r%d, %d]!\n", rd, rb, s12);
else
- printf("ldrsb r%d, [r%d, %d]\n", rd, rb, s12);
+ printf("ldrsb r%d, [r%d, %d]\n", rd, rb, s12);
break;
case 5:
if (A)
- printf("ldrsw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
+ printf("ldrsw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
else
- printf("ldrsw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
+ printf("ldrsw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
break;
case 6:
if (A)
- printf("ldrsl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ printf("ldrsl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
else
- printf("ldrsl r%d, [r%d, %d]\n", rd, rb, s12 << 2);
+ printf("ldrsl r%d, [r%d, %d]\n", rd, rb, s12 << 2);
break;
default:
scf_loge("\n");
switch (ext) {
case 0:
- printf("ldrb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("ldrb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 1:
- printf("ldrw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("ldrw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 2:
- printf("ldrl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("ldrl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 3:
- printf("ldr r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("ldr r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 4:
- printf("ldrsb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("ldrsb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 5:
- printf("ldrsw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("ldrsw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 6:
- printf("ldrsl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("ldrsl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
default:
scf_loge("\n");
switch (ext) {
case 0:
if (A)
- printf("strb r%d, [r%d, %d]!\n", rd, rb, s12);
+ printf("strb r%d, [r%d, %d]!\n", rd, rb, s12);
else
- printf("strb r%d, [r%d, %d]\n", rd, rb, s12);
+ printf("strb r%d, [r%d, %d]\n", rd, rb, s12);
break;
case 1:
if (A)
- printf("strw r%d, [r%d, %d]!\n", rd, rb, s12);
+ printf("strw r%d, [r%d, %d]!\n", rd, rb, s12 << 1);
else
- printf("strw r%d, [r%d, %d]\n", rd, rb, s12);
+ printf("strw r%d, [r%d, %d]\n", rd, rb, s12 << 1);
break;
case 2:
if (A)
- printf("strl r%d, [r%d, %d]!\n", rd, rb, s12);
+ printf("strl r%d, [r%d, %d]!\n", rd, rb, s12 << 2);
else
- printf("strl r%d, [r%d, %d]\n", rd, rb, s12);
+ printf("strl r%d, [r%d, %d]\n", rd, rb, s12 << 2);
break;
case 3:
if (A)
- printf("str r%d, [r%d, %d]!\n", rd, rb, s12 << 3);
+ printf("str r%d, [r%d, %d]!\n", rd, rb, s12 << 3);
else
- printf("str r%d, [r%d, %d]\n", rd, rb, s12 << 3);
+ printf("str r%d, [r%d, %d]\n", rd, rb, s12 << 3);
break;
default:
switch (ext) {
case 0:
- printf("strb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("strb r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 1:
- printf("strw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("strw r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 2:
- printf("strl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("strl r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
case 3:
- printf("str r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ printf("str r%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
break;
default:
if (I) {
uint64_t uimm15 = (inst >> 5) & 0x7fff;
- printf("and r%d, r%d, %#lx\n", rd, rs0, uimm15);
+ printf("and r%d, r%d, %#lx\n", rd, rs0, uimm15);
} else {
int sh = (inst >> 18) & 0x3;
int uimm8 = (inst >> 10) & 0xff;
int rs1 = (inst >> 5) & 0x1f;
if (0 == sh)
- printf("and r%d, r%d, r%d LSL %#x\n", rd, rs0, rs1, uimm8);
+ printf("and r%d, r%d, r%d LSL %#x\n", rd, rs0, rs1, uimm8);
else if (1 == sh)
- printf("and r%d, r%d, r%d LSR %#x\n", rd, rs0, rs1, uimm8);
+ printf("and r%d, r%d, r%d LSR %#x\n", rd, rs0, rs1, uimm8);
else
- printf("and r%d, r%d, r%d ASR %#x\n", rd, rs0, rs1, uimm8);
+ printf("and r%d, r%d, r%d ASR %#x\n", rd, rs0, rs1, uimm8);
}
return 0;
if (I) {
uint64_t uimm15 = (inst >> 5) & 0x7fff;
- printf("teq r%d, %#lx\n", rs0, uimm15);
+ printf("teq r%d, %#lx\n", rs0, uimm15);
} else {
int sh = (inst >> 18) & 0x3;
int uimm8 = (inst >> 10) & 0xff;
int rs1 = (inst >> 5) & 0x1f;
if (0 == sh)
- printf("teq r%d, r%d LSL %#x\n", rs0, rs1, uimm8);
+ printf("teq r%d, r%d LSL %#x\n", rs0, rs1, uimm8);
else if (1 == sh)
- printf("teq r%d, r%d LSR %#x\n", rs0, rs1, uimm8);
+ printf("teq r%d, r%d LSR %#x\n", rs0, rs1, uimm8);
else
- printf("teq r%d, r%d ASR %#x\n", rs0, rs1, uimm8);
+ printf("teq r%d, r%d ASR %#x\n", rs0, rs1, uimm8);
}
return 0;
if (I) {
uint64_t uimm15 = (inst >> 5) & 0x7fff;
- printf("or r%d, r%d, %#lx\n", rd, rs0, uimm15);
+ printf("or r%d, r%d, %#lx\n", rd, rs0, uimm15);
} else {
int sh = (inst >> 18) & 0x3;
int uimm8 = (inst >> 10) & 0xff;
int rs1 = (inst >> 5) & 0x1f;
if (0 == sh)
- printf("or r%d, r%d, r%d LSL %#x\n", rd, rs0, rs1, uimm8);
+ printf("or r%d, r%d, r%d LSL %#x\n", rd, rs0, rs1, uimm8);
else if (1 == sh)
- printf("or r%d, r%d, r%d LSR %#x\n", rd, rs0, rs1, uimm8);
+ printf("or r%d, r%d, r%d LSR %#x\n", rd, rs0, rs1, uimm8);
else
- printf("or r%d, r%d, r%d ASR %#x\n", rd, rs0, rs1, uimm8);
+ printf("or r%d, r%d, r%d ASR %#x\n", rd, rs0, rs1, uimm8);
}
return 0;
simm26 |= 0xfc000000;
uint64_t ip = naja->ip + (simm26 << 2);
- printf("call %#lx\n", ip);
+ printf("call %#lx\n", ip);
return 0;
}
uint64_t ip = naja->ip + s21;
if (0 == cc)
- printf("jz %#lx\n", ip);
+ printf("jz %#lx\n", ip);
else if (1 == cc)
- printf("jnz %#lx\n", ip);
+ printf("jnz %#lx\n", ip);
else if (2 == cc)
- printf("jge %#lx\n", ip);
+ printf("jge %#lx\n", ip);
else if (3 == cc)
- printf("jgt %#lx\n", ip);
+ printf("jgt %#lx\n", ip);
else if (4 == cc)
- printf("jle %#lx\n", ip);
+ printf("jle %#lx\n", ip);
else if (5 == cc)
- printf("jlt %#lx\n", ip);
+ printf("jlt %#lx\n", ip);
else {
scf_loge("\n");
return -EINVAL;
} else {
int rd = (inst >> 21) & 0x1f;
- printf("jmp *r%d\n", rd);
+ printf("jmp *r%d\n", rd);
}
return 0;
}
int rd = (inst >> 21) & 0x1f;
- printf("call r%d\n", rd);
+ printf("call r%d\n", rd);
return 0;
}
if (s21 & 0x100000)
s21 |= ~0x1fffff;
- printf("adrp r%d, [rip, %d]\n", rd, s21);
+ printf("adrp r%d, [rip, %d]\n", rd, s21);
return 0;
}
int cc = (inst >> 17) & 0xf;
if (SCF_VM_Z == cc)
- printf("setz r%d\n", rd);
+ printf("setz r%d\n", rd);
else if (SCF_VM_NZ == cc)
- printf("setnz r%d\n", rd);
+ printf("setnz r%d\n", rd);
else if (SCF_VM_GE == cc)
- printf("setge r%d\n", rd);
+ printf("setge r%d\n", rd);
else if (SCF_VM_GT == cc)
- printf("setgt r%d\n", rd);
+ printf("setgt r%d\n", rd);
else if (SCF_VM_LT == cc)
- printf("setlt r%d\n", rd);
+ printf("setlt r%d\n", rd);
else if (SCF_VM_LE == cc)
- printf("setle r%d\n", rd);
+ printf("setle r%d\n", rd);
else {
scf_loge("inst: %#x\n", inst);
return -EINVAL;
if (I) {
if (0 == opt) {
if (X && (inst & 0x8000))
- printf("movsb r%d, %d\n", rd, inst & 0xffff);
+ printf("movsb r%d, %d\n", rd, inst & 0xffff);
else
- printf("mov r%d, %d\n", rd, inst & 0xffff);
+ printf("mov r%d, %d\n", rd, inst & 0xffff);
} else if (1 == opt)
- printf("mov r%d, %d << 16\n", rd, inst & 0xffff);
+ printf("mov r%d, %d << 16\n", rd, inst & 0xffff);
else if (2 == opt)
- printf("mov r%d, %d << 32\n", rd, inst & 0xffff);
+ printf("mov r%d, %d << 32\n", rd, inst & 0xffff);
else if (3 == opt)
- printf("mov r%d, %d << 48\n", rd, inst & 0xffff);
+ printf("mov r%d, %d << 48\n", rd, inst & 0xffff);
else if (7 == opt)
- printf("mvn r%d, %d\n", rd, inst & 0xffff);
+ printf("mvn r%d, %d\n", rd, inst & 0xffff);
} else {
int rs = inst & 0x1f;
if (0 == opt) {
if (X)
- printf("mov r%d, r%d LSL r%d\n", rd, rs, rs1);
+ printf("mov r%d, r%d LSL r%d\n", rd, rs, rs1);
else {
if (0 == u11)
- printf("mov r%d, r%d\n", rd, rs);
+ printf("mov r%d, r%d\n", rd, rs);
else
- printf("mov r%d, r%d LSL %d\n", rd, rs, u11);
+ printf("mov r%d, r%d LSL %d\n", rd, rs, u11);
}
} else if (1 == opt) {
if (X)
- printf("mov r%d, r%d LSR r%d\n", rd, rs, rs1);
+ printf("mov r%d, r%d LSR r%d\n", rd, rs, rs1);
else {
if (0 == u11)
- printf("mov r%d, r%d\n", rd, rs);
+ printf("mov r%d, r%d\n", rd, rs);
else
- printf("mov r%d, r%d LSR %d\n", rd, rs, u11);
+ printf("mov r%d, r%d LSR %d\n", rd, rs, u11);
}
} else if (2 == opt) {
if (X)
- printf("mov r%d, r%d ASR r%d\n", rd, rs, rs1);
+ printf("mov r%d, r%d ASR r%d\n", rd, rs, rs1);
else {
if (0 == u11)
- printf("mov r%d, r%d\n", rd, rs);
+ printf("mov r%d, r%d\n", rd, rs);
else
- printf("mov r%d, r%d ASR %d\n", rd, rs, u11);
+ printf("mov r%d, r%d ASR %d\n", rd, rs, u11);
}
} else if (3 == opt)
- printf("NOT r%d, r%d\n", rd, rs);
+ printf("NOT r%d, r%d\n", rd, rs);
else if (4 == opt)
- printf("NEG r%d, r%d\n", rd, rs);
+ printf("NEG r%d, r%d\n", rd, rs);
else if (5 == opt) {
if (X)
- printf("movsb r%d, r%d\n", rd, rs);
+ printf("movsb r%d, r%d\n", rd, rs);
else
- printf("movzb r%d, r%d\n", rd, rs);
+ printf("movzb r%d, r%d\n", rd, rs);
} else if (6 == opt) {
if (X)
- printf("movsw r%d, r%d\n", rd, rs);
+ printf("movsw r%d, r%d\n", rd, rs);
else
- printf("movzw r%d, r%d\n", rd, rs);
+ printf("movzw r%d, r%d\n", rd, rs);
} else if (7 == opt) {
if (X)
- printf("movsl r%d, r%d\n", rd, rs);
+ printf("movsl r%d, r%d\n", rd, rs);
else
- printf("movzl r%d, r%d\n", rd, rs);
+ printf("movzl r%d, r%d\n", rd, rs);
}
}
return 0;
}
+static int __naja_fadd(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+
+ printf("fadd r%d, r%d, r%d\n", rd, rs0, rs1);
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fsub(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+
+ printf("fsub r%d, r%d, r%d\n", rd, rs0, rs1);
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fcmp(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+
+ printf("fcmp d%d, d%d\n", rs0, rs1);
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fmul(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+ int rs2 = (inst >> 10) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int opt = (inst >> 18) & 0x3;
+
+ if (0 == opt)
+ printf("fmadd d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+ else if (1 == opt)
+ printf("fmsub d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+ else
+ printf("fmul d%d, d%d, d%d", rd, rs0, rs1);
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fdiv(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs0 = inst & 0x1f;
+ int rs1 = (inst >> 5) & 0x1f;
+ int rs2 = (inst >> 10) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int opt = (inst >> 18) & 0x3;
+
+ if (0 == opt)
+ printf("fdadd d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+ else if (1 == opt)
+ printf("fdsub d%d, d%d, d%d, d%d", rd, rs2, rs0, rs1);
+ else
+ printf("fdiv d%d, d%d, d%d", rd, rs0, rs1);
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fstr_disp(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rb = inst & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int A = (inst >> 20) & 0x1;
+ int ext = (inst >> 17) & 0x7;
+ int s12 = (inst >> 5) & 0xfff;
+
+ if (s12 & 0x800)
+ s12 |= 0xfffff000;
+
+ switch (ext) {
+ case 3:
+ if (A)
+ printf("fstr d%d, [r%d, %d]!\n", rd, rb, s12 << 3);
+ else
+ printf("fstr d%d, [r%d, %d]\n", rd, rb, s12 << 3);
+ break;
+
+ case 6:
+ if (A)
+ printf("fstrf f%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ else
+ printf("fstrf f%d, [r%d, %d]\n", rd, rb, s12 << 2);
+ break;
+ default:
+ scf_loge("ext: %d\n", ext);
+ return -1;
+ break;
+ };
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fldr_disp(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rb = inst & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int A = (inst >> 20) & 0x1;
+ int ext = (inst >> 17) & 0x7;
+ int s12 = (inst >> 5) & 0xfff;
+
+ if (s12 & 0x800)
+ s12 |= 0xfffff000;
+
+ switch (ext) {
+ case 3:
+ if (A)
+ printf("fldr d%d, [r%d, %d]!\n", rd, rb, s12 << 3);
+ else
+ printf("fldr d%d, [r%d, %d]\n", rd, rb, s12 << 3);
+ break;
+
+ case 6:
+ if (A)
+ printf("fldrf f%d, [r%d, %d]!\n", rd, rb, s12 << 2);
+ else
+ printf("fldrf f%d, [r%d, %d]\n", rd, rb, s12 << 2);
+ break;
+ default:
+ scf_loge("ext: %d\n", ext);
+ return -1;
+ break;
+ };
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fldr_sib(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rb = inst & 0x1f;
+ int ri = (inst >> 5) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int ext = (inst >> 17) & 0x7;
+ int u7 = (inst >> 10) & 0x7f;
+
+ switch (ext) {
+ case 3:
+ printf("fldr d%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ break;
+ case 6:
+ printf("fldrf f%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ break;
+ default:
+ scf_loge("\n");
+ return -1;
+ break;
+ };
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fstr_sib(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rb = inst & 0x1f;
+ int ri = (inst >> 5) & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int ext = (inst >> 17) & 0x3;
+ int u7 = (inst >> 10) & 0x7f;
+
+ switch (ext) {
+ case 3:
+ printf("fstr d%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ break;
+
+ case 6:
+ printf("fldrf f%d, [r%d, r%d, %d]\n", rd, rb, ri, u7);
+ break;
+ default:
+ scf_loge("\n");
+ return -1;
+ break;
+ };
+
+ naja->ip += 4;
+ return 0;
+}
+
+static int __naja_fmov(scf_vm_t* vm, uint32_t inst)
+{
+ scf_vm_naja_t* naja = vm->priv;
+
+ int rs = inst & 0x1f;
+ int rd = (inst >> 21) & 0x1f;
+ int opt = (inst >> 16) & 0xf;
+
+ if (0 == opt)
+ printf("fmov d%d, d%d\n", rd, rs);
+
+ else if (1 == opt)
+ printf("fss2sd d%d, f%d\n", rd, rs);
+
+ else if (2 == opt)
+ printf("fsd2ss d%d, f%d\n", rd, rs);
+
+ else if (3 == opt)
+ printf("fneg d%d, d%d\n", rd, rs);
+
+ else if (4 == opt)
+ printf("cvtss2si r%d, f%d\n", rd, rs);
+
+ else if (5 == opt)
+ printf("cvtsd2si r%d, d%d\n", rd, rs);
+
+ else if (6 == opt)
+ printf("cvtss2ui r%d, f%d\n", rd, rs);
+
+ else if (7 == opt)
+ printf("cvtsd2ui r%d, d%d\n", rd, rs);
+
+ else if (0xc == opt)
+ printf("cvtsi2ss f%d, r%d\n", rd, rs);
+
+ else if (0xd == opt)
+ printf("cvtsi2sd d%d, r%d\n", rd, rs);
+
+ else if (0xe == opt)
+ printf("cvtui2ss f%d, r%d\n", rd, rs);
+
+ else if (0xf == opt)
+ printf("cvtui2sd f%d, r%d\n", rd, rs);
+ else {
+ scf_loge("\n");
+ return -EINVAL;
+ }
+
+ naja->ip += 4;
+ return 0;
+}
+
+
static naja_opcode_pt naja_opcodes[64] =
{
__naja_add, // 0
__naja_teq, //14
__naja_mov, //15
- NULL, //16
- NULL, //17
- NULL, //18
- NULL, //19
- NULL, //20
- NULL, //21
+ __naja_fadd, //16
+ __naja_fsub, //17
+ __naja_fmul, //18
+ __naja_fdiv, //19
+ __naja_fldr_disp,//20
+ __naja_fstr_disp,//21
NULL, //22
NULL, //23
__naja_call_disp,//24
- NULL, //25
+ __naja_fcmp, //25
__naja_call_reg, //26
NULL, //27
- NULL, //28
- NULL, //29
+ __naja_fldr_sib, //28
+ __naja_fstr_sib, //29
NULL, //30
- NULL, //31
+ __naja_fmov, //31
NULL, //32
NULL, //33