mirror of
https://github.com/mruby/mruby
synced 2026-06-08 16:11:16 +00:00
Merge pull request #4637 from dearblue/immutable-iseq
Prohibit changes to iseq in principle
This commit is contained in:
+5
-5
@@ -127,8 +127,8 @@ typedef struct {
|
||||
uint16_t ridx;
|
||||
uint16_t epos;
|
||||
struct REnv *env;
|
||||
mrb_code *pc; /* return address */
|
||||
mrb_code *err; /* error position */
|
||||
const mrb_code *pc; /* return address */
|
||||
const mrb_code *err; /* error position */
|
||||
int argc;
|
||||
int acc;
|
||||
struct RClass *target_class;
|
||||
@@ -243,8 +243,8 @@ typedef struct mrb_state {
|
||||
#endif
|
||||
|
||||
#ifdef MRB_ENABLE_DEBUG_HOOK
|
||||
void (*code_fetch_hook)(struct mrb_state* mrb, struct mrb_irep *irep, mrb_code *pc, mrb_value *regs);
|
||||
void (*debug_op_hook)(struct mrb_state* mrb, struct mrb_irep *irep, mrb_code *pc, mrb_value *regs);
|
||||
void (*code_fetch_hook)(struct mrb_state* mrb, struct mrb_irep *irep, const mrb_code *pc, mrb_value *regs);
|
||||
void (*debug_op_hook)(struct mrb_state* mrb, struct mrb_irep *irep, const mrb_code *pc, mrb_value *regs);
|
||||
#endif
|
||||
|
||||
#ifdef MRB_BYTECODE_DECODE_OPTION
|
||||
@@ -1057,7 +1057,7 @@ MRB_API mrb_value mrb_top_self(mrb_state *);
|
||||
MRB_API mrb_value mrb_run(mrb_state*, struct RProc*, mrb_value);
|
||||
MRB_API mrb_value mrb_top_run(mrb_state*, struct RProc*, mrb_value, unsigned int);
|
||||
MRB_API mrb_value mrb_vm_run(mrb_state*, struct RProc*, mrb_value, unsigned int);
|
||||
MRB_API mrb_value mrb_vm_exec(mrb_state*, struct RProc*, mrb_code*);
|
||||
MRB_API mrb_value mrb_vm_exec(mrb_state*, struct RProc*, const mrb_code*);
|
||||
/* compatibility macros */
|
||||
#define mrb_toplevel_run_keep(m,p,k) mrb_top_run((m),(p),mrb_top_self(m),(k))
|
||||
#define mrb_toplevel_run(m,p) mrb_toplevel_run_keep((m),(p),0)
|
||||
|
||||
@@ -32,7 +32,7 @@ typedef struct mrb_irep {
|
||||
uint16_t nregs; /* Number of register variables */
|
||||
uint8_t flags;
|
||||
|
||||
mrb_code *iseq;
|
||||
const mrb_code *iseq;
|
||||
mrb_value *pool;
|
||||
mrb_sym *syms;
|
||||
struct mrb_irep **reps;
|
||||
@@ -80,7 +80,7 @@ struct mrb_insn_data {
|
||||
uint8_t c;
|
||||
};
|
||||
|
||||
struct mrb_insn_data mrb_decode_insn(mrb_code *pc);
|
||||
struct mrb_insn_data mrb_decode_insn(const mrb_code *pc);
|
||||
|
||||
MRB_END_DECL
|
||||
|
||||
|
||||
@@ -428,7 +428,7 @@ mrb_debug_disable_break_all(mrb_state *mrb, mrb_debug_context *dbg)
|
||||
}
|
||||
|
||||
static mrb_bool
|
||||
check_start_pc_for_line(mrb_state *mrb, mrb_irep *irep, mrb_code *pc, uint16_t line)
|
||||
check_start_pc_for_line(mrb_state *mrb, mrb_irep *irep, const mrb_code *pc, uint16_t line)
|
||||
{
|
||||
if (pc > irep->iseq) {
|
||||
if (line == mrb_debug_get_line(mrb, irep, pc - irep->iseq - 1)) {
|
||||
|
||||
@@ -33,7 +33,7 @@ mrdb_check_syntax(mrb_state *mrb, mrb_debug_context *dbg, const char *expr, size
|
||||
mrb_value
|
||||
mrb_debug_eval(mrb_state *mrb, mrb_debug_context *dbg, const char *expr, size_t len, mrb_bool *exc, int direct_eval)
|
||||
{
|
||||
void (*tmp)(struct mrb_state *, struct mrb_irep *, mrb_code *, mrb_value *);
|
||||
void (*tmp)(struct mrb_state *, struct mrb_irep *, const mrb_code *, mrb_value *);
|
||||
mrb_value ruby_code;
|
||||
mrb_value s;
|
||||
mrb_value v;
|
||||
|
||||
@@ -505,7 +505,7 @@ get_and_parse_command(mrb_state *mrb, mrdb_state *mrdb)
|
||||
}
|
||||
|
||||
static int32_t
|
||||
check_method_breakpoint(mrb_state *mrb, mrb_irep *irep, mrb_code *pc, mrb_value *regs)
|
||||
check_method_breakpoint(mrb_state *mrb, mrb_irep *irep, const mrb_code *pc, mrb_value *regs)
|
||||
{
|
||||
struct RClass* c;
|
||||
mrb_sym sym;
|
||||
@@ -546,7 +546,7 @@ check_method_breakpoint(mrb_state *mrb, mrb_irep *irep, mrb_code *pc, mrb_value
|
||||
}
|
||||
|
||||
static void
|
||||
mrb_code_fetch_hook(mrb_state *mrb, mrb_irep *irep, mrb_code *pc, mrb_value *regs)
|
||||
mrb_code_fetch_hook(mrb_state *mrb, mrb_irep *irep, const mrb_code *pc, mrb_value *regs)
|
||||
{
|
||||
const char *file;
|
||||
int32_t line;
|
||||
|
||||
@@ -105,7 +105,7 @@ typedef struct mrb_debug_breakpoint {
|
||||
typedef struct mrb_debug_context {
|
||||
struct mrb_irep *root_irep;
|
||||
struct mrb_irep *irep;
|
||||
mrb_code *pc;
|
||||
const mrb_code *pc;
|
||||
mrb_value *regs;
|
||||
|
||||
const char *prvfile;
|
||||
|
||||
@@ -291,7 +291,7 @@ on_eval(codegen_scope *s)
|
||||
}
|
||||
|
||||
struct mrb_insn_data
|
||||
mrb_decode_insn(mrb_code *pc)
|
||||
mrb_decode_insn(const mrb_code *pc)
|
||||
{
|
||||
struct mrb_insn_data data = { 0 };
|
||||
mrb_code insn = READ_B();
|
||||
|
||||
@@ -102,25 +102,28 @@ patch_irep(mrb_state *mrb, mrb_irep *irep, int bnest, mrb_irep *top)
|
||||
uint8_t c;
|
||||
mrb_code insn;
|
||||
int argc = irep_argc(irep);
|
||||
mrb_code *iseq = (mrb_code *)irep->iseq;
|
||||
|
||||
mrb_assert((irep->flags & MRB_ISEQ_NO_FREE) == 0);
|
||||
|
||||
for (i = 0; i < irep->ilen; ) {
|
||||
insn = irep->iseq[i];
|
||||
insn = iseq[i];
|
||||
switch(insn){
|
||||
case OP_EPUSH:
|
||||
b = PEEK_S(irep->iseq+i+1);
|
||||
b = PEEK_S(iseq+i+1);
|
||||
patch_irep(mrb, irep->reps[b], bnest + 1, top);
|
||||
break;
|
||||
|
||||
case OP_LAMBDA:
|
||||
case OP_BLOCK:
|
||||
a = PEEK_B(irep->iseq+i+1);
|
||||
b = PEEK_B(irep->iseq+i+2);
|
||||
a = PEEK_B(iseq+i+1);
|
||||
b = PEEK_B(iseq+i+2);
|
||||
patch_irep(mrb, irep->reps[b], bnest + 1, top);
|
||||
break;
|
||||
|
||||
case OP_SEND:
|
||||
b = PEEK_B(irep->iseq+i+2);
|
||||
c = PEEK_B(irep->iseq+i+3);
|
||||
b = PEEK_B(iseq+i+2);
|
||||
c = PEEK_B(iseq+i+3);
|
||||
if (c != 0) {
|
||||
break;
|
||||
}
|
||||
@@ -128,24 +131,24 @@ patch_irep(mrb_state *mrb, mrb_irep *irep, int bnest, mrb_irep *top)
|
||||
uint16_t arg = search_variable(mrb, irep->syms[b], bnest);
|
||||
if (arg != 0) {
|
||||
/* must replace */
|
||||
irep->iseq[i] = OP_GETUPVAR;
|
||||
irep->iseq[i+2] = arg >> 8;
|
||||
irep->iseq[i+3] = arg & 0xff;
|
||||
iseq[i] = OP_GETUPVAR;
|
||||
iseq[i+2] = arg >> 8;
|
||||
iseq[i+3] = arg & 0xff;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case OP_MOVE:
|
||||
a = PEEK_B(irep->iseq+i+1);
|
||||
b = PEEK_B(irep->iseq+i+2);
|
||||
a = PEEK_B(iseq+i+1);
|
||||
b = PEEK_B(iseq+i+2);
|
||||
/* src part */
|
||||
if (potential_upvar_p(irep->lv, b, argc, irep->nlocals)) {
|
||||
uint16_t arg = search_variable(mrb, irep->lv[b - 1].name, bnest);
|
||||
if (arg != 0) {
|
||||
/* must replace */
|
||||
irep->iseq[i] = insn = OP_GETUPVAR;
|
||||
irep->iseq[i+2] = arg >> 8;
|
||||
irep->iseq[i+3] = arg & 0xff;
|
||||
iseq[i] = insn = OP_GETUPVAR;
|
||||
iseq[i+2] = arg >> 8;
|
||||
iseq[i+3] = arg & 0xff;
|
||||
}
|
||||
}
|
||||
/* dst part */
|
||||
@@ -153,18 +156,18 @@ patch_irep(mrb_state *mrb, mrb_irep *irep, int bnest, mrb_irep *top)
|
||||
uint16_t arg = search_variable(mrb, irep->lv[a - 1].name, bnest);
|
||||
if (arg != 0) {
|
||||
/* must replace */
|
||||
irep->iseq[i] = insn = OP_SETUPVAR;
|
||||
irep->iseq[i+1] = (mrb_code)b;
|
||||
irep->iseq[i+2] = arg >> 8;
|
||||
irep->iseq[i+3] = arg & 0xff;
|
||||
iseq[i] = insn = OP_SETUPVAR;
|
||||
iseq[i+1] = (mrb_code)b;
|
||||
iseq[i+2] = arg >> 8;
|
||||
iseq[i+3] = arg & 0xff;
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case OP_GETUPVAR:
|
||||
a = PEEK_B(irep->iseq+i+1);
|
||||
b = PEEK_B(irep->iseq+i+2);
|
||||
c = PEEK_B(irep->iseq+i+3);
|
||||
a = PEEK_B(iseq+i+1);
|
||||
b = PEEK_B(iseq+i+2);
|
||||
c = PEEK_B(iseq+i+3);
|
||||
{
|
||||
int lev = c+1;
|
||||
mrb_irep *tmp = search_irep(top, bnest, lev, irep);
|
||||
@@ -172,18 +175,18 @@ patch_irep(mrb_state *mrb, mrb_irep *irep, int bnest, mrb_irep *top)
|
||||
uint16_t arg = search_variable(mrb, tmp->lv[b-1].name, bnest);
|
||||
if (arg != 0) {
|
||||
/* must replace */
|
||||
irep->iseq[i] = OP_GETUPVAR;
|
||||
irep->iseq[i+2] = arg >> 8;
|
||||
irep->iseq[i+3] = arg & 0xff;
|
||||
iseq[i] = OP_GETUPVAR;
|
||||
iseq[i+2] = arg >> 8;
|
||||
iseq[i+3] = arg & 0xff;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case OP_SETUPVAR:
|
||||
a = PEEK_B(irep->iseq+i+1);
|
||||
b = PEEK_B(irep->iseq+i+2);
|
||||
c = PEEK_B(irep->iseq+i+3);
|
||||
a = PEEK_B(iseq+i+1);
|
||||
b = PEEK_B(iseq+i+2);
|
||||
c = PEEK_B(iseq+i+3);
|
||||
{
|
||||
int lev = c+1;
|
||||
mrb_irep *tmp = search_irep(top, bnest, lev, irep);
|
||||
@@ -191,25 +194,25 @@ patch_irep(mrb_state *mrb, mrb_irep *irep, int bnest, mrb_irep *top)
|
||||
uint16_t arg = search_variable(mrb, tmp->lv[b-1].name, bnest);
|
||||
if (arg != 0) {
|
||||
/* must replace */
|
||||
irep->iseq[i] = OP_SETUPVAR;
|
||||
irep->iseq[i+1] = a;
|
||||
irep->iseq[i+2] = arg >> 8;
|
||||
irep->iseq[i+3] = arg & 0xff;
|
||||
iseq[i] = OP_SETUPVAR;
|
||||
iseq[i+1] = a;
|
||||
iseq[i+2] = arg >> 8;
|
||||
iseq[i+3] = arg & 0xff;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case OP_EXT1:
|
||||
insn = PEEK_B(irep->iseq+i+1);
|
||||
insn = PEEK_B(iseq+i+1);
|
||||
i += mrb_insn_size1[insn]+1;
|
||||
continue;
|
||||
case OP_EXT2:
|
||||
insn = PEEK_B(irep->iseq+i+1);
|
||||
insn = PEEK_B(iseq+i+1);
|
||||
i += mrb_insn_size2[insn]+1;
|
||||
continue;
|
||||
case OP_EXT3:
|
||||
insn = PEEK_B(irep->iseq+i+1);
|
||||
insn = PEEK_B(iseq+i+1);
|
||||
i += mrb_insn_size3[insn]+1;
|
||||
continue;
|
||||
}
|
||||
|
||||
+1
-1
@@ -1259,7 +1259,7 @@ mrb_ary_svalue(mrb_state *mrb, mrb_value ary)
|
||||
}
|
||||
}
|
||||
|
||||
static mrb_code each_iseq[] = {
|
||||
static const mrb_code each_iseq[] = {
|
||||
OP_ENTER, 0x0, 0x00, 0x1, /* OP_ENTER 0:0:0:0:0:0:1 */
|
||||
OP_JMPIF, 0x1, 0x0, 19, /* OP_JMPIF R1 19 */
|
||||
OP_LOADSELF, 0x3, /* OP_LOADSELF R3 */
|
||||
|
||||
+2
-2
@@ -26,7 +26,7 @@ typedef void (*each_backtrace_func)(mrb_state*, const struct backtrace_location*
|
||||
static const mrb_data_type bt_type = { "Backtrace", mrb_free };
|
||||
|
||||
static void
|
||||
each_backtrace(mrb_state *mrb, ptrdiff_t ciidx, mrb_code *pc0, each_backtrace_func func, void *data)
|
||||
each_backtrace(mrb_state *mrb, ptrdiff_t ciidx, const mrb_code *pc0, each_backtrace_func func, void *data)
|
||||
{
|
||||
ptrdiff_t i;
|
||||
|
||||
@@ -37,7 +37,7 @@ each_backtrace(mrb_state *mrb, ptrdiff_t ciidx, mrb_code *pc0, each_backtrace_fu
|
||||
struct backtrace_location loc;
|
||||
mrb_callinfo *ci;
|
||||
mrb_irep *irep;
|
||||
mrb_code *pc;
|
||||
const mrb_code *pc;
|
||||
|
||||
ci = &mrb->c->cibase[i];
|
||||
|
||||
|
||||
+1
-1
@@ -2123,7 +2123,7 @@ inspect_main(mrb_state *mrb, mrb_value mod)
|
||||
return mrb_str_new_lit(mrb, "main");
|
||||
}
|
||||
|
||||
static mrb_code new_iseq[] = {
|
||||
static const mrb_code new_iseq[] = {
|
||||
OP_ENTER, 0x0, 0x10, 0x1, /* OP_ENTER 0:0:1:0:0:0:1 */
|
||||
OP_LOADSELF, 0x3, /* OP_LOADSELF R3 */
|
||||
OP_SEND, 0x3, 0x0, 0x0, /* OP_SEND R3 :allocate 0 */
|
||||
|
||||
+1
-1
@@ -69,7 +69,7 @@ static void
|
||||
codedump(mrb_state *mrb, mrb_irep *irep)
|
||||
{
|
||||
int ai;
|
||||
mrb_code *pc, *pcend;
|
||||
const mrb_code *pc, *pcend;
|
||||
mrb_code ins;
|
||||
const char *file = NULL, *next_file;
|
||||
|
||||
|
||||
+2
-2
@@ -198,11 +198,11 @@ static void
|
||||
exc_debug_info(mrb_state *mrb, struct RObject *exc)
|
||||
{
|
||||
mrb_callinfo *ci = mrb->c->ci;
|
||||
mrb_code *pc = ci->pc;
|
||||
const mrb_code *pc = ci->pc;
|
||||
|
||||
if (mrb_obj_iv_defined(mrb, exc, mrb_intern_lit(mrb, "file"))) return;
|
||||
while (ci >= mrb->c->cibase) {
|
||||
mrb_code *err = ci->err;
|
||||
const mrb_code *err = ci->err;
|
||||
|
||||
if (!err && pc) err = pc - 1;
|
||||
if (err && ci->proc && !MRB_PROC_CFUNC_P(ci->proc)) {
|
||||
|
||||
+3
-2
@@ -102,8 +102,9 @@ read_irep_record_1(mrb_state *mrb, const uint8_t *bin, size_t *len, uint8_t flag
|
||||
}
|
||||
else {
|
||||
size_t data_len = sizeof(mrb_code) * irep->ilen;
|
||||
irep->iseq = (mrb_code *)mrb_malloc(mrb, data_len);
|
||||
memcpy(irep->iseq, src, data_len);
|
||||
void *buf = mrb_malloc(mrb, data_len);
|
||||
irep->iseq = (mrb_code *)buf;
|
||||
memcpy(buf, src, data_len);
|
||||
src += data_len;
|
||||
}
|
||||
}
|
||||
|
||||
+2
-2
@@ -9,7 +9,7 @@
|
||||
#include <mruby/proc.h>
|
||||
#include <mruby/opcode.h>
|
||||
|
||||
static mrb_code call_iseq[] = {
|
||||
static const mrb_code call_iseq[] = {
|
||||
OP_CALL,
|
||||
};
|
||||
|
||||
@@ -256,7 +256,7 @@ mrb_int
|
||||
mrb_proc_arity(const struct RProc *p)
|
||||
{
|
||||
struct mrb_irep *irep;
|
||||
mrb_code *pc;
|
||||
const mrb_code *pc;
|
||||
mrb_aspec aspec;
|
||||
int ma, op, ra, pa, arity;
|
||||
|
||||
|
||||
+1
-1
@@ -117,7 +117,7 @@ mrb_irep_free(mrb_state *mrb, mrb_irep *irep)
|
||||
int i;
|
||||
|
||||
if (!(irep->flags & MRB_ISEQ_NO_FREE))
|
||||
mrb_free(mrb, irep->iseq);
|
||||
mrb_free(mrb, (void*)irep->iseq);
|
||||
if (irep->pool) for (i=0; i<irep->plen; i++) {
|
||||
if (mrb_type(irep->pool[i]) == MRB_TT_STRING) {
|
||||
mrb_gc_free_str(mrb, RSTRING(irep->pool[i]));
|
||||
|
||||
@@ -971,10 +971,10 @@ check_target_class(mrb_state *mrb)
|
||||
void mrb_hash_check_kdict(mrb_state *mrb, mrb_value self);
|
||||
|
||||
MRB_API mrb_value
|
||||
mrb_vm_exec(mrb_state *mrb, struct RProc *proc, mrb_code *pc)
|
||||
mrb_vm_exec(mrb_state *mrb, struct RProc *proc, const mrb_code *pc)
|
||||
{
|
||||
/* mrb_assert(MRB_PROC_CFUNC_P(proc)) */
|
||||
mrb_code *pc0 = pc;
|
||||
const mrb_code *pc0 = pc;
|
||||
mrb_irep *irep = proc->body.irep;
|
||||
mrb_value *pool = irep->pool;
|
||||
mrb_sym *syms = irep->syms;
|
||||
|
||||
Reference in New Issue
Block a user