modified the reader to allow redundant semicolons as if blank expressions are specified. redundant semicolons form no expressions.
Some checks failed
continuous-integration/drone/push Build is failing

modified the compiler to emit instructions to return the receiver for methods for classes
This commit is contained in:
hyung-hwan 2023-12-04 22:35:30 +09:00
parent 01fcaba626
commit 89b5089564
2 changed files with 75 additions and 12 deletions

View File

@ -74,18 +74,15 @@ enum
(plus 10 20) (plus 10 20)
<---- minus is now available <---- minus is now available
(minus 10 1) (minus 10 1)
literals --> literals -->
// //
// characeter 'A' // characeter 'A'
// "string" // "string"
// B"byte string" // B"byte string" <-- not yet implemented
// array ---> #[ ] or [ ] ? constant or not? dynamic??? // array ---> #[ ] or [ ] ? constant or not? dynamic???
// hash table - dictionary ---> #{ } or { } <--- ambuguity with blocks... // hash table - dictionary ---> #{ }
// the rest must be manipulated with code... // the rest must be manipulated with code...
------------------------------ */ ------------------------------ */
static int copy_string_to (hcl_t* hcl, const hcl_oocs_t* src, hcl_oocs_t* dst, hcl_oow_t* dstcapa, int append, hcl_ooch_t delim_char) static int copy_string_to (hcl_t* hcl, const hcl_oocs_t* src, hcl_oocs_t* dst, hcl_oow_t* dstcapa, int append, hcl_ooch_t delim_char)
@ -229,9 +226,26 @@ static void kill_temporary_variable_at_offset (hcl_t* hcl, hcl_oow_t offset)
hcl->c->tv.s.ptr[offset] = '('; /* HACK!! put a special character which can't form a variable name */ hcl->c->tv.s.ptr[offset] = '('; /* HACK!! put a special character which can't form a variable name */
} }
static int is_in_top_scope (hcl_t* hcl)
{
hcl_fnblk_info_t* fbi;
/*printf (">>> ---- fnblk.depth ....%d\n", (int)hcl->c->fnblk.depth);*/
if (hcl->c->fnblk.depth > 0) return 0;
HCL_ASSERT (hcl, hcl->c->fnblk.depth >= 0);
fbi = &hcl->c->fnblk.info[hcl->c->fnblk.depth];
/*printf ("fbi->clsblk_top....%d\n", (int)fbi->clsblk_top);*/
return fbi->clsblk_top < 0;
}
static int is_in_top_fun_scope (hcl_t* hcl)
{
return hcl->c->fnblk.depth == 0;
}
static int is_in_class_init_scope (hcl_t* hcl) static int is_in_class_init_scope (hcl_t* hcl)
{ {
hcl_fnblk_info_t* fbi; hcl_fnblk_info_t* fbi;
HCL_ASSERT (hcl, hcl->c->fnblk.depth >= 0);
fbi = &hcl->c->fnblk.info[hcl->c->fnblk.depth]; fbi = &hcl->c->fnblk.info[hcl->c->fnblk.depth];
return fbi->clsblk_top >= 0; return fbi->clsblk_top >= 0;
} }
@ -240,6 +254,7 @@ static int is_in_class_method_scope (hcl_t* hcl)
{ {
hcl_oow_t i; hcl_oow_t i;
HCL_ASSERT (hcl, hcl->c->fnblk.depth >= 0);
for (i = hcl->c->fnblk.depth + 1; i > 0; ) for (i = hcl->c->fnblk.depth + 1; i > 0; )
{ {
hcl_fnblk_info_t* fbi; hcl_fnblk_info_t* fbi;
@ -2376,6 +2391,16 @@ static int compile_class (hcl_t* hcl, hcl_cnode_t* src, int defclass)
} }
obj = HCL_CNODE_CONS_CDR(obj); obj = HCL_CNODE_CONS_CDR(obj);
/*
if (is_in_top_scope(hcl))
{
HCL_DEBUG2(hcl, "AT TOP SCOPE - %.*js\n", HCL_CNODE_GET_TOKLEN(class_name), HCL_CNODE_GET_TOKPTR(class_name));
}
else
{
HCL_DEBUG2(hcl, "NOT NOT NOT NOT NOT AT TOP SCOPE - %.*js\n", HCL_CNODE_GET_TOKLEN(class_name), HCL_CNODE_GET_TOKPTR(class_name));
}
*/
} }
else else
{ {
@ -5240,11 +5265,13 @@ static HCL_INLINE int emit_lambda (hcl_t* hcl)
hcl_oow_t block_code_size, lfsize; hcl_oow_t block_code_size, lfsize;
hcl_ooi_t jip; hcl_ooi_t jip;
hcl_fnblk_info_t* fbi; hcl_fnblk_info_t* fbi;
hcl_loc_t* oploc;
cf = GET_TOP_CFRAME(hcl); cf = GET_TOP_CFRAME(hcl);
HCL_ASSERT (hcl, cf->opcode == COP_EMIT_LAMBDA); HCL_ASSERT (hcl, cf->opcode == COP_EMIT_LAMBDA);
HCL_ASSERT (hcl, cf->operand != HCL_NULL); HCL_ASSERT (hcl, cf->operand != HCL_NULL);
oploc = HCL_CNODE_GET_LOC(cf->operand);
fbi = &hcl->c->fnblk.info[hcl->c->fnblk.depth]; fbi = &hcl->c->fnblk.info[hcl->c->fnblk.depth];
jip = cf->u.lambda.jump_inst_pos; jip = cf->u.lambda.jump_inst_pos;
@ -5259,29 +5286,61 @@ static HCL_INLINE int emit_lambda (hcl_t* hcl)
/* this function block defines one or more return variables */ /* this function block defines one or more return variables */
if (block_code_size > 0) if (block_code_size > 0)
{ {
if (emit_byte_instruction(hcl, HCL_CODE_POP_STACKTOP, HCL_CNODE_GET_LOC(cf->operand)) <= -1) return -1; if (emit_byte_instruction(hcl, HCL_CODE_POP_STACKTOP, oploc) <= -1) return -1;
block_code_size++; block_code_size++;
} }
if (emit_byte_instruction(hcl, HCL_CODE_PUSH_RETURN_R, HCL_CNODE_GET_LOC(cf->operand)) <= -1) return -1; if (emit_byte_instruction(hcl, HCL_CODE_PUSH_RETURN_R, oploc) <= -1) return -1;
block_code_size++; block_code_size++;
} }
else else
{
/* single return value */
if (cf->u.lambda.fun_type == FUN_PLAIN)
{ {
if (block_code_size == 0) if (block_code_size == 0)
{ {
/* no body in lambda - (lambda (a b c)) */ /* no body in lambda - (lambda (a b c)) */
/* TODO: is this correct??? */ /* TODO: is this correct??? */
if (emit_byte_instruction(hcl, HCL_CODE_PUSH_NIL, HCL_CNODE_GET_LOC(cf->operand)) <= -1) return -1; if (emit_byte_instruction(hcl, HCL_CODE_PUSH_NIL, oploc) <= -1) return -1;
block_code_size++;
}
}
else
{
/* class methods */
if (block_code_size == 1)
{
/* simple optimization not to skip emitting POP_STACKTOP */
HCL_ASSERT (hcl, hcl->code.bc.len > 0);
if (hcl->code.bc.ptr[hcl->code.bc.len - 1] == HCL_CODE_PUSH_NIL)
{
hcl->code.bc.len--;
block_code_size--;
}
else if (hcl->code.bc.ptr[hcl->code.bc.len - 1] == HCL_CODE_PUSH_RECEIVER)
{
goto emit_return_from_block;
}
}
if (block_code_size > 0)
{
if (emit_byte_instruction(hcl, HCL_CODE_POP_STACKTOP, oploc) <= -1) return -1;
block_code_size++; block_code_size++;
} }
if (emit_byte_instruction(hcl, HCL_CODE_RETURN_FROM_BLOCK, HCL_CNODE_GET_LOC(cf->operand)) <= -1) return -1; if (emit_byte_instruction(hcl, HCL_CODE_PUSH_RECEIVER, oploc) <= -1) return -1;
block_code_size++;
}
emit_return_from_block:
if (emit_byte_instruction(hcl, HCL_CODE_RETURN_FROM_BLOCK, oploc) <= -1) return -1;
block_code_size++; block_code_size++;
} }
if (block_code_size > MAX_CODE_JUMP * 2) if (block_code_size > MAX_CODE_JUMP * 2)
{ {
hcl_setsynerrbfmt (hcl, HCL_SYNERR_BLKFLOOD, HCL_CNODE_GET_LOC(cf->operand), HCL_NULL, "code too big - size %zu", block_code_size); hcl_setsynerrbfmt (hcl, HCL_SYNERR_BLKFLOOD, oploc, HCL_NULL, "code too big - size %zu", block_code_size);
return -1; return -1;
} }
patch_long_jump (hcl, jip, block_code_size); patch_long_jump (hcl, jip, block_code_size);

View File

@ -1248,8 +1248,12 @@ static int feed_process_token (hcl_t* hcl)
rstl = hcl->c->r.st; rstl = hcl->c->r.st;
if (!rstl || !(rstl->flagv & AUTO_FORGED)) if (!rstl || !(rstl->flagv & AUTO_FORGED))
{ {
#if 0
hcl_setsynerrbfmt (hcl, HCL_SYNERR_SEMICOLON, TOKEN_LOC(hcl), TOKEN_NAME(hcl), "unexpected semicolon"); hcl_setsynerrbfmt (hcl, HCL_SYNERR_SEMICOLON, TOKEN_LOC(hcl), TOKEN_NAME(hcl), "unexpected semicolon");
goto oops; goto oops;
#else
goto ok;
#endif
} }
concode = LIST_FLAG_GET_CONCODE(rstl->flagv); concode = LIST_FLAG_GET_CONCODE(rstl->flagv);