X-Git-Url: https://deadsoftware.ru/gitweb?p=dsw-obn.git;a=blobdiff_plain;f=src%2Foberon.c;h=82566471b9a11b929d832f2d51ef355aa4d23dfc;hp=1b7f5d9b19315aa614ef96e1665f21c11054da9b;hb=dd188cb697c08d52aefb144a4f3a943dbf3388c5;hpb=afdfb61e64fb9c7d05a7612812739aa0d9a560fc diff --git a/src/oberon.c b/src/oberon.c index 1b7f5d9..8256647 100644 --- a/src/oberon.c +++ b/src/oberon.c @@ -305,6 +305,21 @@ oberon_find_object(oberon_scope_t * scope, char * name, bool check_it) return result; } +static oberon_object_t * +oberon_find_object_in_scope(oberon_scope_t * scope, char * name, bool check_it) +{ + oberon_object_t * result = NULL; + + result = oberon_find_object_in_list(scope -> list, name); + + if(check_it && result == NULL) + { + oberon_error(scope -> ctx, "undefined ident %s", name); + } + + return result; +} + static oberon_object_t * oberon_create_object(oberon_scope_t * scope, char * name, int class, bool export, bool read_only) { @@ -2447,6 +2462,12 @@ oberon_proc_decl(oberon_context_t * ctx) char * name; int export; int read_only; + + if(ctx -> token == STAR) + { + oberon_assert_token(ctx, STAR); + } + name = oberon_assert_ident(ctx); oberon_def(ctx, &export, &read_only); @@ -2463,7 +2484,7 @@ oberon_proc_decl(oberon_context_t * ctx) oberon_close_scope(ctx -> decl); oberon_object_t * proc; - proc = oberon_find_object(ctx -> decl, name, 0); + proc = oberon_find_object_in_scope(ctx -> decl, name, 0); if(proc == NULL) { proc = oberon_define_object(ctx -> decl, name, OBERON_CLASS_PROC, export, read_only, false); @@ -2631,9 +2652,8 @@ oberon_field_list(oberon_context_t * ctx, oberon_type_t * rec, oberon_scope_t * static void oberon_type_record_body(oberon_context_t * ctx, oberon_type_t * rec) { - oberon_scope_t * modscope = ctx -> mod -> decl; oberon_scope_t * oldscope = ctx -> decl; - ctx -> decl = modscope; + ctx -> decl = oldscope; if(ctx -> token == LPAREN) { @@ -2674,11 +2694,11 @@ oberon_type_record_body(oberon_context_t * ctx, oberon_type_t * rec) this_scope -> parent = NULL; this_scope -> parent_type = rec; - oberon_field_list(ctx, rec, modscope); + oberon_field_list(ctx, rec, oldscope); while(ctx -> token == SEMICOLON) { oberon_assert_token(ctx, SEMICOLON); - oberon_field_list(ctx, rec, modscope); + oberon_field_list(ctx, rec, oldscope); } rec -> scope = this_scope; @@ -3142,33 +3162,34 @@ oberon_prevent_undeclarated_procedures(oberon_context_t * ctx) static void oberon_decl_seq(oberon_context_t * ctx) { - if(ctx -> token == CONST) + while(ctx -> token >= CONST && ctx -> token <= VAR) { - oberon_assert_token(ctx, CONST); - while(ctx -> token == IDENT) + if(ctx -> token == CONST) { - oberon_const_decl(ctx); - oberon_assert_token(ctx, SEMICOLON); + oberon_assert_token(ctx, CONST); + while(ctx -> token == IDENT) + { + oberon_const_decl(ctx); + oberon_assert_token(ctx, SEMICOLON); + } } - } - - if(ctx -> token == TYPE) - { - oberon_assert_token(ctx, TYPE); - while(ctx -> token == IDENT) + else if(ctx -> token == TYPE) { - oberon_type_decl(ctx); - oberon_assert_token(ctx, SEMICOLON); + oberon_assert_token(ctx, TYPE); + while(ctx -> token == IDENT) + { + oberon_type_decl(ctx); + oberon_assert_token(ctx, SEMICOLON); + } } - } - - if(ctx -> token == VAR) - { - oberon_assert_token(ctx, VAR); - while(ctx -> token == IDENT) + else if(ctx -> token == VAR) { - oberon_var_decl(ctx); - oberon_assert_token(ctx, SEMICOLON); + oberon_assert_token(ctx, VAR); + while(ctx -> token == IDENT) + { + oberon_var_decl(ctx); + oberon_assert_token(ctx, SEMICOLON); + } } } @@ -3322,44 +3343,38 @@ oberon_case_statement(oberon_context_t * ctx) static void oberon_with_guard_do(oberon_context_t * ctx, gen_label_t * end) { - oberon_expr_t * val; - oberon_expr_t * var; - oberon_expr_t * type; + oberon_object_t * var; + oberon_expr_t * var_expr; + oberon_expr_t * type_expr; oberon_expr_t * cond; - oberon_expr_t * cast; + oberon_type_t * type; oberon_type_t * old_type; - gen_var_t * old_var; gen_label_t * this_end; this_end = oberon_generator_reserve_label(ctx); - var = oberon_qualident_expr(ctx); + var_expr = oberon_qualident_expr(ctx); oberon_assert_token(ctx, COLON); - type = oberon_qualident_expr(ctx); - cond = oberon_make_bin_op(ctx, IS, var, type); + type_expr = oberon_qualident_expr(ctx); + cond = oberon_make_bin_op(ctx, IS, var_expr, type_expr); + + var = var_expr -> item.var; + type = type_expr -> result; + old_type = var -> type; oberon_assert_token(ctx, DO); oberon_generate_branch(ctx, cond, false, this_end); - /* Сохраняем ссылку во временной переменной */ - val = oberon_make_temp_var_item(ctx, type -> result); - //cast = oberno_make_record_cast(ctx, var, type -> result); - cast = oberon_cast_expr(ctx, var, type -> result); - oberon_assign(ctx, cast, val); - /* Подменяем тип у оригинальной переменной */ - old_type = var -> item.var -> type; - var -> item.var -> type = type -> result; - /* Подменяем ссылку на переменную */ - old_var = var -> item.var -> gen_var; - var -> item.var -> gen_var = val -> item.var -> gen_var; + var -> type = type; + oberon_set_typecheck(var, true); oberon_statement_seq(ctx); + + var -> type = old_type; + oberon_set_typecheck(var, false); + oberon_generate_goto(ctx, end); oberon_generate_label(ctx, this_end); - - /* Возвращаем исходное состояние */ - var -> item.var -> gen_var = old_var; - var -> item.var -> type = old_type; } static void @@ -4964,7 +4979,10 @@ oberon_create_context(ModuleImportCallback import_module) /* Types */ oberon_new_intrinsic_type(ctx, "BYTE", ctx -> system_byte_type); oberon_new_intrinsic_type(ctx, "PTR", ctx -> system_ptr_type); + oberon_new_intrinsic_type(ctx, "INT8", ctx -> byte_type); + oberon_new_intrinsic_type(ctx, "INT16", ctx -> shortint_type); oberon_new_intrinsic_type(ctx, "INT32", ctx -> int_type); + oberon_new_intrinsic_type(ctx, "INT64", ctx -> longint_type); oberon_new_intrinsic_type(ctx, "SET32", ctx -> set_type); /* Functions */