[llvm] r322136 - Reland "Emit Function IDs table for Control Flow Guard"

Adrian McCarthy via llvm-commits llvm-commits at lists.llvm.org
Tue Jan 9 15:49:31 PST 2018


Author: amccarth
Date: Tue Jan  9 15:49:30 2018
New Revision: 322136

URL: http://llvm.org/viewvc/llvm-project?rev=322136&view=rev
Log:
Reland "Emit Function IDs table for Control Flow Guard"

Adds option /guard:cf to clang-cl and -cfguard to cc1 to emit function IDs
of functions that have their address taken into a section named .gfids$y for
compatibility with Microsoft's Control Flow Guard feature.

The original patch didn't have the lit.local.cfg file that restricts the new
test to x86, thus the new test was failing on the non-x86 bots.

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

The reverts r322008, which was a revert of r322005.

This reverts commit a05b89f9aca70597dc79fe97bc49b50b51f525ba.

Added:
    llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.cpp
    llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.h
    llvm/trunk/test/CodeGen/WinCFGuard/
    llvm/trunk/test/CodeGen/WinCFGuard/cfguard.ll
    llvm/trunk/test/CodeGen/WinCFGuard/lit.local.cfg
    llvm/trunk/test/MC/COFF/symidx.s
Modified:
    llvm/trunk/include/llvm/MC/MCObjectFileInfo.h
    llvm/trunk/include/llvm/MC/MCStreamer.h
    llvm/trunk/include/llvm/MC/MCWinCOFFStreamer.h
    llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp
    llvm/trunk/lib/CodeGen/AsmPrinter/CMakeLists.txt
    llvm/trunk/lib/MC/MCAsmStreamer.cpp
    llvm/trunk/lib/MC/MCObjectFileInfo.cpp
    llvm/trunk/lib/MC/MCParser/COFFAsmParser.cpp
    llvm/trunk/lib/MC/MCStreamer.cpp
    llvm/trunk/lib/MC/MCWinCOFFStreamer.cpp

Modified: llvm/trunk/include/llvm/MC/MCObjectFileInfo.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCObjectFileInfo.h?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/include/llvm/MC/MCObjectFileInfo.h (original)
+++ llvm/trunk/include/llvm/MC/MCObjectFileInfo.h Tue Jan  9 15:49:30 2018
@@ -196,6 +196,7 @@ protected:
   MCSection *PDataSection;
   MCSection *XDataSection;
   MCSection *SXDataSection;
+  MCSection *GFIDsSection;
 
 public:
   void InitMCObjectFileInfo(const Triple &TT, bool PIC, MCContext &ctx,
@@ -349,6 +350,7 @@ public:
   MCSection *getPDataSection() const { return PDataSection; }
   MCSection *getXDataSection() const { return XDataSection; }
   MCSection *getSXDataSection() const { return SXDataSection; }
+  MCSection *getGFIDsSection() const { return GFIDsSection; }
 
   MCSection *getEHFrameSection() {
     return EHFrameSection;

Modified: llvm/trunk/include/llvm/MC/MCStreamer.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCStreamer.h?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/include/llvm/MC/MCStreamer.h (original)
+++ llvm/trunk/include/llvm/MC/MCStreamer.h Tue Jan  9 15:49:30 2018
@@ -500,6 +500,9 @@ public:
 
   virtual void EmitCOFFSafeSEH(MCSymbol const *Symbol);
 
+  /// \brief Emits the symbol table index of a Symbol into the current section.
+  virtual void EmitCOFFSymbolIndex(MCSymbol const *Symbol);
+
   /// \brief Emits a COFF section index.
   ///
   /// \param Symbol - Symbol the section number relocation should point to.

Modified: llvm/trunk/include/llvm/MC/MCWinCOFFStreamer.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/MC/MCWinCOFFStreamer.h?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/include/llvm/MC/MCWinCOFFStreamer.h (original)
+++ llvm/trunk/include/llvm/MC/MCWinCOFFStreamer.h Tue Jan  9 15:49:30 2018
@@ -50,6 +50,7 @@ public:
   void EmitCOFFSymbolType(int Type) override;
   void EndCOFFSymbolDef() override;
   void EmitCOFFSafeSEH(MCSymbol const *Symbol) override;
+  void EmitCOFFSymbolIndex(MCSymbol const *Symbol) override;
   void EmitCOFFSectionIndex(MCSymbol const *Symbol) override;
   void EmitCOFFSecRel32(MCSymbol const *Symbol, uint64_t Offset) override;
   void EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size,

Modified: llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp (original)
+++ llvm/trunk/lib/CodeGen/AsmPrinter/AsmPrinter.cpp Tue Jan  9 15:49:30 2018
@@ -16,6 +16,7 @@
 #include "CodeViewDebug.h"
 #include "DwarfDebug.h"
 #include "DwarfException.h"
+#include "WinCFGuard.h"
 #include "WinException.h"
 #include "llvm/ADT/APFloat.h"
 #include "llvm/ADT/APInt.h"
@@ -130,6 +131,8 @@ static const char *const DbgTimerName =
 static const char *const DbgTimerDescription = "Debug Info Emission";
 static const char *const EHTimerName = "write_exception";
 static const char *const EHTimerDescription = "DWARF Exception Writer";
+static const char *const CFGuardName = "Control Flow Guard";
+static const char *const CFGuardDescription = "Control Flow Guard Tables";
 static const char *const CodeViewLineTablesGroupName = "linetables";
 static const char *const CodeViewLineTablesGroupDescription =
   "CodeView Line Tables";
@@ -354,6 +357,13 @@ bool AsmPrinter::doInitialization(Module
   if (ES)
     Handlers.push_back(HandlerInfo(ES, EHTimerName, EHTimerDescription,
                                    DWARFGroupName, DWARFGroupDescription));
+
+  if (mdconst::extract_or_null<ConstantInt>(
+          MMI->getModule()->getModuleFlag("cfguard")))
+    Handlers.push_back(HandlerInfo(new WinCFGuard(this), CFGuardName,
+                                   CFGuardDescription, DWARFGroupName,
+                                   DWARFGroupDescription));
+
   return false;
 }
 

Modified: llvm/trunk/lib/CodeGen/AsmPrinter/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/CMakeLists.txt?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/lib/CodeGen/AsmPrinter/CMakeLists.txt (original)
+++ llvm/trunk/lib/CodeGen/AsmPrinter/CMakeLists.txt Tue Jan  9 15:49:30 2018
@@ -20,6 +20,7 @@ add_llvm_library(LLVMAsmPrinter
   EHStreamer.cpp
   ErlangGCPrinter.cpp
   OcamlGCPrinter.cpp
+  WinCFGuard.cpp
   WinException.cpp
   CodeViewDebug.cpp
 

Added: llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.cpp?rev=322136&view=auto
==============================================================================
--- llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.cpp (added)
+++ llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.cpp Tue Jan  9 15:49:30 2018
@@ -0,0 +1,45 @@
+//===-- CodeGen/AsmPrinter/WinCFGuard.cpp - Control Flow Guard Impl ------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// This file contains support for writing Win64 exception info into asm files.
+//
+//===----------------------------------------------------------------------===//
+
+#include "WinCFGuard.h"
+#include "llvm/CodeGen/AsmPrinter.h"
+#include "llvm/CodeGen/MachineFunction.h"
+#include "llvm/CodeGen/MachineModuleInfo.h"
+#include "llvm/CodeGen/MachineOperand.h"
+#include "llvm/IR/Constants.h"
+#include "llvm/IR/Metadata.h"
+#include "llvm/MC/MCAsmInfo.h"
+#include "llvm/MC/MCObjectFileInfo.h"
+#include "llvm/MC/MCStreamer.h"
+
+#include <vector>
+
+using namespace llvm;
+
+WinCFGuard::WinCFGuard(AsmPrinter *A) : AsmPrinterHandler(), Asm(A) {}
+
+WinCFGuard::~WinCFGuard() {}
+
+void WinCFGuard::endModule() {
+  const Module *M = Asm->MMI->getModule();
+  std::vector<const Function *> Functions;
+  for (const Function &F : *M)
+    if (F.hasAddressTaken())
+      Functions.push_back(&F);
+  if (Functions.empty())
+    return;
+  auto &OS = *Asm->OutStreamer;
+  OS.SwitchSection(Asm->OutContext.getObjectFileInfo()->getGFIDsSection());
+  for (const Function *F : Functions)
+    OS.EmitCOFFSymbolIndex(Asm->getSymbol(F));
+}

Added: llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.h
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.h?rev=322136&view=auto
==============================================================================
--- llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.h (added)
+++ llvm/trunk/lib/CodeGen/AsmPrinter/WinCFGuard.h Tue Jan  9 15:49:30 2018
@@ -0,0 +1,54 @@
+//===-- WinCFGuard.h - Windows Control Flow Guard Handling ----*- C++ -*--===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+// This file contains support for writing windows exception info into asm files.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef LLVM_LIB_CODEGEN_ASMPRINTER_WINCFGUARD_H
+#define LLVM_LIB_CODEGEN_ASMPRINTER_WINCFGUARD_H
+
+#include "AsmPrinterHandler.h"
+#include "llvm/Support/Compiler.h"
+
+namespace llvm {
+
+class LLVM_LIBRARY_VISIBILITY WinCFGuard : public AsmPrinterHandler {
+  /// Target of directive emission.
+  AsmPrinter *Asm;
+
+public:
+  WinCFGuard(AsmPrinter *A);
+  ~WinCFGuard() override;
+
+  void setSymbolSize(const MCSymbol *Sym, uint64_t Size) override {}
+
+  /// \brief Emit the Control Flow Guard function ID table
+  void endModule() override;
+
+  /// \brief Gather pre-function debug information.
+  /// Every beginFunction(MF) call should be followed by an endFunction(MF)
+  /// call.
+  void beginFunction(const MachineFunction *MF) override {}
+
+  /// \brief Gather post-function debug information.
+  /// Please note that some AsmPrinter implementations may not call
+  /// beginFunction at all.
+  void endFunction(const MachineFunction *MF) override {}
+
+  /// \brief Process beginning of an instruction.
+  void beginInstruction(const MachineInstr *MI) override {}
+
+  /// \brief Process end of an instruction.
+  void endInstruction() override {}
+};
+
+} // namespace llvm
+
+#endif

Modified: llvm/trunk/lib/MC/MCAsmStreamer.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCAsmStreamer.cpp?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/lib/MC/MCAsmStreamer.cpp (original)
+++ llvm/trunk/lib/MC/MCAsmStreamer.cpp Tue Jan  9 15:49:30 2018
@@ -151,6 +151,7 @@ public:
   void EmitCOFFSymbolType(int Type) override;
   void EndCOFFSymbolDef() override;
   void EmitCOFFSafeSEH(MCSymbol const *Symbol) override;
+  void EmitCOFFSymbolIndex(MCSymbol const *Symbol) override;
   void EmitCOFFSectionIndex(MCSymbol const *Symbol) override;
   void EmitCOFFSecRel32(MCSymbol const *Symbol, uint64_t Offset) override;
   void emitELFSize(MCSymbol *Symbol, const MCExpr *Value) override;
@@ -648,6 +649,12 @@ void MCAsmStreamer::EmitCOFFSafeSEH(MCSy
   Symbol->print(OS, MAI);
   EmitEOL();
 }
+
+void MCAsmStreamer::EmitCOFFSymbolIndex(MCSymbol const *Symbol) {
+  OS << "\t.symidx\t";
+  Symbol->print(OS, MAI);
+  EmitEOL();
+}
 
 void MCAsmStreamer::EmitCOFFSectionIndex(MCSymbol const *Symbol) {
   OS << "\t.secidx\t";

Modified: llvm/trunk/lib/MC/MCObjectFileInfo.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCObjectFileInfo.cpp?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/lib/MC/MCObjectFileInfo.cpp (original)
+++ llvm/trunk/lib/MC/MCObjectFileInfo.cpp Tue Jan  9 15:49:30 2018
@@ -819,6 +819,11 @@ void MCObjectFileInfo::initCOFFMCObjectF
   SXDataSection = Ctx->getCOFFSection(".sxdata", COFF::IMAGE_SCN_LNK_INFO,
                                       SectionKind::getMetadata());
 
+  GFIDsSection = Ctx->getCOFFSection(".gfids$y",
+                                     COFF::IMAGE_SCN_CNT_INITIALIZED_DATA |
+                                         COFF::IMAGE_SCN_MEM_READ,
+                                     SectionKind::getMetadata());
+
   TLSDataSection = Ctx->getCOFFSection(
       ".tls$", COFF::IMAGE_SCN_CNT_INITIALIZED_DATA | COFF::IMAGE_SCN_MEM_READ |
                    COFF::IMAGE_SCN_MEM_WRITE,

Modified: llvm/trunk/lib/MC/MCParser/COFFAsmParser.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCParser/COFFAsmParser.cpp?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/lib/MC/MCParser/COFFAsmParser.cpp (original)
+++ llvm/trunk/lib/MC/MCParser/COFFAsmParser.cpp Tue Jan  9 15:49:30 2018
@@ -65,8 +65,9 @@ class COFFAsmParser : public MCAsmParser
     addDirectiveHandler<&COFFAsmParser::ParseDirectiveType>(".type");
     addDirectiveHandler<&COFFAsmParser::ParseDirectiveEndef>(".endef");
     addDirectiveHandler<&COFFAsmParser::ParseDirectiveSecRel32>(".secrel32");
-    addDirectiveHandler<&COFFAsmParser::ParseDirectiveSecIdx>(".secidx");
+    addDirectiveHandler<&COFFAsmParser::ParseDirectiveSymIdx>(".symidx");
     addDirectiveHandler<&COFFAsmParser::ParseDirectiveSafeSEH>(".safeseh");
+    addDirectiveHandler<&COFFAsmParser::ParseDirectiveSecIdx>(".secidx");
     addDirectiveHandler<&COFFAsmParser::ParseDirectiveLinkOnce>(".linkonce");
 
     // Win64 EH directives.
@@ -130,6 +131,7 @@ class COFFAsmParser : public MCAsmParser
   bool ParseDirectiveSecRel32(StringRef, SMLoc);
   bool ParseDirectiveSecIdx(StringRef, SMLoc);
   bool ParseDirectiveSafeSEH(StringRef, SMLoc);
+  bool ParseDirectiveSymIdx(StringRef, SMLoc);
   bool parseCOMDATType(COFF::COMDATType &Type);
   bool ParseDirectiveLinkOnce(StringRef, SMLoc);
 
@@ -520,6 +522,21 @@ bool COFFAsmParser::ParseDirectiveSecIdx
   return false;
 }
 
+bool COFFAsmParser::ParseDirectiveSymIdx(StringRef, SMLoc) {
+  StringRef SymbolID;
+  if (getParser().parseIdentifier(SymbolID))
+    return TokError("expected identifier in directive");
+
+  if (getLexer().isNot(AsmToken::EndOfStatement))
+    return TokError("unexpected token in directive");
+
+  MCSymbol *Symbol = getContext().getOrCreateSymbol(SymbolID);
+
+  Lex();
+  getStreamer().EmitCOFFSymbolIndex(Symbol);
+  return false;
+}
+
 /// ::= [ identifier ]
 bool COFFAsmParser::parseCOMDATType(COFF::COMDATType &Type) {
   StringRef TypeId = getTok().getIdentifier();

Modified: llvm/trunk/lib/MC/MCStreamer.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCStreamer.cpp?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/lib/MC/MCStreamer.cpp (original)
+++ llvm/trunk/lib/MC/MCStreamer.cpp Tue Jan  9 15:49:30 2018
@@ -795,6 +795,8 @@ void MCStreamer::EmitWinCFIEndProlog(SML
 void MCStreamer::EmitCOFFSafeSEH(MCSymbol const *Symbol) {
 }
 
+void MCStreamer::EmitCOFFSymbolIndex(MCSymbol const *Symbol) {}
+
 void MCStreamer::EmitCOFFSectionIndex(MCSymbol const *Symbol) {
 }
 

Modified: llvm/trunk/lib/MC/MCWinCOFFStreamer.cpp
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/MC/MCWinCOFFStreamer.cpp?rev=322136&r1=322135&r2=322136&view=diff
==============================================================================
--- llvm/trunk/lib/MC/MCWinCOFFStreamer.cpp (original)
+++ llvm/trunk/lib/MC/MCWinCOFFStreamer.cpp Tue Jan  9 15:49:30 2018
@@ -193,6 +193,17 @@ void MCWinCOFFStreamer::EmitCOFFSafeSEH(
                    << COFF::SCT_COMPLEX_TYPE_SHIFT);
 }
 
+void MCWinCOFFStreamer::EmitCOFFSymbolIndex(MCSymbol const *Symbol) {
+  MCSection *Sec = getCurrentSectionOnly();
+  getAssembler().registerSection(*Sec);
+  if (Sec->getAlignment() < 4)
+    Sec->setAlignment(4);
+
+  new MCSymbolIdFragment(Symbol, getCurrentSectionOnly());
+
+  getAssembler().registerSymbol(*Symbol);
+}
+
 void MCWinCOFFStreamer::EmitCOFFSectionIndex(const MCSymbol *Symbol) {
   visitUsedSymbol(*Symbol);
   MCDataFragment *DF = getOrCreateDataFragment();

Added: llvm/trunk/test/CodeGen/WinCFGuard/cfguard.ll
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/WinCFGuard/cfguard.ll?rev=322136&view=auto
==============================================================================
--- llvm/trunk/test/CodeGen/WinCFGuard/cfguard.ll (added)
+++ llvm/trunk/test/CodeGen/WinCFGuard/cfguard.ll Tue Jan  9 15:49:30 2018
@@ -0,0 +1,162 @@
+; RUN: llc < %s | FileCheck %s
+
+; CHECK: .section .gfids$y
+; CHECK: .symidx "?address_taken@@YAXXZ"
+; CHECK: .symidx "?virt_method at Derived@@UEBAHXZ"
+
+; ModuleID = 'cfguard.cpp'
+source_filename = "cfguard.cpp"
+target datalayout = "e-m:w-i64:64-f80:128-n8:16:32:64-S128"
+target triple = "x86_64-pc-windows-msvc"
+
+%struct.Derived = type { %struct.Base }
+%struct.Base = type { i32 (...)** }
+%rtti.CompleteObjectLocator = type { i32, i32, i32, i32, i32, i32 }
+%rtti.TypeDescriptor13 = type { i8**, i8*, [14 x i8] }
+%rtti.ClassHierarchyDescriptor = type { i32, i32, i32, i32 }
+%rtti.BaseClassDescriptor = type { i32, i32, i32, i32, i32, i32, i32 }
+%rtti.TypeDescriptor10 = type { i8**, i8*, [11 x i8] }
+
+$"\01??0Derived@@QEAA at XZ" = comdat any
+
+$"\01??0Base@@QEAA at XZ" = comdat any
+
+$"\01?virt_method at Derived@@UEBAHXZ" = comdat any
+
+$"\01??_7Derived@@6B@" = comdat largest
+
+$"\01??_R4Derived@@6B@" = comdat any
+
+$"\01??_R0?AUDerived@@@8" = comdat any
+
+$"\01??_R3Derived@@8" = comdat any
+
+$"\01??_R2Derived@@8" = comdat any
+
+$"\01??_R1A@?0A at EA@Derived@@8" = comdat any
+
+$"\01??_R1A@?0A at EA@Base@@8" = comdat any
+
+$"\01??_R0?AUBase@@@8" = comdat any
+
+$"\01??_R3Base@@8" = comdat any
+
+$"\01??_R2Base@@8" = comdat any
+
+$"\01??_7Base@@6B@" = comdat largest
+
+$"\01??_R4Base@@6B@" = comdat any
+
+@"\01?D@@3UDerived@@A" = global %struct.Derived zeroinitializer, align 8
+ at 0 = private unnamed_addr constant { [2 x i8*] } { [2 x i8*] [i8* bitcast (%rtti.CompleteObjectLocator* @"\01??_R4Derived@@6B@" to i8*), i8* bitcast (i32 (%struct.Derived*)* @"\01?virt_method at Derived@@UEBAHXZ" to i8*)] }, comdat($"\01??_7Derived@@6B@")
+@"\01??_R4Derived@@6B@" = linkonce_odr constant %rtti.CompleteObjectLocator { i32 1, i32 0, i32 0, i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.TypeDescriptor13* @"\01??_R0?AUDerived@@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.ClassHierarchyDescriptor* @"\01??_R3Derived@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.CompleteObjectLocator* @"\01??_R4Derived@@6B@" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32) }, comdat
+@"\01??_7type_info@@6B@" = external constant i8*
+@"\01??_R0?AUDerived@@@8" = linkonce_odr global %rtti.TypeDescriptor13 { i8** @"\01??_7type_info@@6B@", i8* null, [14 x i8] c".?AUDerived@@\00" }, comdat
+ at __ImageBase = external constant i8
+@"\01??_R3Derived@@8" = linkonce_odr constant %rtti.ClassHierarchyDescriptor { i32 0, i32 0, i32 2, i32 trunc (i64 sub nuw nsw (i64 ptrtoint ([3 x i32]* @"\01??_R2Derived@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32) }, comdat
+@"\01??_R2Derived@@8" = linkonce_odr constant [3 x i32] [i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.BaseClassDescriptor* @"\01??_R1A@?0A at EA@Derived@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.BaseClassDescriptor* @"\01??_R1A@?0A at EA@Base@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 0], comdat
+@"\01??_R1A@?0A at EA@Derived@@8" = linkonce_odr constant %rtti.BaseClassDescriptor { i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.TypeDescriptor13* @"\01??_R0?AUDerived@@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 1, i32 0, i32 -1, i32 0, i32 64, i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.ClassHierarchyDescriptor* @"\01??_R3Derived@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32) }, comdat
+@"\01??_R1A@?0A at EA@Base@@8" = linkonce_odr constant %rtti.BaseClassDescriptor { i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.TypeDescriptor10* @"\01??_R0?AUBase@@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 0, i32 0, i32 -1, i32 0, i32 64, i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.ClassHierarchyDescriptor* @"\01??_R3Base@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32) }, comdat
+@"\01??_R0?AUBase@@@8" = linkonce_odr global %rtti.TypeDescriptor10 { i8** @"\01??_7type_info@@6B@", i8* null, [11 x i8] c".?AUBase@@\00" }, comdat
+@"\01??_R3Base@@8" = linkonce_odr constant %rtti.ClassHierarchyDescriptor { i32 0, i32 0, i32 1, i32 trunc (i64 sub nuw nsw (i64 ptrtoint ([2 x i32]* @"\01??_R2Base@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32) }, comdat
+@"\01??_R2Base@@8" = linkonce_odr constant [2 x i32] [i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.BaseClassDescriptor* @"\01??_R1A@?0A at EA@Base@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 0], comdat
+ at 1 = private unnamed_addr constant { [2 x i8*] } { [2 x i8*] [i8* bitcast (%rtti.CompleteObjectLocator* @"\01??_R4Base@@6B@" to i8*), i8* bitcast (void ()* @_purecall to i8*)] }, comdat($"\01??_7Base@@6B@")
+@"\01??_R4Base@@6B@" = linkonce_odr constant %rtti.CompleteObjectLocator { i32 1, i32 0, i32 0, i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.TypeDescriptor10* @"\01??_R0?AUBase@@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.ClassHierarchyDescriptor* @"\01??_R3Base@@8" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32), i32 trunc (i64 sub nuw nsw (i64 ptrtoint (%rtti.CompleteObjectLocator* @"\01??_R4Base@@6B@" to i64), i64 ptrtoint (i8* @__ImageBase to i64)) to i32) }, comdat
+ at llvm.global_ctors = appending global [1 x { i32, void ()*, i8* }] [{ i32, void ()*, i8* } { i32 65535, void ()* @_GLOBAL__sub_I_cfguard.cpp, i8* null }]
+
+@"\01??_7Derived@@6B@" = unnamed_addr alias i8*, getelementptr inbounds ({ [2 x i8*] }, { [2 x i8*] }* @0, i32 0, i32 0, i32 1)
+@"\01??_7Base@@6B@" = unnamed_addr alias i8*, getelementptr inbounds ({ [2 x i8*] }, { [2 x i8*] }* @1, i32 0, i32 0, i32 1)
+
+; Function Attrs: noinline nounwind
+define internal void @"\01??__ED@@YAXXZ"() #0 {
+entry:
+  %call = call %struct.Derived* @"\01??0Derived@@QEAA at XZ"(%struct.Derived* @"\01?D@@3UDerived@@A") #2
+  ret void
+}
+
+; Function Attrs: noinline nounwind optnone
+define linkonce_odr %struct.Derived* @"\01??0Derived@@QEAA at XZ"(%struct.Derived* returned %this) unnamed_addr #1 comdat align 2 {
+entry:
+  %this.addr = alloca %struct.Derived*, align 8
+  store %struct.Derived* %this, %struct.Derived** %this.addr, align 8
+  %this1 = load %struct.Derived*, %struct.Derived** %this.addr, align 8
+  %0 = bitcast %struct.Derived* %this1 to %struct.Base*
+  %call = call %struct.Base* @"\01??0Base@@QEAA at XZ"(%struct.Base* %0) #2
+  %1 = bitcast %struct.Derived* %this1 to i32 (...)***
+  store i32 (...)** bitcast (i8** @"\01??_7Derived@@6B@" to i32 (...)**), i32 (...)*** %1, align 8
+  ret %struct.Derived* %this1
+}
+
+; Function Attrs: noinline nounwind optnone
+define void @"\01?address_taken@@YAXXZ"() #1 {
+entry:
+  ret void
+}
+
+; Function Attrs: noinline nounwind optnone
+define void ()* @"\01?foo@@YAP6AXXZPEAUBase@@@Z"(%struct.Base* %B) #1 {
+entry:
+  %retval = alloca void ()*, align 8
+  %B.addr = alloca %struct.Base*, align 8
+  store %struct.Base* %B, %struct.Base** %B.addr, align 8
+  %0 = load %struct.Base*, %struct.Base** %B.addr, align 8
+  %1 = bitcast %struct.Base* %0 to i32 (%struct.Base*)***
+  %vtable = load i32 (%struct.Base*)**, i32 (%struct.Base*)*** %1, align 8
+  %vfn = getelementptr inbounds i32 (%struct.Base*)*, i32 (%struct.Base*)** %vtable, i64 0
+  %2 = load i32 (%struct.Base*)*, i32 (%struct.Base*)** %vfn, align 8
+  %call = call i32 %2(%struct.Base* %0)
+  %tobool = icmp ne i32 %call, 0
+  br i1 %tobool, label %if.then, label %if.end
+
+if.then:                                          ; preds = %entry
+  store void ()* @"\01?address_taken@@YAXXZ", void ()** %retval, align 8
+  br label %return
+
+if.end:                                           ; preds = %entry
+  store void ()* null, void ()** %retval, align 8
+  br label %return
+
+return:                                           ; preds = %if.end, %if.then
+  %3 = load void ()*, void ()** %retval, align 8
+  ret void ()* %3
+}
+
+; Function Attrs: noinline nounwind optnone
+define linkonce_odr %struct.Base* @"\01??0Base@@QEAA at XZ"(%struct.Base* returned %this) unnamed_addr #1 comdat align 2 {
+entry:
+  %this.addr = alloca %struct.Base*, align 8
+  store %struct.Base* %this, %struct.Base** %this.addr, align 8
+  %this1 = load %struct.Base*, %struct.Base** %this.addr, align 8
+  %0 = bitcast %struct.Base* %this1 to i32 (...)***
+  store i32 (...)** bitcast (i8** @"\01??_7Base@@6B@" to i32 (...)**), i32 (...)*** %0, align 8
+  ret %struct.Base* %this1
+}
+
+; Function Attrs: noinline nounwind optnone
+define linkonce_odr i32 @"\01?virt_method at Derived@@UEBAHXZ"(%struct.Derived* %this) unnamed_addr #1 comdat align 2 {
+entry:
+  %this.addr = alloca %struct.Derived*, align 8
+  store %struct.Derived* %this, %struct.Derived** %this.addr, align 8
+  %this1 = load %struct.Derived*, %struct.Derived** %this.addr, align 8
+  ret i32 42
+}
+
+declare dllimport void @_purecall() unnamed_addr
+
+; Function Attrs: noinline nounwind
+define internal void @_GLOBAL__sub_I_cfguard.cpp() #0 {
+entry:
+  call void @"\01??__ED@@YAXXZ"()
+  ret void
+}
+
+attributes #0 = { noinline nounwind "correctly-rounded-divide-sqrt-fp-math"="false" "disable-tail-calls"="false" "less-precise-fpmad"="false" "no-frame-pointer-elim"="false" "no-infs-fp-math"="false" "no-jump-tables"="false" "no-nans-fp-math"="false" "no-signed-zeros-fp-math"="false" "no-trapping-math"="false" "stack-protector-buffer-size"="8" "target-features"="+mmx,+sse,+sse2,+x87" "unsafe-fp-math"="false" "use-soft-float"="false" }
+attributes #1 = { noinline nounwind optnone "correctly-rounded-divide-sqrt-fp-math"="false" "disable-tail-calls"="false" "less-precise-fpmad"="false" "no-frame-pointer-elim"="false" "no-infs-fp-math"="false" "no-jump-tables"="false" "no-nans-fp-math"="false" "no-signed-zeros-fp-math"="false" "no-trapping-math"="false" "stack-protector-buffer-size"="8" "target-features"="+mmx,+sse,+sse2,+x87" "unsafe-fp-math"="false" "use-soft-float"="false" }
+attributes #2 = { nounwind }
+
+!llvm.module.flags = !{!0, !1}
+!llvm.ident = !{!2}
+
+!0 = !{i32 2, !"cfguard", i32 1}
+!1 = !{i32 1, !"wchar_size", i32 2}
+!2 = !{!"clang version 6.0.0 "}

Added: llvm/trunk/test/CodeGen/WinCFGuard/lit.local.cfg
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/CodeGen/WinCFGuard/lit.local.cfg?rev=322136&view=auto
==============================================================================
--- llvm/trunk/test/CodeGen/WinCFGuard/lit.local.cfg (added)
+++ llvm/trunk/test/CodeGen/WinCFGuard/lit.local.cfg Tue Jan  9 15:49:30 2018
@@ -0,0 +1,2 @@
+if not 'X86' in config.root.targets:
+    config.unsupported = True

Added: llvm/trunk/test/MC/COFF/symidx.s
URL: http://llvm.org/viewvc/llvm-project/llvm/trunk/test/MC/COFF/symidx.s?rev=322136&view=auto
==============================================================================
--- llvm/trunk/test/MC/COFF/symidx.s (added)
+++ llvm/trunk/test/MC/COFF/symidx.s Tue Jan  9 15:49:30 2018
@@ -0,0 +1,15 @@
+// RUN: llvm-mc -triple x86_64-pc-win32 -filetype=obj %s | llvm-objdump -s -t - | FileCheck %s
+.text
+foo:
+  ret
+bar:
+  ret
+.data
+.symidx	bar
+.symidx	foo
+
+// CHECK:      Contents of section .data:
+// CHECK-NEXT:  0000 0[[BAR:[1-9]]]000000 0[[FOO:[1-9]]]000000
+// CHECK:      SYMBOL TABLE:
+// CHECK:      [ [[FOO]]](sec  1)(fl 0x00)(ty   0)(scl   3) (nx 0) 0x00000000 foo
+// CHECK-NEXT: [ [[BAR]]](sec  1)(fl 0x00)(ty   0)(scl   3) (nx 0) 0x00000001 bar




More information about the llvm-commits mailing list