mirror of
https://github.com/CPunch/Cosmo.git
synced 2024-11-05 08:10:05 +00:00
improved nan box performance
This commit is contained in:
parent
b936827cc6
commit
d154d71163
41
src/cvalue.h
41
src/cvalue.h
@ -32,35 +32,46 @@ typedef union CValue {
|
|||||||
cosmo_Number num;
|
cosmo_Number num;
|
||||||
} CValue;
|
} CValue;
|
||||||
|
|
||||||
#define MASK_SIGN_BIT ((uint64_t)1 << 63)
|
#define MASK_TYPE ((uint64_t)0x7)
|
||||||
#define MASK_TYPE ((uint64_t)0xf)
|
#define MASK_PAYLOAD ((uint64_t)0x0007fffffffffff8)
|
||||||
#define MASK_PAYLOAD ((uint64_t)0xfffffffffff0)
|
|
||||||
|
|
||||||
#define MAKE_PAYLOAD(x) ((uint64_t)(x) << 4)
|
// 3 bits (low bits) are reserved for the type
|
||||||
|
#define MAKE_PAYLOAD(x) (((uint64_t)(x) << 3) & MASK_PAYLOAD)
|
||||||
|
#define READ_PAYLOAD(x) (((x).data & MASK_PAYLOAD) >> 3)
|
||||||
|
|
||||||
// The bits that must be set to indicate a quiet NaN.
|
// The bits that must be set to indicate a quiet NaN.
|
||||||
#define MASK_QUIETNAN ((uint64_t)0x7ffc000000000000)
|
#define MASK_QUIETNAN ((uint64_t)0x7ff8000000000000)
|
||||||
|
|
||||||
|
#define GET_TYPE(x) \
|
||||||
|
((((x).data & MASK_QUIETNAN) == MASK_QUIETNAN) ? ((x).data & MASK_TYPE) : COSMO_TNUMBER)
|
||||||
|
|
||||||
// sadly this requires a bit more than a simple macro :(
|
// sadly this requires a bit more than a simple macro :(
|
||||||
static inline CosmoType GET_TYPE(CValue val) {
|
/*static inline CosmoType GET_TYPE(CValue val) {
|
||||||
// it's not not a number (its a number)
|
// it's not not a number (its a number)
|
||||||
if ((((val.data) & MASK_QUIETNAN) != MASK_QUIETNAN))
|
if ((((val.data) & MASK_QUIETNAN) != MASK_QUIETNAN))
|
||||||
return COSMO_TNUMBER;
|
return COSMO_TNUMBER;
|
||||||
|
|
||||||
if ((((val.data) & (MASK_QUIETNAN | MASK_SIGN_BIT)) == (MASK_QUIETNAN | MASK_SIGN_BIT)))
|
|
||||||
return COSMO_TOBJ;
|
|
||||||
|
|
||||||
return (val.data & MASK_TYPE);
|
return (val.data & MASK_TYPE);
|
||||||
}
|
}*/
|
||||||
|
|
||||||
|
#define SIG_MASK (MASK_QUIETNAN | MASK_TYPE)
|
||||||
|
#define BOOL_SIG (MASK_QUIETNAN | COSMO_TBOOLEAN)
|
||||||
|
#define OBJ_SIG (MASK_QUIETNAN | COSMO_TOBJ)
|
||||||
|
#define NIL_SIG (MASK_QUIETNAN | COSMO_TNIL)
|
||||||
|
|
||||||
#define cosmoV_newNumber(x) ((CValue){.num = x})
|
#define cosmoV_newNumber(x) ((CValue){.num = x})
|
||||||
#define cosmoV_newObj(x) ((CValue){.data = MASK_SIGN_BIT | MASK_QUIETNAN | (uint64_t)(uintptr_t)(x)})
|
#define cosmoV_newObj(x) ((CValue){.data = MASK_QUIETNAN | MAKE_PAYLOAD((uintptr_t)x) | COSMO_TOBJ})
|
||||||
#define cosmoV_newBoolean(x) ((CValue){.data = MASK_QUIETNAN | MAKE_PAYLOAD(x) | COSMO_TBOOLEAN})
|
#define cosmoV_newBoolean(x) ((CValue){.data = MASK_QUIETNAN | MAKE_PAYLOAD(x) | COSMO_TBOOLEAN})
|
||||||
#define cosmoV_newNil() ((CValue){.data = MASK_QUIETNAN | COSMO_TNIL})
|
#define cosmoV_newNil() ((CValue){.data = MASK_QUIETNAN | COSMO_TNIL})
|
||||||
|
|
||||||
#define cosmoV_readNumber(x) ((x).num)
|
#define cosmoV_readNumber(x) ((x).num)
|
||||||
#define cosmoV_readBoolean(x) ((bool)((x).data & MASK_PAYLOAD))
|
#define cosmoV_readBoolean(x) ((bool)READ_PAYLOAD(x))
|
||||||
#define cosmoV_readObj(x) (((CObj*)(uintptr_t)(((x).data) & ~(MASK_SIGN_BIT | MASK_QUIETNAN))))
|
#define cosmoV_readObj(x) ((CObj*)READ_PAYLOAD(x))
|
||||||
|
|
||||||
|
#define IS_NUMBER(x) (((x).data & MASK_QUIETNAN) != MASK_QUIETNAN)
|
||||||
|
#define IS_BOOLEAN(x) (((x).data & SIG_MASK) == BOOL_SIG)
|
||||||
|
#define IS_NIL(x) (((x).data & SIG_MASK) == NIL_SIG)
|
||||||
|
#define IS_OBJ(x) (((x).data & SIG_MASK) == OBJ_SIG)
|
||||||
|
|
||||||
#else
|
#else
|
||||||
/*
|
/*
|
||||||
@ -90,13 +101,13 @@ typedef struct CValue {
|
|||||||
#define cosmoV_readBoolean(x) ((bool)(x).val.b)
|
#define cosmoV_readBoolean(x) ((bool)(x).val.b)
|
||||||
#define cosmoV_readObj(x) ((CObj*)(x).val.obj)
|
#define cosmoV_readObj(x) ((CObj*)(x).val.obj)
|
||||||
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#define IS_NUMBER(x) (GET_TYPE(x) == COSMO_TNUMBER)
|
#define IS_NUMBER(x) (GET_TYPE(x) == COSMO_TNUMBER)
|
||||||
#define IS_BOOLEAN(x) (GET_TYPE(x) == COSMO_TBOOLEAN)
|
#define IS_BOOLEAN(x) (GET_TYPE(x) == COSMO_TBOOLEAN)
|
||||||
#define IS_NIL(x) (GET_TYPE(x) == COSMO_TNIL)
|
#define IS_NIL(x) (GET_TYPE(x) == COSMO_TNIL)
|
||||||
#define IS_OBJ(x) (GET_TYPE(x) == COSMO_TOBJ)
|
#define IS_OBJ(x) (GET_TYPE(x) == COSMO_TOBJ)
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
||||||
typedef CValue* StkPtr;
|
typedef CValue* StkPtr;
|
||||||
|
|
||||||
typedef struct CValueArray {
|
typedef struct CValueArray {
|
||||||
|
Loading…
Reference in New Issue
Block a user