@@ -31,6 +31,29 @@ pub struct Meta {
31
31
root : String ,
32
32
}
33
33
34
+ // Linker flags to pass to LLVM's CMake invocation.
35
+ #[ derive( Debug , Clone , Default ) ]
36
+ struct LdFlags {
37
+ // CMAKE_EXE_LINKER_FLAGS
38
+ exe : OsString ,
39
+ // CMAKE_SHARED_LINKER_FLAGS
40
+ shared : OsString ,
41
+ // CMAKE_MODULE_LINKER_FLAGS
42
+ module : OsString ,
43
+ }
44
+
45
+ impl LdFlags {
46
+ fn push_all ( & mut self , s : impl AsRef < OsStr > ) {
47
+ let s = s. as_ref ( ) ;
48
+ self . exe . push ( " " ) ;
49
+ self . exe . push ( s) ;
50
+ self . shared . push ( " " ) ;
51
+ self . shared . push ( s) ;
52
+ self . module . push ( " " ) ;
53
+ self . module . push ( s) ;
54
+ }
55
+ }
56
+
34
57
// This returns whether we've already previously built LLVM.
35
58
//
36
59
// It's used to avoid busting caches during x.py check -- if we've already built
@@ -146,6 +169,7 @@ impl Step for Llvm {
146
169
147
170
// https://llvm.org/docs/CMake.html
148
171
let mut cfg = cmake:: Config :: new ( builder. src . join ( root) ) ;
172
+ let mut ldflags = LdFlags :: default ( ) ;
149
173
150
174
let profile = match ( builder. config . llvm_optimize , builder. config . llvm_release_debuginfo ) {
151
175
( false , _) => "Debug" ,
@@ -242,9 +266,9 @@ impl Step for Llvm {
242
266
if builder. config . llvm_tools_enabled {
243
267
if !target. contains ( "msvc" ) {
244
268
if target. contains ( "apple" ) {
245
- cfg . define ( "CMAKE_EXE_LINKER_FLAGS" , " -static-libstdc++") ;
269
+ ldflags . exe . push ( " -static-libstdc++") ;
246
270
} else {
247
- cfg . define ( "CMAKE_EXE_LINKER_FLAGS" , " -Wl,-Bsymbolic -static-libstdc++") ;
271
+ ldflags . exe . push ( " -Wl,-Bsymbolic -static-libstdc++") ;
248
272
}
249
273
}
250
274
}
@@ -258,11 +282,11 @@ impl Step for Llvm {
258
282
// provides no libatomic in its base system so does
259
283
// not want this.
260
284
if !builder. config . llvm_tools_enabled {
261
- cfg . define ( "CMAKE_EXE_LINKER_FLAGS" , " -latomic") ;
285
+ ldflags . exe . push ( " -latomic") ;
262
286
} else {
263
- cfg . define ( "CMAKE_EXE_LINKER_FLAGS" , " -latomic -static-libstdc++") ;
287
+ ldflags . exe . push ( " -latomic -static-libstdc++") ;
264
288
}
265
- cfg . define ( "CMAKE_SHARED_LINKER_FLAGS" , " -latomic") ;
289
+ ldflags . shared . push ( " -latomic") ;
266
290
}
267
291
268
292
if target. contains ( "msvc" ) {
@@ -309,7 +333,7 @@ impl Step for Llvm {
309
333
310
334
// Workaround for ppc32 lld limitation
311
335
if target == "powerpc-unknown-freebsd" {
312
- cfg . define ( "CMAKE_EXE_LINKER_FLAGS" , " -fuse-ld=bfd") ;
336
+ ldflags . exe . push ( " -fuse-ld=bfd") ;
313
337
}
314
338
315
339
// https://llvm.org/docs/HowToCrossCompileLLVM.html
@@ -351,7 +375,7 @@ impl Step for Llvm {
351
375
cfg. define ( "LLVM_TEMPORARILY_ALLOW_OLD_TOOLCHAIN" , "YES" ) ;
352
376
}
353
377
354
- configure_cmake ( builder, target, & mut cfg, true ) ;
378
+ configure_cmake ( builder, target, & mut cfg, true , ldflags ) ;
355
379
356
380
for ( key, val) in & builder. config . llvm_build_config {
357
381
cfg. define ( key, val) ;
@@ -399,6 +423,7 @@ fn configure_cmake(
399
423
target : TargetSelection ,
400
424
cfg : & mut cmake:: Config ,
401
425
use_compiler_launcher : bool ,
426
+ mut ldflags : LdFlags ,
402
427
) {
403
428
// Do not print installation messages for up-to-date files.
404
429
// LLVM and LLD builds can produce a lot of those and hit CI limits on log size.
@@ -507,31 +532,41 @@ fn configure_cmake(
507
532
}
508
533
509
534
cfg. build_arg ( "-j" ) . build_arg ( builder. jobs ( ) . to_string ( ) ) ;
510
- let mut cflags = builder. cflags ( target, GitRepo :: Llvm ) . join ( " " ) ;
535
+ let mut cflags: OsString = builder. cflags ( target, GitRepo :: Llvm ) . join ( " " ) . into ( ) ;
511
536
if let Some ( ref s) = builder. config . llvm_cflags {
512
- cflags. push_str ( & format ! ( " {}" , s) ) ;
537
+ cflags. push ( " " ) ;
538
+ cflags. push ( s) ;
513
539
}
514
540
// Some compiler features used by LLVM (such as thread locals) will not work on a min version below iOS 10.
515
541
if target. contains ( "apple-ios" ) {
516
542
if target. contains ( "86-" ) {
517
- cflags. push_str ( " -miphonesimulator-version-min=10.0" ) ;
543
+ cflags. push ( " -miphonesimulator-version-min=10.0" ) ;
518
544
} else {
519
- cflags. push_str ( " -miphoneos-version-min=10.0" ) ;
545
+ cflags. push ( " -miphoneos-version-min=10.0" ) ;
520
546
}
521
547
}
522
548
if builder. config . llvm_clang_cl . is_some ( ) {
523
- cflags. push_str ( & format ! ( " --target={}" , target) )
549
+ cflags. push ( & format ! ( " --target={}" , target) ) ;
550
+ }
551
+ if let Some ( flags) = env:: var_os ( "CFLAGS" ) {
552
+ cflags. push ( " " ) ;
553
+ cflags. push ( flags) ;
524
554
}
525
555
cfg. define ( "CMAKE_C_FLAGS" , cflags) ;
526
- let mut cxxflags = builder. cflags ( target, GitRepo :: Llvm ) . join ( " " ) ;
556
+ let mut cxxflags: OsString = builder. cflags ( target, GitRepo :: Llvm ) . join ( " " ) . into ( ) ;
527
557
if builder. config . llvm_static_stdcpp && !target. contains ( "msvc" ) && !target. contains ( "netbsd" ) {
528
- cxxflags. push_str ( " -static-libstdc++" ) ;
558
+ cxxflags. push ( " -static-libstdc++" ) ;
529
559
}
530
560
if let Some ( ref s) = builder. config . llvm_cxxflags {
531
- cxxflags. push_str ( & format ! ( " {}" , s) ) ;
561
+ cxxflags. push ( " " ) ;
562
+ cxxflags. push ( s) ;
532
563
}
533
564
if builder. config . llvm_clang_cl . is_some ( ) {
534
- cxxflags. push_str ( & format ! ( " --target={}" , target) )
565
+ cxxflags. push ( & format ! ( " --target={}" , target) ) ;
566
+ }
567
+ if let Some ( flags) = env:: var_os ( "CXXFLAGS" ) {
568
+ cxxflags. push ( " " ) ;
569
+ cxxflags. push ( flags) ;
535
570
}
536
571
cfg. define ( "CMAKE_CXX_FLAGS" , cxxflags) ;
537
572
if let Some ( ar) = builder. ar ( target) {
@@ -550,12 +585,18 @@ fn configure_cmake(
550
585
}
551
586
}
552
587
553
- if let Some ( ref s) = builder. config . llvm_ldflags {
554
- cfg. define ( "CMAKE_SHARED_LINKER_FLAGS" , s) ;
555
- cfg. define ( "CMAKE_MODULE_LINKER_FLAGS" , s) ;
556
- cfg. define ( "CMAKE_EXE_LINKER_FLAGS" , s) ;
588
+ if let Some ( ref flags) = builder. config . llvm_ldflags {
589
+ ldflags. push_all ( flags) ;
557
590
}
558
591
592
+ if let Some ( flags) = env:: var_os ( "LDFLAGS" ) {
593
+ ldflags. push_all ( & flags) ;
594
+ }
595
+
596
+ cfg. define ( "CMAKE_SHARED_LINKER_FLAGS" , & ldflags. shared ) ;
597
+ cfg. define ( "CMAKE_MODULE_LINKER_FLAGS" , & ldflags. module ) ;
598
+ cfg. define ( "CMAKE_EXE_LINKER_FLAGS" , & ldflags. exe ) ;
599
+
559
600
if env:: var_os ( "SCCACHE_ERROR_LOG" ) . is_some ( ) {
560
601
cfg. env ( "RUSTC_LOG" , "sccache=warn" ) ;
561
602
}
@@ -598,7 +639,7 @@ impl Step for Lld {
598
639
t ! ( fs:: create_dir_all( & out_dir) ) ;
599
640
600
641
let mut cfg = cmake:: Config :: new ( builder. src . join ( "src/llvm-project/lld" ) ) ;
601
- configure_cmake ( builder, target, & mut cfg, true ) ;
642
+ configure_cmake ( builder, target, & mut cfg, true , LdFlags :: default ( ) ) ;
602
643
603
644
// This is an awful, awful hack. Discovered when we migrated to using
604
645
// clang-cl to compile LLVM/LLD it turns out that LLD, when built out of
@@ -788,7 +829,7 @@ impl Step for Sanitizers {
788
829
// Unfortunately sccache currently lacks support to build them successfully.
789
830
// Disable compiler launcher on Darwin targets to avoid potential issues.
790
831
let use_compiler_launcher = !self . target . contains ( "apple-darwin" ) ;
791
- configure_cmake ( builder, self . target , & mut cfg, use_compiler_launcher) ;
832
+ configure_cmake ( builder, self . target , & mut cfg, use_compiler_launcher, LdFlags :: default ( ) ) ;
792
833
793
834
t ! ( fs:: create_dir_all( & out_dir) ) ;
794
835
cfg. out_dir ( out_dir) ;
0 commit comments