2022-09-21 05:16:07 +00:00
|
|
|
#include "stdafx.h"
|
|
|
|
|
2021-09-03 05:11:04 +00:00
|
|
|
#include "../Assembler.h"
|
2022-09-21 05:16:07 +00:00
|
|
|
#include "ScriptAPI.h"
|
2022-07-18 08:31:00 +00:00
|
|
|
#include <Project64-core/N64System/Mips/R4300iInstruction.h>
|
2021-09-03 05:11:04 +00:00
|
|
|
|
2022-09-21 05:16:07 +00:00
|
|
|
void ScriptAPI::Define_asm(duk_context * ctx)
|
2021-09-03 05:11:04 +00:00
|
|
|
{
|
|
|
|
const DukPropListEntry props[] = {
|
2022-09-21 05:16:07 +00:00
|
|
|
{"gprname", DukCFunction(js_asm_gprname)},
|
|
|
|
{"encode", DukCFunction(js_asm_encode)},
|
|
|
|
{"decode", DukCFunction(js_asm_decode)},
|
2022-09-26 02:31:54 +00:00
|
|
|
{nullptr},
|
2021-09-03 05:11:04 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
DefineGlobalInterface(ctx, "asm", props);
|
|
|
|
}
|
|
|
|
|
2022-09-21 05:16:07 +00:00
|
|
|
duk_ret_t ScriptAPI::js_asm_gprname(duk_context * ctx)
|
2021-09-03 05:11:04 +00:00
|
|
|
{
|
2022-09-21 05:16:07 +00:00
|
|
|
const char * names[32] = {
|
2022-09-26 02:31:54 +00:00
|
|
|
"r0",
|
|
|
|
"at",
|
|
|
|
"v0",
|
|
|
|
"v1",
|
|
|
|
"a0",
|
|
|
|
"a1",
|
|
|
|
"a2",
|
|
|
|
"a3",
|
|
|
|
"t0",
|
|
|
|
"t1",
|
|
|
|
"t2",
|
|
|
|
"t3",
|
|
|
|
"t4",
|
|
|
|
"t5",
|
|
|
|
"t6",
|
|
|
|
"t7",
|
|
|
|
"s0",
|
|
|
|
"s1",
|
|
|
|
"s2",
|
|
|
|
"s3",
|
|
|
|
"s4",
|
|
|
|
"s5",
|
|
|
|
"s6",
|
|
|
|
"s7",
|
|
|
|
"t8",
|
|
|
|
"t9",
|
|
|
|
"k0",
|
|
|
|
"k1",
|
|
|
|
"gp",
|
|
|
|
"sp",
|
|
|
|
"fp",
|
|
|
|
"ra",
|
2021-09-03 05:11:04 +00:00
|
|
|
};
|
|
|
|
|
2022-09-21 05:16:07 +00:00
|
|
|
CheckArgs(ctx, {Arg_Number});
|
2021-09-03 05:11:04 +00:00
|
|
|
|
|
|
|
duk_uint_t idx = duk_get_uint(ctx, 0);
|
|
|
|
|
|
|
|
if (idx < 32)
|
|
|
|
{
|
|
|
|
duk_push_string(ctx, names[idx]);
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
return DUK_RET_RANGE_ERROR;
|
|
|
|
}
|
|
|
|
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
2022-09-21 05:16:07 +00:00
|
|
|
duk_ret_t ScriptAPI::js_asm_encode(duk_context * ctx)
|
2021-09-03 05:11:04 +00:00
|
|
|
{
|
2022-09-21 05:16:07 +00:00
|
|
|
CheckArgs(ctx, {Arg_String, Arg_OptNumber});
|
2021-09-03 05:11:04 +00:00
|
|
|
|
2022-09-21 05:16:07 +00:00
|
|
|
const char * code = duk_get_string(ctx, 0);
|
2021-09-03 05:11:04 +00:00
|
|
|
uint32_t address = duk_get_uint_default(ctx, 1, 0);
|
|
|
|
|
|
|
|
// TODO: CAssembler's state is not thread safe.
|
|
|
|
// CAssembler should be object-oriented
|
|
|
|
|
|
|
|
uint32_t opcode;
|
|
|
|
if (!CAssembler::AssembleLine(code, &opcode, address))
|
|
|
|
{
|
|
|
|
duk_push_error_object(ctx, DUK_ERR_ERROR, "ASM syntax error");
|
|
|
|
duk_throw(ctx);
|
|
|
|
}
|
|
|
|
|
|
|
|
duk_push_uint(ctx, opcode);
|
|
|
|
return 1;
|
|
|
|
}
|
|
|
|
|
2022-09-21 05:16:07 +00:00
|
|
|
duk_ret_t ScriptAPI::js_asm_decode(duk_context * ctx)
|
2021-09-03 05:11:04 +00:00
|
|
|
{
|
2022-09-21 05:16:07 +00:00
|
|
|
CheckArgs(ctx, {Arg_Number, Arg_OptNumber});
|
2021-09-03 05:11:04 +00:00
|
|
|
|
|
|
|
uint32_t opcode = duk_get_uint(ctx, 0);
|
|
|
|
uint32_t address = duk_get_uint_default(ctx, 1, 0);
|
2022-07-18 08:31:00 +00:00
|
|
|
duk_push_string(ctx, R4300iInstruction(address, opcode).NameAndParam().c_str());
|
2021-09-03 05:11:04 +00:00
|
|
|
return 1;
|
|
|
|
}
|