[clang] 3e9e8d6 - [Driver] [C++20] [Modules] Support -fmodule-output= (2/2)

Chuanqi Xu via cfe-commits cfe-commits at lists.llvm.org
Sun Jan 15 22:02:44 PST 2023


Author: Chuanqi Xu
Date: 2023-01-16T14:01:05+08:00
New Revision: 3e9e8d6ef44244491e25f7bc918f6e91e16b7714

URL: https://github.com/llvm/llvm-project/commit/3e9e8d6ef44244491e25f7bc918f6e91e16b7714
DIFF: https://github.com/llvm/llvm-project/commit/3e9e8d6ef44244491e25f7bc918f6e91e16b7714.diff

LOG: [Driver] [C++20] [Modules] Support -fmodule-output= (2/2)

The patch implements `-fmodule-output=`. This is helpful if the build
systems want to generate these output files in other places which is not
the same with -o specified or the input file lived.

Reviewed By: dblaikie, iains

Differential Revision: https://reviews.llvm.org/D137059

Added: 
    

Modified: 
    clang/include/clang/Driver/Options.td
    clang/lib/Driver/Driver.cpp
    clang/test/Driver/module-output.cppm

Removed: 
    


################################################################################
diff  --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td
index eaaaebf8702ea..38f2f68b93860 100644
--- a/clang/include/clang/Driver/Options.td
+++ b/clang/include/clang/Driver/Options.td
@@ -2306,6 +2306,8 @@ defm prebuilt_implicit_modules : BoolFOption<"prebuilt-implicit-modules",
   PosFlag<SetTrue, [], "Look up implicit modules in the prebuilt module path">,
   NegFlag<SetFalse>, BothFlags<[NoXarchOption, CC1Option]>>;
 
+def fmodule_output_EQ : Joined<["-"], "fmodule-output=">, Flags<[NoXarchOption, CC1Option]>,
+  HelpText<"Save intermediate module file results when compiling a standard C++ module unit.">;
 def fmodule_output : Flag<["-"], "fmodule-output">, Flags<[NoXarchOption, CC1Option]>,
   HelpText<"Save intermediate module file results when compiling a standard C++ module unit.">;
 

diff  --git a/clang/lib/Driver/Driver.cpp b/clang/lib/Driver/Driver.cpp
index bc70a92551811..e20aad49b0cdf 100644
--- a/clang/lib/Driver/Driver.cpp
+++ b/clang/lib/Driver/Driver.cpp
@@ -5554,8 +5554,12 @@ const char *Driver::CreateTempFile(Compilation &C, StringRef Prefix,
 }
 
 // Calculate the output path of the module file when compiling a module unit
-// with the `-fmodule-output` option specified. The behavior is:
-// - If the output object file of the module unit is specified, the output path
+// with the `-fmodule-output` option or `-fmodule-output=` option specified.
+// The behavior is:
+// - If `-fmodule-output=` is specfied, then the module file is
+//   writing to the value.
+// - Otherwise if the output object file of the module unit is specified, the
+// output path
 //   of the module file should be the same with the output object file except
 //   the corresponding suffix. This requires both `-o` and `-c` are specified.
 // - Otherwise, the output path of the module file will be the same with the
@@ -5563,7 +5567,12 @@ const char *Driver::CreateTempFile(Compilation &C, StringRef Prefix,
 static const char *GetModuleOutputPath(Compilation &C, const JobAction &JA,
                                        const char *BaseInput) {
   assert(isa<PrecompileJobAction>(JA) && JA.getType() == types::TY_ModuleFile &&
-         C.getArgs().hasArg(options::OPT_fmodule_output));
+         (C.getArgs().hasArg(options::OPT_fmodule_output) ||
+          C.getArgs().hasArg(options::OPT_fmodule_output_EQ)));
+
+  if (Arg *ModuleOutputEQ =
+          C.getArgs().getLastArg(options::OPT_fmodule_output_EQ))
+    return C.addResultFile(ModuleOutputEQ->getValue(), &JA);
 
   SmallString<64> OutputPath;
   Arg *FinalOutput = C.getArgs().getLastArg(options::OPT_o);
@@ -5633,14 +5642,16 @@ const char *Driver::GetNamedOutputPath(Compilation &C, const JobAction &JA,
         &JA);
   }
 
-  if (MultipleArchs && C.getArgs().hasArg(options::OPT_fmodule_output))
+  bool SpecifiedModuleOutput =
+      C.getArgs().hasArg(options::OPT_fmodule_output) ||
+      C.getArgs().hasArg(options::OPT_fmodule_output_EQ);
+  if (MultipleArchs && SpecifiedModuleOutput)
     Diag(clang::diag::err_drv_module_output_with_multiple_arch);
 
   // If we're emitting a module output with the specified option
   // `-fmodule-output`.
   if (!AtTopLevel && isa<PrecompileJobAction>(JA) &&
-      JA.getType() == types::TY_ModuleFile &&
-      C.getArgs().hasArg(options::OPT_fmodule_output))
+      JA.getType() == types::TY_ModuleFile && SpecifiedModuleOutput)
     return GetModuleOutputPath(C, JA, BaseInput);
 
   // Output to a temporary file?

diff  --git a/clang/test/Driver/module-output.cppm b/clang/test/Driver/module-output.cppm
index 7d566f4eda636..604cd1791bcdf 100644
--- a/clang/test/Driver/module-output.cppm
+++ b/clang/test/Driver/module-output.cppm
@@ -23,6 +23,11 @@
 // RUN: %clang %t/Hello.cppm -fmodule-output -arch i386 -arch x86_64 -### -target \
 // RUN:   x86_64-apple-darwin 2>&1 | FileCheck %t/Hello.cppm -check-prefix=MULTIPLE-ARCH
 
+// Tests that the .pcm file will be generated in the same path with the specified one
+// in the comamnd line.
+// RUN: %clang -std=c++20 %t/Hello.cppm -fmodule-output=%t/pcm/Hello.pcm -o %t/Hello.o \
+// RUN:   -c -### 2>&1 | FileCheck %t/Hello.cppm --check-prefix=CHECK-SPECIFIED
+
 //--- Hello.cppm
 export module Hello;
 
@@ -31,6 +36,9 @@ export module Hello;
 
 // MULTIPLE-ARCH: option '-fmodule-output' can't be used with multiple arch options
 
+// CHECK-SPECIFIED: "-emit-module-interface" {{.*}}"-main-file-name" "Hello.cppm" {{.*}}"-o" "{{.*}}/pcm/Hello.pcm" "-x" "c++" "{{.*}}/Hello.cppm"
+// CHECK-SPECIFIED: "-emit-obj" {{.*}}"-main-file-name" "Hello.cppm" {{.*}}"-o" "{{.*}}/Hello.o" "-x" "pcm" "{{.*}}/pcm/Hello.pcm"
+
 //--- AnotherModule.cppm
 export module AnotherModule;
 // CHECK: "-emit-module-interface" {{.*}}"-main-file-name" "Hello.cppm" {{.*}}"-o" "{{.*}}/Hello.pcm" "-x" "c++" "{{.*}}/Hello.cppm"


        


More information about the cfe-commits mailing list