diff --git a/qse/include/qse/cmn/str.h b/qse/include/qse/cmn/str.h index 41a6eef4..094a9ce5 100644 --- a/qse/include/qse/cmn/str.h +++ b/qse/include/qse/cmn/str.h @@ -1,5 +1,5 @@ /* - * $Id: str.h 464 2011-05-19 03:33:28Z hyunghwan.chung $ + * $Id: str.h 497 2011-06-20 14:56:40Z hyunghwan.chung $ * Copyright 2006-2011 Chung, Hyung-Hwan. This file is part of QSE. @@ -2166,9 +2166,14 @@ void qse_mbs_fini ( * @return 0 on success, and -1 on failure. */ int qse_mbs_yield ( - qse_mbs_t* str, /**< string */ - qse_mxstr_t* buf, /**< buffer pointer */ - qse_size_t new_capa /**< new capacity */ + qse_mbs_t* str, /**< string */ + qse_mxstr_t* buf, /**< buffer pointer */ + qse_size_t newcapa /**< new capacity */ +); + +qse_mchar_t* qse_mbs_yieldptr ( + qse_mbs_t* str, /**< string */ + qse_size_t newcapa /**< new capacity */ ); /** @@ -2335,6 +2340,11 @@ int qse_wcs_yield ( qse_size_t new_capa /**< new capacity */ ); +qse_wchar_t* qse_wcs_yieldptr ( + qse_wcs_t* str, /**< string */ + qse_size_t newcapa /**< new capacity */ +); + /** * The qse_wcs_getsizer() function gets the sizer. * @return sizer function set or QSE_NULL if no sizer is set. @@ -2465,6 +2475,7 @@ qse_size_t qse_wcs_pac ( # define qse_str_init(str,mmgr,capa) qse_mbs_init(str,mmgr,capa) # define qse_str_fini(str) qse_mbs_fini(str) # define qse_str_yield(str,buf,ncapa) qse_mbs_yield(str,buf,ncapa) +# define qse_str_yieldptr(str,ncapa) qse_mbs_yieldptr(str,ncapa) # define qse_str_getsizer(str) qse_mbs_getsizer(str) # define qse_str_setsizer(str,sizer) qse_mbs_setsizer(str,sizer) # define qse_str_getcapa(str) qse_mbs_getcapa(str) @@ -2490,6 +2501,7 @@ qse_size_t qse_wcs_pac ( # define qse_str_init(str,mmgr,capa) qse_wcs_init(str,mmgr,capa) # define qse_str_fini(str) qse_wcs_fini(str) # define qse_str_yield(str,buf,ncapa) qse_wcs_yield(str,buf,ncapa) +# define qse_str_yieldptr(str,ncapa) qse_wcs_yieldptr(str,ncapa) # define qse_str_getsizer(str) qse_wcs_getsizer(str) # define qse_str_setsizer(str,sizer) qse_wcs_setsizer(str,sizer) # define qse_str_getcapa(str) qse_wcs_getcapa(str) diff --git a/qse/lib/cmn/str_dynm.c b/qse/lib/cmn/str_dynm.c index 36d6bca3..7f56ea17 100644 --- a/qse/lib/cmn/str_dynm.c +++ b/qse/lib/cmn/str_dynm.c @@ -1,5 +1,5 @@ /* - * $Id: str_dynm.c 462 2011-05-18 14:36:40Z hyunghwan.chung $ + * $Id: str_dynm.c 497 2011-06-20 14:56:40Z hyunghwan.chung $ * Copyright 2006-2011 Chung, Hyung-Hwan. This file is part of QSE. @@ -84,15 +84,15 @@ void qse_mbs_fini (qse_mbs_t* str) if (str->val.ptr != QSE_NULL) QSE_MMGR_FREE (str->mmgr, str->val.ptr); } -int qse_mbs_yield (qse_mbs_t* str, qse_mxstr_t* buf, qse_size_t new_capa) +int qse_mbs_yield (qse_mbs_t* str, qse_mxstr_t* buf, qse_size_t newcapa) { qse_mchar_t* tmp; - if (new_capa == 0) tmp = QSE_NULL; + if (newcapa == 0) tmp = QSE_NULL; else { tmp = (qse_mchar_t*) QSE_MMGR_ALLOC ( - str->mmgr, QSE_SIZEOF(qse_mchar_t) * (new_capa + 1)); + str->mmgr, QSE_SIZEOF(qse_mchar_t) * (newcapa + 1)); if (tmp == QSE_NULL) return -1; tmp[0] = QSE_MT('\0'); } @@ -105,11 +105,18 @@ int qse_mbs_yield (qse_mbs_t* str, qse_mxstr_t* buf, qse_size_t new_capa) str->val.ptr = tmp; str->val.len = 0; - str->capa = new_capa; + str->capa = newcapa; return 0; } +qse_mchar_t* qse_mbs_yieldptr (qse_mbs_t* str, qse_size_t newcapa) +{ + qse_mxstr_t mx; + if (qse_mbs_yield (str, &mx, newcapa) <= -1) return QSE_NULL; + return mx.ptr; +} + qse_mbs_sizer_t qse_mbs_getsizer (qse_mbs_t* str) { return str->sizer; diff --git a/qse/lib/cmn/str_dynw.c b/qse/lib/cmn/str_dynw.c index 17b97228..74052954 100644 --- a/qse/lib/cmn/str_dynw.c +++ b/qse/lib/cmn/str_dynw.c @@ -1,5 +1,5 @@ /* - * $Id: str_dynw.c 462 2011-05-18 14:36:40Z hyunghwan.chung $ + * $Id: str_dynw.c 497 2011-06-20 14:56:40Z hyunghwan.chung $ * Copyright 2006-2011 Chung, Hyung-Hwan. This file is part of QSE. @@ -84,15 +84,15 @@ void qse_wcs_fini (qse_wcs_t* str) if (str->val.ptr != QSE_NULL) QSE_MMGR_FREE (str->mmgr, str->val.ptr); } -int qse_wcs_yield (qse_wcs_t* str, qse_wxstr_t* buf, qse_size_t new_capa) +int qse_wcs_yield (qse_wcs_t* str, qse_wxstr_t* buf, qse_size_t newcapa) { qse_wchar_t* tmp; - if (new_capa == 0) tmp = QSE_NULL; + if (newcapa == 0) tmp = QSE_NULL; else { tmp = (qse_wchar_t*) QSE_MMGR_ALLOC ( - str->mmgr, QSE_SIZEOF(qse_wchar_t) * (new_capa + 1)); + str->mmgr, QSE_SIZEOF(qse_wchar_t) * (newcapa + 1)); if (tmp == QSE_NULL) return -1; tmp[0] = QSE_WT('\0'); } @@ -105,11 +105,18 @@ int qse_wcs_yield (qse_wcs_t* str, qse_wxstr_t* buf, qse_size_t new_capa) str->val.ptr = tmp; str->val.len = 0; - str->capa = new_capa; + str->capa = newcapa; return 0; } +qse_wchar_t* qse_wcs_yieldptr (qse_wcs_t* str, qse_size_t newcapa) +{ + qse_wxstr_t wx; + if (qse_wcs_yield (str, &wx, newcapa) <= -1) return QSE_NULL; + return wx.ptr; +} + qse_wcs_sizer_t qse_wcs_getsizer (qse_wcs_t* str) { return str->sizer; diff --git a/qse/lib/stx/par.c b/qse/lib/stx/par.c index 9c0042b5..08d9a884 100644 --- a/qse/lib/stx/par.c +++ b/qse/lib/stx/par.c @@ -2,131 +2,181 @@ * $Id$ */ -#include "stx.h" +#include "par.h" +#include "../cmn/mem.h" + +enum +{ + TOKEN_END, + TOKEN_CHARLIT, + TOKEN_STRLIT, + TOKEN_SYMLIT, + TOKEN_NUMLIT, + TOKEN_IDENT, + TOKEN_BINARY, + TOKEN_KEYWORD, + TOKEN_PRIMITIVE, + TOKEN_ASSIGN, + TOKEN_COLON, + TOKEN_RETURN, + TOKEN_LBRACKET, + TOKEN_RBRACKET, + TOKEN_LPAREN, + TOKEN_RPAREN, + TOKEN_APAREN, + TOKEN_PERIOD, + TOKEN_SEMICOLON +}; static int __parse_method ( - qse_stx_parser_t* parser, + qse_stc_t* stc, qse_word_t method_class, void* input); -static int __finish_method (qse_stx_parser_t* parser); +static int __finish_method (qse_stc_t* stc); -static int __parse_message_pattern (qse_stx_parser_t* parser); -static int __parse_unary_pattern (qse_stx_parser_t* parser); -static int __parse_binary_pattern (qse_stx_parser_t* parser); -static int __parse_keyword_pattern (qse_stx_parser_t* parser); +static int __parse_message_pattern (qse_stc_t* stc); +static int __parse_unary_pattern (qse_stc_t* stc); +static int __parse_binary_pattern (qse_stc_t* stc); +static int __parse_keyword_pattern (qse_stc_t* stc); -static int __parse_temporaries (qse_stx_parser_t* parser); -static int __parse_primitive (qse_stx_parser_t* parser); -static int __parse_statements (qse_stx_parser_t* parser); -static int __parse_block_statements (qse_stx_parser_t* parser); -static int __parse_statement (qse_stx_parser_t* parser); -static int __parse_expression (qse_stx_parser_t* parser); +static int __parse_temporaries (qse_stc_t* stc); +static int __parse_primitive (qse_stc_t* stc); +static int __parse_statements (qse_stc_t* stc); +static int __parse_block_statements (qse_stc_t* stc); +static int __parse_statement (qse_stc_t* stc); +static int __parse_expression (qse_stc_t* stc); static int __parse_assignment ( - qse_stx_parser_t* parser, const qse_char_t* target); + qse_stc_t* stc, const qse_char_t* target); static int __parse_basic_expression ( - qse_stx_parser_t* parser, const qse_char_t* ident); + qse_stc_t* stc, const qse_char_t* ident); static int __parse_primary ( - qse_stx_parser_t* parser, const qse_char_t* ident, qse_bool_t* is_super); + qse_stc_t* stc, const qse_char_t* ident, qse_bool_t* is_super); static int __parse_primary_ident ( - qse_stx_parser_t* parser, const qse_char_t* ident, qse_bool_t* is_super); + qse_stc_t* stc, const qse_char_t* ident, qse_bool_t* is_super); -static int __parse_block_constructor (qse_stx_parser_t* parser); +static int __parse_block_constructor (qse_stc_t* stc); static int __parse_message_continuation ( - qse_stx_parser_t* parser, qse_bool_t is_super); + qse_stc_t* stc, qse_bool_t is_super); static int __parse_keyword_message ( - qse_stx_parser_t* parser, qse_bool_t is_super); + qse_stc_t* stc, qse_bool_t is_super); static int __parse_binary_message ( - qse_stx_parser_t* parser, qse_bool_t is_super); + qse_stc_t* stc, qse_bool_t is_super); static int __parse_unary_message ( - qse_stx_parser_t* parser, qse_bool_t is_super); + qse_stc_t* stc, qse_bool_t is_super); -static int __get_token (qse_stx_parser_t* parser); -static int __get_ident (qse_stx_parser_t* parser); -static int __get_numlit (qse_stx_parser_t* parser, qse_bool_t negated); -static int __get_charlit (qse_stx_parser_t* parser); -static int __get_strlit (qse_stx_parser_t* parser); -static int __get_binary (qse_stx_parser_t* parser); -static int __skip_spaces (qse_stx_parser_t* parser); -static int __skip_comment (qse_stx_parser_t* parser); -static int __get_char (qse_stx_parser_t* parser); -static int __unget_char (qse_stx_parser_t* parser, qse_cint_t c); -static int __open_input (qse_stx_parser_t* parser, void* input); -static int __close_input (qse_stx_parser_t* parser); +static int __get_token (qse_stc_t* stc); +static int __get_ident (qse_stc_t* stc); +static int __get_numlit (qse_stc_t* stc, qse_bool_t negated); +static int __get_charlit (qse_stc_t* stc); +static int __get_strlit (qse_stc_t* stc); +static int __get_binary (qse_stc_t* stc); +static int __skip_spaces (qse_stc_t* stc); +static int __skip_comment (qse_stc_t* stc); +static int __get_char (qse_stc_t* stc); +static int __unget_char (qse_stc_t* stc, qse_cint_t c); +static int __open_input (qse_stc_t* stc, void* input); +static int __close_input (qse_stc_t* stc); -qse_stx_parser_t* qse_stx_parser_open (qse_stx_parser_t* parser, qse_stx_t* stx) +qse_stc_t* qse_stc_open (qse_mmgr_t* mmgr, qse_size_t xtnsize, qse_stx_t* stx) { - if (parser == QSE_NULL) { - parser = (qse_stx_parser_t*) - qse_malloc (qse_sizeof(qse_stx_parser_t)); - if (parser == QSE_NULL) return QSE_NULL; - parser->__dynamic = qse_true; - } - else parser->__dynamic = qse_false; + qse_stc_t* stc; - if (qse_stx_name_open (&parser->method_name, 0) == QSE_NULL) { - if (parser->__dynamic) qse_free (parser); + stc = (qse_stc_t*) QSE_MMGR_ALLOC (mmgr, QSE_SIZEOF(*stc) + xtnsize); + if (stc == QSE_NULL) return QSE_NULL; + + if (qse_stc_init (stc, mmgr, stx) == QSE_NULL) + { + QSE_MMGR_FREE (mmgr, stc); return QSE_NULL; } - if (qse_stx_token_open (&parser->token, 0) == QSE_NULL) { - qse_stx_name_close (&parser->method_name); - if (parser->__dynamic) qse_free (parser); - return QSE_NULL; - } - - if (qse_arr_open ( - &parser->bytecode, 256, - qse_sizeof(qse_byte_t), QSE_NULL) == QSE_NULL) { - qse_stx_name_close (&parser->method_name); - qse_stx_token_close (&parser->token); - if (parser->__dynamic) qse_free (parser); - return QSE_NULL; - } - - parser->stx = stx; - parser->error_code = QSE_STX_PARSER_ERROR_NONE; - - parser->temporary_count = 0; - parser->argument_count = 0; - parser->literal_count = 0; - - parser->curc = QSE_T_EOF; - parser->ungotc_count = 0; - - parser->input_owner = QSE_NULL; - parser->input_func = QSE_NULL; - return parser; + return stc; } -void qse_stx_parser_close (qse_stx_parser_t* parser) +void qse_stc_close (qse_stc_t* stc) { - while (parser->temporary_count > 0) { - qse_free (parser->temporaries[--parser->temporary_count]); - } - parser->argument_count = 0; - - qse_arr_close (&parser->bytecode); - qse_stx_name_close (&parser->method_name); - qse_stx_token_close (&parser->token); - - if (parser->__dynamic) qse_free (parser); + qse_stc_fini (stc); + QSE_MMGR_FREE (stc->mmgr, stc); } -#define GET_CHAR(parser) \ - do { if (__get_char(parser) == -1) return -1; } while (0) -#define UNGET_CHAR(parser,c) \ - do { if (__unget_char(parser,c) == -1) return -1; } while (0) -#define GET_TOKEN(parser) \ - do { if (__get_token(parser) == -1) return -1; } while (0) -#define ADD_TOKEN_CHAR(parser,c) \ +qse_stc_t* qse_stc_init (qse_stc_t* stc, qse_mmgr_t* mmgr, qse_stx_t* stx) +{ + QSE_MEMSET (stc, 0, QSE_SIZEOF(*stc)); + stc->mmgr = mmgr; + stc->stx = stx; + + if (qse_str_init (&stc->method_name, mmgr, 0) == QSE_NULL) + { + return QSE_NULL; + } + + if (qse_str_init (&stc->token.name, mmgr, 0) == QSE_NULL) + { + qse_str_fini (&stc->method_name); + return QSE_NULL; + } + stc->token.type = TOKEN_END; + + if (qse_lda_init ( + &stc->bytecode, mmgr, 256, + QSE_SIZEOF(qse_byte_t), QSE_NULL) == QSE_NULL) + { + qse_str_fini (&stc->method_name); + qse_str_fini (&stc->token.name); + return QSE_NULL; + } + + stc->stx = stx; + stc->error_code = QSE_STC_ERROR_NONE; + + stc->temporary_count = 0; + stc->argument_count = 0; + stc->literal_count = 0; + + stc->curc = QSE_CHAR_EOF; + stc->ungotc_count = 0; + + stc->input_owner = QSE_NULL; + stc->input_func = QSE_NULL; + return stc; +} + +void qse_stc_fini (qse_stc_t* stc) +{ + while (stc->temporary_count > 0) + QSE_MMGR_FREE (stc->mmgr, stc->temporaries[--stc->temporary_count]); + stc->argument_count = 0; + + qse_lda_fini (&stc->bytecode); + qse_str_fini (&stc->token.name); + qse_str_fini (&stc->method_name); +} + +#define GET_CHAR(stc) \ + do { if (__get_char(stc) == -1) return -1; } while (0) +#define UNGET_CHAR(stc,c) \ + do { if (__unget_char(stc,c) == -1) return -1; } while (0) +#define GET_TOKEN(stc) \ + do { if (__get_token(stc) == -1) return -1; } while (0) + +#define ADD_TOKEN_CHAR(stc,c) \ do { \ - if (qse_stx_token_addc (&(parser)->token, c) == -1) { \ - (parser)->error_code = QSE_STX_PARSER_ERROR_MEMORY; \ + if (qse_str_ccat (&(stc)->token.name, c) == -1) { \ + (stc)->error_code = QSE_STC_ERROR_MEMORY; \ return -1; \ } \ } while (0) + +#define CLEAR_TOKEN(stc) QSE_BLOCK ( \ + qse_str_clear (&(stc)->token.name); \ + stc->token.type = TOKEN_END; \ +) + +#define YIELD_TOKEN_TO(stc,var) QSE_BLOCK ( \ + var = qse_str_yieldptr (&(stc)->token.name, 0); \ +) -const qse_char_t* qse_stx_parser_error_string (qse_stx_parser_t* parser) +const qse_char_t* qse_stc_error_string (qse_stc_t* stc) { static const qse_char_t* msg[] = { @@ -165,47 +215,48 @@ const qse_char_t* qse_stx_parser_error_string (qse_stx_parser_t* parser) QSE_T("too many literals") }; - if (parser->error_code >= 0 && - parser->error_code < qse_countof(msg)) return msg[parser->error_code]; + if (stc->error_code >= 0 && + stc->error_code < QSE_COUNTOF(msg)) return msg[stc->error_code]; return QSE_T("unknown error"); } -static INLINE qse_bool_t __is_pseudo_variable (const qse_stx_token_t* token) -{ - return token->type == QSE_STX_TOKEN_IDENT && - (qse_strcmp(token->name.buffer, QSE_T("self")) == 0 || - qse_strcmp(token->name.buffer, QSE_T("super")) == 0 || - qse_strcmp(token->name.buffer, QSE_T("nil")) == 0 || - qse_strcmp(token->name.buffer, QSE_T("true")) == 0 || - qse_strcmp(token->name.buffer, QSE_T("false")) == 0); -} - -static INLINE qse_bool_t __is_vbar_token (const qse_stx_token_t* token) +static QSE_INLINE int __is_token_pseudo_variable (qse_stc_t* stc) { return - token->type == QSE_STX_TOKEN_BINARY && - token->name.size == 1 && - token->name.buffer[0] == QSE_T('|'); + stc->token.type == TOKEN_IDENT && + (qse_strcmp(QSE_STR_PTR(&stc->token.name), QSE_T("self")) == 0 || + qse_strcmp(QSE_STR_PTR(&stc->token.name), QSE_T("super")) == 0 || + qse_strcmp(QSE_STR_PTR(&stc->token.name), QSE_T("nil")) == 0 || + qse_strcmp(QSE_STR_PTR(&stc->token.name), QSE_T("true")) == 0 || + qse_strcmp(QSE_STR_PTR(&stc->token.name), QSE_T("false")) == 0); } -static INLINE qse_bool_t __is_primitive_opener (const qse_stx_token_t* token) +static QSE_INLINE int __is_token_vertical_bar (qse_stc_t* stc) { return - token->type == QSE_STX_TOKEN_BINARY && - token->name.size == 1 && - token->name.buffer[0] == QSE_T('<'); + stc->token.type == TOKEN_BINARY && + QSE_STR_LEN(&stc->token.name) == 1 && + QSE_STR_CHAR(&stc->token.name,0) == QSE_T('|'); } -static INLINE qse_bool_t __is_primitive_closer (const qse_stx_token_t* token) +static QSE_INLINE int __is_token_primitive_opener (qse_stc_t* stc) { - return - token->type == QSE_STX_TOKEN_BINARY && - token->name.size == 1 && - token->name.buffer[0] == QSE_T('>'); + return + stc->token.type == TOKEN_BINARY && + QSE_STR_LEN(&stc->token.name) == 1 && + QSE_STR_CHAR(&stc->token.name,0) == QSE_T('<'); } -static INLINE qse_bool_t __is_binary_char (qse_cint_t c) +static QSE_INLINE int __is_token_primitive_closer (qse_stc_t* stc) +{ + return + stc->token.type == TOKEN_BINARY && + QSE_STR_LEN(&stc->token.name) == 1 && + QSE_STR_CHAR(&stc->token.name,0) == QSE_T('>'); +} + +static QSE_INLINE qse_bool_t __is_binary_char (qse_cint_t c) { /* * binaryCharacter ::= @@ -225,7 +276,7 @@ static INLINE qse_bool_t __is_binary_char (qse_cint_t c) c == QSE_T('~') || c == QSE_T('-'); } -static INLINE qse_bool_t __is_closing_char (qse_cint_t c) +static QSE_INLINE qse_bool_t __is_closing_char (qse_cint_t c) { return c == QSE_T('.') || c == QSE_T(']') || @@ -233,276 +284,277 @@ static INLINE qse_bool_t __is_closing_char (qse_cint_t c) c == QSE_T('\"') || c == QSE_T('\''); } -#define EMIT_CODE_TEST(parser,high,low) \ - do { if (__emit_code_test(parser,high,low) == -1) return -1; } while (0) +#define EMIT_CODE_TEST(stc,high,low) \ + do { if (__emit_code_test(stc,high,low) == -1) return -1; } while (0) -#define EMIT_CODE(parser,code) \ - do { if (__emit_code(parser,code) == -1) return -1; } while(0) +#define EMIT_CODE(stc,code) \ + do { if (__emit_code(stc,code) == -1) return -1; } while(0) -#define EMIT_PUSH_RECEIVER_VARIABLE(parser,pos) \ +#define EMIT_PUSH_RECEIVER_VARIABLE(stc,pos) \ do { \ if (__emit_stack_positional ( \ - parser, PUSH_RECEIVER_VARIABLE, pos) == -1) return -1; \ + stc, PUSH_RECEIVER_VARIABLE, pos) == -1) return -1; \ } while (0) -#define EMIT_PUSH_TEMPORARY_LOCATION(parser,pos) \ +#define EMIT_PUSH_TEMPORARY_LOCATION(stc,pos) \ do { \ if (__emit_stack_positional ( \ - parser, PUSH_TEMPORARY_LOCATION, pos) == -1) return -1; \ + stc, PUSH_TEMPORARY_LOCATION, pos) == -1) return -1; \ } while (0) -#define EMIT_PUSH_LITERAL_CONSTANT(parser,pos) \ +#define EMIT_PUSH_LITERAL_CONSTANT(stc,pos) \ do { \ if (__emit_stack_positional ( \ - parser, PUSH_LITERAL_CONSTANT, pos) == -1) return -1; \ + stc, PUSH_LITERAL_CONSTANT, pos) == -1) return -1; \ } while (0) -#define EMIT_PUSH_LITERAL_VARIABLE(parser,pos) \ +#define EMIT_PUSH_LITERAL_VARIABLE(stc,pos) \ do { \ if (__emit_stack_positional ( \ - parser, PUSH_LITERAL_VARIABLE, pos) == -1) return -1; \ + stc, PUSH_LITERAL_VARIABLE, pos) == -1) return -1; \ } while (0) -#define EMIT_STORE_RECEIVER_VARIABLE(parser,pos) \ +#define EMIT_STORE_RECEIVER_VARIABLE(stc,pos) \ do { \ if (__emit_stack_positional ( \ - parser, STORE_RECEIVER_VARIABLE, pos) == -1) return -1; \ + stc, STORE_RECEIVER_VARIABLE, pos) == -1) return -1; \ } while (0) -#define EMIT_STORE_TEMPORARY_LOCATION(parser,pos) \ +#define EMIT_STORE_TEMPORARY_LOCATION(stc,pos) \ do { \ if (__emit_stack_positional ( \ - parser, STORE_TEMPORARY_LOCATION, pos) == -1) return -1; \ + stc, STORE_TEMPORARY_LOCATION, pos) == -1) return -1; \ } while (0) -#define EMIT_POP_STACK_TOP(parser) EMIT_CODE(parser, POP_STACK_TOP) -#define EMIT_DUPLICATE_STACK_TOP(parser) EMIT_CODE(parser, DUPLICATE_STACK_TOP) -#define EMIT_PUSH_ACTIVE_CONTEXT(parser) EMIT_CODE(parser, PUSH_ACTIVE_CONTEXT) -#define EMIT_RETURN_FROM_MESSAGE(parser) EMIT_CODE(parser, RETURN_FROM_MESSAGE) -#define EMIT_RETURN_FROM_BLOCK(parser) EMIT_CODE(parser, RETURN_FROM_BLOCK) +#define EMIT_POP_STACK_TOP(stc) EMIT_CODE(stc, POP_STACK_TOP) +#define EMIT_DUPLICATE_STACK_TOP(stc) EMIT_CODE(stc, DUPLICATE_STACK_TOP) +#define EMIT_PUSH_ACTIVE_CONTEXT(stc) EMIT_CODE(stc, PUSH_ACTIVE_CONTEXT) +#define EMIT_RETURN_FROM_MESSAGE(stc) EMIT_CODE(stc, RETURN_FROM_MESSAGE) +#define EMIT_RETURN_FROM_BLOCK(stc) EMIT_CODE(stc, RETURN_FROM_BLOCK) -#define EMIT_SEND_TO_SELF(parser,nargs,selector) \ +#define EMIT_SEND_TO_SELF(stc,nargs,selector) \ do { \ - if (__emit_send_to_self(parser,nargs,selector) == -1) return -1; \ + if (__emit_send_to_self(stc,nargs,selector) == -1) return -1; \ } while (0) -#define EMIT_SEND_TO_SUPER(parser,nargs,selector) \ +#define EMIT_SEND_TO_SUPER(stc,nargs,selector) \ do { \ - if (__emit_send_to_super(parser,nargs,selector) == -1) return -1; \ + if (__emit_send_to_super(stc,nargs,selector) == -1) return -1; \ } while (0) -#define EMIT_DO_PRIMITIVE(parser,no) \ - do { if (__emit_do_primitive(parser,no) == -1) return -1; } while(0) +#define EMIT_DO_PRIMITIVE(stc,no) \ + do { if (__emit_do_primitive(stc,no) == -1) return -1; } while(0) -static INLINE int __emit_code_test ( - qse_stx_parser_t* parser, const qse_char_t* high, const qse_char_t* low) +static QSE_INLINE int __emit_code_test ( + qse_stc_t* stc, const qse_char_t* high, const qse_char_t* low) { qse_printf (QSE_T("CODE: %s %s\n"), high, low); return 0; } -static INLINE int __emit_code (qse_stx_parser_t* parser, qse_byte_t code) +static QSE_INLINE int __emit_code (qse_stc_t* stc, qse_byte_t code) { - if (qse_arr_adddatum(&parser->bytecode, &code) == QSE_NULL) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + if (qse_lda_adddatum(&stc->bytecode, &code) == QSE_NULL) { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } return 0; } -static INLINE int __emit_stack_positional ( - qse_stx_parser_t* parser, int opcode, int pos) +static QSE_INLINE int __emit_stack_positional ( + qse_stc_t* stc, int opcode, int pos) { qse_assert (pos >= 0x0 && pos <= 0xFF); if (pos <= 0x0F) { - EMIT_CODE (parser, (opcode & 0xF0) | (pos & 0x0F)); + EMIT_CODE (stc, (opcode & 0xF0) | (pos & 0x0F)); } else { - EMIT_CODE (parser, (opcode >> 4) & 0x6F); - EMIT_CODE (parser, pos & 0xFF); + EMIT_CODE (stc, (opcode >> 4) & 0x6F); + EMIT_CODE (stc, pos & 0xFF); } return 0; } -static INLINE int __emit_send_to_self ( - qse_stx_parser_t* parser, int nargs, int selector) +static QSE_INLINE int __emit_send_to_self ( + qse_stc_t* stc, int nargs, int selector) { qse_assert (nargs >= 0x00 && nargs <= 0xFF); qse_assert (selector >= 0x00 && selector <= 0xFF); if (nargs <= 0x08 && selector <= 0x1F) { - EMIT_CODE (parser, SEND_TO_SELF); - EMIT_CODE (parser, (nargs << 5) | selector); + EMIT_CODE (stc, SEND_TO_SELF); + EMIT_CODE (stc, (nargs << 5) | selector); } else { - EMIT_CODE (parser, SEND_TO_SELF_EXTENDED); - EMIT_CODE (parser, nargs); - EMIT_CODE (parser, selector); + EMIT_CODE (stc, SEND_TO_SELF_EXTENDED); + EMIT_CODE (stc, nargs); + EMIT_CODE (stc, selector); } return 0; } -static INLINE int __emit_send_to_super ( - qse_stx_parser_t* parser, int nargs, int selector) +static QSE_INLINE int __emit_send_to_super ( + qse_stc_t* stc, int nargs, int selector) { qse_assert (nargs >= 0x00 && nargs <= 0xFF); qse_assert (selector >= 0x00 && selector <= 0xFF); if (nargs <= 0x08 && selector <= 0x1F) { - EMIT_CODE (parser, SEND_TO_SUPER); - EMIT_CODE (parser, (nargs << 5) | selector); + EMIT_CODE (stc, SEND_TO_SUPER); + EMIT_CODE (stc, (nargs << 5) | selector); } else { - EMIT_CODE (parser, SEND_TO_SUPER_EXTENDED); - EMIT_CODE (parser, nargs); - EMIT_CODE (parser, selector); + EMIT_CODE (stc, SEND_TO_SUPER_EXTENDED); + EMIT_CODE (stc, nargs); + EMIT_CODE (stc, selector); } return 0; } -static INLINE int __emit_do_primitive (qse_stx_parser_t* parser, int no) +static QSE_INLINE int __emit_do_primitive (qse_stc_t* stc, int no) { qse_assert (no >= 0x0 && no <= 0xFFF); - EMIT_CODE (parser, DO_PRIMITIVE | ((no >> 8) & 0x0F)); - EMIT_CODE (parser, no & 0xFF); + EMIT_CODE (stc, DO_PRIMITIVE | ((no >> 8) & 0x0F)); + EMIT_CODE (stc, no & 0xFF); return 0; } -static int __add_literal (qse_stx_parser_t* parser, qse_word_t literal) +static int __add_literal (qse_stc_t* stc, qse_word_t literal) { qse_word_t i; - for (i = 0; i < parser->literal_count; i++) { + for (i = 0; i < stc->literal_count; i++) { /* * it would remove redundancy of symbols and small integers. * more complex redundacy check may be done somewhere else * like in __add_string_literal. */ - if (parser->literals[i] == literal) return i; + if (stc->literals[i] == literal) return i; } - if (parser->literal_count >= qse_countof(parser->literals)) { - parser->error_code = QSE_STX_PARSER_ERROR_TOO_MANY_LITERALS; + if (stc->literal_count >= QSE_COUNTOF(stc->literals)) { + stc->error_code = QSE_STC_ERROR_TOO_MANY_LITERALS; return -1; } - parser->literals[parser->literal_count++] = literal; - return parser->literal_count - 1; + stc->literals[stc->literal_count++] = literal; + return stc->literal_count - 1; } -static int __add_character_literal (qse_stx_parser_t* parser, qse_char_t ch) +static int __add_character_literal (qse_stc_t* stc, qse_char_t ch) { qse_word_t i, c, literal; - qse_stx_t* stx = parser->stx; + qse_stx_t* stx = stc->stx; - for (i = 0; i < parser->literal_count; i++) { - c = QSE_STX_ISSMALLINT(parser->literals[i])? - stx->class_smallinteger: QSE_STX_CLASS (stx, parser->literals[i]); + for (i = 0; i < stc->literal_count; i++) + { + c = QSE_STX_ISSMALLINT(stc->literals[i])? + stx->class_smallinteger: QSE_STX_CLASS (stx, stc->literals[i]); if (c != stx->class_character) continue; - if (ch == QSE_STX_CHAR_AT(stx,parser->literals[i],0)) return i; + if (ch == QSE_STX_CHAR_AT(stx,stc->literals[i],0)) return i; } literal = qse_stx_instantiate ( stx, stx->class_character, &ch, QSE_NULL, 0); - return __add_literal (parser, literal); + return __add_literal (stc, literal); } static int __add_string_literal ( - qse_stx_parser_t* parser, const qse_char_t* str, qse_word_t size) + qse_stc_t* stc, const qse_char_t* str, qse_word_t size) { qse_word_t i, c, literal; - qse_stx_t* stx = parser->stx; + qse_stx_t* stx = stc->stx; - for (i = 0; i < parser->literal_count; i++) { - c = QSE_STX_ISSMALLINT(parser->literals[i])? - stx->class_smallinteger: QSE_STX_CLASS (stx, parser->literals[i]); + for (i = 0; i < stc->literal_count; i++) { + c = QSE_STX_ISSMALLINT(stc->literals[i])? + stx->class_smallinteger: QSE_STX_CLASS (stx, stc->literals[i]); if (c != stx->class_string) continue; if (qse_strxncmp (str, size, - QSE_STX_DATA(stx,parser->literals[i]), - QSE_STX_SIZE(stx,parser->literals[i])) == 0) return i; + QSE_STX_DATA(stx,stc->literals[i]), + QSE_STX_SIZE(stx,stc->literals[i])) == 0) return i; } literal = qse_stx_instantiate ( stx, stx->class_string, QSE_NULL, str, size); - return __add_literal (parser, literal); + return __add_literal (stc, literal); } static int __add_symbol_literal ( - qse_stx_parser_t* parser, const qse_char_t* str, qse_word_t size) + qse_stc_t* stc, const qse_char_t* str, qse_word_t size) { - qse_stx_t* stx = parser->stx; - return __add_literal (parser, qse_stx_new_symbolx(stx, str, size)); + qse_stx_t* stx = stc->stx; + return __add_literal (stc, qse_stx_new_symbolx(stx, str, size)); } -int qse_stx_parser_parse_method ( - qse_stx_parser_t* parser, qse_word_t method_class, void* input) +int qse_stc_parse_method ( + qse_stc_t* stc, qse_word_t method_class, void* input) { int n; - if (parser->input_func == QSE_NULL) { - parser->error_code = QSE_STX_PARSER_ERROR_INPUT_FUNC; + if (stc->input_func == QSE_NULL) { + stc->error_code = QSE_STC_ERROR_INPUT_FUNC; return -1; } - parser->method_class = method_class; - if (__open_input(parser, input) == -1) return -1; - n = __parse_method (parser, method_class, input); - if (__close_input(parser) == -1) return -1; + stc->method_class = method_class; + if (__open_input(stc, input) == -1) return -1; + n = __parse_method (stc, method_class, input); + if (__close_input(stc) == -1) return -1; return n; } static int __parse_method ( - qse_stx_parser_t* parser, qse_word_t method_class, void* input) + qse_stc_t* stc, qse_word_t method_class, void* input) { /* * ::= * [] [] [] */ - GET_CHAR (parser); - GET_TOKEN (parser); + GET_CHAR (stc); + GET_TOKEN (stc); - qse_stx_name_clear (&parser->method_name); - qse_arr_clear (&parser->bytecode); + qse_stx_name_clear (&stc->method_name); + qse_lda_clear (&stc->bytecode); - while (parser->temporary_count > 0) { - qse_free (parser->temporaries[--parser->temporary_count]); + while (stc->temporary_count > 0) { + qse_free (stc->temporaries[--stc->temporary_count]); } - parser->argument_count = 0; - parser->literal_count = 0; + stc->argument_count = 0; + stc->literal_count = 0; - if (__parse_message_pattern(parser) == -1) return -1; - if (__parse_temporaries(parser) == -1) return -1; - if (__parse_primitive(parser) == -1) return -1; - if (__parse_statements(parser) == -1) return -1; - if (__finish_method (parser) == -1) return -1; + if (__parse_message_pattern(stc) == -1) return -1; + if (__parse_temporaries(stc) == -1) return -1; + if (__parse_primitive(stc) == -1) return -1; + if (__parse_statements(stc) == -1) return -1; + if (__finish_method (stc) == -1) return -1; return 0; } -static int __finish_method (qse_stx_parser_t* parser) +static int __finish_method (qse_stc_t* stc) { - qse_stx_t* stx = parser->stx; + qse_stx_t* stx = stc->stx; qse_stx_class_t* class_obj; qse_stx_method_t* method_obj; qse_word_t method, selector; - qse_assert (parser->bytecode.size != 0); + qse_assert (stc->bytecode.size != 0); class_obj = (qse_stx_class_t*) - QSE_STX_OBJPTR(stx, parser->method_class); + QSE_STX_OBJPTR(stx, stc->method_class); if (class_obj->methods == stx->nil) { /* TODO: reconfigure method dictionary size */ @@ -513,32 +565,32 @@ static int __finish_method (qse_stx_parser_t* parser) qse_assert (class_obj->methods != stx->nil); selector = qse_stx_new_symbolx ( - stx, parser->method_name.buffer, parser->method_name.size); + stx, stc->method_name.buffer, stc->method_name.size); method = qse_stx_instantiate(stx, stx->class_method, - QSE_NULL, parser->literals, parser->literal_count); + QSE_NULL, stc->literals, stc->literal_count); method_obj = (qse_stx_method_t*)QSE_STX_OBJPTR(stx, method); /* TODO: text saving must be optional */ /*method_obj->text = qse_stx_instantiate ( stx, stx->class_string, QSE_NULL, - parser->text, qse_strlen(parser->text)); + stc->text, qse_strlen(stc->text)); */ method_obj->selector = selector; method_obj->bytecodes = qse_stx_instantiate ( stx, stx->class_bytearray, QSE_NULL, - parser->bytecode.buf, parser->bytecode.size); + stc->bytecode.buf, stc->bytecode.size); /* TODO: better way to store argument count & temporary count */ method_obj->tmpcount = - QSE_STX_TO_SMALLINT(parser->temporary_count - parser->argument_count); - method_obj->argcount = QSE_STX_TO_SMALLINT(parser->argument_count); + QSE_STX_TO_SMALLINT(stc->temporary_count - stc->argument_count); + method_obj->argcount = QSE_STX_TO_SMALLINT(stc->argument_count); qse_stx_dict_put (stx, class_obj->methods, selector, method); return 0; } -static int __parse_message_pattern (qse_stx_parser_t* parser) +static int __parse_message_pattern (qse_stc_t* stc) { /* * ::= @@ -549,160 +601,170 @@ static int __parse_message_pattern (qse_stx_parser_t* parser) */ int n; - if (parser->token.type == QSE_STX_TOKEN_IDENT) { - n = __parse_unary_pattern (parser); + if (stc->token.type == TOKEN_IDENT) { + n = __parse_unary_pattern (stc); } - else if (parser->token.type == QSE_STX_TOKEN_BINARY) { - n = __parse_binary_pattern (parser); + else if (stc->token.type == TOKEN_BINARY) { + n = __parse_binary_pattern (stc); } - else if (parser->token.type == QSE_STX_TOKEN_KEYWORD) { - n = __parse_keyword_pattern (parser); + else if (stc->token.type == TOKEN_KEYWORD) { + n = __parse_keyword_pattern (stc); } else { - parser->error_code = QSE_STX_PARSER_ERROR_MESSAGE_SELECTOR; + stc->error_code = QSE_STC_ERROR_MESSAGE_SELECTOR; n = -1; } - parser->temporary_count = parser->argument_count; + stc->temporary_count = stc->argument_count; return n; } -static int __parse_unary_pattern (qse_stx_parser_t* parser) +static int __parse_unary_pattern (qse_stc_t* stc) { /* TODO: check if the method name exists */ - if (qse_stx_name_adds( - &parser->method_name, parser->token.name.buffer) == -1) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + if (qse_str_cat ( + &stc->method_name, QSE_STR_PTR(&stc->token.name)) == (qse_size_t)-1) { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } - GET_TOKEN (parser); + GET_TOKEN (stc); return 0; } -static int __parse_binary_pattern (qse_stx_parser_t* parser) +static int __parse_binary_pattern (qse_stc_t* stc) { /* TODO: check if the method name exists */ - if (qse_stx_name_adds( - &parser->method_name, parser->token.name.buffer) == -1) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + if (qse_str_cat ( + &stc->method_name, + QSE_STR_PTR(&stc->token.name)) == (qse_size_t)-1) + { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } - GET_TOKEN (parser); - if (parser->token.type != QSE_STX_TOKEN_IDENT) { - parser->error_code = QSE_STX_PARSER_ERROR_ARGUMENT_NAME; + GET_TOKEN (stc); + if (stc->token.type != TOKEN_IDENT) + { + stc->error_code = QSE_STC_ERROR_ARGUMENT_NAME; return -1; } - if (parser->argument_count >= qse_countof(parser->temporaries)) { - parser->error_code = QSE_STX_PARSER_ERROR_TOO_MANY_ARGUMENTS; + if (stc->argument_count >= QSE_COUNTOF(stc->temporaries)) + { + stc->error_code = QSE_STC_ERROR_TOO_MANY_ARGUMENTS; return -1; } /* TODO: check for duplicate entries...in instvars */ - parser->temporaries[parser->argument_count] = - qse_stx_token_yield (&parser->token, 0); - if (parser->temporaries[parser->argument_count] == QSE_NULL) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + YIELD_TOKEN_TO (stc, stc->temporaries[stc->argument_count]); + if (stc->temporaries[stc->argument_count] == QSE_NULL) + { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } - parser->argument_count++; + stc->argument_count++; - GET_TOKEN (parser); + GET_TOKEN (stc); return 0; } -static int __parse_keyword_pattern (qse_stx_parser_t* parser) +static int __parse_keyword_pattern (qse_stc_t* stc) { - do { - if (qse_stx_name_adds( - &parser->method_name, parser->token.name.buffer) == -1) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + do + { + if (qse_str_cat ( + &stc->method_name, QSE_STR_PTR(&stc->token.name)) == (qse_size_t)-1) + { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } - GET_TOKEN (parser); - if (parser->token.type != QSE_STX_TOKEN_IDENT) { - parser->error_code = QSE_STX_PARSER_ERROR_ARGUMENT_NAME; + GET_TOKEN (stc); + if (stc->token.type != TOKEN_IDENT) + { + stc->error_code = QSE_STC_ERROR_ARGUMENT_NAME; return -1; } - if (__is_pseudo_variable(&parser->token)) { - parser->error_code = QSE_STX_PARSER_ERROR_PSEUDO_VARIABLE; + if (__is_token_pseudo_variable(stc)) + { + stc->error_code = QSE_STC_ERROR_PSEUDO_VARIABLE; return -1; } - if (parser->argument_count >= qse_countof(parser->temporaries)) { - parser->error_code = QSE_STX_PARSER_ERROR_TOO_MANY_ARGUMENTS; + if (stc->argument_count >= QSE_COUNTOF(stc->temporaries)) + { + stc->error_code = QSE_STC_ERROR_TOO_MANY_ARGUMENTS; return -1; } - parser->temporaries[parser->argument_count] = - qse_stx_token_yield (&parser->token, 0); - if (parser->temporaries[parser->argument_count] == QSE_NULL) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + YIELD_TOKEN_TO (stc, stc->temporaries[stc->argument_count]); + if (stc->temporaries[stc->argument_count] == QSE_NULL) + { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } /* TODO: check for duplicate entries...in instvars/arguments */ - parser->argument_count++; + stc->argument_count++; - GET_TOKEN (parser); - } while (parser->token.type == QSE_STX_TOKEN_KEYWORD); + GET_TOKEN (stc); + } + while (stc->token.type == TOKEN_KEYWORD); /* TODO: check if the method name exists */ /* if it exists, collapse arguments */ -qse_printf (QSE_T("METHOD NAME ==> [%s]\n"), parser->method_name.buffer); +qse_printf (QSE_T("METHOD NAME ==> [%s]\n"), stc->method_name.buffer); return 0; } -static int __parse_temporaries (qse_stx_parser_t* parser) +static int __parse_temporaries (qse_stc_t* stc) { /* * ::= '|' '|' * ::= identifier* */ - if (!__is_vbar_token(&parser->token)) return 0; + if (!__is_token_vertical_bar(stc)) return 0; - GET_TOKEN (parser); - while (parser->token.type == QSE_STX_TOKEN_IDENT) { - if (parser->temporary_count >= qse_countof(parser->temporaries)) { - parser->error_code = QSE_STX_PARSER_ERROR_TOO_MANY_TEMPORARIES; + GET_TOKEN (stc); + while (stc->token.type == TOKEN_IDENT) { + if (stc->temporary_count >= QSE_COUNTOF(stc->temporaries)) { + stc->error_code = QSE_STC_ERROR_TOO_MANY_TEMPORARIES; return -1; } - if (__is_pseudo_variable(&parser->token)) { - parser->error_code = QSE_STX_PARSER_ERROR_PSEUDO_VARIABLE; + if (__is_token_pseudo_variable(stc)) { + stc->error_code = QSE_STC_ERROR_PSEUDO_VARIABLE; return -1; } - parser->temporaries[parser->temporary_count] = - qse_stx_token_yield (&parser->token, 0); - if (parser->temporaries[parser->temporary_count] == QSE_NULL) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + YIELD_TOKEN_TO (stc, stc->temporaries[stc->temporary_count]); + if (stc->temporaries[stc->temporary_count] == QSE_NULL) + { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } /* TODO: check for duplicate entries...in instvars/arguments/temporaries */ - parser->temporary_count++; + stc->temporary_count++; - GET_TOKEN (parser); + GET_TOKEN (stc); } - if (!__is_vbar_token(&parser->token)) { - parser->error_code = QSE_STX_PARSER_ERROR_TEMPORARIES_NOT_CLOSED; + if (!__is_token_vertical_bar(stc)) { + stc->error_code = QSE_STC_ERROR_TEMPORARIES_NOT_CLOSED; return -1; } - GET_TOKEN (parser); + GET_TOKEN (stc); return 0; } -static int __parse_primitive (qse_stx_parser_t* parser) +static int __parse_primitive (qse_stc_t* stc) { /* * ::= '<' 'primitive:' number '>' @@ -710,46 +772,51 @@ static int __parse_primitive (qse_stx_parser_t* parser) int prim_no; - if (!__is_primitive_opener(&parser->token)) return 0; - GET_TOKEN (parser); + if (!__is_token_primitive_opener(stc)) return 0; + GET_TOKEN (stc); - if (parser->token.type != QSE_STX_TOKEN_KEYWORD || - qse_strcmp (parser->token.name.buffer, QSE_T("primitive:")) != 0) { - parser->error_code = QSE_STX_PARSER_ERROR_PRIMITIVE_KEYWORD; + if (stc->token.type != TOKEN_KEYWORD || + qse_strcmp (QSE_STR_PTR(&stc->token.name), QSE_T("primitive:")) != 0) + { + stc->error_code = QSE_STC_ERROR_PRIMITIVE_KEYWORD; return -1; } - GET_TOKEN (parser); /* TODO: only integer */ - if (parser->token.type != QSE_STX_TOKEN_NUMLIT) { - parser->error_code = QSE_STX_PARSER_ERROR_PRIMITIVE_NUMBER; + GET_TOKEN (stc); /* TODO: only integer */ + if (stc->token.type != TOKEN_NUMLIT) + { + stc->error_code = QSE_STC_ERROR_PRIMITIVE_NUMBER; return -1; } /*TODO: more checks the validity of the primitive number */ - if (!qse_stristype(parser->token.name.buffer, qse_isdigit)) { - parser->error_code = QSE_STX_PARSER_ERROR_PRIMITIVE_NUMBER; + if (!qse_stristype(QSE_STR_PTR(&stc->token.name), qse_isdigit)) + { + stc->error_code = QSE_STC_ERROR_PRIMITIVE_NUMBER; return -1; } - QSE_STRTOI (prim_no, parser->token.name.buffer, QSE_NULL, 10); - if (prim_no < 0 || prim_no > 0xFF) { - parser->error_code = QSE_STX_PARSER_ERROR_PRIMITIVE_NUMBER_RANGE; + QSE_STRTOI (prim_no, QSE_STR_PTR(&stc->token.name), QSE_NULL, 10); + if (prim_no < 0 || prim_no > 0xFF) + { + stc->error_code = QSE_STC_ERROR_PRIMITIVE_NUMBER_RANGE; return -1; } - EMIT_DO_PRIMITIVE (parser, prim_no); + EMIT_DO_PRIMITIVE (stc, prim_no); - GET_TOKEN (parser); - if (!__is_primitive_closer(&parser->token)) { - parser->error_code = QSE_STX_PARSER_ERROR_PRIMITIVE_NOT_CLOSED; + GET_TOKEN (stc); + if (!__is_token_primitive_closer(stc)) + { + stc->error_code = QSE_STC_ERROR_PRIMITIVE_NOT_CLOSED; return -1; } - GET_TOKEN (parser); + GET_TOKEN (stc); return 0; } -static int __parse_statements (qse_stx_parser_t* parser) +static int __parse_statements (qse_stc_t* stc) { /* * ::= (ORIGINAL->maybe wrong) @@ -759,38 +826,38 @@ static int __parse_statements (qse_stx_parser_t* parser) * ['. []] */ - while (parser->token.type != QSE_STX_TOKEN_END) { - if (__parse_statement (parser) == -1) return -1; + while (stc->token.type != TOKEN_END) { + if (__parse_statement (stc) == -1) return -1; - if (parser->token.type == QSE_STX_TOKEN_PERIOD) { - GET_TOKEN (parser); + if (stc->token.type == TOKEN_PERIOD) { + GET_TOKEN (stc); continue; } - if (parser->token.type != QSE_STX_TOKEN_END) { - parser->error_code = QSE_STX_PARSER_ERROR_NO_PERIOD; + if (stc->token.type != TOKEN_END) { + stc->error_code = QSE_STC_ERROR_NO_PERIOD; return -1; } } - EMIT_CODE (parser, RETURN_RECEIVER); + EMIT_CODE (stc, RETURN_RECEIVER); return 0; } -static int __parse_block_statements (qse_stx_parser_t* parser) +static int __parse_block_statements (qse_stc_t* stc) { - while (parser->token.type != QSE_STX_TOKEN_RBRACKET && - parser->token.type != QSE_STX_TOKEN_END) { + while (stc->token.type != TOKEN_RBRACKET && + stc->token.type != TOKEN_END) { - if (__parse_statement(parser) == -1) return -1; - if (parser->token.type != QSE_STX_TOKEN_PERIOD) break; - GET_TOKEN (parser); + if (__parse_statement(stc) == -1) return -1; + if (stc->token.type != TOKEN_PERIOD) break; + GET_TOKEN (stc); } return 0; } -static int __parse_statement (qse_stx_parser_t* parser) +static int __parse_statement (qse_stc_t* stc) { /* * ::= | @@ -798,19 +865,19 @@ static int __parse_statement (qse_stx_parser_t* parser) * returnOperator ::= '^' */ - if (parser->token.type == QSE_STX_TOKEN_RETURN) { - GET_TOKEN (parser); - if (__parse_expression(parser) == -1) return -1; - EMIT_RETURN_FROM_MESSAGE (parser); + if (stc->token.type == TOKEN_RETURN) { + GET_TOKEN (stc); + if (__parse_expression(stc) == -1) return -1; + EMIT_RETURN_FROM_MESSAGE (stc); } else { - if (__parse_expression(parser) == -1) return -1; + if (__parse_expression(stc) == -1) return -1; } return 0; } -static int __parse_expression (qse_stx_parser_t* parser) +static int __parse_expression (qse_stc_t* stc) { /* * ::= | @@ -819,25 +886,33 @@ static int __parse_expression (qse_stx_parser_t* parser) * ::= identifier * assignmentOperator ::= ':=' */ - qse_stx_t* stx = parser->stx; + qse_stx_t* stx = stc->stx; - if (parser->token.type == QSE_STX_TOKEN_IDENT) { - qse_char_t* ident = qse_stx_token_yield (&parser->token, 0); - if (ident == QSE_NULL) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + if (stc->token.type == TOKEN_IDENT) + { + qse_char_t* ident; + + YIELD_TOKEN_TO (stc, ident); + if (ident == QSE_NULL) + { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } - GET_TOKEN (parser); - if (parser->token.type == QSE_STX_TOKEN_ASSIGN) { - GET_TOKEN (parser); - if (__parse_assignment(parser, ident) == -1) { + GET_TOKEN (stc); + if (stc->token.type == TOKEN_ASSIGN) + { + GET_TOKEN (stc); + if (__parse_assignment(stc, ident) == -1) + { qse_free (ident); return -1; } } - else { - if (__parse_basic_expression(parser, ident) == -1) { + else + { + if (__parse_basic_expression(stc, ident) == -1) + { qse_free (ident); return -1; } @@ -845,61 +920,62 @@ static int __parse_expression (qse_stx_parser_t* parser) qse_free (ident); } - else { - if (__parse_basic_expression(parser, QSE_NULL) == -1) return -1; + else + { + if (__parse_basic_expression(stc, QSE_NULL) == -1) return -1; } return 0; } static int __parse_basic_expression ( - qse_stx_parser_t* parser, const qse_char_t* ident) + qse_stc_t* stc, const qse_char_t* ident) { /* * ::= [ ] */ qse_bool_t is_super; - if (__parse_primary(parser, ident, &is_super) == -1) return -1; - if (parser->token.type != QSE_STX_TOKEN_END && - parser->token.type != QSE_STX_TOKEN_PERIOD) { - if (__parse_message_continuation(parser, is_super) == -1) return -1; + if (__parse_primary(stc, ident, &is_super) == -1) return -1; + if (stc->token.type != TOKEN_END && + stc->token.type != TOKEN_PERIOD) { + if (__parse_message_continuation(stc, is_super) == -1) return -1; } return 0; } static int __parse_assignment ( - qse_stx_parser_t* parser, const qse_char_t* target) + qse_stc_t* stc, const qse_char_t* target) { /* * ::= assignmentOperator */ qse_word_t i; - qse_stx_t* stx = parser->stx; + qse_stx_t* stx = stc->stx; - for (i = parser->argument_count; i < parser->temporary_count; i++) { - if (qse_strcmp (target, parser->temporaries[i]) == 0) { - if (__parse_expression(parser) == -1) return -1; - EMIT_STORE_TEMPORARY_LOCATION (parser, i); + for (i = stc->argument_count; i < stc->temporary_count; i++) { + if (qse_strcmp (target, stc->temporaries[i]) == 0) { + if (__parse_expression(stc) == -1) return -1; + EMIT_STORE_TEMPORARY_LOCATION (stc, i); return 0; } } if (qse_stx_get_instance_variable_index ( - stx, parser->method_class, target, &i) == 0) { - if (__parse_expression(parser) == -1) return -1; - EMIT_STORE_RECEIVER_VARIABLE (parser, i); + stx, stc->method_class, target, &i) == 0) { + if (__parse_expression(stc) == -1) return -1; + EMIT_STORE_RECEIVER_VARIABLE (stc, i); return 0; } if (qse_stx_lookup_class_variable ( - stx, parser->method_class, target) != stx->nil) { - if (__parse_expression(parser) == -1) return -1; + stx, stc->method_class, target) != stx->nil) { + if (__parse_expression(stc) == -1) return -1; /* TODO */ - EMIT_CODE_TEST (parser, QSE_T("ASSIGN_CLASSVAR #"), target); - //EMIT_STORE_CLASS_VARIABLE (parser, target); + EMIT_CODE_TEST (stc, QSE_T("ASSIGN_CLASSVAR #"), target); + //EMIT_STORE_CLASS_VARIABLE (stc, target); return 0; } @@ -907,12 +983,12 @@ static int __parse_assignment ( /* TODO: IMPLEMENT GLOBLAS, but i don't like this idea */ - parser->error_code = QSE_STX_PARSER_ERROR_UNDECLARED_NAME; + stc->error_code = QSE_STC_ERROR_UNDECLARED_NAME; return -1; } static int __parse_primary ( - qse_stx_parser_t* parser, const qse_char_t* ident, qse_bool_t* is_super) + qse_stc_t* stc, const qse_char_t* ident, qse_bool_t* is_super) { /* * ::= @@ -920,7 +996,7 @@ static int __parse_primary ( * | ( '('')' ) */ - qse_stx_t* stx = parser->stx; + qse_stx_t* stx = stc->stx; if (ident == QSE_NULL) { int pos; @@ -928,121 +1004,121 @@ static int __parse_primary ( *is_super = qse_false; - if (parser->token.type == QSE_STX_TOKEN_IDENT) { - if (__parse_primary_ident(parser, - parser->token.name.buffer, is_super) == -1) return -1; - GET_TOKEN (parser); + if (stc->token.type == TOKEN_IDENT) { + if (__parse_primary_ident(stc, + QSE_STR_PTR(&stc->token.name), is_super) == -1) return -1; + GET_TOKEN (stc); } - else if (parser->token.type == QSE_STX_TOKEN_CHARLIT) { + else if (stc->token.type == TOKEN_CHARLIT) { pos = __add_character_literal( - parser, parser->token.name.buffer[0]); + stc, QSE_STR_PTR(&stc->token.name)[0]); if (pos == -1) return -1; - EMIT_PUSH_LITERAL_CONSTANT (parser, pos); - GET_TOKEN (parser); + EMIT_PUSH_LITERAL_CONSTANT (stc, pos); + GET_TOKEN (stc); } - else if (parser->token.type == QSE_STX_TOKEN_STRLIT) { - pos = __add_string_literal (parser, - parser->token.name.buffer, parser->token.name.size); + else if (stc->token.type == TOKEN_STRLIT) { + pos = __add_string_literal (stc, + QSE_STR_PTR(&stc->token.name), QSE_STR_LEN(&stc->token.name)); if (pos == -1) return -1; - EMIT_PUSH_LITERAL_CONSTANT (parser, pos); - GET_TOKEN (parser); + EMIT_PUSH_LITERAL_CONSTANT (stc, pos); + GET_TOKEN (stc); } - else if (parser->token.type == QSE_STX_TOKEN_NUMLIT) { + else if (stc->token.type == TOKEN_NUMLIT) { /* TODO: other types of numbers, negative numbers, etc */ qse_word_t tmp; - QSE_STRTOI (tmp, parser->token.name.buffer, QSE_NULL, 10); + QSE_STRTOI (tmp, QSE_STR_PTR(&stc->token.name), QSE_NULL, 10); literal = QSE_STX_TO_SMALLINT(tmp); - pos = __add_literal(parser, literal); + pos = __add_literal(stc, literal); if (pos == -1) return -1; - EMIT_PUSH_LITERAL_CONSTANT (parser, pos); - GET_TOKEN (parser); + EMIT_PUSH_LITERAL_CONSTANT (stc, pos); + GET_TOKEN (stc); } - else if (parser->token.type == QSE_STX_TOKEN_SYMLIT) { - pos = __add_symbol_literal (parser, - parser->token.name.buffer, parser->token.name.size); + else if (stc->token.type == TOKEN_SYMLIT) { + pos = __add_symbol_literal (stc, + QSE_STR_PTR(&stc->token.name), QSE_STR_LEN(&stc->token.name)); if (pos == -1) return -1; - EMIT_PUSH_LITERAL_CONSTANT (parser, pos); - GET_TOKEN (parser); + EMIT_PUSH_LITERAL_CONSTANT (stc, pos); + GET_TOKEN (stc); } - else if (parser->token.type == QSE_STX_TOKEN_LBRACKET) { - GET_TOKEN (parser); - if (__parse_block_constructor(parser) == -1) return -1; + else if (stc->token.type == TOKEN_LBRACKET) { + GET_TOKEN (stc); + if (__parse_block_constructor(stc) == -1) return -1; } - else if (parser->token.type == QSE_STX_TOKEN_APAREN) { + else if (stc->token.type == TOKEN_APAREN) { /* TODO: array literal */ } - else if (parser->token.type == QSE_STX_TOKEN_LPAREN) { - GET_TOKEN (parser); - if (__parse_expression(parser) == -1) return -1; - if (parser->token.type != QSE_STX_TOKEN_RPAREN) { - parser->error_code = QSE_STX_PARSER_ERROR_NO_RPAREN; + else if (stc->token.type == TOKEN_LPAREN) { + GET_TOKEN (stc); + if (__parse_expression(stc) == -1) return -1; + if (stc->token.type != TOKEN_RPAREN) { + stc->error_code = QSE_STC_ERROR_NO_RPAREN; return -1; } - GET_TOKEN (parser); + GET_TOKEN (stc); } else { - parser->error_code = QSE_STX_PARSER_ERROR_PRIMARY; + stc->error_code = QSE_STC_ERROR_PRIMARY; return -1; } } else { - /*if (__parse_primary_ident(parser, parser->token.name.buffer) == -1) return -1;*/ - if (__parse_primary_ident(parser, ident, is_super) == -1) return -1; + /*if (__parse_primary_ident(stc, QSE_STR_PTR(&stc->token.name)) == -1) return -1;*/ + if (__parse_primary_ident(stc, ident, is_super) == -1) return -1; } return 0; } static int __parse_primary_ident ( - qse_stx_parser_t* parser, const qse_char_t* ident, qse_bool_t* is_super) + qse_stc_t* stc, const qse_char_t* ident, qse_bool_t* is_super) { qse_word_t i; - qse_stx_t* stx = parser->stx; + qse_stx_t* stx = stc->stx; *is_super = qse_false; if (qse_strcmp(ident, QSE_T("self")) == 0) { - EMIT_CODE (parser, PUSH_RECEIVER); + EMIT_CODE (stc, PUSH_RECEIVER); return 0; } else if (qse_strcmp(ident, QSE_T("super")) == 0) { *is_super = qse_true; - EMIT_CODE (parser, PUSH_RECEIVER); + EMIT_CODE (stc, PUSH_RECEIVER); return 0; } else if (qse_strcmp(ident, QSE_T("nil")) == 0) { - EMIT_CODE (parser, PUSH_NIL); + EMIT_CODE (stc, PUSH_NIL); return 0; } else if (qse_strcmp(ident, QSE_T("true")) == 0) { - EMIT_CODE (parser, PUSH_TRUE); + EMIT_CODE (stc, PUSH_TRUE); return 0; } else if (qse_strcmp(ident, QSE_T("false")) == 0) { - EMIT_CODE (parser, PUSH_FALSE); + EMIT_CODE (stc, PUSH_FALSE); return 0; } /* Refer to __parse_assignment for identifier lookup */ - for (i = 0; i < parser->temporary_count; i++) + for (i = 0; i < stc->temporary_count; i++) { - if (qse_strcmp(ident, parser->temporaries[i]) == 0) + if (qse_strcmp(ident, stc->temporaries[i]) == 0) { - EMIT_PUSH_TEMPORARY_LOCATION (parser, i); + EMIT_PUSH_TEMPORARY_LOCATION (stc, i); return 0; } } if (qse_stx_get_instance_variable_index ( - stx, parser->method_class, ident, &i) == 0) + stx, stc->method_class, ident, &i) == 0) { - EMIT_PUSH_RECEIVER_VARIABLE (parser, i); + EMIT_PUSH_RECEIVER_VARIABLE (stc, i); return 0; } @@ -1052,8 +1128,8 @@ static int __parse_primary_ident ( /* 3. Implement a vm instruction to do it */ /* if (qse_stx_lookup_class_variable ( - stx, parser->method_class, ident) != stx->nil) { - //EMIT_LOOKUP_CLASS_VARIABLE (parser, ident); + stx, stc->method_class, ident) != stx->nil) { + //EMIT_LOOKUP_CLASS_VARIABLE (stc, ident); return 0; } */ @@ -1062,11 +1138,11 @@ static int __parse_primary_ident ( /* TODO: IMPLEMENT GLOBLAS, but i don't like this idea */ - parser->error_code = QSE_STX_PARSER_ERROR_UNDECLARED_NAME; + stc->error_code = QSE_STC_ERROR_UNDECLARED_NAME; return -1; } -static int __parse_block_constructor (qse_stx_parser_t* parser) +static int __parse_block_constructor (qse_stc_t* stc) { /* * ::= '[' ']' @@ -1075,43 +1151,43 @@ static int __parse_block_constructor (qse_stx_parser_t* parser) * ::= ':' identifier */ - if (parser->token.type == QSE_STX_TOKEN_COLON) + if (stc->token.type == TOKEN_COLON) { do { - GET_TOKEN (parser); + GET_TOKEN (stc); - if (parser->token.type != QSE_STX_TOKEN_IDENT) + if (stc->token.type != TOKEN_IDENT) { - parser->error_code = QSE_STX_PARSER_ERROR_BLOCK_ARGUMENT_NAME; + stc->error_code = QSE_STC_ERROR_BLOCK_ARGUMENT_NAME; return -1; } /* TODO : store block arguments */ - GET_TOKEN (parser); + GET_TOKEN (stc); } - while (parser->token.type == QSE_STX_TOKEN_COLON); + while (stc->token.type == TOKEN_COLON); - if (!__is_vbar_token(&parser->token)) + if (!__is_token_vertical_bar(stc)) { - parser->error_code = QSE_STX_PARSER_ERROR_BLOCK_ARGUMENT_LIST; + stc->error_code = QSE_STC_ERROR_BLOCK_ARGUMENT_LIST; return -1; } - GET_TOKEN (parser); + GET_TOKEN (stc); } /* TODO: create a block closure */ - if (__parse_temporaries(parser) == -1) return -1; - if (__parse_block_statements(parser) == -1) return -1; + if (__parse_temporaries(stc) == -1) return -1; + if (__parse_block_statements(stc) == -1) return -1; - if (parser->token.type != QSE_STX_TOKEN_RBRACKET) + if (stc->token.type != TOKEN_RBRACKET) { - parser->error_code = QSE_STX_PARSER_ERROR_BLOCK_NOT_CLOSED; + stc->error_code = QSE_STC_ERROR_BLOCK_NOT_CLOSED; return -1; } - GET_TOKEN (parser); + GET_TOKEN (stc); /* TODO: do special treatment for block closures */ @@ -1119,7 +1195,7 @@ static int __parse_block_constructor (qse_stx_parser_t* parser) } static int __parse_message_continuation ( - qse_stx_parser_t* parser, qse_bool_t is_super) + qse_stc_t* stc, qse_bool_t is_super) { /* * ::= @@ -1128,81 +1204,74 @@ static int __parse_message_continuation ( * * ::= (';' )* */ - if (__parse_keyword_message(parser, is_super) == -1) return -1; + if (__parse_keyword_message(stc, is_super) == -1) return -1; - while (parser->token.type == QSE_STX_TOKEN_SEMICOLON) + while (stc->token.type == TOKEN_SEMICOLON) { - EMIT_CODE_TEST (parser, QSE_T("DoSpecial(DUP_RECEIVER(CASCADE))"), QSE_T("")); - GET_TOKEN (parser); + EMIT_CODE_TEST (stc, QSE_T("DoSpecial(DUP_RECEIVER(CASCADE))"), QSE_T("")); + GET_TOKEN (stc); - if (__parse_keyword_message(parser, qse_false) == -1) return -1; - EMIT_CODE_TEST (parser, QSE_T("DoSpecial(POP_TOP)"), QSE_T("")); + if (__parse_keyword_message(stc, qse_false) == -1) return -1; + EMIT_CODE_TEST (stc, QSE_T("DoSpecial(POP_TOP)"), QSE_T("")); } return 0; } -static int __parse_keyword_message (qse_stx_parser_t* parser, qse_bool_t is_super) +static int __parse_keyword_message (qse_stc_t* stc, qse_bool_t is_super) { /* * ::= (keyword )+ * ::= * * */ - - qse_stx_name_t name; + qse_str_t name; qse_word_t pos; qse_bool_t is_super2; int nargs = 0, n; - if (__parse_binary_message (parser, is_super) == -1) return -1; - if (parser->token.type != QSE_STX_TOKEN_KEYWORD) return 0; + if (__parse_binary_message (stc, is_super) == -1) return -1; + if (stc->token.type != TOKEN_KEYWORD) return 0; - if (qse_stx_name_open(&name, 0) == QSE_NULL) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + if (qse_str_init (&name, stc->mmgr, 0) == QSE_NULL) + { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } - do { - if (qse_stx_name_adds(&name, parser->token.name.buffer) == -1) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; - qse_stx_name_close (&name); - return -1; + do + { + if (qse_str_cat (&name, QSE_STR_PTR(&stc->token.name)) == (qse_size_t)-1) + { + stc->error_code = QSE_STC_ERROR_MEMORY; + goto oops; } - GET_TOKEN (parser); - if (__parse_primary(parser, QSE_NULL, &is_super2) == -1) { - qse_stx_name_close (&name); - return -1; - } - - if (__parse_binary_message(parser, is_super2) == -1) { - qse_stx_name_close (&name); - return -1; - } + if (__get_token(stc) == -1) goto oops; + if (__parse_primary(stc, QSE_NULL, &is_super2) == -1) goto oops; + if (__parse_binary_message(stc, is_super2) == -1) goto oops; nargs++; /* TODO: check if it has too many arguments.. */ - } while (parser->token.type == QSE_STX_TOKEN_KEYWORD); + } + while (stc->token.type == TOKEN_KEYWORD); - pos = __add_symbol_literal (parser, name.buffer, name.size); - if (pos == -1) { - qse_stx_name_close (&name); - return -1; - } + pos = __add_symbol_literal (stc, name.buffer, name.size); + if (pos <= -1) goto oops; n = (is_super)? - __emit_send_to_super(parser,nargs,pos): - __emit_send_to_self(parser,nargs,pos); - if (n == -1) { - qse_stx_name_close (&name); - return -1; - } + __emit_send_to_super(stc,nargs,pos): + __emit_send_to_self(stc,nargs,pos); + if (n <= -1) goto oops; - qse_stx_name_close (&name); + qse_str_fini (&name); return 0; + +oops: + qse_str_fini (&name); + return -1; } -static int __parse_binary_message (qse_stx_parser_t* parser, qse_bool_t is_super) +static int __parse_binary_message (qse_stc_t* stc, qse_bool_t is_super) { /* * ::= binarySelector @@ -1212,36 +1281,43 @@ static int __parse_binary_message (qse_stx_parser_t* parser, qse_bool_t is_super qse_bool_t is_super2; int n; - if (__parse_unary_message (parser, is_super) == -1) return -1; + if (__parse_unary_message (stc, is_super) == -1) return -1; - while (parser->token.type == QSE_STX_TOKEN_BINARY) { - qse_char_t* op = qse_stx_token_yield (&parser->token, 0); - if (op == QSE_NULL) { - parser->error_code = QSE_STX_PARSER_ERROR_MEMORY; + while (stc->token.type == TOKEN_BINARY) + { + + YIELD_TOKEN_TO (stc, op); + if (op == QSE_NULL) + { + stc->error_code = QSE_STC_ERROR_MEMORY; return -1; } - GET_TOKEN (parser); - if (__parse_primary(parser, QSE_NULL, &is_super2) == -1) { + GET_TOKEN (stc); + if (__parse_primary(stc, QSE_NULL, &is_super2) == -1) + { qse_free (op); return -1; } - if (__parse_unary_message(parser, is_super2) == -1) { + if (__parse_unary_message(stc, is_super2) == -1) + { qse_free (op); return -1; } - pos = __add_symbol_literal (parser, op, qse_strlen(op)); - if (pos == -1) { + pos = __add_symbol_literal (stc, op, qse_strlen(op)); + if (pos == -1) + { qse_free (op); return -1; } n = (is_super)? - __emit_send_to_super(parser,2,pos): - __emit_send_to_self(parser,2,pos); - if (n == -1) { + __emit_send_to_super(stc,2,pos): + __emit_send_to_self(stc,2,pos); + if (n == -1) + { qse_free (op); return -1; } @@ -1252,180 +1328,183 @@ static int __parse_binary_message (qse_stx_parser_t* parser, qse_bool_t is_super return 0; } -static int __parse_unary_message (qse_stx_parser_t* parser, qse_bool_t is_super) +static int __parse_unary_message (qse_stc_t* stc, qse_bool_t is_super) { /* ::= unarySelector */ qse_word_t pos; int n; - while (parser->token.type == QSE_STX_TOKEN_IDENT) { - pos = __add_symbol_literal (parser, - parser->token.name.buffer, parser->token.name.size); + while (stc->token.type == TOKEN_IDENT) + { + pos = __add_symbol_literal (stc, + QSE_STR_PTR(&stc->token.name), + QSE_STR_LEN(&stc->token.name)); if (pos == -1) return -1; n = (is_super)? - __emit_send_to_super(parser,0,pos): - __emit_send_to_self(parser,0,pos); + __emit_send_to_super(stc,0,pos): + __emit_send_to_self(stc,0,pos); if (n == -1) return -1; - GET_TOKEN (parser); + GET_TOKEN (stc); } return 0; } -static int __get_token (qse_stx_parser_t* parser) +static int __get_token (qse_stc_t* stc) { qse_cint_t c; do { - if (__skip_spaces(parser) == -1) return -1; - if (parser->curc == QSE_T('"')) { - GET_CHAR (parser); - if (__skip_comment(parser) == -1) return -1; + if (__skip_spaces(stc) == -1) return -1; + if (stc->curc == QSE_T('"')) { + GET_CHAR (stc); + if (__skip_comment(stc) == -1) return -1; } else break; } while (1); - c = parser->curc; - qse_stx_token_clear (&parser->token); + c = stc->curc; - if (c == QSE_T_EOF) { - parser->token.type = QSE_STX_TOKEN_END; + CLEAR_TOKEN (); + + if (c == QSE_CHAR_EOF) { + stc->token.type = TOKEN_END; } else if (qse_isalpha(c)) { - if (__get_ident(parser) == -1) return -1; + if (__get_ident(stc) == -1) return -1; } else if (qse_isdigit(c)) { - if (__get_numlit(parser, qse_false) == -1) return -1; + if (__get_numlit(stc, qse_false) == -1) return -1; } else if (c == QSE_T('$')) { - GET_CHAR (parser); - if (__get_charlit(parser) == -1) return -1; + GET_CHAR (stc); + if (__get_charlit(stc) == -1) return -1; } else if (c == QSE_T('\'')) { - GET_CHAR (parser); - if (__get_strlit(parser) == -1) return -1; + GET_CHAR (stc); + if (__get_strlit(stc) == -1) return -1; } else if (c == QSE_T(':')) { - parser->token.type = QSE_STX_TOKEN_COLON; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_COLON; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); - c = parser->curc; + c = stc->curc; if (c == QSE_T('=')) { - parser->token.type = QSE_STX_TOKEN_ASSIGN; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_ASSIGN; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); } } else if (c == QSE_T('^')) { - parser->token.type = QSE_STX_TOKEN_RETURN; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_RETURN; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); } else if (c == QSE_T('[')) { - parser->token.type = QSE_STX_TOKEN_LBRACKET; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_LBRACKET; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); } else if (c == QSE_T(']')) { - parser->token.type = QSE_STX_TOKEN_RBRACKET; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_RBRACKET; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); } else if (c == QSE_T('(')) { - parser->token.type = QSE_STX_TOKEN_LPAREN; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_LPAREN; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); } else if (c == QSE_T(')')) { - parser->token.type = QSE_STX_TOKEN_RPAREN; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_RPAREN; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); } else if (c == QSE_T('#')) { - /*ADD_TOKEN_CHAR(parser, c);*/ - GET_CHAR (parser); + /*ADD_TOKEN_CHAR(stc, c);*/ + GET_CHAR (stc); - c = parser->curc; - if (c == QSE_T_EOF) { - parser->error_code = QSE_STX_PARSER_ERROR_LITERAL; + c = stc->curc; + if (c == QSE_CHAR_EOF) { + stc->error_code = QSE_STC_ERROR_LITERAL; return -1; } else if (c == QSE_T('(')) { - ADD_TOKEN_CHAR(parser, c); - parser->token.type = QSE_STX_TOKEN_APAREN; - GET_CHAR (parser); + ADD_TOKEN_CHAR(stc, c); + stc->token.type = TOKEN_APAREN; + GET_CHAR (stc); } else if (c == QSE_T('\'')) { - GET_CHAR (parser); - if (__get_strlit(parser) == -1) return -1; - parser->token.type = QSE_STX_TOKEN_SYMLIT; + GET_CHAR (stc); + if (__get_strlit(stc) == -1) return -1; + stc->token.type = TOKEN_SYMLIT; } else if (!__is_closing_char(c) && !qse_isspace(c)) { do { - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); - c = parser->curc; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); + c = stc->curc; } while (!__is_closing_char(c) && !qse_isspace(c)); - parser->token.type = QSE_STX_TOKEN_SYMLIT; + stc->token.type = TOKEN_SYMLIT; } else { - parser->error_code = QSE_STX_PARSER_ERROR_LITERAL; + stc->error_code = QSE_STC_ERROR_LITERAL; return -1; } } else if (c == QSE_T('.')) { - parser->token.type = QSE_STX_TOKEN_PERIOD; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_PERIOD; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); } else if (c == QSE_T(';')) { - parser->token.type = QSE_STX_TOKEN_SEMICOLON; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_SEMICOLON; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); } else if (__is_binary_char(c)) { - if (__get_binary(parser) == -1) return -1; + if (__get_binary(stc) == -1) return -1; } else { - parser->error_code = QSE_STX_PARSER_ERROR_CHAR; + stc->error_code = QSE_STC_ERROR_CHAR; return -1; } -//qse_printf (QSE_T("TOKEN: %s\n"), parser->token.name.buffer); +//qse_printf (QSE_T("TOKEN: %s\n"), QSE_STR_PTR(&stc->token.name)); return 0; } -static int __get_ident (qse_stx_parser_t* parser) +static int __get_ident (qse_stc_t* stc) { /* * identifier ::= letter (letter | digit)* * keyword ::= identifier ':' */ - qse_cint_t c = parser->curc; - parser->token.type = QSE_STX_TOKEN_IDENT; + qse_cint_t c = stc->curc; + stc->token.type = TOKEN_IDENT; do { - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); - c = parser->curc; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); + c = stc->curc; } while (qse_isalnum(c)); if (c == QSE_T(':')) { - ADD_TOKEN_CHAR (parser, c); - parser->token.type = QSE_STX_TOKEN_KEYWORD; - GET_CHAR (parser); + ADD_TOKEN_CHAR (stc, c); + stc->token.type = TOKEN_KEYWORD; + GET_CHAR (stc); } return 0; } -static int __get_numlit (qse_stx_parser_t* parser, qse_bool_t negated) +static int __get_numlit (qse_stc_t* stc, qse_bool_t negated) { /* * ::= ['-'] @@ -1445,39 +1524,39 @@ static int __get_numlit (qse_stx_parser_t* parser, qse_bool_t negated) * fractionalDigits ::= decimalInteger */ - qse_cint_t c = parser->curc; - parser->token.type = QSE_STX_TOKEN_NUMLIT; + qse_cint_t c = stc->curc; + stc->token.type = TOKEN_NUMLIT; do { - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); - c = parser->curc; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); + c = stc->curc; } while (qse_isalnum(c)); /* TODO; more */ return 0; } -static int __get_charlit (qse_stx_parser_t* parser) +static int __get_charlit (qse_stc_t* stc) { /* * character_literal ::= '$' character * character ::= "Any character in the implementation-defined character set" */ - qse_cint_t c = parser->curc; /* even a new-line or white space would be taken */ - if (c == QSE_T_EOF) { - parser->error_code = QSE_STX_PARSER_ERROR_CHARLIT; + qse_cint_t c = stc->curc; /* even a new-line or white space would be taken */ + if (c == QSE_CHAR_EOF) { + stc->error_code = QSE_STC_ERROR_CHARLIT; return -1; } - parser->token.type = QSE_STX_TOKEN_CHARLIT; - ADD_TOKEN_CHAR(parser, c); - GET_CHAR (parser); + stc->token.type = TOKEN_CHARLIT; + ADD_TOKEN_CHAR(stc, c); + GET_CHAR (stc); return 0; } -static int __get_strlit (qse_stx_parser_t* parser) +static int __get_strlit (qse_stc_t* stc) { /* * string_literal ::= stringDelimiter stringBody stringDelimiter @@ -1487,127 +1566,127 @@ static int __get_strlit (qse_stx_parser_t* parser) /* TODO: C-like string */ - qse_cint_t c = parser->curc; - parser->token.type = QSE_STX_TOKEN_STRLIT; + qse_cint_t c = stc->curc; + stc->token.type = TOKEN_STRLIT; do { do { - ADD_TOKEN_CHAR (parser, c); - GET_CHAR (parser); - c = parser->curc; + ADD_TOKEN_CHAR (stc, c); + GET_CHAR (stc); + c = stc->curc; - if (c == QSE_T_EOF) { - parser->error_code = QSE_STX_PARSER_ERROR_STRLIT; + if (c == QSE_CHAR_EOF) { + stc->error_code = QSE_STC_ERROR_STRLIT; return -1; } } while (c != QSE_T('\'')); - GET_CHAR (parser); - c = parser->curc; + GET_CHAR (stc); + c = stc->curc; } while (c == QSE_T('\'')); return 0; } -static int __get_binary (qse_stx_parser_t* parser) +static int __get_binary (qse_stc_t* stc) { /* * binarySelector ::= binaryCharacter+ */ - qse_cint_t c = parser->curc; - ADD_TOKEN_CHAR (parser, c); + qse_cint_t c = stc->curc; + ADD_TOKEN_CHAR (stc, c); if (c == QSE_T('-')) { - GET_CHAR (parser); - c = parser->curc; - if (qse_isdigit(c)) return __get_numlit(parser,qse_true); + GET_CHAR (stc); + c = stc->curc; + if (qse_isdigit(c)) return __get_numlit(stc,qse_true); } else { - GET_CHAR (parser); - c = parser->curc; + GET_CHAR (stc); + c = stc->curc; } /* up to 2 characters only */ if (__is_binary_char(c)) { - ADD_TOKEN_CHAR (parser, c); - GET_CHAR (parser); - c = parser->curc; + ADD_TOKEN_CHAR (stc, c); + GET_CHAR (stc); + c = stc->curc; } /* or up to any occurrences */ /* while (__is_binary_char(c)) { - ADD_TOKEN_CHAR (parser, c); - GET_CHAR (parser); - c = parser->curc; + ADD_TOKEN_CHAR (stc, c); + GET_CHAR (stc); + c = stc->curc; } */ - parser->token.type = QSE_STX_TOKEN_BINARY; + stc->token.type = TOKEN_BINARY; return 0; } -static int __skip_spaces (qse_stx_parser_t* parser) +static int __skip_spaces (qse_stc_t* stc) { - while (qse_isspace(parser->curc)) GET_CHAR (parser); + while (qse_isspace(stc->curc)) GET_CHAR (stc); return 0; } -static int __skip_comment (qse_stx_parser_t* parser) +static int __skip_comment (qse_stc_t* stc) { - while (parser->curc != QSE_T('"')) GET_CHAR (parser); - GET_CHAR (parser); + while (stc->curc != QSE_T('"')) GET_CHAR (stc); + GET_CHAR (stc); return 0; } -static int __get_char (qse_stx_parser_t* parser) +static int __get_char (qse_stc_t* stc) { qse_cint_t c; - if (parser->ungotc_count > 0) { - parser->curc = parser->ungotc[parser->ungotc_count--]; + if (stc->ungotc_count > 0) { + stc->curc = stc->ungotc[stc->ungotc_count--]; } else { - if (parser->input_func ( - QSE_STX_PARSER_INPUT_CONSUME, - parser->input_owner, (void*)&c) == -1) { - parser->error_code = QSE_STX_PARSER_ERROR_INPUT; + if (stc->input_func ( + QSE_STC_INPUT_CONSUME, + stc->input_owner, (void*)&c) == -1) { + stc->error_code = QSE_STC_ERROR_INPUT; return -1; } - parser->curc = c; + stc->curc = c; } return 0; } -static int __unget_char (qse_stx_parser_t* parser, qse_cint_t c) +static int __unget_char (qse_stc_t* stc, qse_cint_t c) { - if (parser->ungotc_count >= qse_countof(parser->ungotc)) return -1; - parser->ungotc[parser->ungotc_count++] = c; + if (stc->ungotc_count >= QSE_COUNTOF(stc->ungotc)) return -1; + stc->ungotc[stc->ungotc_count++] = c; return 0; } -static int __open_input (qse_stx_parser_t* parser, void* input) +static int __open_input (qse_stc_t* stc, void* input) { - if (parser->input_func( - QSE_STX_PARSER_INPUT_OPEN, - (void*)&parser->input_owner, input) == -1) { - parser->error_code = QSE_STX_PARSER_ERROR_INPUT; + if (stc->input_func( + QSE_STC_INPUT_OPEN, + (void*)&stc->input_owner, input) == -1) { + stc->error_code = QSE_STC_ERROR_INPUT; return -1; } - parser->error_code = QSE_STX_PARSER_ERROR_NONE; - parser->curc = QSE_T_EOF; - parser->ungotc_count = 0; + stc->error_code = QSE_STC_ERROR_NONE; + stc->curc = QSE_CHAR_EOF; + stc->ungotc_count = 0; return 0; } -static int __close_input (qse_stx_parser_t* parser) +static int __close_input (qse_stc_t* stc) { - if (parser->input_func( - QSE_STX_PARSER_INPUT_CLOSE, - parser->input_owner, QSE_NULL) == -1) { - parser->error_code = QSE_STX_PARSER_ERROR_INPUT; + if (stc->input_func( + QSE_STC_INPUT_CLOSE, + stc->input_owner, QSE_NULL) == -1) { + stc->error_code = QSE_STC_ERROR_INPUT; return -1; } diff --git a/qse/lib/stx/par.h b/qse/lib/stx/par.h index d0de7e05..131fbc00 100644 --- a/qse/lib/stx/par.h +++ b/qse/lib/stx/par.h @@ -1,73 +1,75 @@ /* - * $Id: parser.h 118 2008-03-03 11:21:33Z baconevi $ + * $Id: stc.h 118 2008-03-03 11:21:33Z baconevi $ */ -#ifndef _QSE_STX_PARSER_H_ -#define _QSE_STX_PARSER_H_ +#ifndef _QSE_LIB_STX_PAR_H_ +#define _QSE_LIB_STX_PAR_H_ -#include -#include -#include -#include +#include "stx.h" + +#include +#include enum { - QSE_STX_PARSER_ERROR_NONE, + QSE_STC_ERROR_NONE, /* system errors */ - QSE_STX_PARSER_ERROR_INPUT_FUNC, - QSE_STX_PARSER_ERROR_INPUT, - QSE_STX_PARSER_ERROR_MEMORY, + QSE_STC_ERROR_INPUT_FUNC, + QSE_STC_ERROR_INPUT, + QSE_STC_ERROR_MEMORY, /* lexical errors */ - QSE_STX_PARSER_ERROR_CHAR, - QSE_STX_PARSER_ERROR_CHARLIT, - QSE_STX_PARSER_ERROR_STRLIT, - QSE_STX_PARSER_ERROR_LITERAL, + QSE_STC_ERROR_CHAR, + QSE_STC_ERROR_CHARLIT, + QSE_STC_ERROR_STRLIT, + QSE_STC_ERROR_LITERAL, /* syntatic error */ - QSE_STX_PARSER_ERROR_MESSAGE_SELECTOR, - QSE_STX_PARSER_ERROR_ARGUMENT_NAME, - QSE_STX_PARSER_ERROR_TOO_MANY_ARGUMENTS, + QSE_STC_ERROR_MESSAGE_SELECTOR, + QSE_STC_ERROR_ARGUMENT_NAME, + QSE_STC_ERROR_TOO_MANY_ARGUMENTS, - QSE_STX_PARSER_ERROR_PRIMITIVE_KEYWORD, - QSE_STX_PARSER_ERROR_PRIMITIVE_NUMBER, - QSE_STX_PARSER_ERROR_PRIMITIVE_NUMBER_RANGE, - QSE_STX_PARSER_ERROR_PRIMITIVE_NOT_CLOSED, + QSE_STC_ERROR_PRIMITIVE_KEYWORD, + QSE_STC_ERROR_PRIMITIVE_NUMBER, + QSE_STC_ERROR_PRIMITIVE_NUMBER_RANGE, + QSE_STC_ERROR_PRIMITIVE_NOT_CLOSED, - QSE_STX_PARSER_ERROR_TEMPORARIES_NOT_CLOSED, - QSE_STX_PARSER_ERROR_TOO_MANY_TEMPORARIES, - QSE_STX_PARSER_ERROR_PSEUDO_VARIABLE, - QSE_STX_PARSER_ERROR_PRIMARY, + QSE_STC_ERROR_TEMPORARIES_NOT_CLOSED, + QSE_STC_ERROR_TOO_MANY_TEMPORARIES, + QSE_STC_ERROR_PSEUDO_VARIABLE, + QSE_STC_ERROR_PRIMARY, - QSE_STX_PARSER_ERROR_NO_PERIOD, - QSE_STX_PARSER_ERROR_NO_RPAREN, - QSE_STX_PARSER_ERROR_BLOCK_ARGUMENT_NAME, - QSE_STX_PARSER_ERROR_BLOCK_ARGUMENT_LIST, - QSE_STX_PARSER_ERROR_BLOCK_NOT_CLOSED, + QSE_STC_ERROR_NO_PERIOD, + QSE_STC_ERROR_NO_RPAREN, + QSE_STC_ERROR_BLOCK_ARGUMENT_NAME, + QSE_STC_ERROR_BLOCK_ARGUMENT_LIST, + QSE_STC_ERROR_BLOCK_NOT_CLOSED, - QSE_STX_PARSER_ERROR_UNDECLARED_NAME, - QSE_STX_PARSER_ERROR_TOO_MANY_LITERALS + QSE_STC_ERROR_UNDECLARED_NAME, + QSE_STC_ERROR_TOO_MANY_LITERALS }; enum { /* input_func cmd */ - QSE_STX_PARSER_INPUT_OPEN, - QSE_STX_PARSER_INPUT_CLOSE, - QSE_STX_PARSER_INPUT_CONSUME, - QSE_STX_PARSER_INPUT_REWIND + QSE_STC_INPUT_OPEN, + QSE_STC_INPUT_CLOSE, + QSE_STC_INPUT_CONSUME, + QSE_STC_INPUT_REWIND }; -typedef struct qse_stx_parser_t qse_stx_parser_t; +typedef struct qse_stc_t qse_stc_t; -struct qse_stx_parser_t +struct qse_stc_t { + qse_mmgr_t* mmgr; + qse_stx_t* stx; int error_code; qse_word_t method_class; - qse_stx_name_t method_name; + qse_str_t method_name; qse_char_t* temporaries[256]; /* TODO: different size? or dynamic? */ qse_word_t argument_count; @@ -76,29 +78,56 @@ struct qse_stx_parser_t qse_word_t literals[256]; /* TODO: make it a dynamic array */ qse_word_t literal_count; - qse_arr_t bytecode; + qse_lda_t bytecode; + + struct + { + int type; + /* + qse_stx_int_t ivalue; + qse_stx_real_t fvalue; + */ + qse_str_t name; + } token; - qse_stx_token_t token; qse_cint_t curc; qse_cint_t ungotc[5]; qse_size_t ungotc_count; void* input_owner; int (*input_func) (int cmd, void* owner, void* arg); - - qse_bool_t __dynamic; }; #ifdef __cplusplus extern "C" { #endif -qse_stx_parser_t* qse_stx_parser_open (qse_stx_parser_t* parser, qse_stx_t* stx); -void qse_stx_parser_close (qse_stx_parser_t* parser); +qse_stc_t* qse_stc_open ( + qse_mmgr_t* mmgr, + qse_size_t xtnsize, + qse_stx_t* stx +); -const qse_char_t* qse_stx_parser_error_string (qse_stx_parser_t* parser); -int qse_stx_parser_parse_method ( - qse_stx_parser_t* parser, qse_word_t method_class, void* input); +void qse_stc_close ( + qse_stc_t* stc +); + +qse_stc_t* qse_stc_init ( + qse_stc_t* stc, + qse_mmgr_t* mmgr, + qse_stx_t* stx +); + +void qse_stc_fini ( + qse_stc_t* stc +); + + +int qse_stc_parsemethod ( + qse_stc_t* stc, + qse_word_t method_class, + void* input +); #ifdef __cplusplus }