@@ -16,7 +16,7 @@ use crate::ModuleLlvm;
1616use log:: debug;
1717use rustc:: bug;
1818use rustc:: ty:: TyCtxt ;
19- use rustc_codegen_ssa:: back:: write:: { run_assembler, CodegenContext , ModuleConfig } ;
19+ use rustc_codegen_ssa:: back:: write:: { run_assembler, CodegenContext , EmbedBitcode , ModuleConfig } ;
2020use rustc_codegen_ssa:: traits:: * ;
2121use rustc_codegen_ssa:: { CompiledModule , ModuleCodegen , RLIB_BYTECODE_EXTENSION } ;
2222use rustc_data_structures:: small_c_str:: SmallCStr ;
@@ -634,30 +634,24 @@ pub(crate) unsafe fn codegen(
634634 f ( cpm)
635635 }
636636
637- // If we don't have the integrated assembler, then we need to emit asm
638- // from LLVM and use `gcc` to create the object file.
639- let asm_to_obj = config. emit_obj && config. no_integrated_as ;
640-
641- // Change what we write and cleanup based on whether obj files are
642- // just llvm bitcode. In that case write bitcode, and possibly
643- // delete the bitcode if it wasn't requested. Don't generate the
644- // machine code, instead copy the .o file from the .bc
645- let write_bc = config. emit_bc || config. obj_is_bitcode ;
646- let rm_bc = !config. emit_bc && config. obj_is_bitcode ;
647- let write_obj = config. emit_obj && !config. obj_is_bitcode && !asm_to_obj;
648- let copy_bc_to_obj = config. emit_obj && config. obj_is_bitcode ;
637+ // Two things to note:
638+ // - If object files are just LLVM bitcode we write bitcode, copy it to
639+ // the .o file, and delete the bitcode if it wasn't otherwise
640+ // requested.
641+ // - If we don't have the integrated assembler then we need to emit
642+ // asm from LLVM and use `gcc` to create the object file.
649643
650644 let bc_out = cgcx. output_filenames . temp_path ( OutputType :: Bitcode , module_name) ;
651645 let obj_out = cgcx. output_filenames . temp_path ( OutputType :: Object , module_name) ;
652646
653- if write_bc || config. emit_bc_compressed || config . embed_bitcode {
647+ if config. bitcode_needed ( ) {
654648 let _timer = cgcx
655649 . prof
656650 . generic_activity_with_arg ( "LLVM_module_codegen_make_bitcode" , & module. name [ ..] ) ;
657651 let thin = ThinBuffer :: new ( llmod) ;
658652 let data = thin. data ( ) ;
659653
660- if write_bc {
654+ if config . emit_bc || config . obj_is_bitcode {
661655 let _timer = cgcx. prof . generic_activity_with_arg (
662656 "LLVM_module_codegen_emit_bitcode" ,
663657 & module. name [ ..] ,
@@ -668,7 +662,7 @@ pub(crate) unsafe fn codegen(
668662 }
669663 }
670664
671- if config. embed_bitcode {
665+ if config. embed_bitcode == EmbedBitcode :: Full {
672666 let _timer = cgcx. prof . generic_activity_with_arg (
673667 "LLVM_module_codegen_embed_bitcode" ,
674668 & module. name [ ..] ,
@@ -688,81 +682,75 @@ pub(crate) unsafe fn codegen(
688682 diag_handler. err ( & msg) ;
689683 }
690684 }
691- } else if config. embed_bitcode_marker {
685+ } else if config. embed_bitcode == EmbedBitcode :: Marker {
692686 embed_bitcode ( cgcx, llcx, llmod, None ) ;
693687 }
694688
695- {
696- if config. emit_ir {
697- let _timer = cgcx
698- . prof
699- . generic_activity_with_arg ( "LLVM_module_codegen_emit_ir" , & module. name [ ..] ) ;
700- let out = cgcx. output_filenames . temp_path ( OutputType :: LlvmAssembly , module_name) ;
701- let out_c = path_to_c_string ( & out) ;
702-
703- extern "C" fn demangle_callback (
704- input_ptr : * const c_char ,
705- input_len : size_t ,
706- output_ptr : * mut c_char ,
707- output_len : size_t ,
708- ) -> size_t {
709- let input = unsafe {
710- slice:: from_raw_parts ( input_ptr as * const u8 , input_len as usize )
711- } ;
712-
713- let input = match str:: from_utf8 ( input) {
714- Ok ( s) => s,
715- Err ( _) => return 0 ,
716- } ;
717-
718- let output = unsafe {
719- slice:: from_raw_parts_mut ( output_ptr as * mut u8 , output_len as usize )
720- } ;
721- let mut cursor = io:: Cursor :: new ( output) ;
722-
723- let demangled = match rustc_demangle:: try_demangle ( input) {
724- Ok ( d) => d,
725- Err ( _) => return 0 ,
726- } ;
727-
728- if write ! ( cursor, "{:#}" , demangled) . is_err ( ) {
729- // Possible only if provided buffer is not big enough
730- return 0 ;
731- }
732-
733- cursor. position ( ) as size_t
689+ if config. emit_ir {
690+ let _timer = cgcx
691+ . prof
692+ . generic_activity_with_arg ( "LLVM_module_codegen_emit_ir" , & module. name [ ..] ) ;
693+ let out = cgcx. output_filenames . temp_path ( OutputType :: LlvmAssembly , module_name) ;
694+ let out_c = path_to_c_string ( & out) ;
695+
696+ extern "C" fn demangle_callback (
697+ input_ptr : * const c_char ,
698+ input_len : size_t ,
699+ output_ptr : * mut c_char ,
700+ output_len : size_t ,
701+ ) -> size_t {
702+ let input =
703+ unsafe { slice:: from_raw_parts ( input_ptr as * const u8 , input_len as usize ) } ;
704+
705+ let input = match str:: from_utf8 ( input) {
706+ Ok ( s) => s,
707+ Err ( _) => return 0 ,
708+ } ;
709+
710+ let output = unsafe {
711+ slice:: from_raw_parts_mut ( output_ptr as * mut u8 , output_len as usize )
712+ } ;
713+ let mut cursor = io:: Cursor :: new ( output) ;
714+
715+ let demangled = match rustc_demangle:: try_demangle ( input) {
716+ Ok ( d) => d,
717+ Err ( _) => return 0 ,
718+ } ;
719+
720+ if write ! ( cursor, "{:#}" , demangled) . is_err ( ) {
721+ // Possible only if provided buffer is not big enough
722+ return 0 ;
734723 }
735724
736- let result = llvm:: LLVMRustPrintModule ( llmod, out_c. as_ptr ( ) , demangle_callback) ;
737- result. into_result ( ) . map_err ( |( ) | {
738- let msg = format ! ( "failed to write LLVM IR to {}" , out. display( ) ) ;
739- llvm_err ( diag_handler, & msg)
740- } ) ?;
725+ cursor. position ( ) as size_t
741726 }
742727
743- if config. emit_asm || asm_to_obj {
744- let _timer = cgcx
745- . prof
746- . generic_activity_with_arg ( "LLVM_module_codegen_emit_asm" , & module. name [ ..] ) ;
747- let path = cgcx. output_filenames . temp_path ( OutputType :: Assembly , module_name) ;
728+ let result = llvm:: LLVMRustPrintModule ( llmod, out_c. as_ptr ( ) , demangle_callback) ;
729+ result. into_result ( ) . map_err ( |( ) | {
730+ let msg = format ! ( "failed to write LLVM IR to {}" , out. display( ) ) ;
731+ llvm_err ( diag_handler, & msg)
732+ } ) ?;
733+ }
748734
749- // We can't use the same module for asm and binary output, because that triggers
750- // various errors like invalid IR or broken binaries, so we might have to clone the
751- // module to produce the asm output
752- let llmod = if config. emit_obj { llvm:: LLVMCloneModule ( llmod) } else { llmod } ;
753- with_codegen ( tm, llmod, config. no_builtins , |cpm| {
754- write_output_file (
755- diag_handler,
756- tm,
757- cpm,
758- llmod,
759- & path,
760- llvm:: FileType :: AssemblyFile ,
761- )
762- } ) ?;
763- }
735+ let config_emit_normal_obj = config. emit_obj && !config. obj_is_bitcode ;
764736
765- if write_obj {
737+ if config. emit_asm || ( config_emit_normal_obj && config. no_integrated_as ) {
738+ let _timer = cgcx
739+ . prof
740+ . generic_activity_with_arg ( "LLVM_module_codegen_emit_asm" , & module. name [ ..] ) ;
741+ let path = cgcx. output_filenames . temp_path ( OutputType :: Assembly , module_name) ;
742+
743+ // We can't use the same module for asm and binary output, because that triggers
744+ // various errors like invalid IR or broken binaries, so we might have to clone the
745+ // module to produce the asm output
746+ let llmod = if config. emit_obj { llvm:: LLVMCloneModule ( llmod) } else { llmod } ;
747+ with_codegen ( tm, llmod, config. no_builtins , |cpm| {
748+ write_output_file ( diag_handler, tm, cpm, llmod, & path, llvm:: FileType :: AssemblyFile )
749+ } ) ?;
750+ }
751+
752+ if config_emit_normal_obj {
753+ if !config. no_integrated_as {
766754 let _timer = cgcx
767755 . prof
768756 . generic_activity_with_arg ( "LLVM_module_codegen_emit_obj" , & module. name [ ..] ) ;
@@ -776,7 +764,7 @@ pub(crate) unsafe fn codegen(
776764 llvm:: FileType :: ObjectFile ,
777765 )
778766 } ) ?;
779- } else if asm_to_obj {
767+ } else {
780768 let _timer = cgcx
781769 . prof
782770 . generic_activity_with_arg ( "LLVM_module_codegen_asm_to_obj" , & module. name [ ..] ) ;
@@ -789,17 +777,19 @@ pub(crate) unsafe fn codegen(
789777 }
790778 }
791779
792- if copy_bc_to_obj {
793- debug ! ( "copying bitcode {:?} to obj {:?}" , bc_out, obj_out) ;
794- if let Err ( e) = link_or_copy ( & bc_out, & obj_out) {
795- diag_handler. err ( & format ! ( "failed to copy bitcode to object file: {}" , e) ) ;
780+ if config. obj_is_bitcode {
781+ if config. emit_obj {
782+ debug ! ( "copying bitcode {:?} to obj {:?}" , bc_out, obj_out) ;
783+ if let Err ( e) = link_or_copy ( & bc_out, & obj_out) {
784+ diag_handler. err ( & format ! ( "failed to copy bitcode to object file: {}" , e) ) ;
785+ }
796786 }
797- }
798787
799- if rm_bc {
800- debug ! ( "removing_bitcode {:?}" , bc_out) ;
801- if let Err ( e) = fs:: remove_file ( & bc_out) {
802- diag_handler. err ( & format ! ( "failed to remove bitcode: {}" , e) ) ;
788+ if !config. emit_bc {
789+ debug ! ( "removing_bitcode {:?}" , bc_out) ;
790+ if let Err ( e) = fs:: remove_file ( & bc_out) {
791+ diag_handler. err ( & format ! ( "failed to remove bitcode: {}" , e) ) ;
792+ }
803793 }
804794 }
805795
0 commit comments