*fixed a crash bug with conflicting routine and class identifier.
*fixed a dangling pointer bug with incomplete structures. *fixed a memory leak with wrong routine or class identifier. *fixed a memory leak with incomplete structures.
This commit is contained in:
parent
5e52e72cf7
commit
ef73407de3
12
HISTORY
12
HISTORY
@ -1,18 +1,24 @@
|
|||||||
|
Nov. 5 2017
|
||||||
|
Fixed a crash bug with conflicting routine and class identifier
|
||||||
|
Fixed a dangling pointer bug with incomplete structures
|
||||||
|
Fixed a memory leak with wrong routine or class identifier
|
||||||
|
Fixed a memory leak with incomplete structures
|
||||||
|
|
||||||
Nov. 1 2017
|
Nov. 1 2017
|
||||||
Added some location parameters to the mb_get_last_error function
|
Added some location parameters to the mb_get_last_error function
|
||||||
|
|
||||||
Oct. 30 2017
|
Oct. 30 2017
|
||||||
Added support to apply the STR statement to a type value
|
Added support to apply the STR statement to a type value
|
||||||
Fixed a referencing bug with an unnamed array
|
Fixed a referencing bug with unnamed array
|
||||||
|
|
||||||
Oct. 29 2017
|
Oct. 29 2017
|
||||||
Fixed a crash bug when access an unnamed array
|
Fixed a crash bug when access an unnamed array
|
||||||
|
|
||||||
Oct. 25 2017
|
Oct. 25 2017
|
||||||
Fixed a memory leak with an unexpected value
|
Fixed a memory leak with unexpected value
|
||||||
|
|
||||||
Oct. 24 2017
|
Oct. 24 2017
|
||||||
Fixed a memory leak with a hanged value
|
Fixed a memory leak with dangling value
|
||||||
|
|
||||||
Oct. 23 2017
|
Oct. 23 2017
|
||||||
Added support to apply the CLONE statement to a referenced usertype
|
Added support to apply the CLONE statement to a referenced usertype
|
||||||
|
@ -1456,6 +1456,8 @@ static void _end_of_file(_parsing_context_t* context);
|
|||||||
#define _RETURN_CHAR '\r'
|
#define _RETURN_CHAR '\r'
|
||||||
#define _STRING_POSTFIX_CHAR '$'
|
#define _STRING_POSTFIX_CHAR '$'
|
||||||
#define _DUMMY_ASSIGN_CHAR "#"
|
#define _DUMMY_ASSIGN_CHAR "#"
|
||||||
|
#define _INVALID_CLASS_CHAR 0x18
|
||||||
|
#define _INVALID_ROUTINE_CHAR 0x1B
|
||||||
|
|
||||||
#define _REMARK_STR "REM"
|
#define _REMARK_STR "REM"
|
||||||
|
|
||||||
@ -5189,6 +5191,8 @@ static int _create_symbol(mb_interpreter_t* s, _ls_node_t* l, char* sym, _object
|
|||||||
break;
|
break;
|
||||||
#ifdef MB_ENABLE_CLASS
|
#ifdef MB_ENABLE_CLASS
|
||||||
case _DT_CLASS:
|
case _DT_CLASS:
|
||||||
|
if(!_is_identifier_char(*sym))
|
||||||
|
*sym = _INVALID_CLASS_CHAR;
|
||||||
glbsyminscope = _search_identifier_in_scope_chain(s, 0, sym, _PATHING_NONE, 0, 0);
|
glbsyminscope = _search_identifier_in_scope_chain(s, 0, sym, _PATHING_NONE, 0, 0);
|
||||||
if(glbsyminscope && ((_object_t*)glbsyminscope->data)->type == _DT_CLASS) {
|
if(glbsyminscope && ((_object_t*)glbsyminscope->data)->type == _DT_CLASS) {
|
||||||
(*obj)->data.instance = ((_object_t*)glbsyminscope->data)->data.instance;
|
(*obj)->data.instance = ((_object_t*)glbsyminscope->data)->data.instance;
|
||||||
@ -5200,15 +5204,11 @@ static int _create_symbol(mb_interpreter_t* s, _ls_node_t* l, char* sym, _object
|
|||||||
_push_scope_by_class(s, (*obj)->data.instance->scope);
|
_push_scope_by_class(s, (*obj)->data.instance->scope);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
_var_t* var = 0;
|
|
||||||
|
|
||||||
tmp.instance = (_class_t*)mb_malloc(sizeof(_class_t));
|
tmp.instance = (_class_t*)mb_malloc(sizeof(_class_t));
|
||||||
_init_class(s, tmp.instance, sym);
|
_init_class(s, tmp.instance, sym);
|
||||||
_push_scope_by_class(s, tmp.instance->scope);
|
_push_scope_by_class(s, tmp.instance->scope);
|
||||||
s->last_instance = tmp.instance;
|
s->last_instance = tmp.instance;
|
||||||
|
|
||||||
mb_unrefvar(var);
|
|
||||||
|
|
||||||
(*obj)->data.instance = tmp.instance;
|
(*obj)->data.instance = tmp.instance;
|
||||||
|
|
||||||
ul = _ht_set_or_insert(running->var_dict, sym, *obj);
|
ul = _ht_set_or_insert(running->var_dict, sym, *obj);
|
||||||
@ -5223,6 +5223,8 @@ static int _create_symbol(mb_interpreter_t* s, _ls_node_t* l, char* sym, _object
|
|||||||
break;
|
break;
|
||||||
#endif /* MB_ENABLE_CLASS */
|
#endif /* MB_ENABLE_CLASS */
|
||||||
case _DT_ROUTINE:
|
case _DT_ROUTINE:
|
||||||
|
if(!_is_identifier_char(*sym))
|
||||||
|
*sym = _INVALID_ROUTINE_CHAR;
|
||||||
glbsyminscope = _search_identifier_in_scope_chain(s, 0, sym, _PATHING_NONE, 0, 0);
|
glbsyminscope = _search_identifier_in_scope_chain(s, 0, sym, _PATHING_NONE, 0, 0);
|
||||||
if(glbsyminscope && ((_object_t*)glbsyminscope->data)->type == _DT_ROUTINE) {
|
if(glbsyminscope && ((_object_t*)glbsyminscope->data)->type == _DT_ROUTINE) {
|
||||||
(*obj)->data.routine = ((_object_t*)glbsyminscope->data)->data.routine;
|
(*obj)->data.routine = ((_object_t*)glbsyminscope->data)->data.routine;
|
||||||
@ -5514,6 +5516,8 @@ _end_import:
|
|||||||
#ifdef MB_ENABLE_CLASS
|
#ifdef MB_ENABLE_CLASS
|
||||||
if(context->last_symbol) {
|
if(context->last_symbol) {
|
||||||
glbsyminscope = _search_identifier_in_scope_chain(s, 0, sym, _PATHING_NONE, 0, 0);
|
glbsyminscope = _search_identifier_in_scope_chain(s, 0, sym, _PATHING_NONE, 0, 0);
|
||||||
|
if(glbsyminscope && ((_object_t*)glbsyminscope->data)->type == _DT_ROUTINE)
|
||||||
|
goto _routine;
|
||||||
if(glbsyminscope && ((_object_t*)glbsyminscope->data)->type == _DT_CLASS) {
|
if(glbsyminscope && ((_object_t*)glbsyminscope->data)->type == _DT_CLASS) {
|
||||||
if(_IS_FUNC(context->last_symbol, _core_class)) {
|
if(_IS_FUNC(context->last_symbol, _core_class)) {
|
||||||
_handle_error_now(s, SE_RN_DUPLICATE_CLASS, s->source_file, MB_FUNC_ERR);
|
_handle_error_now(s, SE_RN_DUPLICATE_CLASS, s->source_file, MB_FUNC_ERR);
|
||||||
@ -5558,6 +5562,7 @@ _end_import:
|
|||||||
_pop_scope(s, false);
|
_pop_scope(s, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
_routine:
|
||||||
#endif /* MB_ENABLE_CLASS */
|
#endif /* MB_ENABLE_CLASS */
|
||||||
/* _routine_t */
|
/* _routine_t */
|
||||||
if(context->last_symbol && !_is_bracket_char(sym[0])) {
|
if(context->last_symbol && !_is_bracket_char(sym[0])) {
|
||||||
@ -5709,7 +5714,7 @@ static int _parse_char(mb_interpreter_t* s, const char* str, int n, int pos, uns
|
|||||||
int result = MB_FUNC_OK;
|
int result = MB_FUNC_OK;
|
||||||
_parsing_context_t* context = 0;
|
_parsing_context_t* context = 0;
|
||||||
char last_char = _ZERO_CHAR;
|
char last_char = _ZERO_CHAR;
|
||||||
char c = '\0';
|
char c = _ZERO_CHAR;
|
||||||
#ifdef MB_ENABLE_UNICODE_ID
|
#ifdef MB_ENABLE_UNICODE_ID
|
||||||
unsigned uc = 0;
|
unsigned uc = 0;
|
||||||
#else /* MB_ENABLE_UNICODE_ID */
|
#else /* MB_ENABLE_UNICODE_ID */
|
||||||
@ -6102,7 +6107,7 @@ static void _real_to_str(real_t r, char* str, size_t size, size_t afterpoint) {
|
|||||||
if(--afterpoint == 0)
|
if(--afterpoint == 0)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
str[pos] = '\0';
|
str[pos] = _ZERO_CHAR;
|
||||||
}
|
}
|
||||||
#endif /* MB_MANUAL_REAL_FORMATTING */
|
#endif /* MB_MANUAL_REAL_FORMATTING */
|
||||||
|
|
||||||
@ -10425,17 +10430,27 @@ static void _tidy_scope_chain(mb_interpreter_t* s) {
|
|||||||
mb_assert(s);
|
mb_assert(s);
|
||||||
|
|
||||||
context = s->parsing_context;
|
context = s->parsing_context;
|
||||||
if(!context)
|
if(!context) {
|
||||||
|
while(s->running_context->prev)
|
||||||
|
_pop_scope(s, false);
|
||||||
|
|
||||||
return;
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
while(context->routine_state && s->running_context->meta != _SCOPE_META_ROOT) {
|
while(context->routine_state && s->running_context->meta != _SCOPE_META_ROOT) {
|
||||||
if(_end_routine(s))
|
if(_end_routine(s)) {
|
||||||
|
if(!s->running_context->prev)
|
||||||
|
break;
|
||||||
_pop_scope(s, false);
|
_pop_scope(s, false);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
#ifdef MB_ENABLE_CLASS
|
#ifdef MB_ENABLE_CLASS
|
||||||
while(context->class_state != _CLASS_STATE_NONE) {
|
while(context->class_state != _CLASS_STATE_NONE) {
|
||||||
if(_end_class(s))
|
if(_end_class(s)) {
|
||||||
|
if(!s->running_context->prev)
|
||||||
|
break;
|
||||||
_pop_scope(s, false);
|
_pop_scope(s, false);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
#endif /* MB_ENABLE_CLASS */
|
#endif /* MB_ENABLE_CLASS */
|
||||||
}
|
}
|
||||||
@ -11830,7 +11845,6 @@ int mb_reset(struct mb_interpreter_t** s, bool_t clrf) {
|
|||||||
int result = MB_FUNC_OK;
|
int result = MB_FUNC_OK;
|
||||||
_ht_node_t* global_scope = 0;
|
_ht_node_t* global_scope = 0;
|
||||||
_ls_node_t* ast;
|
_ls_node_t* ast;
|
||||||
_parsing_context_t* context = 0;
|
|
||||||
_running_context_t* running = 0;
|
_running_context_t* running = 0;
|
||||||
|
|
||||||
if(!s || !(*s))
|
if(!s || !(*s))
|
||||||
@ -11839,6 +11853,10 @@ int mb_reset(struct mb_interpreter_t** s, bool_t clrf) {
|
|||||||
(*s)->run_count = 0;
|
(*s)->run_count = 0;
|
||||||
(*s)->has_run = false;
|
(*s)->has_run = false;
|
||||||
(*s)->jump_set = _JMP_NIL;
|
(*s)->jump_set = _JMP_NIL;
|
||||||
|
#ifdef MB_ENABLE_CLASS
|
||||||
|
(*s)->last_instance = 0;
|
||||||
|
(*s)->calling = false;
|
||||||
|
#endif /* MB_ENABLE_CLASS */
|
||||||
(*s)->last_routine = 0;
|
(*s)->last_routine = 0;
|
||||||
(*s)->no_eat_comma_mark = 0;
|
(*s)->no_eat_comma_mark = 0;
|
||||||
(*s)->handled_error = false;
|
(*s)->handled_error = false;
|
||||||
@ -11850,8 +11868,6 @@ int mb_reset(struct mb_interpreter_t** s, bool_t clrf) {
|
|||||||
running->next_loop_var = 0;
|
running->next_loop_var = 0;
|
||||||
memset(&(running->intermediate_value), 0, sizeof(mb_value_t));
|
memset(&(running->intermediate_value), 0, sizeof(mb_value_t));
|
||||||
|
|
||||||
(*s)->parsing_context = context = _reset_parsing_context((*s)->parsing_context);
|
|
||||||
|
|
||||||
ast = (*s)->ast;
|
ast = (*s)->ast;
|
||||||
_ls_foreach(ast, _destroy_object);
|
_ls_foreach(ast, _destroy_object);
|
||||||
_ls_clear(ast);
|
_ls_clear(ast);
|
||||||
@ -11865,8 +11881,11 @@ int mb_reset(struct mb_interpreter_t** s, bool_t clrf) {
|
|||||||
_ls_clear((*s)->multiline_enabled);
|
_ls_clear((*s)->multiline_enabled);
|
||||||
#endif /* _MULTILINE_STATEMENT */
|
#endif /* _MULTILINE_STATEMENT */
|
||||||
|
|
||||||
|
_tidy_scope_chain(*s);
|
||||||
_clear_scope_chain(*s);
|
_clear_scope_chain(*s);
|
||||||
|
|
||||||
|
(*s)->parsing_context = _reset_parsing_context((*s)->parsing_context);
|
||||||
|
|
||||||
if(clrf) {
|
if(clrf) {
|
||||||
#ifdef MB_ENABLE_MODULE
|
#ifdef MB_ENABLE_MODULE
|
||||||
global_scope = (*s)->module_func_dict;
|
global_scope = (*s)->module_func_dict;
|
||||||
@ -13866,6 +13885,7 @@ int mb_run(struct mb_interpreter_t* s, bool_t clear_parser) {
|
|||||||
s->parsing_context->routine_state = 0;
|
s->parsing_context->routine_state = 0;
|
||||||
result = MB_FUNC_ERR;
|
result = MB_FUNC_ERR;
|
||||||
_handle_error_now(s, SE_RN_INCOMPLETE_ROUTINE, s->source_file, result);
|
_handle_error_now(s, SE_RN_INCOMPLETE_ROUTINE, s->source_file, result);
|
||||||
|
_tidy_scope_chain(s);
|
||||||
|
|
||||||
goto _exit;
|
goto _exit;
|
||||||
}
|
}
|
||||||
@ -13874,6 +13894,7 @@ int mb_run(struct mb_interpreter_t* s, bool_t clear_parser) {
|
|||||||
s->parsing_context->class_state = _CLASS_STATE_NONE;
|
s->parsing_context->class_state = _CLASS_STATE_NONE;
|
||||||
result = MB_FUNC_ERR;
|
result = MB_FUNC_ERR;
|
||||||
_handle_error_now(s, SE_RN_INCOMPLETE_CLASS, s->source_file, result);
|
_handle_error_now(s, SE_RN_INCOMPLETE_CLASS, s->source_file, result);
|
||||||
|
_tidy_scope_chain(s);
|
||||||
|
|
||||||
goto _exit;
|
goto _exit;
|
||||||
}
|
}
|
||||||
@ -13930,6 +13951,8 @@ int mb_run(struct mb_interpreter_t* s, bool_t clear_parser) {
|
|||||||
|
|
||||||
_exit:
|
_exit:
|
||||||
if(s) {
|
if(s) {
|
||||||
|
if(!s->suspent_point)
|
||||||
|
s->source_file = 0;
|
||||||
if(clear_parser)
|
if(clear_parser)
|
||||||
_destroy_parsing_context(&s->parsing_context);
|
_destroy_parsing_context(&s->parsing_context);
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user