added a new keyword @nil

This commit is contained in:
hyung-hwan 2020-11-10 02:56:29 +00:00
parent 93aa76e104
commit 7ab601303c
7 changed files with 100 additions and 51 deletions

View File

@ -399,7 +399,7 @@ enum hawk_nde_type_t
/* expression */
/* if you change the following values including their order,
* you should change __evaluator of __eval_expression
* you should change __evaluator of eval_expression0()
* in run.c accordingly */
HAWK_NDE_GRP,
HAWK_NDE_ASS,
@ -416,6 +416,7 @@ enum hawk_nde_type_t
HAWK_NDE_STR,
HAWK_NDE_MBS,
HAWK_NDE_REX,
HAWK_NDE_XNIL,
HAWK_NDE_FUN,
/* keep this order for the following items otherwise, you may have

View File

@ -35,6 +35,7 @@ enum hawk_kwid_t
HAWK_KWID_XINCLUDE,
HAWK_KWID_XINCLUDE_ONCE,
HAWK_KWID_XLOCAL,
HAWK_KWID_XNIL,
HAWK_KWID_XPRAGMA,
HAWK_KWID_XRESET,
HAWK_KWID_BEGIN,

View File

@ -178,6 +178,7 @@ enum tok_t
TOK_STR,
TOK_MBS,
TOK_REX,
TOK_XNIL,
__TOKEN_COUNT__
};
@ -281,13 +282,14 @@ struct kwent_t
static kwent_t kwtab[] =
{
/* keep this table in sync with the kw_t enums in <parse.h>.
/* keep this table in sync with the kw_t enums in "parse-prv.h".
* also keep it sorted by the first field for binary search */
{ { HAWK_T("@abort"), 6 }, TOK_XABORT, 0 },
{ { HAWK_T("@global"), 7 }, TOK_XGLOBAL, 0 },
{ { HAWK_T("@include"), 8 }, TOK_XINCLUDE, 0 },
{ { HAWK_T("@include_once"), 13 }, TOK_XINCLUDE_ONCE, 0 },
{ { HAWK_T("@local"), 6 }, TOK_XLOCAL, 0 },
{ { HAWK_T("@nil"), 4 }, TOK_XNIL, 0 },
{ { HAWK_T("@pragma"), 7 }, TOK_XPRAGMA, 0 },
{ { HAWK_T("@reset"), 6 }, TOK_XRESET, 0 },
{ { HAWK_T("BEGIN"), 5 }, TOK_BEGIN, HAWK_PABLOCK },
@ -1566,7 +1568,7 @@ static hawk_nde_t* parse_function (hawk_t* hawk)
hawk_arr_clear (hawk->parse.params);
fun = (hawk_fun_t*)hawk_callocmem(hawk, HAWK_SIZEOF(*fun));
if (fun == HAWK_NULL)
if (HAWK_UNLIKELY(!fun))
{
ADJERR_LOC (hawk, &hawk->tok.loc);
goto oops;
@ -1579,7 +1581,7 @@ static hawk_nde_t* parse_function (hawk_t* hawk)
fun->body = body;
pair = hawk_htb_insert(hawk->tree.funs, name.ptr, name.len, fun, 0);
if (pair == HAWK_NULL)
if (HAWK_UNLIKELY(!pair))
{
/* if hawk_htb_insert() fails for other reasons than memory
* shortage, there should be implementaion errors as duplicate
@ -1616,8 +1618,8 @@ static hawk_nde_t* parse_begin (hawk_t* hawk)
HAWK_ASSERT (MATCH(hawk,TOK_LBRACE));
if (get_token(hawk) <= -1) return HAWK_NULL;
nde = parse_block_dc (hawk, &xloc, 1);
if (nde == HAWK_NULL) return HAWK_NULL;
nde = parse_block_dc(hawk, &xloc, 1);
if (HAWK_UNLIKELY(!nde)) return HAWK_NULL;
if (hawk->tree.begin == HAWK_NULL)
{
@ -1642,8 +1644,8 @@ static hawk_nde_t* parse_end (hawk_t* hawk)
HAWK_ASSERT (MATCH(hawk,TOK_LBRACE));
if (get_token(hawk) <= -1) return HAWK_NULL;
nde = parse_block_dc (hawk, &xloc, 1);
if (nde == HAWK_NULL) return HAWK_NULL;
nde = parse_block_dc(hawk, &xloc, 1);
if (HAWK_UNLIKELY(!nde)) return HAWK_NULL;
if (hawk->tree.end == HAWK_NULL)
{
@ -1658,8 +1660,7 @@ static hawk_nde_t* parse_end (hawk_t* hawk)
return nde;
}
static hawk_chain_t* parse_action_block (
hawk_t* hawk, hawk_nde_t* ptn, int blockless)
static hawk_chain_t* parse_action_block (hawk_t* hawk, hawk_nde_t* ptn, int blockless)
{
hawk_nde_t* nde;
hawk_chain_t* chain;
@ -1672,11 +1673,11 @@ static hawk_chain_t* parse_action_block (
HAWK_ASSERT (MATCH(hawk,TOK_LBRACE));
if (get_token(hawk) <= -1) return HAWK_NULL;
nde = parse_block_dc(hawk, &xloc, 1);
if (nde == HAWK_NULL) return HAWK_NULL;
if (HAWK_UNLIKELY(!nde)) return HAWK_NULL;
}
chain = (hawk_chain_t*)hawk_callocmem(hawk, HAWK_SIZEOF(*chain));
if (chain == HAWK_NULL)
if (HAWK_UNLIKELY(!chain))
{
hawk_clrpt (hawk, nde);
ADJERR_LOC (hawk, &xloc);
@ -1749,13 +1750,13 @@ static hawk_nde_t* parse_block (hawk_t* hawk, const hawk_loc_t* xloc, int istop)
/* @local ... */
if (get_token(hawk) <= -1)
{
hawk_arr_delete (hawk->parse.lcls, nlcls, HAWK_ARR_SIZE(hawk->parse.lcls)-nlcls);
hawk_arr_delete (hawk->parse.lcls, nlcls, HAWK_ARR_SIZE(hawk->parse.lcls) - nlcls);
return HAWK_NULL;
}
if (collect_locals (hawk, nlcls, istop) == HAWK_NULL)
if (collect_locals(hawk, nlcls, istop) == HAWK_NULL)
{
hawk_arr_delete (hawk->parse.lcls, nlcls, HAWK_ARR_SIZE(hawk->parse.lcls)-nlcls);
hawk_arr_delete (hawk->parse.lcls, nlcls, HAWK_ARR_SIZE(hawk->parse.lcls) - nlcls);
return HAWK_NULL;
}
}
@ -1776,10 +1777,8 @@ static hawk_nde_t* parse_block (hawk_t* hawk, const hawk_loc_t* xloc, int istop)
/* if EOF is met before the right brace, this is an error */
if (MATCH(hawk,TOK_EOF))
{
hawk_arr_delete (
hawk->parse.lcls, nlcls,
HAWK_ARR_SIZE(hawk->parse.lcls) - nlcls);
if (head != HAWK_NULL) hawk_clrpt (hawk, head);
hawk_arr_delete (hawk->parse.lcls, nlcls, HAWK_ARR_SIZE(hawk->parse.lcls) - nlcls);
if (head) hawk_clrpt (hawk, head);
hawk_seterrnum (hawk, &hawk->tok.loc, HAWK_EEOF);
return HAWK_NULL;
}
@ -1789,10 +1788,8 @@ static hawk_nde_t* parse_block (hawk_t* hawk, const hawk_loc_t* xloc, int istop)
{
if (get_token(hawk) <= -1)
{
hawk_arr_delete (
hawk->parse.lcls, nlcls,
HAWK_ARR_SIZE(hawk->parse.lcls)-nlcls);
if (head != HAWK_NULL) hawk_clrpt (hawk, head);
hawk_arr_delete (hawk->parse.lcls, nlcls, HAWK_ARR_SIZE(hawk->parse.lcls)-nlcls);
if (head) hawk_clrpt (hawk, head);
return HAWK_NULL;
}
@ -1827,14 +1824,12 @@ static hawk_nde_t* parse_block (hawk_t* hawk, const hawk_loc_t* xloc, int istop)
{
hawk_loc_t sloc;
sloc = hawk->tok.loc;
nde = parse_statement (hawk, &sloc);
nde = parse_statement(hawk, &sloc);
}
if (HAWK_UNLIKELY(!nde))
{
hawk_arr_delete (
hawk->parse.lcls, nlcls,
HAWK_ARR_SIZE(hawk->parse.lcls)-nlcls);
hawk_arr_delete (hawk->parse.lcls, nlcls, HAWK_ARR_SIZE(hawk->parse.lcls)-nlcls);
if (head) hawk_clrpt (hawk, head);
return HAWK_NULL;
}
@ -1846,8 +1841,7 @@ static hawk_nde_t* parse_block (hawk_t* hawk, const hawk_loc_t* xloc, int istop)
hawk_clrpt (hawk, nde);
continue;
}
if (nde->type == HAWK_NDE_BLK &&
((hawk_nde_blk_t*)nde)->body == HAWK_NULL)
if (nde->type == HAWK_NDE_BLK && ((hawk_nde_blk_t*)nde)->body == HAWK_NULL)
{
hawk_clrpt (hawk, nde);
continue;
@ -1871,7 +1865,7 @@ static hawk_nde_t* parse_block (hawk_t* hawk, const hawk_loc_t* xloc, int istop)
tmp = HAWK_ARR_SIZE(hawk->parse.lcls);
if (tmp > hawk->parse.nlcls_max) hawk->parse.nlcls_max = tmp;
/* remove all lcls to move it up to the top level */
/* remove all lcls to move them up to the top level */
hawk_arr_delete (hawk->parse.lcls, nlcls, tmp - nlcls);
/* adjust the number of lcls for a block without any statements */
@ -1904,6 +1898,7 @@ static hawk_nde_t* parse_block_dc (hawk_t* hawk, const hawk_loc_t* xloc, int ist
{
hawk_nde_t* nde;
/* perform the depth check before calling parse_block() */
if (hawk->opt.depth.s.block_parse > 0 &&
hawk->parse.depth.block >= hawk->opt.depth.s.block_parse)
{
@ -3015,11 +3010,9 @@ static hawk_nde_t* parse_delete (hawk_t* hawk, const hawk_loc_t* xloc)
hawk_nde_type_t type;
int inparen = 0;
HAWK_ASSERT (hawk->ptok.type == TOK_DELETE ||
hawk->ptok.type == TOK_XRESET);
HAWK_ASSERT (hawk->ptok.type == TOK_DELETE || hawk->ptok.type == TOK_XRESET);
type = (hawk->ptok.type == TOK_DELETE)?
HAWK_NDE_DELETE: HAWK_NDE_RESET;
type = (hawk->ptok.type == TOK_DELETE)? HAWK_NDE_DELETE: HAWK_NDE_RESET;
if (MATCH(hawk,TOK_LPAREN))
{
@ -3455,7 +3448,7 @@ static hawk_nde_t* parse_statement (hawk_t* hawk, const hawk_loc_t* xloc)
tloc = hawk->ptok.loc;
if (get_token(hawk) <= -1) return HAWK_NULL;
nde = parse_block_dc (hawk, &tloc, 0);
nde = parse_block_dc(hawk, &tloc, 0);
}
else
{
@ -4532,8 +4525,8 @@ static hawk_nde_t* parse_increment (hawk_t* hawk, const hawk_loc_t* xloc)
}
ploc = hawk->tok.loc;
left = parse_primary (hawk, &ploc);
if (left == HAWK_NULL) return HAWK_NULL;
left = parse_primary(hawk, &ploc);
if (HAWK_UNLIKELY(!left)) return HAWK_NULL;
/* check for postfix increment operator */
opcode2 = MATCH(hawk,TOK_PLUSPLUS)? HAWK_INCOP_PLUS:
@ -5076,6 +5069,31 @@ oops:
return HAWK_NULL;
}
static hawk_nde_t* parse_primary_xnil (hawk_t* hawk, const hawk_loc_t* xloc)
{
hawk_nde_xnil_t* nde;
nde = (hawk_nde_xnil_t*)hawk_callocmem(hawk, HAWK_SIZEOF(*nde));
if (HAWK_UNLIKELY(!nde))
{
ADJERR_LOC (hawk, xloc);
return HAWK_NULL;
}
nde->type = HAWK_NDE_XNIL;
nde->loc = *xloc;
if (get_token(hawk) <= -1) goto oops;
return (hawk_nde_t*)nde;
oops:
HAWK_ASSERT (nde != HAWK_NULL);
hawk_freemem (hawk, nde);
return HAWK_NULL;
}
static hawk_nde_t* parse_primary_nopipe (hawk_t* hawk, const hawk_loc_t* xloc)
{
switch (hawk->tok.type)
@ -5111,6 +5129,10 @@ static hawk_nde_t* parse_primary_nopipe (hawk_t* hawk, const hawk_loc_t* xloc)
case TOK_GETLINE:
return parse_primary_getline(hawk, xloc, 0);
case TOK_XNIL:
return parse_primary_xnil(hawk, xloc);
default:
{
hawk_tok_t* xtok;

View File

@ -162,6 +162,7 @@ static hawk_val_t* eval_flt (hawk_rtx_t* rtx, hawk_nde_t* nde);
static hawk_val_t* eval_str (hawk_rtx_t* rtx, hawk_nde_t* nde);
static hawk_val_t* eval_mbs (hawk_rtx_t* rtx, hawk_nde_t* nde);
static hawk_val_t* eval_rex (hawk_rtx_t* rtx, hawk_nde_t* nde);
static hawk_val_t* eval_xnil (hawk_rtx_t* rtx, hawk_nde_t* nde);
static hawk_val_t* eval_fun (hawk_rtx_t* rtx, hawk_nde_t* nde);
static hawk_val_t* eval_named (hawk_rtx_t* rtx, hawk_nde_t* nde);
static hawk_val_t* eval_gbl (hawk_rtx_t* rtx, hawk_nde_t* nde);
@ -3621,6 +3622,7 @@ static hawk_val_t* eval_expression0 (hawk_rtx_t* rtx, hawk_nde_t* nde)
eval_str,
eval_mbs,
eval_rex,
eval_xnil,
eval_fun,
eval_named,
eval_gbl,
@ -6892,7 +6894,7 @@ static hawk_val_t* eval_int (hawk_rtx_t* rtx, hawk_nde_t* nde)
{
hawk_val_t* val;
val = hawk_rtx_makeintval(rtx, ((hawk_nde_int_t*)nde)->val);
if (val == HAWK_NULL) ADJERR_LOC (rtx, &nde->loc);
if (HAWK_UNLIKELY(!val)) ADJERR_LOC (rtx, &nde->loc);
else if (HAWK_VTR_IS_POINTER(val)) ((hawk_val_int_t*)val)->nde = nde;
return val;
}
@ -6901,7 +6903,7 @@ static hawk_val_t* eval_flt (hawk_rtx_t* rtx, hawk_nde_t* nde)
{
hawk_val_t* val;
val = hawk_rtx_makefltval(rtx, ((hawk_nde_flt_t*)nde)->val);
if (val == HAWK_NULL) ADJERR_LOC (rtx, &nde->loc);
if (HAWK_UNLIKELY(!val)) ADJERR_LOC (rtx, &nde->loc);
else ((hawk_val_flt_t*)val)->nde = nde;
return val;
}
@ -6910,7 +6912,7 @@ static hawk_val_t* eval_str (hawk_rtx_t* rtx, hawk_nde_t* nde)
{
hawk_val_t* val;
val = hawk_rtx_makestrvalwithoochars(rtx, ((hawk_nde_str_t*)nde)->ptr, ((hawk_nde_str_t*)nde)->len);
if (val == HAWK_NULL) ADJERR_LOC (rtx, &nde->loc);
if (HAWK_UNLIKELY(!val)) ADJERR_LOC (rtx, &nde->loc);
return val;
}
@ -6918,7 +6920,7 @@ static hawk_val_t* eval_mbs (hawk_rtx_t* rtx, hawk_nde_t* nde)
{
hawk_val_t* val;
val = hawk_rtx_makembsvalwithbchars(rtx, ((hawk_nde_mbs_t*)nde)->ptr, ((hawk_nde_mbs_t*)nde)->len);
if (val == HAWK_NULL) ADJERR_LOC (rtx, &nde->loc);
if (HAWK_UNLIKELY(!val)) ADJERR_LOC (rtx, &nde->loc);
return val;
}
@ -6926,7 +6928,15 @@ static hawk_val_t* eval_rex (hawk_rtx_t* rtx, hawk_nde_t* nde)
{
hawk_val_t* val;
val = hawk_rtx_makerexval(rtx, &((hawk_nde_rex_t*)nde)->str, ((hawk_nde_rex_t*)nde)->code);
if (val == HAWK_NULL) ADJERR_LOC (rtx, &nde->loc);
if (HAWK_UNLIKELY(!val)) ADJERR_LOC (rtx, &nde->loc);
return val;
}
static hawk_val_t* eval_xnil (hawk_rtx_t* rtx, hawk_nde_t* nde)
{
hawk_val_t* val;
val = hawk_rtx_makenilval(rtx);
if (HAWK_UNLIKELY(!val)) ADJERR_LOC (rtx, &nde->loc);
return val;
}
@ -6958,7 +6968,7 @@ static hawk_val_t* eval_fun (hawk_rtx_t* rtx, hawk_nde_t* nde)
}
val = hawk_rtx_makefunval(rtx, fun);
if (!val) ADJERR_LOC (rtx, &nde->loc);
if (HAWK_UNLIKELY(!val)) ADJERR_LOC (rtx, &nde->loc);
return val;
}

View File

@ -63,6 +63,7 @@ typedef struct hawk_nde_str_t hawk_nde_str_t;
typedef struct hawk_nde_mbs_t hawk_nde_mbs_t;
typedef struct hawk_nde_rex_t hawk_nde_rex_t;
typedef struct hawk_nde_fun_t hawk_nde_fun_t;
typedef struct hawk_nde_xnil_t hawk_nde_xnil_t;
typedef struct hawk_nde_var_t hawk_nde_var_t;
typedef struct hawk_nde_fncall_t hawk_nde_fncall_t;
@ -174,6 +175,11 @@ struct hawk_nde_rex_t
hawk_tre_t* code[2]; /* [0]: case sensitive, [1]: case insensitive */
};
struct hawk_nde_xnil_t
{
HAWK_NDE_HDR;
};
/* HAWK_NDE_FUN - function as a value */
struct hawk_nde_fun_t
{

View File

@ -498,6 +498,12 @@ static int print_expr (hawk_t* hawk, hawk_nde_t* nde)
break;
}
case HAWK_NDE_XNIL:
{
PUT_SRCSTR (hawk, HAWK_T("@nil"));
break;
}
case HAWK_NDE_FUN:
{
PUT_SRCSTRN (hawk,
@ -715,9 +721,7 @@ static int print_expr (hawk_t* hawk, hawk_nde_t* nde)
PUT_SRCSTR (hawk, HAWK_T("("));
if (px->in != HAWK_NULL &&
(px->in_type == HAWK_IN_PIPE ||
px->in_type == HAWK_IN_RWPIPE))
if (px->in && (px->in_type == HAWK_IN_PIPE || px->in_type == HAWK_IN_RWPIPE))
{
PRINT_EXPR (hawk, px->in);
PUT_SRCSTR (hawk, HAWK_T(" "));
@ -727,14 +731,13 @@ static int print_expr (hawk_t* hawk, hawk_nde_t* nde)
hawk_getkwname (hawk, (px->mbs? HAWK_KWID_GETBLINE: HAWK_KWID_GETLINE), &kw);
PUT_SRCSTRN (hawk, kw.ptr, kw.len);
if (px->var != HAWK_NULL)
if (px->var)
{
PUT_SRCSTR (hawk, HAWK_T(" "));
PRINT_EXPR (hawk, px->var);
}
if (px->in != HAWK_NULL &&
px->in_type == HAWK_IN_FILE)
if (px->in && px->in_type == HAWK_IN_FILE)
{
PUT_SRCSTR (hawk, HAWK_T(" "));
PUT_SRCSTR (hawk, getline_inop_str[px->in_type]);
@ -750,7 +753,7 @@ static int print_expr (hawk_t* hawk, hawk_nde_t* nde)
case HAWK_NDE_PRINTF:
{
PUT_SRCSTR (hawk, HAWK_T("("));
if (print_printx (hawk, (hawk_nde_print_t*)nde) <= -1) return -1;
if (print_printx(hawk, (hawk_nde_print_t*)nde) <= -1) return -1;
PUT_SRCSTR (hawk, HAWK_T(")"));
break;
}
@ -1385,6 +1388,12 @@ void hawk_clrpt (hawk_t* hawk, hawk_nde_t* tree)
break;
}
case HAWK_NDE_XNIL:
{
hawk_freemem (hawk, p);
break;
}
case HAWK_NDE_FUN:
{
hawk_freemem (hawk, ((hawk_nde_fun_t*)p)->name.ptr);

View File

@ -244,7 +244,7 @@ function main()
{
@local bool, b, c;
@reset(c);
c = @nil;
bool = ((b = 1) in c);
ensure (bool, 0, @SCRIPTNAME, @SCRIPTLINE);
ensure (b, 1, @SCRIPTNAME, @SCRIPTLINE);