about summary refs log tree commit diff
diff options
context:
space:
mode:
-rw-r--r--src/librustc_codegen_ssa/back/link.rs10
-rw-r--r--src/librustc_codegen_utils/link.rs2
-rw-r--r--src/librustc_interface/util.rs2
-rw-r--r--src/librustc_metadata/dependency_format.rs4
-rw-r--r--src/librustc_session/session.rs41
-rw-r--r--src/test/ui/proc-macro/musl-proc-macro.rs15
6 files changed, 57 insertions, 17 deletions
diff --git a/src/librustc_codegen_ssa/back/link.rs b/src/librustc_codegen_ssa/back/link.rs
index 90601521b19..387312addfa 100644
--- a/src/librustc_codegen_ssa/back/link.rs
+++ b/src/librustc_codegen_ssa/back/link.rs
@@ -497,7 +497,7 @@ fn link_natively<'a, B: ArchiveBuilder<'a>>(
         cmd.args(args);
     }
     if let Some(args) = sess.target.target.options.pre_link_args_crt.get(&flavor) {
-        if sess.crt_static() {
+        if sess.crt_static(Some(crate_type)) {
             cmd.args(args);
         }
     }
@@ -523,7 +523,7 @@ fn link_natively<'a, B: ArchiveBuilder<'a>>(
         cmd.arg(get_file_path(sess, obj));
     }
 
-    if crate_type == config::CrateType::Executable && sess.crt_static() {
+    if crate_type == config::CrateType::Executable && sess.crt_static(Some(crate_type)) {
         for obj in &sess.target.target.options.pre_link_objects_exe_crt {
             cmd.arg(get_file_path(sess, obj));
         }
@@ -558,7 +558,7 @@ fn link_natively<'a, B: ArchiveBuilder<'a>>(
     for obj in &sess.target.target.options.post_link_objects {
         cmd.arg(get_file_path(sess, obj));
     }
-    if sess.crt_static() {
+    if sess.crt_static(Some(crate_type)) {
         for obj in &sess.target.target.options.post_link_objects_crt {
             cmd.arg(get_file_path(sess, obj));
         }
@@ -1288,7 +1288,7 @@ fn link_args<'a, B: ArchiveBuilder<'a>>(
             let more_args = &sess.opts.cg.link_arg;
             let mut args = args.iter().chain(more_args.iter()).chain(used_link_args.iter());
 
-            if is_pic(sess) && !sess.crt_static() && !args.any(|x| *x == "-static") {
+            if is_pic(sess) && !sess.crt_static(Some(crate_type)) && !args.any(|x| *x == "-static") {
                 position_independent_executable = true;
             }
         }
@@ -1373,7 +1373,7 @@ fn link_args<'a, B: ArchiveBuilder<'a>>(
     if crate_type != config::CrateType::Executable {
         cmd.build_dylib(out_filename);
     }
-    if crate_type == config::CrateType::Executable && sess.crt_static() {
+    if crate_type == config::CrateType::Executable && sess.crt_static(Some(crate_type)) {
         cmd.build_static_executable();
     }
 
diff --git a/src/librustc_codegen_utils/link.rs b/src/librustc_codegen_utils/link.rs
index 524fb0a59c2..f80c19a79e2 100644
--- a/src/librustc_codegen_utils/link.rs
+++ b/src/librustc_codegen_utils/link.rs
@@ -167,7 +167,7 @@ pub fn invalid_output_for_target(sess: &Session, crate_type: config::CrateType)
             if !sess.target.target.options.dynamic_linking {
                 return true;
             }
-            if sess.crt_static() && !sess.target.target.options.crt_static_allows_dylibs {
+            if sess.crt_static(Some(crate_type)) && !sess.target.target.options.crt_static_allows_dylibs {
                 return true;
             }
         }
diff --git a/src/librustc_interface/util.rs b/src/librustc_interface/util.rs
index 10a8c0a63f1..ce0665a00ec 100644
--- a/src/librustc_interface/util.rs
+++ b/src/librustc_interface/util.rs
@@ -49,7 +49,7 @@ pub fn add_configuration(
 
     cfg.extend(codegen_backend.target_features(sess).into_iter().map(|feat| (tf, Some(feat))));
 
-    if sess.crt_static_feature() {
+    if sess.crt_static_feature(None) {
         cfg.insert((tf, Some(Symbol::intern("crt-static"))));
     }
 }
diff --git a/src/librustc_metadata/dependency_format.rs b/src/librustc_metadata/dependency_format.rs
index 9e71839dbfd..13cda397f24 100644
--- a/src/librustc_metadata/dependency_format.rs
+++ b/src/librustc_metadata/dependency_format.rs
@@ -97,7 +97,7 @@ fn calculate_type(tcx: TyCtxt<'_>, ty: config::CrateType) -> DependencyList {
 
         // If the global prefer_dynamic switch is turned off, or the final
         // executable will be statically linked, prefer static crate linkage.
-        config::CrateType::Executable if !sess.opts.cg.prefer_dynamic || sess.crt_static() => {
+        config::CrateType::Executable if !sess.opts.cg.prefer_dynamic || sess.crt_static(Some(ty)) => {
             Linkage::Static
         }
         config::CrateType::Executable => Linkage::Dynamic,
@@ -129,7 +129,7 @@ fn calculate_type(tcx: TyCtxt<'_>, ty: config::CrateType) -> DependencyList {
         // If any are not found, generate some nice pretty errors.
         if ty == config::CrateType::Staticlib
             || (ty == config::CrateType::Executable
-                && sess.crt_static()
+                && sess.crt_static(Some(ty))
                 && !sess.target.target.options.crt_static_allows_dylibs)
         {
             for &cnum in tcx.crates().iter() {
diff --git a/src/librustc_session/session.rs b/src/librustc_session/session.rs
index 2fb7977dce9..dcd9ae44e88 100644
--- a/src/librustc_session/session.rs
+++ b/src/librustc_session/session.rs
@@ -540,25 +540,50 @@ impl Session {
             .unwrap_or(self.opts.debug_assertions)
     }
 
-    pub fn crt_static(&self) -> bool {
+    /// Check whether this compile session and crate type use static crt.
+    pub fn crt_static(&self, crate_type: Option<config::CrateType>) -> bool {
         // If the target does not opt in to crt-static support, use its default.
         if self.target.target.options.crt_static_respected {
-            self.crt_static_feature()
+            self.crt_static_feature(crate_type)
         } else {
             self.target.target.options.crt_static_default
         }
     }
 
-    pub fn crt_static_feature(&self) -> bool {
+    /// Check whether this compile session and crate type use `crt-static` feature.
+    pub fn crt_static_feature(&self, crate_type: Option<config::CrateType>) -> bool {
         let requested_features = self.opts.cg.target_feature.split(',');
         let found_negative = requested_features.clone().any(|r| r == "-crt-static");
         let found_positive = requested_features.clone().any(|r| r == "+crt-static");
 
-        // If the target we're compiling for requests a static crt by default,
-        // then see if the `-crt-static` feature was passed to disable that.
-        // Otherwise if we don't have a static crt by default then see if the
-        // `+crt-static` feature was passed.
-        if self.target.target.options.crt_static_default { !found_negative } else { found_positive }
+        if self.target.target.options.crt_static_default {
+            // `proc-macro` always required to be compiled to dylibs.
+            // We don't use a static crt unless the `+crt-static` feature was passed.
+            if !self.target.target.options.crt_static_allows_dylibs {
+                match crate_type {
+                    Some(config::CrateType::ProcMacro) => found_positive,
+                    Some(_) => !found_negative,
+                    None => {
+                        // FIXME: When crate_type is not available, 
+                        // we use compiler options to determine the crate_type.
+                        // We can't check `#![crate_type = "proc-macro"]` here.
+                        if self.opts.crate_types.contains(&config::CrateType::ProcMacro) {
+                            found_positive
+                        } else {
+                            !found_negative
+                        }
+                    }
+                }
+            } else {
+                // If the target we're compiling for requests a static crt by default,
+                // then see if the `-crt-static` feature was passed to disable that.
+                !found_negative
+            }
+        } else {
+            // If the target we're compiling for don't have a static crt by default then see if the
+            // `+crt-static` feature was passed.
+            found_positive
+        }
     }
 
     pub fn must_not_eliminate_frame_pointers(&self) -> bool {
diff --git a/src/test/ui/proc-macro/musl-proc-macro.rs b/src/test/ui/proc-macro/musl-proc-macro.rs
new file mode 100644
index 00000000000..44abfcf129b
--- /dev/null
+++ b/src/test/ui/proc-macro/musl-proc-macro.rs
@@ -0,0 +1,15 @@
+// Test proc-macro crate can be built without addtional RUSTFLAGS
+// on musl target
+
+// run-pass
+// compile-flags: --target=x86_64-unknown-linux-musl
+#![crate_type = "proc-macro"]
+
+extern crate proc_macro;
+
+use proc_macro::TokenStream;
+
+#[proc_macro_derive(Foo)]
+pub fn derive_foo(input: TokenStream) -> TokenStream {
+    input
+}