From 81f11051a4e23daabb0ba7c99a6fe6730c7f1c84 Mon Sep 17 00:00:00 2001 From: yui-knk Date: Mon, 29 May 2023 16:44:28 +0900 Subject: [PATCH] wip --- ast.c | 10 +-- compile.c | 6 +- debug.c | 2 +- node.c | 80 ++++++++++++++++---- node.h | 13 +++- node_dump.c | 4 +- parse.y | 181 ++++++++++++++++++++++++++++++++++++++++----- ruby_parser.c | 2 + st2.c | 148 ++---------------------------------- universal_parser.c | 3 + 10 files changed, 266 insertions(+), 183 deletions(-) diff --git a/ast.c b/ast.c index 76875833390c7c..d3e217dafcca2a 100644 --- a/ast.c +++ b/ast.c @@ -277,9 +277,9 @@ rb_ast_node_alloc(VALUE klass) } static const char* -node_type_to_str(rb_ast_t *ast, const NODE *node) +node_type_to_str(const NODE *node) { - return (ruby_node_name(nd_type(node), rb_bug) + rb_strlen_lit("NODE_")); + return (ruby_node_name(nd_type(node)) + rb_strlen_lit("NODE_")); } static VALUE @@ -288,7 +288,7 @@ ast_node_type(rb_execution_context_t *ec, VALUE self) struct ASTNodeData *data; TypedData_Get_Struct(self, struct ASTNodeData, &rb_node_type, data); - return rb_sym_intern_ascii_cstr(node_type_to_str(data->ast, data->node)); + return rb_sym_intern_ascii_cstr(node_type_to_str(data->node)); } static VALUE @@ -675,7 +675,7 @@ node_children(rb_ast_t *ast, const NODE *node) break; } - rb_bug("node_children: unknown node: %s", ruby_node_name(type, rb_bug)); + rb_bug("node_children: unknown node: %s", ruby_node_name(type)); } static VALUE @@ -745,7 +745,7 @@ ast_node_inspect(rb_execution_context_t *ec, VALUE self) rb_str_append(str, cname); rb_str_catf(str, ":%s@%d:%d-%d:%d>", - node_type_to_str(data->ast, data->node), + node_type_to_str(data->node), nd_first_lineno(data->node), nd_first_column(data->node), nd_last_lineno(data->node), nd_last_column(data->node)); diff --git a/compile.c b/compile.c index a6505c41214bb3..7ceb936f06d405 100644 --- a/compile.c +++ b/compile.c @@ -404,7 +404,7 @@ do { \ if (error_type != (ndtype)) { \ COMPILE_ERROR(ERROR_ARGS_AT(error_node) \ prefix ": " #ndtype " is expected, but %s", \ - ruby_node_name(error_type, rb_bug)); \ + ruby_node_name(error_type)); \ return errval; \ } \ } while (0) @@ -420,7 +420,7 @@ do { \ do { \ const NODE *error_node = (node); \ COMPILE_ERROR(ERROR_ARGS_AT(error_node) prefix ": unknown node (%s)", \ - ruby_node_name(nd_type(error_node), rb_bug)); \ + ruby_node_name(nd_type(error_node))); \ return errval; \ } while (0) @@ -8910,7 +8910,7 @@ compile_op_cdecl(rb_iseq_t *iseq, LINK_ANCHOR *const ret, const NODE *const node break; default: COMPILE_ERROR(ERROR_ARGS "%s: invalid node in NODE_OP_CDECL", - ruby_node_name(nd_type(node->nd_head), rb_bug)); + ruby_node_name(nd_type(node->nd_head))); return COMPILE_NG; } mid = node->nd_head->nd_mid; diff --git a/debug.c b/debug.c index 61051a025f51a7..d3f41f1a3a1ebe 100644 --- a/debug.c +++ b/debug.c @@ -148,7 +148,7 @@ ruby_debug_print_node(int level, int debug_level, const char *header, const NODE { if (level < debug_level) { fprintf(stderr, "DBG> %s: %s (%u)\n", header, - ruby_node_name(nd_type(node), rb_bug), nd_line(node)); + ruby_node_name(nd_type(node)), nd_line(node)); } return (NODE *)node; } diff --git a/node.c b/node.c index 7d109678d845f8..3eafbce184b6bb 100644 --- a/node.c +++ b/node.c @@ -53,6 +53,33 @@ rb_node_init(NODE *n, enum node_type type, VALUE a0, VALUE a1, VALUE a2) n->node_id = -1; } +const char * +rb_node_name(int node) +{ + switch (node) { +#include "node_name.inc" + default: + return 0; + } +} + +#ifdef UNIVERSAL_PARSER +const char * +ruby_node_name(int node) +{ + return rb_node_name(node); +} +#else +const char * +ruby_node_name(int node) +{ + const char *name = rb_node_name(node); + + if (!name) rb_bug("unknown node: %d", node); + return name; +} +#endif + static void init_node_buffer_list(node_buffer_list_t * nb, node_buffer_elem_t *head) { @@ -63,6 +90,7 @@ init_node_buffer_list(node_buffer_list_t * nb, node_buffer_elem_t *head) nb->head->next = NULL; } +#ifdef UNIVERSAL_PARSER static node_buffer_t * rb_node_buffer_new(rb_parser_config_t *config) { @@ -81,6 +109,25 @@ rb_node_buffer_new(rb_parser_config_t *config) nb->config = config; return nb; } +#else +static node_buffer_t * +rb_node_buffer_new(void) +{ + const size_t bucket_size = offsetof(node_buffer_elem_t, buf) + NODE_BUF_DEFAULT_LEN * sizeof(NODE); + const size_t alloc_size = sizeof(node_buffer_t) + (bucket_size * 2); + STATIC_ASSERT( + integer_overflow, + offsetof(node_buffer_elem_t, buf) + NODE_BUF_DEFAULT_LEN * sizeof(NODE) + > sizeof(node_buffer_t) + 2 * sizeof(node_buffer_elem_t)); + node_buffer_t *nb = ruby_xmalloc(alloc_size); + init_node_buffer_list(&nb->unmarkable, (node_buffer_elem_t*)&nb[1]); + init_node_buffer_list(&nb->markable, (node_buffer_elem_t*)((size_t)nb->unmarkable.head + bucket_size)); + nb->local_tables = 0; + nb->mark_hash = Qnil; + nb->tokens = Qnil; + return nb; +} +#endif static void node_buffer_list_free(rb_ast_t *ast, node_buffer_list_t * nb) @@ -154,17 +201,6 @@ nodetype_markable_p(enum node_type type) } } -const char * -ruby_node_name(int node, bug_report_func rb_bug) -{ - switch (node) { -#include "node_name.inc" - default: - rb_bug("unknown node: %d", node); - return 0; - } -} - NODE * rb_ast_newnode(rb_ast_t *ast, enum node_type type) { @@ -181,7 +217,7 @@ rb_ast_node_type_change(NODE *n, enum node_type type) enum node_type old_type = nd_type(n); if (nodetype_markable_p(old_type) != nodetype_markable_p(type)) { rb_bug("node type changed: %s -> %s", - ruby_node_name(old_type, rb_bug), ruby_node_name(type, rb_bug)); + ruby_node_name(old_type), ruby_node_name(type)); } } #endif @@ -218,6 +254,7 @@ rb_ast_delete_node(rb_ast_t *ast, NODE *n) /* should we implement freelist? */ } +#ifdef UNIVERSAL_PARSER rb_ast_t * rb_ast_new(rb_parser_config_t *config) { @@ -225,6 +262,15 @@ rb_ast_new(rb_parser_config_t *config) config->counter++; return config->ast_new((VALUE)nb); } +#else +rb_ast_t * +rb_ast_new(void) +{ + node_buffer_t *nb = rb_node_buffer_new(); + rb_ast_t *ast = (rb_ast_t *)rb_imemo_new(imemo_ast, 0, 0, 0, (VALUE)nb); + return ast; +} +#endif typedef void node_itr_t(rb_ast_t *ast, void *ctx, NODE * node); @@ -255,7 +301,9 @@ iterate_node_values(rb_ast_t *ast, node_buffer_list_t *nb, node_itr_t * func, vo static void mark_ast_value(rb_ast_t *ast, void *ctx, NODE * node) { +#ifdef UNIVERSAL_PARSER bug_report_func rb_bug = ast->node_buffer->config->bug; +#endif switch (nd_type(node)) { case NODE_ARGS: @@ -279,14 +327,16 @@ mark_ast_value(rb_ast_t *ast, void *ctx, NODE * node) rb_gc_mark_movable(node->nd_rval); break; default: - rb_bug("unreachable node %s", ruby_node_name(nd_type(node), rb_bug)); + rb_bug("unreachable node %s", ruby_node_name(nd_type(node))); } } static void update_ast_value(rb_ast_t *ast, void *ctx, NODE * node) { +#ifdef UNIVERSAL_PARSER bug_report_func rb_bug = ast->node_buffer->config->bug; +#endif switch (nd_type(node)) { case NODE_ARGS: @@ -341,14 +391,18 @@ void rb_ast_free(rb_ast_t *ast) { if (ast->node_buffer) { +#ifdef UNIVERSAL_PARSER rb_parser_config_t *config = ast->node_buffer->config; +#endif rb_node_buffer_free(ast, ast->node_buffer); ast->node_buffer = 0; +#ifdef UNIVERSAL_PARSER config->counter--; if (config->counter <= 0) { rb_ruby_parser_config_free(config); } +#endif } } diff --git a/node.h b/node.h index 7e0cadc23f8b39..69f73fc7984377 100644 --- a/node.h +++ b/node.h @@ -16,7 +16,6 @@ #include "ruby/backward/2/attributes.h" typedef void (*bug_report_func)(const char *fmt, ...); -typedef struct rb_parser_config_struct rb_parser_config_t; typedef struct node_buffer_elem_struct { struct node_buffer_elem_struct *next; @@ -30,6 +29,10 @@ typedef struct { node_buffer_elem_t *last; } node_buffer_list_t; +#ifdef UNIVERSAL_PARSER +typedef struct rb_parser_config_struct rb_parser_config_t; +#endif + struct node_buffer_struct { node_buffer_list_t unmarkable; node_buffer_list_t markable; @@ -41,19 +44,25 @@ struct node_buffer_struct { // - location info // Array, whose entry is array VALUE tokens; +#ifdef UNIVERSAL_PARSER rb_parser_config_t *config; +#endif }; RUBY_SYMBOL_EXPORT_BEGIN +#ifdef UNIVERSAL_PARSER rb_ast_t *rb_ast_new(rb_parser_config_t *config); +#else +rb_ast_t *rb_ast_new(); +#endif size_t rb_ast_memsize(const rb_ast_t*); void rb_ast_dispose(rb_ast_t*); VALUE rb_ast_tokens(rb_ast_t *ast); #if RUBY_DEBUG void rb_ast_node_type_change(NODE *n, enum node_type type); #endif -const char *ruby_node_name(int node, bug_report_func); +const char *ruby_node_name(int node); void rb_node_init(NODE *n, enum node_type type, VALUE a0, VALUE a1, VALUE a2); void rb_ast_mark(rb_ast_t*); diff --git a/node_dump.c b/node_dump.c index e98eedfeb55750..685849e3d6d25f 100644 --- a/node_dump.c +++ b/node_dump.c @@ -27,7 +27,7 @@ #define A_LIT(lit) AR(rb_dump_literal(lit)) #define A_NODE_HEADER(node, term) \ rb_str_catf(buf, "@ %s (id: %d, line: %d, location: (%d,%d)-(%d,%d))%s"term, \ - ruby_node_name(nd_type(node), rb_bug), nd_node_id(node), nd_line(node), \ + ruby_node_name(nd_type(node)), nd_node_id(node), nd_line(node), \ nd_first_lineno(node), nd_first_column(node), \ nd_last_lineno(node), nd_last_column(node), \ (node->flags & NODE_FL_NEWLINE ? "*" : "")) @@ -1105,7 +1105,7 @@ dump_node(VALUE buf, VALUE indent, int comment, const NODE * node) break; } - rb_bug("dump_node: unknown node: %s", ruby_node_name(nd_type(node), rb_bug)); + rb_bug("dump_node: unknown node: %s", ruby_node_name(nd_type(node))); } VALUE diff --git a/parse.y b/parse.y index a02baf02095095..1874cc3f19b65b 100644 --- a/parse.y +++ b/parse.y @@ -454,7 +454,9 @@ struct parser_params { struct lex_context ctxt; +#ifdef UNIVERSAL_PARSER rb_parser_config_t *config; +#endif unsigned int command_start:1; unsigned int eofp: 1; @@ -1395,7 +1397,7 @@ static int looking_at_eol_p(struct parser_params *p); %printer { #ifndef RIPPER if ($$) { - rb_parser_printf(p, "%s", ruby_node_name(nd_type($$), rb_bug)); + rb_parser_printf(p, "%s", ruby_node_name(nd_type($$))); } #else #endif @@ -6883,7 +6885,7 @@ yycompile(struct parser_params *p, VALUE fname, int line) p->lvtbl = NULL; - p->ast = ast = rb_ast_new(p->config); + p->ast = ast = rb_ast_new(); compile_callback(yycompile0, (VALUE)p); p->ast = 0; @@ -8228,12 +8230,16 @@ static VALUE parser_dedent_string(VALUE self, VALUE input, VALUE width) { int wid, col; +#ifdef UNIVERSAL_PARSER rb_parser_config_t config; +#endif struct parser_params p; +#ifdef UNIVERSAL_PARSER // TODO: It might be better to malloc `struct parser_params' rb_parser_config_initialize(&config); p.config = &config; +#endif StringValue(input); wid = NUM2UINT(width); @@ -11113,7 +11119,7 @@ symbol_append(struct parser_params *p, NODE *symbols, NODE *symbol) RB_OBJ_WRITTEN(p->ast, Qnil, symbol->nd_lit = rb_str_intern(symbol->nd_lit)); break; default: - compile_error(p, "unexpected node as symbol: %s", ruby_node_name(type, rb_bug)); + compile_error(p, "unexpected node as symbol: %s", ruby_node_name(type)); } return list_append(p, symbols, symbol); } @@ -13778,7 +13784,9 @@ rb_ruby_parser_free(void *ptr) { struct parser_params *p = (struct parser_params*)ptr; struct local_vars *local, *prev; +#ifdef UNIVERSAL_PARSER rb_parser_config_t *config = p->config; +#endif if (p->tokenbuf) { ruby_sized_xfree(p->tokenbuf, p->toksiz); @@ -13796,10 +13804,13 @@ rb_ruby_parser_free(void *ptr) } } xfree(ptr); + +#ifdef UNIVERSAL_PARSER config->counter--; if (config->counter <= 0) { rb_ruby_parser_config_free(config); } +#endif } size_t @@ -13817,19 +13828,6 @@ rb_ruby_parser_memsize(const void *ptr) return size; } -#ifdef RIPPER -// TODO: rename -static const rb_data_type_t parser_data_type = { - "ripper", - { - rb_ruby_parser_mark, - rb_ruby_parser_free, - rb_ruby_parser_memsize, - }, - 0, 0, RUBY_TYPED_FREE_IMMEDIATELY -}; -#endif - rb_parser_config_t * rb_ruby_parser_config_new(void *(*malloc)(size_t size)) { @@ -13851,6 +13849,7 @@ rb_reserved_word(const char *str, unsigned int len) return reserved_word(str, len); } +#ifdef UNIVERSAL_PARSER rb_parser_t * rb_ruby_parser_new(rb_parser_config_t *config) { @@ -13861,6 +13860,7 @@ rb_ruby_parser_new(rb_parser_config_t *config) parser_initialize(p); return p; } +#endif rb_parser_t * rb_ruby_parser_set_context(rb_parser_t *p, const struct rb_iseq_struct *base, int main) @@ -13892,7 +13892,154 @@ rb_ruby_parser_keep_tokens(rb_parser_t *p) p->tokens = rb_ary_new(); } +#ifndef UNIVERSAL_PARSER + +static const rb_data_type_t parser_data_type = { +#ifndef RIPPER + "parser", +#else + "ripper", #endif + { + rb_ruby_parser_mark, + rb_ruby_parser_free, + rb_ruby_parser_memsize, + }, + 0, 0, RUBY_TYPED_FREE_IMMEDIATELY +}; + +rb_ast_t* +rb_parser_compile_file_path(VALUE vparser, VALUE fname, VALUE file, int start) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + return rb_ruby_parser_compile_file_path(p, fname, file, start); +} + +rb_ast_t* +rb_parser_compile_generic(VALUE vparser, VALUE (*lex_gets)(VALUE, int), VALUE fname, VALUE input, int start) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + return rb_ruby_parser_compile_generic(p, lex_gets, fname, input, start); +} + +rb_ast_t* +rb_parser_compile_string(VALUE vparser, const char *f, VALUE s, int line) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + return rb_ruby_parser_compile_string(p, f, s, line); +} + +rb_ast_t* +rb_parser_compile_string_path(VALUE vparser, VALUE f, VALUE s, int line) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + return rb_ruby_parser_compile_string_path(p, f, s, line); +} + +VALUE +rb_parser_encoding(VALUE vparser) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + return rb_ruby_parser_encoding(p); +} + +VALUE +rb_parser_end_seen_p(VALUE vparser) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + return RBOOL(rb_ruby_parser_end_seen_p(p)); +} + +void +rb_parser_error_tolerant(VALUE vparser) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + rb_ruby_parser_error_tolerant(p); +} + +void +rb_parser_keep_script_lines(VALUE vparser) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + rb_ruby_parser_keep_script_lines(p); +} + +void +rb_parser_keep_tokens(VALUE vparser) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + rb_ruby_parser_keep_tokens(p); +} + +VALUE +rb_parser_new(void) +{ + struct parser_params *p; + VALUE parser = TypedData_Make_Struct(0, struct parser_params, + &parser_data_type, p); + parser_initialize(p); + return parser; +} + +VALUE +rb_parser_set_context(VALUE vparser, const struct rb_iseq_struct *base, int main) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + rb_ruby_parser_set_context(p, base, main); + return vparser; +} + +void +rb_parser_set_options(VALUE vparser, int print, int loop, int chomp, int split) +{ + struct parser_params *p; + + TypedData_Get_Struct(vparser, struct parser_params, &parser_data_type, p); + rb_ruby_parser_set_options(p, print, loop, chomp, split); +} + +VALUE +rb_parser_set_yydebug(VALUE self, VALUE flag) +{ + struct parser_params *p; + + TypedData_Get_Struct(self, struct parser_params, &parser_data_type, p); + rb_ruby_parser_set_yydebug(p, RTEST(flag)); + return flag; +} + +void +rb_strterm_mark(VALUE obj) +{ + rb_strterm_t *strterm = (rb_strterm_t*)obj; + if (RBASIC(obj)->flags & STRTERM_HEREDOC) { + rb_strterm_heredoc_t *heredoc = &strterm->u.heredoc; + rb_gc_mark(heredoc->lastline); + } +} +#endif /* !UNIVERSAL_PARSER */ + +#endif /* !RIPPER */ #ifdef RIPPER #define rb_parser_end_seen_p ripper_parser_end_seen_p @@ -14446,7 +14593,7 @@ ripper_parse0(VALUE parser_v) TypedData_Get_Struct(parser_v, struct parser_params, &parser_data_type, p); parser_prepare(p); - p->ast = rb_ast_new(p->config); + p->ast = rb_ast_new(); ripper_yyparse((void*)p); rb_ast_dispose(p->ast); p->ast = 0; diff --git a/ruby_parser.c b/ruby_parser.c index 1f6a892ba08c04..5fd0b1fecefa2d 100644 --- a/ruby_parser.c +++ b/ruby_parser.c @@ -1,4 +1,5 @@ /* This is a wrapper for parse.y */ +#ifdef UNIVERSAL_PARSER #include "internal.h" #include "internal/array.h" @@ -956,3 +957,4 @@ rb_parser_set_yydebug(VALUE vparser, VALUE flag) rb_ruby_parser_set_yydebug(parser->parser_params, RTEST(flag)); return flag; } +#endif diff --git a/st2.c b/st2.c index 6f20d4689deabf..a9a3d46fd1f350 100644 --- a/st2.c +++ b/st2.c @@ -102,7 +102,14 @@ #include "st2.h" #include "bits2.h" -#include "internal/sanitizers.h" + +#ifndef TRUE +# define TRUE 1 +#endif + +#ifndef FALSE +# define FALSE 0 +#endif #define NOT_RUBY 1 #undef RUBY @@ -2093,142 +2100,3 @@ st_numhash(st_data_t n) enum {s1 = 11, s2 = 3}; return (st_index_t)((n>>s1|(n<>s2)); } - -/* Expand TAB to be suitable for holding SIZ entries in total. - Pre-existing entries remain not deleted inside of TAB, but its bins - are cleared to expect future reconstruction. See rehash below. */ -static void -st_expand_table(st_table *tab, st_index_t siz) -{ - st_table *tmp; - st_index_t n; - - if (siz <= get_allocated_entries(tab)) - return; /* enough room already */ - - tmp = st_init_table_with_size(tab->type, tab->functions, siz); - n = get_allocated_entries(tab); - MEMCPY(tab, tmp->entries, tab->entries, st_table_entry, n); - free(tab->entries); - if (tab->bins != NULL) - free(tab->bins); - if (tmp->bins != NULL) - free(tmp->bins); - tab->entry_power = tmp->entry_power; - tab->bin_power = tmp->bin_power; - tab->size_ind = tmp->size_ind; - tab->entries = tmp->entries; - tab->bins = NULL; - tab->rebuilds_num++; - free(tmp); -} - -/* Rehash using linear search. Return TRUE if we found that the table - was rebuilt. */ -static int -st_rehash_linear(st_table *tab) -{ - int eq_p, rebuilt_p; - st_index_t i, j; - st_table_entry *p, *q; - if (tab->bins) { - free(tab->bins); - tab->bins = NULL; - } - for (i = tab->entries_start; i < tab->entries_bound; i++) { - p = &tab->entries[i]; - if (DELETED_ENTRY_P(p)) - continue; - for (j = i + 1; j < tab->entries_bound; j++) { - q = &tab->entries[j]; - if (DELETED_ENTRY_P(q)) - continue; - DO_PTR_EQUAL_CHECK(tab, p, q->hash, q->key, eq_p, rebuilt_p); - if (EXPECT(rebuilt_p, 0)) - return TRUE; - if (eq_p) { - *p = *q; - MARK_ENTRY_DELETED(q); - tab->num_entries--; - update_range_for_deleted(tab, j); - } - } - } - return FALSE; -} - -/* Rehash using index. Return TRUE if we found that the table was - rebuilt. */ -static int -st_rehash_indexed(st_table *tab) -{ - int eq_p, rebuilt_p; - st_index_t i; - st_index_t const n = bins_size(tab); - unsigned int const size_ind = get_size_ind(tab); - st_index_t *bins = realloc(tab->bins, n); - tab->bins = bins; - initialize_bins(tab); - for (i = tab->entries_start; i < tab->entries_bound; i++) { - st_table_entry *p = &tab->entries[i]; - st_index_t ind; -#ifdef QUADRATIC_PROBE - st_index_t d = 1; -#else - st_index_t perturb = p->hash; -#endif - - if (DELETED_ENTRY_P(p)) - continue; - - ind = hash_bin(p->hash, tab); - for (;;) { - st_index_t bin = get_bin(bins, size_ind, ind); - if (EMPTY_OR_DELETED_BIN_P(bin)) { - /* ok, new room */ - set_bin(bins, size_ind, ind, i + ENTRY_BASE); - break; - } - else { - st_table_entry *q = &tab->entries[bin - ENTRY_BASE]; - DO_PTR_EQUAL_CHECK(tab, q, p->hash, p->key, eq_p, rebuilt_p); - if (EXPECT(rebuilt_p, 0)) - return TRUE; - if (eq_p) { - /* duplicated key; delete it */ - q->record = p->record; - MARK_ENTRY_DELETED(p); - tab->num_entries--; - update_range_for_deleted(tab, bin); - break; - } - else { - /* hash collision; skip it */ -#ifdef QUADRATIC_PROBE - ind = hash_bin(ind + d, tab); - d++; -#else - ind = secondary_hash(ind, tab, &perturb); -#endif - } - } - } - } - return FALSE; -} - -/* Reconstruct TAB's bins according to TAB's entries. This function - permits conflicting keys inside of entries. No errors are reported - then. All but one of them are discarded silently. */ -static void -st_rehash(st_table *tab) -{ - int rebuilt_p; - - do { - if (tab->bin_power <= MAX_POWER2_FOR_TABLES_WITHOUT_BINS) - rebuilt_p = st_rehash_linear(tab); - else - rebuilt_p = st_rehash_indexed(tab); - } while (rebuilt_p); -} diff --git a/universal_parser.c b/universal_parser.c index 738371b3325327..f875de6216bc06 100644 --- a/universal_parser.c +++ b/universal_parser.c @@ -329,3 +329,6 @@ struct rb_imemo_tmpbuf_struct { #define st_init_table_with_size(type, size) \ rb_st2_init_table_with_size(type, &p->config->st_functions, size) + +#define rb_ast_new() \ + rb_ast_new(p->config)