Feature #14460 ยป 0001-Use-shared-substrings-in-feature-index-cache-hash.patch
load.c | ||
---|---|---|
return GET_VM()->loaded_features_index;
|
||
}
|
||
static VALUE
|
||
get_loaded_features_index_pool_raw(void)
|
||
{
|
||
return GET_VM()->loaded_features_index_pool;
|
||
}
|
||
static st_table *
|
||
get_loading_table(void)
|
||
{
|
||
... | ... | |
}
|
||
static void
|
||
features_index_add_single(VALUE short_feature, VALUE offset)
|
||
features_index_add_single(const char *short_feature_cstr, VALUE offset)
|
||
{
|
||
struct st_table *features_index;
|
||
VALUE this_feature_index = Qnil;
|
||
char *short_feature_cstr;
|
||
Check_Type(offset, T_FIXNUM);
|
||
Check_Type(short_feature, T_STRING);
|
||
short_feature_cstr = StringValueCStr(short_feature);
|
||
features_index = get_loaded_features_index_raw();
|
||
st_lookup(features_index, (st_data_t)short_feature_cstr, (st_data_t *)&this_feature_index);
|
||
if (NIL_P(this_feature_index)) {
|
||
st_insert(features_index, (st_data_t)ruby_strdup(short_feature_cstr), (st_data_t)offset);
|
||
st_insert(features_index, (st_data_t)short_feature_cstr, (st_data_t)offset);
|
||
}
|
||
else if (RB_TYPE_P(this_feature_index, T_FIXNUM)) {
|
||
VALUE feature_indexes[2];
|
||
... | ... | |
static void
|
||
features_index_add(VALUE feature, VALUE offset)
|
||
{
|
||
VALUE short_feature;
|
||
const char *feature_str, *feature_end, *ext, *p;
|
||
VALUE short_feature_no_ext;
|
||
const char *feature_str, *feature_end, *feature_no_ext_str, *ext, *p;
|
||
feature_str = StringValuePtr(feature);
|
||
feature_end = feature_str + RSTRING_LEN(feature);
|
||
... | ... | |
/* Now `ext` points to the only string matching %r{^\.[^./]*$} that is
|
||
at the end of `feature`, or is NULL if there is no such string. */
|
||
p = ext ? ext : feature_end;
|
||
if (ext) {
|
||
p = ext;
|
||
short_feature_no_ext = rb_fstring(rb_str_freeze(rb_str_subseq(feature, 0, ext - feature_str)));
|
||
feature_no_ext_str = StringValuePtr(short_feature_no_ext);
|
||
rb_ary_push(get_loaded_features_index_pool_raw(), short_feature_no_ext);
|
||
} else {
|
||
p = feature_end;
|
||
short_feature_no_ext = Qnil;
|
||
}
|
||
while (1) {
|
||
long beg;
|
||
... | ... | |
break;
|
||
/* Now *p == '/'. We reach this point for every '/' in `feature`. */
|
||
beg = p + 1 - feature_str;
|
||
short_feature = rb_str_subseq(feature, beg, feature_end - p - 1);
|
||
features_index_add_single(short_feature, offset);
|
||
features_index_add_single(feature_str + beg, offset);
|
||
if (ext) {
|
||
short_feature = rb_str_subseq(feature, beg, ext - p - 1);
|
||
features_index_add_single(short_feature, offset);
|
||
features_index_add_single(feature_no_ext_str + beg, offset);
|
||
}
|
||
}
|
||
features_index_add_single(feature, offset);
|
||
features_index_add_single(feature_str, offset);
|
||
if (ext) {
|
||
short_feature = rb_str_subseq(feature, 0, ext - feature_str);
|
||
features_index_add_single(short_feature, offset);
|
||
features_index_add_single(feature_no_ext_str, offset);
|
||
}
|
||
}
|
||
... | ... | |
rb_ary_free(obj);
|
||
xfree((void *)obj);
|
||
}
|
||
xfree((char *)key);
|
||
return ST_DELETE;
|
||
}
|
||
... | ... | |
/* The sharing was broken; something (other than us in rb_provide_feature())
|
||
modified loaded_features. Rebuild the index. */
|
||
st_foreach(vm->loaded_features_index, loaded_features_index_clear_i, 0);
|
||
rb_ary_clear(vm->loaded_features_index_pool);
|
||
features = vm->loaded_features;
|
||
for (i = 0; i < RARRAY_LEN(features); i++) {
|
||
VALUE entry, as_str;
|
||
... | ... | |
vm->loaded_features = rb_ary_new();
|
||
vm->loaded_features_snapshot = rb_ary_tmp_new(0);
|
||
vm->loaded_features_index = st_init_strtable();
|
||
vm->loaded_features_index_pool = rb_ary_new();
|
||
rb_define_global_function("load", rb_f_load, -1);
|
||
rb_define_global_function("require", rb_f_require, 1);
|
vm.c | ||
---|---|---|
rb_gc_mark(vm->expanded_load_path);
|
||
rb_gc_mark(vm->loaded_features);
|
||
rb_gc_mark(vm->loaded_features_snapshot);
|
||
rb_gc_mark(vm->loaded_features_index_pool);
|
||
rb_gc_mark(vm->top_self);
|
||
RUBY_MARK_UNLESS_NULL(vm->coverages);
|
||
rb_gc_mark(vm->defined_module_hash);
|
vm_core.h | ||
---|---|---|
VALUE expanded_load_path;
|
||
VALUE loaded_features;
|
||
VALUE loaded_features_snapshot;
|
||
VALUE loaded_features_index_pool;
|
||
struct st_table *loaded_features_index;
|
||
struct st_table *loading_table;
|
||