@@ -401,7 +401,7 @@ JL_DLLEXPORT jl_value_t *jl_get_binding_leaf_partitions_value_if_const(jl_bindin
401401 return NULL ;
402402}
403403
404- JL_DLLEXPORT jl_module_t * jl_new_module__ (jl_sym_t * name , jl_module_t * parent )
404+ static jl_module_t * jl_new_module__ (jl_sym_t * name , jl_module_t * parent )
405405{
406406 jl_task_t * ct = jl_current_task ;
407407 const jl_uuid_t uuid_zero = {0 , 0 };
@@ -410,7 +410,7 @@ JL_DLLEXPORT jl_module_t *jl_new_module__(jl_sym_t *name, jl_module_t *parent)
410410 jl_set_typetagof (m , jl_module_tag , 0 );
411411 assert (jl_is_symbol (name ));
412412 m -> name = name ;
413- m -> parent = parent ;
413+ m -> parent = parent ? parent : m ;
414414 m -> istopmod = 0 ;
415415 m -> uuid = uuid_zero ;
416416 static unsigned int mcounter ; // simple counter backup, in case hrtime is not incrementing
@@ -437,23 +437,22 @@ JL_DLLEXPORT jl_module_t *jl_new_module__(jl_sym_t *name, jl_module_t *parent)
437437 return m ;
438438}
439439
440- JL_DLLEXPORT void jl_add_default_names (jl_module_t * m , uint8_t default_using_core , uint8_t self_name )
440+ static void jl_add_default_names (jl_module_t * m , uint8_t default_using_core , uint8_t self_name )
441441{
442442 if (jl_core_module ) {
443443 // Bootstrap: Before jl_core_module is defined, we don't have enough infrastructure
444444 // for bindings, so Core itself gets special handling in jltypes.c
445445 if (default_using_core ) {
446- jl_module_using (m , jl_core_module );
446+ jl_module_initial_using (m , jl_core_module );
447447 }
448448 if (self_name ) {
449449 // export own name, so "using Foo" makes "Foo" itself visible
450- jl_set_const (m , m -> name , (jl_value_t * )m );
451- jl_module_public (m , m -> name , 1 );
450+ jl_set_initial_const (m , m -> name , (jl_value_t * )m , 1 );
452451 }
453452 }
454453}
455454
456- JL_DLLEXPORT jl_module_t * jl_new_module_ (jl_sym_t * name , jl_module_t * parent , uint8_t default_using_core , uint8_t self_name )
455+ jl_module_t * jl_new_module_ (jl_sym_t * name , jl_module_t * parent , uint8_t default_using_core , uint8_t self_name )
457456{
458457 jl_module_t * m = jl_new_module__ (name , parent );
459458 JL_GC_PUSH1 (& m );
@@ -1231,6 +1230,19 @@ void jl_add_usings_backedge(jl_module_t *from, jl_module_t *to)
12311230 JL_UNLOCK (& from -> lock );
12321231}
12331232
1233+ void jl_module_initial_using (jl_module_t * to , jl_module_t * from )
1234+ {
1235+ struct _jl_module_using new_item = {
1236+ .mod = from ,
1237+ .min_world = 0 ,
1238+ .max_world = ~(size_t )0
1239+ };
1240+ arraylist_grow (& to -> usings , sizeof (struct _jl_module_using )/sizeof (void * ));
1241+ memcpy (& to -> usings .items [to -> usings .len - 3 ], & new_item , sizeof (struct _jl_module_using ));
1242+ jl_gc_wb (to , from );
1243+ jl_add_usings_backedge (from , to );
1244+ }
1245+
12341246JL_DLLEXPORT void jl_module_using (jl_module_t * to , jl_module_t * from )
12351247{
12361248 if (to == from )
@@ -1325,6 +1337,7 @@ JL_DLLEXPORT jl_value_t *jl_get_module_binding_or_nothing(jl_module_t *m, jl_sym
13251337
13261338JL_DLLEXPORT void jl_module_public (jl_module_t * from , jl_sym_t * s , int exported )
13271339{
1340+ // caller must hold world_counter_lock
13281341 jl_binding_t * b = jl_get_module_binding (from , s , 1 );
13291342 JL_LOCK (& world_counter_lock );
13301343 size_t new_world = jl_atomic_load_acquire (& jl_world_counter )+ 1 ;
@@ -1370,13 +1383,6 @@ JL_DLLEXPORT int jl_boundp(jl_module_t *m, jl_sym_t *var, int allow_import) // u
13701383 return jl_atomic_load (& b -> value ) != NULL ;
13711384}
13721385
1373- JL_DLLEXPORT int jl_defines_or_exports_p (jl_module_t * m , jl_sym_t * var )
1374- {
1375- jl_binding_t * b = jl_get_module_binding (m , var , 0 );
1376- jl_binding_partition_t * bpart = jl_get_binding_partition (b , jl_current_task -> world_age );
1377- return b && ((bpart -> kind & PARTITION_FLAG_EXPORTED ) || jl_binding_kind (bpart ) == PARTITION_KIND_GLOBAL );
1378- }
1379-
13801386JL_DLLEXPORT int jl_module_exports_p (jl_module_t * m , jl_sym_t * var )
13811387{
13821388 jl_binding_t * b = jl_get_module_binding (m , var , 0 );
@@ -1475,9 +1481,25 @@ JL_DLLEXPORT void jl_set_global(jl_module_t *m JL_ROOTING_ARGUMENT, jl_sym_t *va
14751481 jl_checked_assignment (bp , m , var , val );
14761482}
14771483
1484+ JL_DLLEXPORT void jl_set_initial_const (jl_module_t * m JL_ROOTING_ARGUMENT , jl_sym_t * var , jl_value_t * val JL_ROOTED_ARGUMENT , int exported )
1485+ {
1486+ // this function is only valid during initialization, so there is no risk of data races her are not too important to use
1487+ int kind = PARTITION_KIND_CONST | (exported ? PARTITION_FLAG_EXPORTED : 0 );
1488+ // jl_declare_constant_val3(NULL, m, var, (jl_value_t*)jl_any_type, kind, 0);
1489+ jl_binding_t * bp = jl_get_module_binding (m , var , 1 );
1490+ jl_binding_partition_t * bpart = jl_get_binding_partition (bp , 0 );
1491+ assert (bpart -> min_world == 0 );
1492+ jl_atomic_store_relaxed (& bpart -> max_world , ~(size_t )0 ); // jl_check_new_binding_implicit likely incorrectly truncated it
1493+ if (exported )
1494+ jl_atomic_fetch_or_relaxed (& bp -> flags , BINDING_FLAG_PUBLICP );
1495+ bpart -> kind = kind | (bpart -> kind & PARTITION_MASK_FLAG );
1496+ bpart -> restriction = val ;
1497+ jl_gc_wb (bpart , val );
1498+ }
1499+
14781500JL_DLLEXPORT void jl_set_const (jl_module_t * m JL_ROOTING_ARGUMENT , jl_sym_t * var , jl_value_t * val JL_ROOTED_ARGUMENT )
14791501{
1480- // this function is mostly only used during initialization, so the data races here are not too important to us
1502+ // this function is dangerous and unsound. do not use.
14811503 jl_binding_t * bp = jl_get_module_binding (m , var , 1 );
14821504 jl_binding_partition_t * bpart = jl_get_binding_partition (bp , jl_current_task -> world_age );
14831505 bpart -> min_world = 0 ;
0 commit comments