utf8 range limiting.

compiler work for class variable access in the class defintion scope
This commit is contained in:
hyung-hwan 2022-01-08 09:26:54 +00:00
parent 7c6511d4ad
commit 0fd038ddb6
6 changed files with 77 additions and 33 deletions

View File

@ -760,7 +760,7 @@ static int emit_variable_access (hcl_t* hcl, int mode, const hcl_var_info_t* vi,
{ {
{ HCL_CODE_PUSH_CTXTEMPVAR_0, HCL_CODE_POP_INTO_CTXTEMPVAR_0, HCL_CODE_STORE_INTO_CTXTEMPVAR_0 }, { HCL_CODE_PUSH_CTXTEMPVAR_0, HCL_CODE_POP_INTO_CTXTEMPVAR_0, HCL_CODE_STORE_INTO_CTXTEMPVAR_0 },
{ HCL_CODE_PUSH_INSTVAR_0, HCL_CODE_POP_INTO_INSTVAR_0, HCL_CODE_STORE_INTO_INSTVAR_0 }, { HCL_CODE_PUSH_INSTVAR_0, HCL_CODE_POP_INTO_INSTVAR_0, HCL_CODE_STORE_INTO_INSTVAR_0 },
{ HCL_CODE_PUSH_OBJVAR_0, HCL_CODE_POP_INTO_OBJVAR_0, HCL_CODE_STORE_INTO_OBJVAR_0 }, { HCL_CODE_PUSH_CLSVAR_X, HCL_CODE_POP_INTO_CLSVAR_X, HCL_CODE_STORE_INTO_CLSVAR_X },
}; };
switch (vi->type) switch (vi->type)
@ -774,7 +774,7 @@ static int emit_variable_access (hcl_t* hcl, int mode, const hcl_var_info_t* vi,
case VAR_CLASS: case VAR_CLASS:
HCL_ASSERT (hcl, vi->ctx_offset == 0); HCL_ASSERT (hcl, vi->ctx_offset == 0);
//return emit_double_param_instruction(hcl, inst_map[2][mode], vi->index_in_ctx, <<index to the class name in literal table>>, srcloc); return emit_single_param_instruction(hcl, inst_map[2][mode], vi->index_in_ctx, srcloc);
} }
return -1; return -1;
@ -2091,25 +2091,28 @@ static HCL_INLINE int compile_class_p1 (hcl_t* hcl)
{ {
/* instance variables */ /* instance variables */
hcl_oow_t checkpoint; hcl_oow_t checkpoint;
if (!HCL_CNODE_IS_CONS_CONCODED(tmp, HCL_CONCODE_VLIST)) break; if (!HCL_CNODE_IS_CONS_CONCODED(tmp, HCL_CONCODE_VLIST)) break;
checkpoint = hcl->c->tv.s.len; checkpoint = hcl->c->tv.s.len;
if (collect_vardcl(hcl, obj, &obj, tv_dup_check_start, &dclcount, "instance") <= -1) return -1; if (collect_vardcl(hcl, obj, &obj, tv_dup_check_start, &dclcount, "instance") <= -1) return -1;
nivars += dclcount; nivars += dclcount;
if (ivar_len <= 0) ivar_start = checkpoint; if (ivar_len <= 0) ivar_start = (cvar_len <= 0)? checkpoint: cvar_start;
ivar_len += hcl->c->tv.s.len - checkpoint; ivar_len += hcl->c->tv.s.len - checkpoint;
if (cvar_len > 0) if (cvar_len > 0)
{ {
/* place the instance variables before the class variables
* if class variables "a b" has been collected before instance variables "cc dd ee"
* the rotation below manipulates the buffer to contain "cc dd ee a b".
*/
hcl_rotate_oochars (&hcl->c->tv.s.ptr[cvar_start], hcl->c->tv.s.len - cvar_start, -1, cvar_len); hcl_rotate_oochars (&hcl->c->tv.s.ptr[cvar_start], hcl->c->tv.s.len - cvar_start, -1, cvar_len);
ivar_start = cvar_start;
cvar_start += hcl->c->tv.s.len - checkpoint; cvar_start += hcl->c->tv.s.len - checkpoint;
} }
} }
} }
//HCL_DEBUG4 (hcl, "AAAAAAAAAAAAAAAAAAAAAAA>>>> [%.*js] [%.*js]\n", ivar_len, &hcl->c->tv.s.ptr[ivar_start], cvar_len, &hcl->c->tv.s.ptr[cvar_start]);
if (nivars > 0) if (nivars > 0)
{ {
hcl_oop_t tmp; hcl_oop_t tmp;
@ -3710,7 +3713,7 @@ redo:
switch (HCL_CNODE_ELIST_CONCODE(oprnd)) switch (HCL_CNODE_ELIST_CONCODE(oprnd))
{ {
case HCL_CONCODE_XLIST: case HCL_CONCODE_XLIST:
hcl_setsynerrbfmt (hcl, HCL_SYNERR_VARDCLBANNED, HCL_CNODE_GET_LOC(oprnd), HCL_NULL, "empty executable list"); hcl_setsynerrbfmt (hcl, HCL_SYNERR_BANNED, HCL_CNODE_GET_LOC(oprnd), HCL_NULL, "empty executable list");
return -1; return -1;
case HCL_CONCODE_ARRAY: case HCL_CONCODE_ARRAY:
@ -3730,7 +3733,7 @@ redo:
goto done; goto done;
case HCL_CONCODE_VLIST: case HCL_CONCODE_VLIST:
hcl_setsynerrbfmt (hcl, HCL_SYNERR_VARDCLBANNED, HCL_CNODE_GET_LOC(oprnd), HCL_NULL, "variable declaration disallowed"); hcl_setsynerrbfmt (hcl, HCL_SYNERR_BANNED, HCL_CNODE_GET_LOC(oprnd), HCL_NULL, "empty variable declaration");
return -1; return -1;
default: default:

View File

@ -77,6 +77,9 @@ static hcl_ooch_t errstr_35[] = {'a','r','g','u','m','e','n','t',' ','n','u','m'
static hcl_ooch_t errstr_36[] = {'r','e','t','u','r','n',' ','c','o','u','n','t',' ','e','r','r','o','r','\0'}; static hcl_ooch_t errstr_36[] = {'r','e','t','u','r','n',' ','c','o','u','n','t',' ','e','r','r','o','r','\0'};
static hcl_ooch_t errstr_37[] = {'t','o','o',' ','m','a','n','y',' ','s','e','m','a','p','h','o','r','e','s','\0'}; static hcl_ooch_t errstr_37[] = {'t','o','o',' ','m','a','n','y',' ','s','e','m','a','p','h','o','r','e','s','\0'};
static hcl_ooch_t errstr_38[] = {'e','x','c','e','p','a','i','o','n',' ','n','o','t',' ','h','a','n','d','l','e','d','\0'}; static hcl_ooch_t errstr_38[] = {'e','x','c','e','p','a','i','o','n',' ','n','o','t',' ','h','a','n','d','l','e','d','\0'};
static hcl_ooch_t errstr_39[] = {'s','t','a','c','k',' ','u','n','d','e','r','f','l','o','w','\0'};
static hcl_ooch_t errstr_40[] = {'s','t','a','c','k',' ','o','v','e','r','f','l','o','w','\0'};
static hcl_ooch_t* errstr[] = static hcl_ooch_t* errstr[] =
{ {
@ -84,7 +87,8 @@ static hcl_ooch_t* errstr[] =
errstr_8, errstr_9, errstr_10, errstr_11, errstr_12, errstr_13, errstr_14, errstr_15, errstr_8, errstr_9, errstr_10, errstr_11, errstr_12, errstr_13, errstr_14, errstr_15,
errstr_16, errstr_17, errstr_18, errstr_19, errstr_20, errstr_21, errstr_22, errstr_23, errstr_16, errstr_17, errstr_18, errstr_19, errstr_20, errstr_21, errstr_22, errstr_23,
errstr_24, errstr_25, errstr_26, errstr_27, errstr_28, errstr_29, errstr_30, errstr_31, errstr_24, errstr_25, errstr_26, errstr_27, errstr_28, errstr_29, errstr_30, errstr_31,
errstr_32, errstr_33, errstr_34, errstr_35, errstr_36, errstr_37, errstr_38 errstr_32, errstr_33, errstr_34, errstr_35, errstr_36, errstr_37, errstr_38, errstr_39,
errstr_40
}; };

View File

@ -3442,7 +3442,12 @@ if (do_throw(hcl, hcl->_nil, fetched_instruction_pointer) <= -1)
case HCL_CODE_CLASS_EXIT: case HCL_CODE_CLASS_EXIT:
{ {
LOG_INST_0 (hcl, "class_exit"); LOG_INST_0 (hcl, "class_exit");
/* TODO: stack underflow check? */ if (HCL_CLSTACK_IS_EMPTY(hcl))
{
hcl_seterrbfmt (hcl, HCL_ESTKUNDFLW, "class stack underflow");
supplement_errmsg (hcl, fetched_instruction_pointer);
goto oops;
}
HCL_CLSTACK_POP (hcl); HCL_CLSTACK_POP (hcl);
break; break;
} }
@ -3452,7 +3457,13 @@ if (do_throw(hcl, hcl->_nil, fetched_instruction_pointer) <= -1)
hcl_oop_t c; hcl_oop_t c;
LOG_INST_0 (hcl, "class_push_exit"); LOG_INST_0 (hcl, "class_push_exit");
/* TODO: stack underflow check? */
if (HCL_CLSTACK_IS_EMPTY(hcl))
{
hcl_seterrbfmt (hcl, HCL_ESTKUNDFLW, "class stack underflow");
supplement_errmsg (hcl, fetched_instruction_pointer);
goto oops;
}
HCL_CLSTACK_POP_TO (hcl, c); HCL_CLSTACK_POP_TO (hcl, c);
HCL_STACK_PUSH (hcl, c); HCL_STACK_PUSH (hcl, c);
@ -3633,6 +3644,12 @@ if (do_throw(hcl, hcl->_nil, fetched_instruction_pointer) <= -1)
hcl_oop_class_t t; hcl_oop_class_t t;
FETCH_PARAM_CODE_TO (hcl, b1); FETCH_PARAM_CODE_TO (hcl, b1);
LOG_INST_1 (hcl, "store_into_clsvar %zu", b1); LOG_INST_1 (hcl, "store_into_clsvar %zu", b1);
if (HCL_CLSTACK_IS_EMPTY(hcl))
{
hcl_seterrbfmt (hcl, HCL_ESTKUNDFLW, "empty class stack");
supplement_errmsg (hcl, fetched_instruction_pointer);
goto oops;
}
HCL_CLSTACK_FETCH_TOP_TO(hcl, t); HCL_CLSTACK_FETCH_TOP_TO(hcl, t);
t->cvar[b1] = HCL_STACK_GETTOP(hcl); t->cvar[b1] = HCL_STACK_GETTOP(hcl);
break; break;
@ -3643,6 +3660,12 @@ if (do_throw(hcl, hcl->_nil, fetched_instruction_pointer) <= -1)
hcl_oop_class_t t; hcl_oop_class_t t;
FETCH_PARAM_CODE_TO (hcl, b1); FETCH_PARAM_CODE_TO (hcl, b1);
LOG_INST_1 (hcl, "pop_into_clsvar %zu", b1); LOG_INST_1 (hcl, "pop_into_clsvar %zu", b1);
if (HCL_CLSTACK_IS_EMPTY(hcl))
{
hcl_seterrbfmt (hcl, HCL_ESTKUNDFLW, "empty class stack");
supplement_errmsg (hcl, fetched_instruction_pointer);
goto oops;
}
HCL_CLSTACK_FETCH_TOP_TO(hcl, t); HCL_CLSTACK_FETCH_TOP_TO(hcl, t);
t->cvar[b1] = HCL_STACK_GETTOP(hcl); t->cvar[b1] = HCL_STACK_GETTOP(hcl);
HCL_STACK_POP (hcl); HCL_STACK_POP (hcl);

View File

@ -68,29 +68,31 @@ enum hcl_errnum_t
HCL_EPIPE, HCL_EPIPE,
HCL_EAGAIN, HCL_EAGAIN,
HCL_EBADHND, HCL_EBADHND,
HCL_EFRMFLOOD, /**< too many frames */ HCL_EFRMFLOOD, /**< too many frames */
HCL_EMSGRCV, /**< mesasge receiver error */ HCL_EMSGRCV, /**< mesasge receiver error */
HCL_EMSGSND, /**< message sending error. even doesNotUnderstand: is not found */ HCL_EMSGSND, /**< message sending error. even doesNotUnderstand: is not found */
HCL_ENUMARGS, /**< wrong number of arguments */ HCL_ENUMARGS, /**< wrong number of arguments */
HCL_ERANGE, /**< range error. overflow and underflow */ HCL_ERANGE, /**< range error. overflow and underflow */
HCL_EBCFULL, /**< byte-code full */ HCL_EBCFULL, /**< byte-code full */
HCL_EDFULL, /**< dictionary full */ HCL_EDFULL, /**< dictionary full */
HCL_EPFULL, /**< processor full */ HCL_EPFULL, /**< processor full */
HCL_EFINIS, /**< unexpected end of data/input/stream/etc */ HCL_EFINIS, /**< unexpected end of data/input/stream/etc */
HCL_EFLOOD, /**< too many items/data */ HCL_EFLOOD, /**< too many items/data */
HCL_EDIVBY0, /**< divide by zero */ HCL_EDIVBY0, /**< divide by zero */
HCL_EIOERR, /**< I/O error */ HCL_EIOERR, /**< I/O error */
HCL_EECERR, /**< encoding conversion error */ HCL_EECERR, /**< encoding conversion error */
HCL_EBUFFULL, /**< buffer full */ HCL_EBUFFULL, /**< buffer full */
HCL_ESYNERR, /**< syntax error */ HCL_ESYNERR, /**< syntax error */
HCL_ECALL, /**< runtime error - cannot call */ HCL_ECALL, /**< runtime error - cannot call */
HCL_ECALLARG, /**< runtime error - wrong number of arguments to call */ HCL_ECALLARG, /**< runtime error - wrong number of arguments to call */
HCL_ECALLRET, /**< runtime error - wrong number of return variables to call */ HCL_ECALLRET, /**< runtime error - wrong number of return variables to call */
HCL_ESEMFLOOD, /**< runtime error - too many semaphores */ HCL_ESEMFLOOD, /**< runtime error - too many semaphores */
HCL_EEXCEPT /**< runtime error - exception not handled */ HCL_EEXCEPT, /**< runtime error - exception not handled */
HCL_ESTKOVRFLW, /**< runtime error - stack overflow */
HCL_ESTKUNDFLW /**< runtime error - stack overflow */
}; };
typedef enum hcl_errnum_t hcl_errnum_t; typedef enum hcl_errnum_t hcl_errnum_t;

View File

@ -360,7 +360,7 @@ hcl_oop_t hcl_makeclass (hcl_t* hcl, hcl_oop_t superclass, hcl_ooi_t nivars, hcl
hcl_pushvolat (hcl, &superclass); hcl_pushvolat (hcl, &superclass);
hcl_pushvolat (hcl, &ivars_str); hcl_pushvolat (hcl, &ivars_str);
hcl_pushvolat (hcl, &cvars_str); hcl_pushvolat (hcl, &cvars_str);
c = (hcl_oop_class_t)hcl_allocoopobj(hcl, HCL_BRAND_CLASS, HCL_CLASS_NAMED_INSTVARS); c = (hcl_oop_class_t)hcl_allocoopobj(hcl, HCL_BRAND_CLASS, HCL_CLASS_NAMED_INSTVARS + ncvars);
hcl_popvolats (hcl, 3); hcl_popvolats (hcl, 3);
if (HCL_UNLIKELY(!c)) return HCL_NULL; if (HCL_UNLIKELY(!c)) return HCL_NULL;

View File

@ -26,6 +26,8 @@
#include "hcl-prv.h" #include "hcl-prv.h"
/*#define RETAIN_RFC2279 1*/
/* /*
* from RFC 2279 UTF-8, a transformation format of ISO 10646 * from RFC 2279 UTF-8, a transformation format of ISO 10646
* *
@ -36,6 +38,12 @@
* 4:4 00010000-001FFFFF 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx * 4:4 00010000-001FFFFF 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
* inv 00200000-03FFFFFF 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx * inv 00200000-03FFFFFF 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
* inv 04000000-7FFFFFFF 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx * inv 04000000-7FFFFFFF 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
*
* RFC3629 limits the ranges like this:
* 1:2 00000000-0000007F 0xxxxxxx
* 2:2 00000080-000007FF 110xxxxx 10xxxxxx
* 3:2 00000800-0000FFFF 1110xxxx 10xxxxxx 10xxxxxx
* 4:4 00010000-0010FFFF 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
*/ */
struct __utf8_t struct __utf8_t
@ -55,9 +63,13 @@ static __utf8_t utf8_table[] =
{0x00000000ul, 0x0000007Ful, 0x00, 0x80, 0x7F, 1}, {0x00000000ul, 0x0000007Ful, 0x00, 0x80, 0x7F, 1},
{0x00000080ul, 0x000007FFul, 0xC0, 0xE0, 0x1F, 2}, {0x00000080ul, 0x000007FFul, 0xC0, 0xE0, 0x1F, 2},
{0x00000800ul, 0x0000FFFFul, 0xE0, 0xF0, 0x0F, 3}, {0x00000800ul, 0x0000FFFFul, 0xE0, 0xF0, 0x0F, 3},
#if defined(RETAIN_RFC2279)
{0x00010000ul, 0x001FFFFFul, 0xF0, 0xF8, 0x07, 4}, {0x00010000ul, 0x001FFFFFul, 0xF0, 0xF8, 0x07, 4},
{0x00200000ul, 0x03FFFFFFul, 0xF8, 0xFC, 0x03, 5}, {0x00200000ul, 0x03FFFFFFul, 0xF8, 0xFC, 0x03, 5},
{0x04000000ul, 0x7FFFFFFFul, 0xFC, 0xFE, 0x01, 6} {0x04000000ul, 0x7FFFFFFFul, 0xFC, 0xFE, 0x01, 6}
#else
{0x00010000ul, 0x0010FFFFul, 0xF0, 0xF8, 0x07, 4}
#endif
}; };
static HCL_INLINE __utf8_t* get_utf8_slot (hcl_uch_t uc) static HCL_INLINE __utf8_t* get_utf8_slot (hcl_uch_t uc)
@ -81,7 +93,7 @@ static HCL_INLINE __utf8_t* get_utf8_slot (hcl_uch_t uc)
hcl_oow_t hcl_uc_to_utf8 (hcl_uch_t uc, hcl_bch_t* utf8, hcl_oow_t size) hcl_oow_t hcl_uc_to_utf8 (hcl_uch_t uc, hcl_bch_t* utf8, hcl_oow_t size)
{ {
__utf8_t* cur = get_utf8_slot (uc); __utf8_t* cur = get_utf8_slot(uc);
if (cur == HCL_NULL) return 0; /* illegal character */ if (cur == HCL_NULL) return 0; /* illegal character */