more error information handling touch-up in parse.c

This commit is contained in:
hyung-hwan 2020-01-03 14:16:24 +00:00
parent ec5e61278c
commit dae8b5428d
5 changed files with 60 additions and 46 deletions

View File

@ -74,7 +74,7 @@ const hawk_ooch_t* hawk_dflerrstr (hawk_t* awk, hawk_errnum_t errnum)
HAWK_T("unexpected end of input"), HAWK_T("unexpected end of input"),
HAWK_T("comment not closed properly"), HAWK_T("comment not closed properly"),
HAWK_T("string or regular expression not closed"), HAWK_T("string or regular expression not closed"),
HAWK_T("invalid mbs character '${0}'"), HAWK_T("invalid mbs character"),
HAWK_T("left brace expected in place of '${0}'"), HAWK_T("left brace expected in place of '${0}'"),
HAWK_T("left parenthesis expected in place of '${0}'"), HAWK_T("left parenthesis expected in place of '${0}'"),
HAWK_T("right parenthesis expected in place of '${0}'"), HAWK_T("right parenthesis expected in place of '${0}'"),
@ -92,7 +92,7 @@ const hawk_ooch_t* hawk_dflerrstr (hawk_t* awk, hawk_errnum_t errnum)
HAWK_T("keyword 'while' expected in place of '${0}'"), HAWK_T("keyword 'while' expected in place of '${0}'"),
HAWK_T("invalid assignment statement"), HAWK_T("invalid assignment statement"),
HAWK_T("identifier expected in place of '${0}'"), HAWK_T("identifier expected in place of '${0}'"),
HAWK_T("'${0}' not a valid function name"), HAWK_T("not a valid function name"),
HAWK_T("BEGIN not followed by left bracket on the same line"), HAWK_T("BEGIN not followed by left bracket on the same line"),
HAWK_T("END not followed by left bracket on the same line"), HAWK_T("END not followed by left bracket on the same line"),
HAWK_T("keyword redefined"), HAWK_T("keyword redefined"),
@ -104,10 +104,10 @@ const hawk_ooch_t* hawk_dflerrstr (hawk_t* awk, hawk_errnum_t errnum)
HAWK_T("duplicate parameter name"), HAWK_T("duplicate parameter name"),
HAWK_T("duplicate global variable"), HAWK_T("duplicate global variable"),
HAWK_T("duplicate local variable"), HAWK_T("duplicate local variable"),
HAWK_T("'${0}' not a valid parameter name"), HAWK_T("not a valid parameter name"),
HAWK_T("'${0}' not a valid variable name"), HAWK_T("not a valid variable name"),
HAWK_T("variable name missing"), HAWK_T("variable name missing"),
HAWK_T("undefined identifier '${0}'"), HAWK_T("undefined identifier"),
HAWK_T("l-value required"), HAWK_T("l-value required"),
HAWK_T("too many global variables"), HAWK_T("too many global variables"),
HAWK_T("too many local variables"), HAWK_T("too many local variables"),

View File

@ -804,7 +804,7 @@ enum hawk_errnum_t
HAWK_EEOF, /**< unexpected end of source */ HAWK_EEOF, /**< unexpected end of source */
HAWK_ECMTNC, /**< comment not closed properly */ HAWK_ECMTNC, /**< comment not closed properly */
HAWK_ESTRNC, /**< string or regular expression not closed */ HAWK_ESTRNC, /**< string or regular expression not closed */
HAWK_EMBSCHR, /**< invalid mbs character '%{0}' */ HAWK_EMBSCHR, /**< invalid mbs character */
HAWK_ELBRACE, /**< left brace expected in place of '${0}' */ HAWK_ELBRACE, /**< left brace expected in place of '${0}' */
HAWK_ELPAREN, /**< left parenthesis expected in place of '${0}' */ HAWK_ELPAREN, /**< left parenthesis expected in place of '${0}' */
HAWK_ERPAREN, /**< right parenthesis expected in place of '${0}' */ HAWK_ERPAREN, /**< right parenthesis expected in place of '${0}' */
@ -822,7 +822,7 @@ enum hawk_errnum_t
HAWK_EKWWHL, /**< keyword 'while' expected in place of '${0}' */ HAWK_EKWWHL, /**< keyword 'while' expected in place of '${0}' */
HAWK_EASSIGN, /**< assignment statement expected */ HAWK_EASSIGN, /**< assignment statement expected */
HAWK_EIDENT, /**< identifier expected in place of '${0}' */ HAWK_EIDENT, /**< identifier expected in place of '${0}' */
HAWK_EFUNNAM, /**< '${0}' not a valid function name */ HAWK_EFUNNAM, /**< not a valid function name */
HAWK_EBLKBEG, /**< BEGIN not followed by left bracket on the same line */ HAWK_EBLKBEG, /**< BEGIN not followed by left bracket on the same line */
HAWK_EBLKEND, /**< END not followed by left bracket on the same line */ HAWK_EBLKEND, /**< END not followed by left bracket on the same line */
HAWK_EKWRED, /**< keyword redefined */ HAWK_EKWRED, /**< keyword redefined */
@ -833,11 +833,11 @@ enum hawk_errnum_t
HAWK_EVARRED, /**< variable redefined */ HAWK_EVARRED, /**< variable redefined */
HAWK_EDUPPAR, /**< duplicate parameter name */ HAWK_EDUPPAR, /**< duplicate parameter name */
HAWK_EDUPGBL, /**< duplicate global variable name */ HAWK_EDUPGBL, /**< duplicate global variable name */
HAWK_EDUPLCL, /**< duplicate local variable name' */ HAWK_EDUPLCL, /**< duplicate local variable name */
HAWK_EBADPAR, /**< '${0}' not a valid parameter name */ HAWK_EBADPAR, /**< not a valid parameter name */
HAWK_EBADVAR, /**< '${0}' not a valid variable name */ HAWK_EBADVAR, /**< not a valid variable name */
HAWK_EVARMS, /**< variable name missing */ HAWK_EVARMS, /**< variable name missing */
HAWK_EUNDEF, /**< undefined identifier '${0}' */ HAWK_EUNDEF, /**< undefined identifier */
HAWK_ELVALUE, /**< l-value required */ HAWK_ELVALUE, /**< l-value required */
HAWK_EGBLTM, /**< too many global variables */ HAWK_EGBLTM, /**< too many global variables */
HAWK_ELCLTM, /**< too many local variables */ HAWK_ELCLTM, /**< too many local variables */

View File

@ -553,8 +553,8 @@ static fnctab_t fnctab[] =
/* keep this table sorted for binary search in query(). */ /* keep this table sorted for binary search in query(). */
{ HAWK_T("fromcharcode"), { { 0, A_MAX, HAWK_NULL }, fnc_fromcharcode, 0 } }, { HAWK_T("fromcharcode"), { { 0, A_MAX, HAWK_NULL }, fnc_fromcharcode, 0 } },
{ HAWK_T("frommbs"), { { 1, 2, HAWK_NULL }, fnc_frommbs, 0 } }, { HAWK_T("frommbs"), { { 1, 2, HAWK_NULL }, fnc_frommbs, 0 } },
{ HAWK_T("gsub"), { { 2, 3, HAWK_T("xvr")}, hawk_fnc_gsub, 0 } }, { HAWK_T("gsub"), { { 2, 3, HAWK_T("xvr")}, hawk_fnc_gsub, 0 } },
{ HAWK_T("index"), { { 2, 3, HAWK_NULL }, hawk_fnc_index, 0 } }, { HAWK_T("index"), { { 2, 3, HAWK_NULL }, hawk_fnc_index, 0 } },
{ HAWK_T("isalnum"), { { 1, 1, HAWK_NULL }, fnc_isalnum, 0 } }, { HAWK_T("isalnum"), { { 1, 1, HAWK_NULL }, fnc_isalnum, 0 } },
{ HAWK_T("isalpha"), { { 1, 1, HAWK_NULL }, fnc_isalpha, 0 } }, { HAWK_T("isalpha"), { { 1, 1, HAWK_NULL }, fnc_isalpha, 0 } },
{ HAWK_T("isblank"), { { 1, 1, HAWK_NULL }, fnc_isblank, 0 } }, { HAWK_T("isblank"), { { 1, 1, HAWK_NULL }, fnc_isblank, 0 } },
@ -567,21 +567,21 @@ static fnctab_t fnctab[] =
{ HAWK_T("isspace"), { { 1, 1, HAWK_NULL }, fnc_isspace, 0 } }, { HAWK_T("isspace"), { { 1, 1, HAWK_NULL }, fnc_isspace, 0 } },
{ HAWK_T("isupper"), { { 1, 1, HAWK_NULL }, fnc_isupper, 0 } }, { HAWK_T("isupper"), { { 1, 1, HAWK_NULL }, fnc_isupper, 0 } },
{ HAWK_T("isxdigit"), { { 1, 1, HAWK_NULL }, fnc_isxdigit, 0 } }, { HAWK_T("isxdigit"), { { 1, 1, HAWK_NULL }, fnc_isxdigit, 0 } },
{ HAWK_T("length"), { { 1, 1, HAWK_NULL }, hawk_fnc_length, 0 } }, { HAWK_T("length"), { { 1, 1, HAWK_NULL }, hawk_fnc_length, 0 } },
{ HAWK_T("ltrim"), { { 1, 1, HAWK_NULL }, fnc_ltrim, 0 } }, { HAWK_T("ltrim"), { { 1, 1, HAWK_NULL }, fnc_ltrim, 0 } },
{ HAWK_T("match"), { { 2, 4, HAWK_T("vxvr") }, hawk_fnc_match, 0 } }, { HAWK_T("match"), { { 2, 4, HAWK_T("vxvr") }, hawk_fnc_match, 0 } },
{ HAWK_T("normspace"), { { 1, 1, HAWK_NULL }, fnc_normspace, 0 } }, /* deprecated, use trim("xxx", str::TRIM_PAC_SPACES) */ { HAWK_T("normspace"), { { 1, 1, HAWK_NULL }, fnc_normspace, 0 } }, /* deprecated, use trim("xxx", str::TRIM_PAC_SPACES) */
{ HAWK_T("printf"), { { 1, A_MAX, HAWK_NULL }, hawk_fnc_sprintf, 0 } }, { HAWK_T("printf"), { { 1, A_MAX, HAWK_NULL }, hawk_fnc_sprintf, 0 } },
{ HAWK_T("rindex"), { { 2, 3, HAWK_NULL }, hawk_fnc_rindex, 0 } }, { HAWK_T("rindex"), { { 2, 3, HAWK_NULL }, hawk_fnc_rindex, 0 } },
{ HAWK_T("rtrim"), { { 1, 1, HAWK_NULL }, fnc_rtrim, 0 } }, { HAWK_T("rtrim"), { { 1, 1, HAWK_NULL }, fnc_rtrim, 0 } },
{ HAWK_T("split"), { { 2, 3, HAWK_T("vrx") }, hawk_fnc_split, 0 } }, { HAWK_T("split"), { { 2, 3, HAWK_T("vrx") }, hawk_fnc_split, 0 } },
{ HAWK_T("sub"), { { 2, 3, HAWK_T("xvr") }, hawk_fnc_sub, 0 } }, { HAWK_T("sub"), { { 2, 3, HAWK_T("xvr") }, hawk_fnc_sub, 0 } },
{ HAWK_T("substr"), { { 2, 3, HAWK_NULL }, hawk_fnc_substr, 0 } }, { HAWK_T("substr"), { { 2, 3, HAWK_NULL }, hawk_fnc_substr, 0 } },
{ HAWK_T("tocharcode"), { { 1, 2, HAWK_NULL }, fnc_tocharcode, 0 } }, { HAWK_T("tocharcode"), { { 1, 2, HAWK_NULL }, fnc_tocharcode, 0 } },
{ HAWK_T("tolower"), { { 1, 1, HAWK_NULL }, hawk_fnc_tolower, 0 } }, { HAWK_T("tolower"), { { 1, 1, HAWK_NULL }, hawk_fnc_tolower, 0 } },
{ HAWK_T("tombs"), { { 1, 2, HAWK_NULL }, fnc_tombs, 0 } }, { HAWK_T("tombs"), { { 1, 2, HAWK_NULL }, fnc_tombs, 0 } },
{ HAWK_T("tonum"), { { 1, 2, HAWK_NULL }, fnc_tonum, 0 } }, { HAWK_T("tonum"), { { 1, 2, HAWK_NULL }, fnc_tonum, 0 } },
{ HAWK_T("toupper"), { { 1, 1, HAWK_NULL }, hawk_fnc_toupper, 0 } }, { HAWK_T("toupper"), { { 1, 1, HAWK_NULL }, hawk_fnc_toupper, 0 } },
{ HAWK_T("trim"), { { 1, 2, HAWK_NULL }, fnc_trim, 0 } } { HAWK_T("trim"), { { 1, 2, HAWK_NULL }, fnc_trim, 0 } }
}; };

View File

@ -413,15 +413,6 @@ static global_t gtab[] =
#define SETERR_TOK(awk,code) \ #define SETERR_TOK(awk,code) \
hawk_seterror (awk, code, HAWK_OOECS_OOCS((awk)->tok.name), &(awk)->tok.loc) hawk_seterror (awk, code, HAWK_OOECS_OOCS((awk)->tok.name), &(awk)->tok.loc)
#define SETERR_ARG_LOC(awk,code,ep,el,loc) \
do { \
hawk_oocs_t __ea; \
__ea.len = (el); __ea.ptr = (ep); \
hawk_seterror ((awk), (code), &__ea, (loc)); \
} while (0)
#define SETERR_ARG(awk,code,ep,el) SETERR_ARG_LOC(awk,code,ep,el,HAWK_NULL)
#define ADJERR_LOC(hawk,l) do { (hawk)->_gem.errloc = *(l); } while (0) #define ADJERR_LOC(hawk,l) do { (hawk)->_gem.errloc = *(l); } while (0)
static HAWK_INLINE int is_plain_var (hawk_nde_t* nde) static HAWK_INLINE int is_plain_var (hawk_nde_t* nde)
@ -1225,7 +1216,7 @@ static hawk_nde_t* parse_function (hawk_t* awk)
if (!MATCH(awk,TOK_IDENT)) if (!MATCH(awk,TOK_IDENT))
{ {
/* cannot find a valid identifier for a function name */ /* cannot find a valid identifier for a function name */
SETERR_TOK (awk, HAWK_EFUNNAM); hawk_seterrfmt (awk, &awk->tok.loc, HAWK_EFUNNAM, HAWK_T("'%.*js' not a valid function name"), HAWK_OOECS_LEN(awk->tok.name), HAWK_OOECS_PTR(awk->tok.name));
return HAWK_NULL; return HAWK_NULL;
} }
@ -1303,7 +1294,7 @@ static hawk_nde_t* parse_function (hawk_t* awk)
if (!MATCH(awk,TOK_IDENT)) if (!MATCH(awk,TOK_IDENT))
{ {
SETERR_TOK (awk, HAWK_EBADPAR); hawk_seterrfmt (awk, &awk->tok.loc, HAWK_EBADPAR, HAWK_T("'%.*js' not a valid parameter name"), HAWK_OOECS_LEN(awk->tok.name), HAWK_OOECS_PTR(awk->tok.name));
goto oops; goto oops;
} }
@ -2162,7 +2153,7 @@ static hawk_t* collect_globals (hawk_t* awk)
{ {
if (!MATCH(awk,TOK_IDENT)) if (!MATCH(awk,TOK_IDENT))
{ {
SETERR_TOK (awk, HAWK_EBADVAR); hawk_seterrfmt (awk, &awk->tok.loc, HAWK_EBADVAR, HAWK_T("'%.*js' not a valid variable name"), HAWK_OOECS_LEN(awk->tok.name), HAWK_OOECS_PTR(awk->tok.name));
return HAWK_NULL; return HAWK_NULL;
} }
@ -2217,7 +2208,7 @@ static hawk_t* collect_locals (hawk_t* awk, hawk_oow_t nlcls, int istop)
if (!MATCH(awk,TOK_IDENT)) if (!MATCH(awk,TOK_IDENT))
{ {
SETERR_TOK (awk, HAWK_EBADVAR); hawk_seterrfmt (awk, &awk->tok.loc, HAWK_EBADVAR, HAWK_T("'%.*js' not a valid variable name"), HAWK_OOECS_LEN(awk->tok.name), HAWK_OOECS_PTR(awk->tok.name));
return HAWK_NULL; return HAWK_NULL;
} }
@ -5098,7 +5089,7 @@ static hawk_nde_t* parse_variable (hawk_t* awk, const hawk_loc_t* xloc, hawk_nde
* the value of var_xxx and 1. * the value of var_xxx and 1.
*/ */
/* a variable is not a function */ /* a variable is not a function */
SETERR_ARG_LOC (awk, HAWK_EFUNNAM, name->ptr, name->len, xloc); hawk_seterrfmt (awk, xloc, HAWK_EFUNNAM, HAWK_T("'%.*js' not a valid function name"), name->len, name->ptr);
return HAWK_NULL; return HAWK_NULL;
} }
} }
@ -5376,7 +5367,7 @@ static hawk_nde_t* parse_primary_ident_noseg (hawk_t* awk, const hawk_loc_t* xlo
else else
{ {
/* undefined variable */ /* undefined variable */
SETERR_ARG_LOC (awk, HAWK_EUNDEF, name->ptr, name->len, xloc); hawk_seterrfmt (awk, xloc, HAWK_EUNDEF, HAWK_T("undefined identifier '%.*js'"), name->len, name->ptr);
} }
} }
} }
@ -5405,7 +5396,7 @@ static hawk_nde_t* parse_primary_ident_segs (hawk_t* awk, const hawk_loc_t* xloc
case HAWK_MOD_FNC: case HAWK_MOD_FNC:
if ((awk->opt.trait & sym.u.fnc.trait) != sym.u.fnc.trait) if ((awk->opt.trait & sym.u.fnc.trait) != sym.u.fnc.trait)
{ {
SETERR_ARG_LOC (awk, HAWK_EUNDEF, full->ptr, full->len, xloc); hawk_seterrfmt (awk, xloc, HAWK_EUNDEF, HAWK_T("undefined identifier '%.*js'"), full->len, full->ptr);
break; break;
} }
@ -5436,7 +5427,7 @@ static hawk_nde_t* parse_primary_ident_segs (hawk_t* awk, const hawk_loc_t* xloc
default: default:
/* TODO: support MOD_VAR */ /* TODO: support MOD_VAR */
SETERR_ARG_LOC (awk, HAWK_EUNDEF, full->ptr, full->len, xloc); hawk_seterrfmt (awk, xloc, HAWK_EUNDEF, HAWK_T("undefined identifier '%.*js'"), full->len, full->ptr);
break; break;
} }
} }
@ -5521,7 +5512,7 @@ static hawk_nde_t* parse_hashidx (hawk_t* awk, const hawk_oocs_t* name, const ha
hawk_loc_t eloc; hawk_loc_t eloc;
eloc = awk->tok.loc; eloc = awk->tok.loc;
tmp = parse_expr_withdc (awk, &eloc); tmp = parse_expr_withdc(awk, &eloc);
} }
if (tmp == HAWK_NULL) if (tmp == HAWK_NULL)
{ {
@ -5596,7 +5587,7 @@ static hawk_nde_t* parse_hashidx (hawk_t* awk, const hawk_oocs_t* name, const ha
} }
/* gets the global variable index */ /* gets the global variable index */
idxa = get_global (awk, name); idxa = get_global(awk, name);
if (idxa != HAWK_ARR_NIL) if (idxa != HAWK_ARR_NIL)
{ {
nde->type = HAWK_NDE_GBLIDX; nde->type = HAWK_NDE_GBLIDX;
@ -5638,7 +5629,7 @@ static hawk_nde_t* parse_hashidx (hawk_t* awk, const hawk_oocs_t* name, const ha
} }
/* undefined variable */ /* undefined variable */
SETERR_ARG_LOC (awk, HAWK_EUNDEF, name->ptr, name->len, xloc); hawk_seterrfmt (awk, xloc, HAWK_EUNDEF, HAWK_T("undefined identifier '%.*js'"), name->len, name->ptr);
exit_func: exit_func:
hawk_clrpt (awk, idx); hawk_clrpt (awk, idx);
@ -5899,8 +5890,7 @@ static int get_string (
#else #else
if (byte_only && c != HAWK_T('\\') && !HAWK_BYTE_PRINTABLE(c)) if (byte_only && c != HAWK_T('\\') && !HAWK_BYTE_PRINTABLE(c))
{ {
hawk_ooch_t wc = c; hawk_seterrfmt (awk, &awk->tok.loc, HAWK_EMBSCHR, HAWK_T("invalid mbs character '%jc'"), (hawk_ooch_t)c);
SETERR_ARG_LOC (awk, HAWK_EMBSCHR, &wc, 1, &awk->tok.loc);
return -1; return -1;
} }
#endif #endif
@ -6115,8 +6105,7 @@ static int get_single_quoted_string (hawk_t* awk, int byte_only, hawk_tok_t* tok
#else #else
if (byte_only && c != HAWK_T('\\') && !HAWK_BYTE_PRINTABLE(c)) if (byte_only && c != HAWK_T('\\') && !HAWK_BYTE_PRINTABLE(c))
{ {
hawk_ooch_t wc = c; hawk_seterrfmt (awk, &awk->tok.loc, HAWK_EMBSCHR, HAWK_T("invalid mbs character '%jc'"), (hawk_ooch_t)c);
SETERR_ARG_LOC (awk, HAWK_EMBSCHR, &wc, 1, &awk->tok.loc);
return -1; return -1;
} }
#endif #endif

View File

@ -128,3 +128,28 @@ $ ~/xxx/bin/hawk 'function test(ax, bx) { @local ARGC; }'
ERROR: CODE 65 LINE 1 COLUMN 32 - duplicate local variable name - ARGC ERROR: CODE 65 LINE 1 COLUMN 32 - duplicate local variable name - ARGC
$ ~/xxx/bin/hawk '@global 10; '
HAWK_EBADVAR -> ERROR: CODE 67 LINE 1 COLUMN 9 - '10' not a valid variable name
$ ~/xxx/bin/hawk '{ @local 10; }'
HAWK_EBADVAR -> ERROR: CODE 67 LINE 1 COLUMN 10 - '10' not a valid variable name
$ ~/xxx/bin/hawk 'function test(10) {} '
HAWK_EBADPAR -> ERROR: CODE 66 LINE 1 COLUMN 15 - '10' not a valid parameter name
$ ~/xxx/bin/hawk 'BEGIN { print B"abc^Bdef"; }'
HAWK_EMBSCHR -> ERROR: CODE 37 LINE 1 COLUMN 15 - invalid mbs character ''
$ ~/xxx/bin/hawk "BEGIN { print B'abf^Bdef'; }"
HAWK_EMBSCHR -> ERROR: CODE 37 LINE 1 COLUMN 16 - invalid mbs character ''
$ ~/xxx/bin/hawk --implicit=off 'BEGIN { print kcx[10]; }'
HAWK_EUNDEF -> ERROR: CODE 69 LINE 1 COLUMN 16 - undefined identifier 'kcx'
$ ~/xxx/bin/hawk --implicit=off 'BEGIN { print ax; }'
ERROR: CODE 69 LINE 1 COLUMN 16 - undefined identifier 'ax'
$ ~/xxx/bin/hawk 'function 1.2(a) {}'
ERROR: CODE 54 LINE 1 COLUMN 10 - '1.2' not a valid function name