[Bug #19592] Fix ext/Setup support
After [1], using ext/Setup to link some, but not all extensions failed during linking. I did not know about this option, and had assumed that only `--with-static-linked-ext` builds can include statically linked extensions. Include the support code for statically linked extensions in all configurations like before [1]. Initialize the table lazily to minimize footprint on builds that have no statically linked extensions. [1]: 790cf4b6d0475614afb127b416e87cfa39044d67 "Fix autoload status of statically linked extensions"
This commit is contained in:
parent
92466e440d
commit
adaff1fc49
Notes:
git
2023-04-26 19:02:55 +00:00
28
load.c
28
load.c
@ -1032,8 +1032,10 @@ search_required(rb_vm_t *vm, VALUE fname, volatile VALUE *path, feature_func rb_
|
|||||||
}
|
}
|
||||||
tmp = fname;
|
tmp = fname;
|
||||||
type = rb_find_file_ext(&tmp, ft == 's' ? ruby_ext : loadable_ext);
|
type = rb_find_file_ext(&tmp, ft == 's' ? ruby_ext : loadable_ext);
|
||||||
#if EXTSTATIC
|
|
||||||
if (!ft && type != 1) { // not already a feature and not found as a dynamic library
|
// Check if it's a statically linked extension when
|
||||||
|
// not already a feature and not found as a dynamic library.
|
||||||
|
if (!ft && type != 1 && vm->static_ext_inits) {
|
||||||
VALUE lookup_name = tmp;
|
VALUE lookup_name = tmp;
|
||||||
// Append ".so" if not already present so for example "etc" can find "etc.so".
|
// Append ".so" if not already present so for example "etc" can find "etc.so".
|
||||||
// We always register statically linked extensions with a ".so" extension.
|
// We always register statically linked extensions with a ".so" extension.
|
||||||
@ -1048,7 +1050,7 @@ search_required(rb_vm_t *vm, VALUE fname, volatile VALUE *path, feature_func rb_
|
|||||||
return 's';
|
return 's';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case 0:
|
case 0:
|
||||||
if (ft)
|
if (ft)
|
||||||
@ -1087,19 +1089,18 @@ load_ext(VALUE path)
|
|||||||
return (VALUE)dln_load(RSTRING_PTR(path));
|
return (VALUE)dln_load(RSTRING_PTR(path));
|
||||||
}
|
}
|
||||||
|
|
||||||
#if EXTSTATIC
|
|
||||||
static bool
|
static bool
|
||||||
run_static_ext_init(rb_vm_t *vm, const char *feature)
|
run_static_ext_init(rb_vm_t *vm, const char *feature)
|
||||||
{
|
{
|
||||||
st_data_t key = (st_data_t)feature;
|
st_data_t key = (st_data_t)feature;
|
||||||
st_data_t init_func;
|
st_data_t init_func;
|
||||||
if (st_delete(vm->static_ext_inits, &key, &init_func)) {
|
|
||||||
|
if (vm->static_ext_inits && st_delete(vm->static_ext_inits, &key, &init_func)) {
|
||||||
((void (*)(void))init_func)();
|
((void (*)(void))init_func)();
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
static int
|
static int
|
||||||
no_feature_p(rb_vm_t *vm, const char *feature, const char *ext, int rb, int expanded, const char **fn)
|
no_feature_p(rb_vm_t *vm, const char *feature, const char *ext, int rb, int expanded, const char **fn)
|
||||||
@ -1203,11 +1204,9 @@ require_internal(rb_execution_context_t *ec, VALUE fname, int exception, bool wa
|
|||||||
else if (!*ftptr) {
|
else if (!*ftptr) {
|
||||||
result = TAG_RETURN;
|
result = TAG_RETURN;
|
||||||
}
|
}
|
||||||
#if EXTSTATIC
|
|
||||||
else if (found == 's' && run_static_ext_init(th->vm, RSTRING_PTR(path))) {
|
else if (found == 's' && run_static_ext_init(th->vm, RSTRING_PTR(path))) {
|
||||||
result = TAG_RETURN;
|
result = TAG_RETURN;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
else if (RTEST(rb_hash_aref(realpaths,
|
else if (RTEST(rb_hash_aref(realpaths,
|
||||||
realpath = rb_realpath_internal(Qnil, path, 1)))) {
|
realpath = rb_realpath_internal(Qnil, path, 1)))) {
|
||||||
result = 0;
|
result = 0;
|
||||||
@ -1326,7 +1325,6 @@ rb_require(const char *fname)
|
|||||||
return rb_require_string(rb_str_new_cstr(fname));
|
return rb_require_string(rb_str_new_cstr(fname));
|
||||||
}
|
}
|
||||||
|
|
||||||
#if EXTSTATIC
|
|
||||||
static int
|
static int
|
||||||
register_init_ext(st_data_t *key, st_data_t *value, st_data_t init, int existing)
|
register_init_ext(st_data_t *key, st_data_t *value, st_data_t init, int existing)
|
||||||
{
|
{
|
||||||
@ -1341,17 +1339,25 @@ register_init_ext(st_data_t *key, st_data_t *value, st_data_t init, int existing
|
|||||||
return ST_CONTINUE;
|
return ST_CONTINUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Private API for statically linked extensions.
|
||||||
|
// Used with the ext/Setup file, the --with-setup and
|
||||||
|
// --with-static-linked-ext configuration option, etc.
|
||||||
void
|
void
|
||||||
ruby_init_ext(const char *name, void (*init)(void))
|
ruby_init_ext(const char *name, void (*init)(void))
|
||||||
{
|
{
|
||||||
|
st_table *inits_table;
|
||||||
rb_vm_t *vm = GET_VM();
|
rb_vm_t *vm = GET_VM();
|
||||||
st_table *inits_table = vm->static_ext_inits;
|
|
||||||
|
|
||||||
if (feature_provided(vm, name, 0))
|
if (feature_provided(vm, name, 0))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
inits_table = vm->static_ext_inits;
|
||||||
|
if (!inits_table) {
|
||||||
|
inits_table = st_init_strtable();
|
||||||
|
vm->static_ext_inits = inits_table;
|
||||||
|
}
|
||||||
st_update(inits_table, (st_data_t)name, register_init_ext, (st_data_t)init);
|
st_update(inits_table, (st_data_t)name, register_init_ext, (st_data_t)init);
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* call-seq:
|
* call-seq:
|
||||||
|
3
vm.c
3
vm.c
@ -4037,9 +4037,6 @@ Init_vm_objects(void)
|
|||||||
vm->mark_object_ary = rb_ary_hidden_new(128);
|
vm->mark_object_ary = rb_ary_hidden_new(128);
|
||||||
vm->loading_table = st_init_strtable();
|
vm->loading_table = st_init_strtable();
|
||||||
vm->frozen_strings = st_init_table_with_size(&rb_fstring_hash_type, 10000);
|
vm->frozen_strings = st_init_table_with_size(&rb_fstring_hash_type, 10000);
|
||||||
#if EXTSTATIC
|
|
||||||
vm->static_ext_inits = st_init_strtable();
|
|
||||||
#endif
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Stub for builtin function when not building YJIT units*/
|
/* Stub for builtin function when not building YJIT units*/
|
||||||
|
@ -557,10 +557,6 @@ struct rb_iseq_struct {
|
|||||||
|
|
||||||
#define ISEQ_BODY(iseq) ((iseq)->body)
|
#define ISEQ_BODY(iseq) ((iseq)->body)
|
||||||
|
|
||||||
#ifndef EXTSTATIC
|
|
||||||
#define EXTSTATIC 0
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifndef USE_LAZY_LOAD
|
#ifndef USE_LAZY_LOAD
|
||||||
#define USE_LAZY_LOAD 0
|
#define USE_LAZY_LOAD 0
|
||||||
#endif
|
#endif
|
||||||
@ -686,11 +682,9 @@ typedef struct rb_vm_struct {
|
|||||||
VALUE loaded_features_realpath_map;
|
VALUE loaded_features_realpath_map;
|
||||||
struct st_table *loaded_features_index;
|
struct st_table *loaded_features_index;
|
||||||
struct st_table *loading_table;
|
struct st_table *loading_table;
|
||||||
#if EXTSTATIC
|
|
||||||
// For running the init function of statically linked
|
// For running the init function of statically linked
|
||||||
// extensions when they are loaded
|
// extensions when they are loaded
|
||||||
struct st_table *static_ext_inits;
|
struct st_table *static_ext_inits;
|
||||||
#endif
|
|
||||||
|
|
||||||
/* signal */
|
/* signal */
|
||||||
struct {
|
struct {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user