@@ -647,13 +647,19 @@ fir::GlobalOp Fortran::lower::defineGlobal(
647
647
648
648
// / Return linkage attribute for \p var.
649
649
static mlir::StringAttr
650
- getLinkageAttribute (fir::FirOpBuilder &builder ,
650
+ getLinkageAttribute (Fortran::lower::AbstractConverter &converter ,
651
651
const Fortran::lower::pft::Variable &var) {
652
+ fir::FirOpBuilder &builder = converter.getFirOpBuilder ();
652
653
// Runtime type info for a same derived type is identical in each compilation
653
654
// unit. It desired to avoid having to link against module that only define a
654
655
// type. Therefore the runtime type info is generated everywhere it is needed
655
- // with `linkonce_odr` LLVM linkage.
656
- if (var.isRuntimeTypeInfoData ())
656
+ // with `linkonce_odr` LLVM linkage (unless the skipExternalRttiDefinition
657
+ // option is set, in which case one will need to link against objects of
658
+ // modules defining types). Builtin objects rtti is always generated because
659
+ // the builtin module is currently not compiled or part of the runtime.
660
+ if (var.isRuntimeTypeInfoData () &&
661
+ (!converter.getLoweringOptions ().getSkipExternalRttiDefinition () ||
662
+ Fortran::semantics::IsFromBuiltinModule (var.getSymbol ())))
657
663
return builder.createLinkOnceODRLinkage ();
658
664
if (var.isModuleOrSubmoduleVariable ())
659
665
return {}; // external linkage
@@ -673,7 +679,7 @@ static void instantiateGlobal(Fortran::lower::AbstractConverter &converter,
673
679
fir::FirOpBuilder &builder = converter.getFirOpBuilder ();
674
680
std::string globalName = converter.mangleName (sym);
675
681
mlir::Location loc = genLocation (converter, sym);
676
- mlir::StringAttr linkage = getLinkageAttribute (builder , var);
682
+ mlir::StringAttr linkage = getLinkageAttribute (converter , var);
677
683
fir::GlobalOp global;
678
684
if (var.isModuleOrSubmoduleVariable ()) {
679
685
// A non-intrinsic module global is defined when lowering the module.
@@ -1265,7 +1271,7 @@ instantiateAggregateStore(Fortran::lower::AbstractConverter &converter,
1265
1271
if (var.isGlobal ()) {
1266
1272
fir::GlobalOp global;
1267
1273
auto &aggregate = var.getAggregateStore ();
1268
- mlir::StringAttr linkage = getLinkageAttribute (builder , var);
1274
+ mlir::StringAttr linkage = getLinkageAttribute (converter , var);
1269
1275
if (var.isModuleOrSubmoduleVariable ()) {
1270
1276
// A module global was or will be defined when lowering the module. Emit
1271
1277
// only a declaration if the global does not exist at that point.
@@ -2470,8 +2476,7 @@ void Fortran::lower::defineModuleVariable(
2470
2476
AbstractConverter &converter, const Fortran::lower::pft::Variable &var) {
2471
2477
// Use empty linkage for module variables, which makes them available
2472
2478
// for use in another unit.
2473
- mlir::StringAttr linkage =
2474
- getLinkageAttribute (converter.getFirOpBuilder (), var);
2479
+ mlir::StringAttr linkage = getLinkageAttribute (converter, var);
2475
2480
if (!var.isGlobal ())
2476
2481
fir::emitFatalError (converter.getCurrentLocation (),
2477
2482
" attempting to lower module variable as local" );
@@ -2606,10 +2611,9 @@ void Fortran::lower::createIntrinsicModuleGlobal(
2606
2611
void Fortran::lower::createRuntimeTypeInfoGlobal (
2607
2612
Fortran::lower::AbstractConverter &converter,
2608
2613
const Fortran::semantics::Symbol &typeInfoSym) {
2609
- fir::FirOpBuilder &builder = converter.getFirOpBuilder ();
2610
2614
std::string globalName = converter.mangleName (typeInfoSym);
2611
2615
auto var = Fortran::lower::pft::Variable (typeInfoSym, /* global=*/ true );
2612
- mlir::StringAttr linkage = getLinkageAttribute (builder , var);
2616
+ mlir::StringAttr linkage = getLinkageAttribute (converter , var);
2613
2617
defineGlobal (converter, var, globalName, linkage);
2614
2618
}
2615
2619
0 commit comments