@@ -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 )
@@ -1323,11 +1335,10 @@ JL_DLLEXPORT jl_value_t *jl_get_module_binding_or_nothing(jl_module_t *m, jl_sym
13231335 return (jl_value_t * )b ;
13241336}
13251337
1326- JL_DLLEXPORT void jl_module_public (jl_module_t * from , jl_sym_t * s , int exported )
1338+ int jl_module_public_ (jl_module_t * from , jl_sym_t * s , int exported , size_t new_world )
13271339{
1340+ // caller must hold world_counter_lock
13281341 jl_binding_t * b = jl_get_module_binding (from , s , 1 );
1329- JL_LOCK (& world_counter_lock );
1330- size_t new_world = jl_atomic_load_acquire (& jl_world_counter )+ 1 ;
13311342 jl_binding_partition_t * bpart = jl_get_binding_partition (b , new_world );
13321343 int was_exported = (bpart -> kind & PARTITION_FLAG_EXPORTED ) != 0 ;
13331344 if (jl_atomic_load_relaxed (& b -> flags ) & BINDING_FLAG_PUBLICP ) {
@@ -1342,9 +1353,9 @@ JL_DLLEXPORT void jl_module_public(jl_module_t *from, jl_sym_t *s, int exported)
13421353 jl_atomic_fetch_or_relaxed (& b -> flags , BINDING_FLAG_PUBLICP );
13431354 if (was_exported != exported ) {
13441355 jl_replace_binding_locked2 (b , bpart , bpart -> restriction , bpart -> kind | PARTITION_FLAG_EXPORTED , new_world );
1345- jl_atomic_store_release ( & jl_world_counter , new_world ) ;
1356+ return 1 ;
13461357 }
1347- JL_UNLOCK ( & world_counter_lock ) ;
1358+ return 0 ;
13481359}
13491360
13501361JL_DLLEXPORT int jl_boundp (jl_module_t * m , jl_sym_t * var , int allow_import ) // unlike most queries here, this is currently seq_cst
@@ -1370,13 +1381,6 @@ JL_DLLEXPORT int jl_boundp(jl_module_t *m, jl_sym_t *var, int allow_import) // u
13701381 return jl_atomic_load (& b -> value ) != NULL ;
13711382}
13721383
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-
13801384JL_DLLEXPORT int jl_module_exports_p (jl_module_t * m , jl_sym_t * var )
13811385{
13821386 jl_binding_t * b = jl_get_module_binding (m , var , 0 );
@@ -1475,9 +1479,25 @@ JL_DLLEXPORT void jl_set_global(jl_module_t *m JL_ROOTING_ARGUMENT, jl_sym_t *va
14751479 jl_checked_assignment (bp , m , var , val );
14761480}
14771481
1482+ 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 )
1483+ {
1484+ // this function is only valid during initialization, so there is no risk of data races her are not too important to use
1485+ int kind = PARTITION_KIND_CONST | (exported ? PARTITION_FLAG_EXPORTED : 0 );
1486+ // jl_declare_constant_val3(NULL, m, var, (jl_value_t*)jl_any_type, kind, 0);
1487+ jl_binding_t * bp = jl_get_module_binding (m , var , 1 );
1488+ jl_binding_partition_t * bpart = jl_get_binding_partition (bp , 0 );
1489+ assert (bpart -> min_world == 0 );
1490+ jl_atomic_store_relaxed (& bpart -> max_world , ~(size_t )0 ); // jl_check_new_binding_implicit likely incorrectly truncated it
1491+ if (exported )
1492+ jl_atomic_fetch_or_relaxed (& bp -> flags , BINDING_FLAG_PUBLICP );
1493+ bpart -> kind = kind | (bpart -> kind & PARTITION_MASK_FLAG );
1494+ bpart -> restriction = val ;
1495+ jl_gc_wb (bpart , val );
1496+ }
1497+
14781498JL_DLLEXPORT void jl_set_const (jl_module_t * m JL_ROOTING_ARGUMENT , jl_sym_t * var , jl_value_t * val JL_ROOTED_ARGUMENT )
14791499{
1480- // this function is mostly only used during initialization, so the data races here are not too important to us
1500+ // this function is dangerous and unsound. do not use.
14811501 jl_binding_t * bp = jl_get_module_binding (m , var , 1 );
14821502 jl_binding_partition_t * bpart = jl_get_binding_partition (bp , jl_current_task -> world_age );
14831503 bpart -> min_world = 0 ;
0 commit comments