[llvm] [clang] [clang][Driver] Don't ignore -gmodules .gch files (PR #77711)

2024-01-16 Thread Michael Spencer via cfe-commits

https://github.com/Bigcheese closed 
https://github.com/llvm/llvm-project/pull/77711
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[llvm] [clang] [clang][Driver] Don't ignore -gmodules .gch files (PR #77711)

2024-01-15 Thread Michael Spencer via cfe-commits

https://github.com/Bigcheese updated 
https://github.com/llvm/llvm-project/pull/77711

>From d3e928fc5b725cb3e484a8cfd50fa23c26f7eb22 Mon Sep 17 00:00:00 2001
From: Michael Spencer 
Date: Wed, 10 Jan 2024 16:58:59 -0800
Subject: [PATCH] [clang][Driver] Don't ignore -gmodules .gch files

A previous commit (82f75ed) made clang ignore .gch files that were not
Clang AST files. This broke `-gmodules`, which embeds the Clang AST
into an object file containing debug info.

This changes the probing to detect any valid object file as a
potential Clang PCH.
---
 clang/lib/Driver/ToolChains/Clang.cpp  | 26 +++---
 clang/test/PCH/gch-probe.c |  4 
 llvm/include/llvm/BinaryFormat/Magic.h |  1 +
 llvm/lib/BinaryFormat/Magic.cpp|  2 ++
 llvm/lib/Object/Binary.cpp |  1 +
 llvm/lib/Object/ObjectFile.cpp |  1 +
 6 files changed, 28 insertions(+), 7 deletions(-)

diff --git a/clang/lib/Driver/ToolChains/Clang.cpp 
b/clang/lib/Driver/ToolChains/Clang.cpp
index 9edae3fec91a87..997ec2d491d02c 100644
--- a/clang/lib/Driver/ToolChains/Clang.cpp
+++ b/clang/lib/Driver/ToolChains/Clang.cpp
@@ -43,7 +43,9 @@
 #include "clang/Driver/XRayArgs.h"
 #include "llvm/ADT/SmallSet.h"
 #include "llvm/ADT/StringExtras.h"
+#include "llvm/BinaryFormat/Magic.h"
 #include "llvm/Config/llvm-config.h"
+#include "llvm/Object/ObjectFile.h"
 #include "llvm/Option/ArgList.h"
 #include "llvm/Support/CodeGen.h"
 #include "llvm/Support/Compiler.h"
@@ -948,11 +950,21 @@ static void handleAMDGPUCodeObjectVersionOptions(const 
Driver ,
   }
 }
 
-static bool hasClangPchSignature(const Driver , StringRef Path) {
-  if (llvm::ErrorOr> MemBuf =
-  D.getVFS().getBufferForFile(Path))
-return (*MemBuf)->getBuffer().starts_with("CPCH");
-  return false;
+static bool maybeHasClangPchSignature(const Driver , StringRef Path) {
+  llvm::ErrorOr> MemBuf =
+  D.getVFS().getBufferForFile(Path);
+  if (!MemBuf)
+return false;
+  llvm::file_magic Magic = llvm::identify_magic((*MemBuf)->getBuffer());
+  if (Magic == llvm::file_magic::unknown)
+return false;
+  // Return true for both raw Clang AST files and object files which may
+  // contain a __clangast section.
+  if (Magic == llvm::file_magic::clang_ast)
+return true;
+  Expected> Obj =
+  llvm::object::ObjectFile::createObjectFile(**MemBuf, Magic);
+  return !Obj.takeError();
 }
 
 static bool gchProbe(const Driver , StringRef Path) {
@@ -964,14 +976,14 @@ static bool gchProbe(const Driver , StringRef Path) {
 std::error_code EC;
 for (llvm::vfs::directory_iterator DI = D.getVFS().dir_begin(Path, EC), DE;
  !EC && DI != DE; DI = DI.increment(EC)) {
-  if (hasClangPchSignature(D, DI->path()))
+  if (maybeHasClangPchSignature(D, DI->path()))
 return true;
 }
 D.Diag(diag::warn_drv_pch_ignoring_gch_dir) << Path;
 return false;
   }
 
-  if (hasClangPchSignature(D, Path))
+  if (maybeHasClangPchSignature(D, Path))
 return true;
   D.Diag(diag::warn_drv_pch_ignoring_gch_file) << Path;
   return false;
diff --git a/clang/test/PCH/gch-probe.c b/clang/test/PCH/gch-probe.c
index 8b1e1fab5ad97b..0905c9baebdae0 100644
--- a/clang/test/PCH/gch-probe.c
+++ b/clang/test/PCH/gch-probe.c
@@ -2,6 +2,10 @@
 // RUN: %clang -x c-header -c %s -o %t.h.gch
 // RUN: %clang -fsyntax-only -include %t.h %s
 
+// -gmodules embeds the Clang AST file in an object file.
+// RUN: %clang -x c-header -c %s -gmodules -o %t.h.gch
+// RUN: %clang -fsyntax-only -include %t.h %s
+
 // gch probing should ignore files which are not clang pch files.
 // RUN: %clang -fsyntax-only -include %S/Inputs/gch-probe.h %s 2>&1 | 
FileCheck %s
 // CHECK: warning: precompiled header '{{.*}}gch-probe.h.gch' was ignored 
because it is not a clang PCH file
diff --git a/llvm/include/llvm/BinaryFormat/Magic.h 
b/llvm/include/llvm/BinaryFormat/Magic.h
index c635a269576587..6978c066bda468 100644
--- a/llvm/include/llvm/BinaryFormat/Magic.h
+++ b/llvm/include/llvm/BinaryFormat/Magic.h
@@ -21,6 +21,7 @@ struct file_magic {
   enum Impl {
 unknown = 0,   ///< Unrecognized file
 bitcode,   ///< Bitcode file
+clang_ast, ///< Clang PCH or PCM
 archive,   ///< ar style archive file
 elf,   ///< ELF Unknown type
 elf_relocatable,   ///< ELF Relocatable object file
diff --git a/llvm/lib/BinaryFormat/Magic.cpp b/llvm/lib/BinaryFormat/Magic.cpp
index 45a0b7e11452b4..bd378337ed3338 100644
--- a/llvm/lib/BinaryFormat/Magic.cpp
+++ b/llvm/lib/BinaryFormat/Magic.cpp
@@ -98,6 +98,8 @@ file_magic llvm::identify_magic(StringRef Magic) {
   case 'C':
 if (startswith(Magic, "CCOB"))
   return file_magic::offload_bundle_compressed;
+if (startswith(Magic, "CPCH"))
+  return file_magic::clang_ast;
 break;
   case '!':
 if (startswith(Magic, "!\n") || startswith(Magic, "!\n"))
diff --git a/llvm/lib/Object/Binary.cpp b/llvm/lib/Object/Binary.cpp
index 

[llvm] [clang] [clang][Driver] Don't ignore -gmodules .gch files (PR #77711)

2024-01-12 Thread via cfe-commits

https://github.com/zmodem approved this pull request.

lgtm

https://github.com/llvm/llvm-project/pull/77711
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[llvm] [clang] [clang][Driver] Don't ignore -gmodules .gch files (PR #77711)

2024-01-11 Thread Michael Spencer via cfe-commits

Bigcheese wrote:

I updated the patch to try to actually open the object file.

https://github.com/llvm/llvm-project/pull/77711
___
cfe-commits mailing list
cfe-commits@lists.llvm.org
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


[llvm] [clang] [clang][Driver] Don't ignore -gmodules .gch files (PR #77711)

2024-01-11 Thread Michael Spencer via cfe-commits

https://github.com/Bigcheese updated 
https://github.com/llvm/llvm-project/pull/77711

>From ef781002ef63817afa4df4834742ec3c2f22 Mon Sep 17 00:00:00 2001
From: Michael Spencer 
Date: Wed, 10 Jan 2024 16:58:59 -0800
Subject: [PATCH] [clang][Driver] Don't ignore -gmodules .gch files

A previous commit (82f75ed) made clang ignore .gch files that were not
Clang AST files. This broke `-gmodules`, which embeds the Clang AST
into an object file containing debug info.

This changes the probing to detect any valid object file as a
potential Clang PCH.
---
 clang/lib/Driver/ToolChains/Clang.cpp  | 26 +++---
 clang/test/PCH/gch-probe.c |  4 
 llvm/include/llvm/BinaryFormat/Magic.h |  1 +
 llvm/lib/BinaryFormat/Magic.cpp|  2 ++
 llvm/lib/Object/Binary.cpp |  1 +
 llvm/lib/Object/ObjectFile.cpp |  1 +
 6 files changed, 28 insertions(+), 7 deletions(-)

diff --git a/clang/lib/Driver/ToolChains/Clang.cpp 
b/clang/lib/Driver/ToolChains/Clang.cpp
index 1ee7ae602f3ce5..526c1789651011 100644
--- a/clang/lib/Driver/ToolChains/Clang.cpp
+++ b/clang/lib/Driver/ToolChains/Clang.cpp
@@ -43,7 +43,9 @@
 #include "clang/Driver/XRayArgs.h"
 #include "llvm/ADT/SmallSet.h"
 #include "llvm/ADT/StringExtras.h"
+#include "llvm/BinaryFormat/Magic.h"
 #include "llvm/Config/llvm-config.h"
+#include "llvm/Object/ObjectFile.h"
 #include "llvm/Option/ArgList.h"
 #include "llvm/Support/CodeGen.h"
 #include "llvm/Support/Compiler.h"
@@ -948,11 +950,21 @@ static void handleAMDGPUCodeObjectVersionOptions(const 
Driver ,
   }
 }
 
-static bool hasClangPchSignature(const Driver , StringRef Path) {
-  if (llvm::ErrorOr> MemBuf =
-  D.getVFS().getBufferForFile(Path))
-return (*MemBuf)->getBuffer().starts_with("CPCH");
-  return false;
+static bool maybeHasClangPchSignature(const Driver , StringRef Path) {
+  llvm::ErrorOr> MemBuf =
+  D.getVFS().getBufferForFile(Path);
+  if (!MemBuf)
+return false;
+  llvm::file_magic Magic = llvm::identify_magic((*MemBuf)->getBuffer());
+  if (Magic == llvm::file_magic::unknown)
+return false;
+  // Return true for both raw Clang AST files and object files which may
+  // contain a __clangast section.
+  if (Magic == llvm::file_magic::clang_ast)
+return true;
+  Expected> Obj =
+  llvm::object::ObjectFile::createObjectFile(**MemBuf, Magic);
+  return !Obj.takeError();
 }
 
 static bool gchProbe(const Driver , StringRef Path) {
@@ -964,14 +976,14 @@ static bool gchProbe(const Driver , StringRef Path) {
 std::error_code EC;
 for (llvm::vfs::directory_iterator DI = D.getVFS().dir_begin(Path, EC), DE;
  !EC && DI != DE; DI = DI.increment(EC)) {
-  if (hasClangPchSignature(D, DI->path()))
+  if (maybeHasClangPchSignature(D, DI->path()))
 return true;
 }
 D.Diag(diag::warn_drv_pch_ignoring_gch_dir) << Path;
 return false;
   }
 
-  if (hasClangPchSignature(D, Path))
+  if (maybeHasClangPchSignature(D, Path))
 return true;
   D.Diag(diag::warn_drv_pch_ignoring_gch_file) << Path;
   return false;
diff --git a/clang/test/PCH/gch-probe.c b/clang/test/PCH/gch-probe.c
index 8b1e1fab5ad97b..0905c9baebdae0 100644
--- a/clang/test/PCH/gch-probe.c
+++ b/clang/test/PCH/gch-probe.c
@@ -2,6 +2,10 @@
 // RUN: %clang -x c-header -c %s -o %t.h.gch
 // RUN: %clang -fsyntax-only -include %t.h %s
 
+// -gmodules embeds the Clang AST file in an object file.
+// RUN: %clang -x c-header -c %s -gmodules -o %t.h.gch
+// RUN: %clang -fsyntax-only -include %t.h %s
+
 // gch probing should ignore files which are not clang pch files.
 // RUN: %clang -fsyntax-only -include %S/Inputs/gch-probe.h %s 2>&1 | 
FileCheck %s
 // CHECK: warning: precompiled header '{{.*}}gch-probe.h.gch' was ignored 
because it is not a clang PCH file
diff --git a/llvm/include/llvm/BinaryFormat/Magic.h 
b/llvm/include/llvm/BinaryFormat/Magic.h
index c635a269576587..6978c066bda468 100644
--- a/llvm/include/llvm/BinaryFormat/Magic.h
+++ b/llvm/include/llvm/BinaryFormat/Magic.h
@@ -21,6 +21,7 @@ struct file_magic {
   enum Impl {
 unknown = 0,   ///< Unrecognized file
 bitcode,   ///< Bitcode file
+clang_ast, ///< Clang PCH or PCM
 archive,   ///< ar style archive file
 elf,   ///< ELF Unknown type
 elf_relocatable,   ///< ELF Relocatable object file
diff --git a/llvm/lib/BinaryFormat/Magic.cpp b/llvm/lib/BinaryFormat/Magic.cpp
index 45a0b7e11452b4..bd378337ed3338 100644
--- a/llvm/lib/BinaryFormat/Magic.cpp
+++ b/llvm/lib/BinaryFormat/Magic.cpp
@@ -98,6 +98,8 @@ file_magic llvm::identify_magic(StringRef Magic) {
   case 'C':
 if (startswith(Magic, "CCOB"))
   return file_magic::offload_bundle_compressed;
+if (startswith(Magic, "CPCH"))
+  return file_magic::clang_ast;
 break;
   case '!':
 if (startswith(Magic, "!\n") || startswith(Magic, "!\n"))
diff --git a/llvm/lib/Object/Binary.cpp b/llvm/lib/Object/Binary.cpp
index