diff options
| author | kimu_shu <[email protected]> | 2013-05-26 09:43:30 +0900 |
|---|---|---|
| committer | kimu_shu <[email protected]> | 2013-05-26 10:09:17 +0900 |
| commit | e720782f815b809a692818851582be019afe52a9 (patch) | |
| tree | a3c25239fb5afe2a33708e38d185a142f1c543a3 /include | |
| parent | d78f23d28b4706e58622493de60e17818b491fde (diff) | |
| download | mruby-e720782f815b809a692818851582be019afe52a9.tar.gz mruby-e720782f815b809a692818851582be019afe52a9.zip | |
Add MRB_WORD_BOXING mode (represent mrb_value as a word)
Diffstat (limited to 'include')
| -rw-r--r-- | include/mrbconf.h | 3 | ||||
| -rw-r--r-- | include/mruby.h | 4 | ||||
| -rw-r--r-- | include/mruby/value.h | 262 |
3 files changed, 208 insertions, 61 deletions
diff --git a/include/mrbconf.h b/include/mrbconf.h index 2b9cc5e60..0d65ae13a 100644 --- a/include/mrbconf.h +++ b/include/mrbconf.h @@ -26,6 +26,9 @@ /* define on big endian machines; used by MRB_NAN_BOXING */ //#define MRB_ENDIAN_BIG +/* represent mrb_value as a word (natural unit of data for the processor) */ +// #define MRB_WORD_BOXING + /* argv max size in mrb_funcall */ //#define MRB_FUNCALL_ARGC_MAX 16 diff --git a/include/mruby.h b/include/mruby.h index fac7e6fcd..f9f448b45 100644 --- a/include/mruby.h +++ b/include/mruby.h @@ -273,11 +273,11 @@ int mrb_gc_arena_save(mrb_state*); void mrb_gc_arena_restore(mrb_state*,int); void mrb_gc_mark(mrb_state*,struct RBasic*); #define mrb_gc_mark_value(mrb,val) do {\ - if (mrb_type(val) >= MRB_TT_OBJECT) mrb_gc_mark((mrb), mrb_basic_ptr(val));\ + if (mrb_type(val) >= MRB_TT_HAS_BASIC) mrb_gc_mark((mrb), mrb_basic_ptr(val));\ } while (0) void mrb_field_write_barrier(mrb_state *, struct RBasic*, struct RBasic*); #define mrb_field_write_barrier_value(mrb, obj, val) do{\ - if ((val.tt >= MRB_TT_OBJECT)) mrb_field_write_barrier((mrb), (obj), mrb_basic_ptr(val));\ + if ((val.tt >= MRB_TT_HAS_BASIC)) mrb_field_write_barrier((mrb), (obj), mrb_basic_ptr(val));\ } while (0) void mrb_write_barrier(mrb_state *, struct RBasic*); diff --git a/include/mruby/value.h b/include/mruby/value.h index fa2a68ac8..d4030ed2d 100644 --- a/include/mruby/value.h +++ b/include/mruby/value.h @@ -8,63 +8,9 @@ #define MRUBY_VALUE_H typedef uint8_t mrb_bool; +struct mrb_state; -#ifndef MRB_NAN_BOXING - -enum mrb_vtype { - MRB_TT_FALSE = 0, /* 0 */ - MRB_TT_FREE, /* 1 */ - MRB_TT_TRUE, /* 2 */ - MRB_TT_FIXNUM, /* 3 */ - MRB_TT_SYMBOL, /* 4 */ - MRB_TT_UNDEF, /* 5 */ - MRB_TT_FLOAT, /* 6 */ - MRB_TT_VOIDP, /* 7 */ - MRB_TT_OBJECT, /* 8 */ - MRB_TT_CLASS, /* 9 */ - MRB_TT_MODULE, /* 10 */ - MRB_TT_ICLASS, /* 11 */ - MRB_TT_SCLASS, /* 12 */ - MRB_TT_PROC, /* 13 */ - MRB_TT_ARRAY, /* 14 */ - MRB_TT_HASH, /* 15 */ - MRB_TT_STRING, /* 16 */ - MRB_TT_RANGE, /* 17 */ - MRB_TT_EXCEPTION, /* 18 */ - MRB_TT_FILE, /* 19 */ - MRB_TT_ENV, /* 20 */ - MRB_TT_DATA, /* 21 */ - MRB_TT_FIBER, /* 22 */ - MRB_TT_MAXDEFINE /* 23 */ -}; - -typedef struct mrb_value { - union { - mrb_float f; - void *p; - mrb_int i; - mrb_sym sym; - } value; - enum mrb_vtype tt; -} mrb_value; - -#define mrb_type(o) (o).tt -#define mrb_float(o) (o).value.f - -#define MRB_SET_VALUE(o, ttt, attr, v) do {\ - (o).tt = ttt;\ - (o).attr = v;\ -} while (0) - -static inline mrb_value -mrb_float_value(mrb_float f) -{ - mrb_value v; - - MRB_SET_VALUE(v, MRB_TT_FLOAT, value.f, f); - return v; -} -#else /* MRB_NAN_BOXING */ +#if defined(MRB_NAN_BOXING) #ifdef MRB_USE_FLOAT # error ---->> MRB_NAN_BOXING and MRB_USE_FLOAT conflict <<---- @@ -97,6 +43,8 @@ enum mrb_vtype { MRB_TT_MAXDEFINE /* 24 */ }; +#define MRB_TT_HAS_BASIC MRB_TT_OBJECT + #ifdef MRB_ENDIAN_BIG #define MRB_ENDIAN_LOHI(a,b) a b #else @@ -130,7 +78,7 @@ typedef struct mrb_value { } while (0) static inline mrb_value -mrb_float_value(mrb_float f) +mrb_float_value(struct mrb_state *mrb, mrb_float f) { mrb_value v; @@ -142,7 +90,163 @@ mrb_float_value(mrb_float f) } return v; } -#endif /* MRB_NAN_BOXING */ + +#elif defined(MRB_WORD_BOXING) + +enum mrb_vtype { + MRB_TT_FALSE = 0, /* 0 */ + MRB_TT_FREE, /* 1 */ + MRB_TT_TRUE, /* 2 */ + MRB_TT_FIXNUM, /* 3 */ + MRB_TT_SYMBOL, /* 4 */ + MRB_TT_UNDEF, /* 5 */ + MRB_TT_FLOAT, /* 6 */ + MRB_TT_VOIDP, /* 7 */ + MRB_TT_OBJECT, /* 8 */ + MRB_TT_CLASS, /* 9 */ + MRB_TT_MODULE, /* 10 */ + MRB_TT_ICLASS, /* 11 */ + MRB_TT_SCLASS, /* 12 */ + MRB_TT_PROC, /* 13 */ + MRB_TT_ARRAY, /* 14 */ + MRB_TT_HASH, /* 15 */ + MRB_TT_STRING, /* 16 */ + MRB_TT_RANGE, /* 17 */ + MRB_TT_EXCEPTION, /* 18 */ + MRB_TT_FILE, /* 19 */ + MRB_TT_ENV, /* 20 */ + MRB_TT_DATA, /* 21 */ + MRB_TT_FIBER, /* 22 */ + MRB_TT_MAXDEFINE /* 23 */ +}; + +#define MRB_TT_HAS_BASIC MRB_TT_FLOAT + +enum mrb_special_consts { + MRB_Qnil = 0, + MRB_Qfalse = 2, + MRB_Qtrue = 4, + MRB_Qundef = 6, + + MRB_FIXNUM_FLAG = 0x01, + MRB_FIXNUM_SHIFT = 1, + MRB_SYMBOL_FLAG = 0x0e, + MRB_SPECIAL_SHIFT = 8, +}; + +typedef union mrb_value { + union { + void *p; + struct { + unsigned int i_flag : MRB_FIXNUM_SHIFT; + mrb_int i : (sizeof(mrb_int) * 8 - MRB_FIXNUM_SHIFT); + }; + struct { + unsigned int sym_flag : MRB_SPECIAL_SHIFT; + int sym : (sizeof(mrb_sym) * 8); + }; + struct RBasic *bp; + struct RFloat *fp; + struct RVoidp *vp; + } value; + unsigned long w; +} mrb_value; + +#define mrb_float(o) (o).value.fp->f + +#define MRB_SET_VALUE(o, ttt, attr, v) do {\ + (o).w = 0;\ + (o).attr = (v);\ + switch (ttt) {\ + case MRB_TT_FALSE: (o).w = (v) ? MRB_Qfalse : MRB_Qnil; break;\ + case MRB_TT_TRUE: (o).w = MRB_Qtrue; break;\ + case MRB_TT_UNDEF: (o).w = MRB_Qundef; break;\ + case MRB_TT_FIXNUM: (o).value.i_flag = MRB_FIXNUM_FLAG; break;\ + case MRB_TT_SYMBOL: (o).value.sym_flag = MRB_SYMBOL_FLAG; break;\ + default: if ((o).value.bp) (o).value.bp->tt = ttt; break;\ + }\ +} while (0) + +extern mrb_value +mrb_float_value(struct mrb_state *mrb, mrb_float f); + +#else /* No MRB_xxx_BOXING */ + +enum mrb_vtype { + MRB_TT_FALSE = 0, /* 0 */ + MRB_TT_FREE, /* 1 */ + MRB_TT_TRUE, /* 2 */ + MRB_TT_FIXNUM, /* 3 */ + MRB_TT_SYMBOL, /* 4 */ + MRB_TT_UNDEF, /* 5 */ + MRB_TT_FLOAT, /* 6 */ + MRB_TT_VOIDP, /* 7 */ + MRB_TT_OBJECT, /* 8 */ + MRB_TT_CLASS, /* 9 */ + MRB_TT_MODULE, /* 10 */ + MRB_TT_ICLASS, /* 11 */ + MRB_TT_SCLASS, /* 12 */ + MRB_TT_PROC, /* 13 */ + MRB_TT_ARRAY, /* 14 */ + MRB_TT_HASH, /* 15 */ + MRB_TT_STRING, /* 16 */ + MRB_TT_RANGE, /* 17 */ + MRB_TT_EXCEPTION, /* 18 */ + MRB_TT_FILE, /* 19 */ + MRB_TT_ENV, /* 20 */ + MRB_TT_DATA, /* 21 */ + MRB_TT_FIBER, /* 22 */ + MRB_TT_MAXDEFINE /* 23 */ +}; + +#define MRB_TT_HAS_BASIC MRB_TT_OBJECT + +typedef struct mrb_value { + union { + mrb_float f; + void *p; + mrb_int i; + mrb_sym sym; + } value; + enum mrb_vtype tt; +} mrb_value; + +#define mrb_type(o) (o).tt +#define mrb_float(o) (o).value.f + +#define MRB_SET_VALUE(o, ttt, attr, v) do {\ + (o).tt = ttt;\ + (o).attr = v;\ +} while (0) + +static inline mrb_value +mrb_float_value(struct mrb_state *mrb, mrb_float f) +{ + mrb_value v; + + MRB_SET_VALUE(v, MRB_TT_FLOAT, value.f, f); + return v; +} +#endif /* no boxing */ + +#ifdef MRB_WORD_BOXING + +#define mrb_fixnum(o) (o).value.i +#define mrb_symbol(o) (o).value.sym +#define mrb_voidp(o) (o).value.vp->p +#define mrb_fixnum_p(o) ((o).value.i_flag == MRB_FIXNUM_FLAG) +#define mrb_float_p(o) (mrb_type(o) == MRB_TT_FLOAT) +#define mrb_undef_p(o) ((o).w == MRB_Qundef) +#define mrb_nil_p(o) ((o).w == MRB_Qnil) +#define mrb_symbol_p(o) ((o).value.sym_flag == MRB_SYMBOL_FLAG) +#define mrb_array_p(o) (mrb_type(o) == MRB_TT_ARRAY) +#define mrb_string_p(o) (mrb_type(o) == MRB_TT_STRING) +#define mrb_hash_p(o) (mrb_type(o) == MRB_TT_HASH) +#define mrb_voidp_p(o) (mrb_type(o) == MRB_TT_VOIDP) +#define mrb_bool(o) ((o).w != MRB_Qnil && (o).w != MRB_Qfalse) +#define mrb_test(o) mrb_bool(o) + +#else #define mrb_fixnum(o) (o).value.i #define mrb_symbol(o) (o).value.sym @@ -159,6 +263,8 @@ mrb_float_value(mrb_float f) #define mrb_bool(o) (mrb_type(o) != MRB_TT_FALSE) #define mrb_test(o) mrb_bool(o) +#endif /* no boxing */ + #define MRB_OBJECT_HEADER \ enum mrb_vtype tt:8;\ uint32_t color:3;\ @@ -209,6 +315,39 @@ struct RFiber { struct mrb_context *cxt; }; +#ifdef MRB_WORD_BOXING +struct RFloat { + MRB_OBJECT_HEADER; + mrb_float f; +}; + +struct RVoidp { + MRB_OBJECT_HEADER; + void *p; +}; + +static inline enum mrb_vtype +mrb_type(mrb_value o) +{ + switch (o.w) { + case MRB_Qfalse: + case MRB_Qnil: + return MRB_TT_FALSE; + case MRB_Qtrue: + return MRB_TT_TRUE; + case MRB_Qundef: + return MRB_TT_UNDEF; + } + if (o.value.i_flag == MRB_FIXNUM_FLAG) { + return MRB_TT_FIXNUM; + } + if (o.value.sym_flag == MRB_SYMBOL_FLAG) { + return MRB_TT_SYMBOL; + } + return o.value.bp->tt; +} +#endif /* MRB_WORD_BOXING */ + static inline mrb_value mrb_fixnum_value(mrb_int i) { @@ -237,14 +376,19 @@ mrb_obj_value(void *p) return v; } +#ifdef MRB_WORD_BOXING +mrb_value +mrb_voidp_value(struct mrb_state *mrb, void *p); +#else static inline mrb_value -mrb_voidp_value(void *p) +mrb_voidp_value(struct mrb_state *mrb, void *p) { mrb_value v; MRB_SET_VALUE(v, MRB_TT_VOIDP, value.p, p); return v; } +#endif static inline mrb_value mrb_false_value(void) |
