[clang] 7201272 - Revert "[clang] Frontend components for the relative vtables ABI"

Leonard Chan via cfe-commits cfe-commits at lists.llvm.org
Wed Jun 10 13:52:32 PDT 2020


Author: Leonard Chan
Date: 2020-06-10T13:50:05-07:00
New Revision: 7201272d4c1b7822c11593ea3ef97bc65b647e54

URL: https://github.com/llvm/llvm-project/commit/7201272d4c1b7822c11593ea3ef97bc65b647e54
DIFF: https://github.com/llvm/llvm-project/commit/7201272d4c1b7822c11593ea3ef97bc65b647e54.diff

LOG: Revert "[clang] Frontend components for the relative vtables ABI"

This reverts commit 2e009dbcb3e373a59e6e84dce6d51ae8a29f60a5.

Reverting since there were some test failures on buildbots that used the
new pass manager. ASan and MSan are also finding some bugs in this that
I'll need to address.

Added: 
    

Modified: 
    clang/include/clang/AST/VTableBuilder.h
    clang/include/clang/Basic/LangOptions.def
    clang/include/clang/CodeGen/ConstantInitBuilder.h
    clang/include/clang/Driver/Options.td
    clang/lib/AST/ASTContext.cpp
    clang/lib/AST/VTableBuilder.cpp
    clang/lib/CodeGen/CGClass.cpp
    clang/lib/CodeGen/CGVTables.cpp
    clang/lib/CodeGen/CGVTables.h
    clang/lib/CodeGen/ConstantInitBuilder.cpp
    clang/lib/CodeGen/ItaniumCXXABI.cpp
    clang/lib/CodeGen/MicrosoftCXXABI.cpp
    clang/lib/Frontend/CompilerInvocation.cpp

Removed: 
    clang/test/CodeGenCXX/RelativeVTablesABI/child-inheritted-from-parent-in-comdat.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/child-vtable-in-comdat.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/cross-translation-unit-1.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/cross-translation-unit-2.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/cross-tu-header.h
    clang/test/CodeGenCXX/RelativeVTablesABI/diamond-inheritance.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/diamond-virtual-inheritance.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/dynamic-cast.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/inheritted-virtual-function.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/inline-virtual-function.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/inlined-key-function.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/member-function-pointer.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/multiple-inheritance.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/no-alias-when-dso-local.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/no-stub-when-dso-local.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/override-pure-virtual-method.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/overriden-virtual-function.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/parent-and-child-in-comdats.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/parent-vtable-in-comdat.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/pass-byval-attributes.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/relative-vtables-flag.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/simple-vtable-definition.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/stub-linkages.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/thunk-mangling.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/type-info.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/vbase-offset.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/virtual-function-call.cpp
    clang/test/CodeGenCXX/RelativeVTablesABI/vtable-hidden-when-in-comdat.cpp


################################################################################
diff  --git a/clang/include/clang/AST/VTableBuilder.h b/clang/include/clang/AST/VTableBuilder.h
index e6557e438919..43c84292c091 100644
--- a/clang/include/clang/AST/VTableBuilder.h
+++ b/clang/include/clang/AST/VTableBuilder.h
@@ -238,11 +238,6 @@ class VTableLayout {
   typedef llvm::DenseMap<BaseSubobject, AddressPointLocation>
       AddressPointsMapTy;
 
-  // Mapping between the VTable index and address point index. This is useful
-  // when you don't care about the base subobjects and only want the address
-  // point for a given vtable index.
-  typedef llvm::SmallVector<unsigned, 4> AddressPointsIndexMapTy;
-
 private:
   // Stores the component indices of the first component of each virtual table in
   // the virtual table group. To save a little memory in the common case where
@@ -258,9 +253,6 @@ class VTableLayout {
   /// Address points for all vtables.
   AddressPointsMapTy AddressPoints;
 
-  /// Address points for all vtable indices.
-  AddressPointsIndexMapTy AddressPointIndices;
-
 public:
   VTableLayout(ArrayRef<size_t> VTableIndices,
                ArrayRef<VTableComponent> VTableComponents,
@@ -285,10 +277,6 @@ class VTableLayout {
     return AddressPoints;
   }
 
-  const AddressPointsIndexMapTy &getAddressPointIndices() const {
-    return AddressPointIndices;
-  }
-
   size_t getNumVTables() const {
     if (VTableIndices.empty())
       return 1;
@@ -383,17 +371,7 @@ class ItaniumVTableContext : public VTableContextBase {
   void computeVTableRelatedInformation(const CXXRecordDecl *RD) override;
 
 public:
-  enum VTableComponentLayout {
-    /// Components in the vtable are pointers to other structs/functions.
-    Pointer,
-
-    /// Components in the vtable are relative offsets between the vtable and the
-    /// other structs/functions.
-    Relative,
-  };
-
-  ItaniumVTableContext(ASTContext &Context,
-                       VTableComponentLayout ComponentLayout = Pointer);
+  ItaniumVTableContext(ASTContext &Context);
   ~ItaniumVTableContext() override;
 
   const VTableLayout &getVTableLayout(const CXXRecordDecl *RD) {
@@ -424,16 +402,6 @@ class ItaniumVTableContext : public VTableContextBase {
   static bool classof(const VTableContextBase *VT) {
     return !VT->isMicrosoft();
   }
-
-  VTableComponentLayout getVTableComponentLayout() const {
-    return ComponentLayout;
-  }
-
-  bool isPointerLayout() const { return ComponentLayout == Pointer; }
-  bool isRelativeLayout() const { return ComponentLayout == Relative; }
-
-private:
-  VTableComponentLayout ComponentLayout;
 };
 
 /// Holds information about the inheritance path to a virtual base or function

diff  --git a/clang/include/clang/Basic/LangOptions.def b/clang/include/clang/Basic/LangOptions.def
index 9236327f688f..caddae213a26 100644
--- a/clang/include/clang/Basic/LangOptions.def
+++ b/clang/include/clang/Basic/LangOptions.def
@@ -376,9 +376,6 @@ LANGOPT(BranchTargetEnforcement, 1, 0, "Branch-target enforcement enabled")
 
 LANGOPT(SpeculativeLoadHardening, 1, 0, "Speculative load hardening enabled")
 
-LANGOPT(RelativeCXXABIVTables, 1, 0,
-        "Use an ABI-incompatible v-table layout that uses relative references")
-
 #undef LANGOPT
 #undef COMPATIBLE_LANGOPT
 #undef BENIGN_LANGOPT

diff  --git a/clang/include/clang/CodeGen/ConstantInitBuilder.h b/clang/include/clang/CodeGen/ConstantInitBuilder.h
index 88e357a0c29c..fd07e91ba6ae 100644
--- a/clang/include/clang/CodeGen/ConstantInitBuilder.h
+++ b/clang/include/clang/CodeGen/ConstantInitBuilder.h
@@ -226,13 +226,6 @@ class ConstantAggregateBuilderBase {
     add(getRelativeOffset(type, target));
   }
 
-  /// Same as addRelativeOffset(), but instead relative to an element in this
-  /// aggregate, identified by its index.
-  void addRelativeOffsetToPosition(llvm::IntegerType *type,
-                                   llvm::Constant *target, size_t position) {
-    add(getRelativeOffsetToPosition(type, target, position));
-  }
-
   /// Add a relative offset to the target address, plus a small
   /// constant offset.  This is primarily useful when the relative
   /// offset is known to be a multiple of (say) four and therefore
@@ -305,18 +298,10 @@ class ConstantAggregateBuilderBase {
   /// position to be filled.  This is computed with an indexed
   /// getelementptr rather than by computing offsets.
   ///
-  /// The returned pointer will have type T*, where T is the given type. This
-  /// type can 
diff er from the type of the actual element.
+  /// The returned pointer will have type T*, where T is the given
+  /// position.
   llvm::Constant *getAddrOfCurrentPosition(llvm::Type *type);
 
-  /// Produce an address which points to a position in the aggregate being
-  /// constructed. This is computed with an indexed getelementptr rather than by
-  /// computing offsets.
-  ///
-  /// The returned pointer will have type T*, where T is the given type. This
-  /// type can 
diff er from the type of the actual element.
-  llvm::Constant *getAddrOfPosition(llvm::Type *type, size_t position);
-
   llvm::ArrayRef<llvm::Constant*> getGEPIndicesToCurrentPosition(
                            llvm::SmallVectorImpl<llvm::Constant*> &indices) {
     getGEPIndicesTo(indices, Builder.Buffer.size());
@@ -334,10 +319,6 @@ class ConstantAggregateBuilderBase {
   llvm::Constant *getRelativeOffset(llvm::IntegerType *offsetType,
                                     llvm::Constant *target);
 
-  llvm::Constant *getRelativeOffsetToPosition(llvm::IntegerType *offsetType,
-                                              llvm::Constant *target,
-                                              size_t position);
-
   CharUnits getOffsetFromGlobalTo(size_t index) const;
 };
 

diff  --git a/clang/include/clang/Driver/Options.td b/clang/include/clang/Driver/Options.td
index 1f4fea9a0be5..b84b9293779f 100644
--- a/clang/include/clang/Driver/Options.td
+++ b/clang/include/clang/Driver/Options.td
@@ -1299,13 +1299,6 @@ def fno_fine_grained_bitfield_accesses : Flag<["-"],
   "fno-fine-grained-bitfield-accesses">, Group<f_clang_Group>, Flags<[CC1Option]>,
   HelpText<"Use large-integer access for consecutive bitfield runs.">;
 
-def fexperimental_relative_cxx_abi_vtables : Flag<["-"], "fexperimental-relative-c++-abi-vtables">,
-  Group<f_Group>, Flags<[CC1Option]>,
-  HelpText<"Use the experimental C++ class ABI for classes with virtual tables">;
-def fno_experimental_relative_cxx_abi_vtables : Flag<["-"], "fno-experimental-relative-c++-abi-vtables">,
-  Group<f_Group>, Flags<[CC1Option]>,
-  HelpText<"Do not use the experimental C++ class ABI for classes with virtual tables">;
-
 def flat__namespace : Flag<["-"], "flat_namespace">;
 def flax_vector_conversions_EQ : Joined<["-"], "flax-vector-conversions=">, Group<f_Group>,
   HelpText<"Enable implicit vector bit-casts">, Values<"none,integer,all">, Flags<[CC1Option]>;

diff  --git a/clang/lib/AST/ASTContext.cpp b/clang/lib/AST/ASTContext.cpp
index e2df64107c9e..60482ea0664d 100644
--- a/clang/lib/AST/ASTContext.cpp
+++ b/clang/lib/AST/ASTContext.cpp
@@ -10600,15 +10600,10 @@ bool ASTContext::isNearlyEmpty(const CXXRecordDecl *RD) const {
 
 VTableContextBase *ASTContext::getVTableContext() {
   if (!VTContext.get()) {
-    auto ABI = Target->getCXXABI();
-    if (ABI.isMicrosoft())
+    if (Target->getCXXABI().isMicrosoft())
       VTContext.reset(new MicrosoftVTableContext(*this));
-    else {
-      auto ComponentLayout = getLangOpts().RelativeCXXABIVTables
-                                 ? ItaniumVTableContext::Relative
-                                 : ItaniumVTableContext::Pointer;
-      VTContext.reset(new ItaniumVTableContext(*this, ComponentLayout));
-    }
+    else
+      VTContext.reset(new ItaniumVTableContext(*this));
   }
   return VTContext.get();
 }

diff  --git a/clang/lib/AST/VTableBuilder.cpp b/clang/lib/AST/VTableBuilder.cpp
index 013ebe23ec91..0bff976905fc 100644
--- a/clang/lib/AST/VTableBuilder.cpp
+++ b/clang/lib/AST/VTableBuilder.cpp
@@ -535,8 +535,6 @@ class VCallAndVBaseOffsetBuilder {
     VBaseOffsetOffsetsMapTy;
 
 private:
-  const ItaniumVTableContext &VTables;
-
   /// MostDerivedClass - The most derived class for which we're building vcall
   /// and vbase offsets.
   const CXXRecordDecl *MostDerivedClass;
@@ -585,15 +583,13 @@ class VCallAndVBaseOffsetBuilder {
   CharUnits getCurrentOffsetOffset() const;
 
 public:
-  VCallAndVBaseOffsetBuilder(const ItaniumVTableContext &VTables,
-                             const CXXRecordDecl *MostDerivedClass,
+  VCallAndVBaseOffsetBuilder(const CXXRecordDecl *MostDerivedClass,
                              const CXXRecordDecl *LayoutClass,
                              const FinalOverriders *Overriders,
                              BaseSubobject Base, bool BaseIsVirtual,
                              CharUnits OffsetInLayoutClass)
-      : VTables(VTables), MostDerivedClass(MostDerivedClass),
-        LayoutClass(LayoutClass), Context(MostDerivedClass->getASTContext()),
-        Overriders(Overriders) {
+    : MostDerivedClass(MostDerivedClass), LayoutClass(LayoutClass),
+    Context(MostDerivedClass->getASTContext()), Overriders(Overriders) {
 
     // Add vcall and vbase offsets.
     AddVCallAndVBaseOffsets(Base, BaseIsVirtual, OffsetInLayoutClass);
@@ -666,13 +662,9 @@ CharUnits VCallAndVBaseOffsetBuilder::getCurrentOffsetOffset() const {
   // vcall offset itself).
   int64_t OffsetIndex = -(int64_t)(3 + Components.size());
 
-  // Under the relative ABI, the offset widths are 32-bit ints instead of
-  // pointer widths.
-  CharUnits OffsetWidth = Context.toCharUnitsFromBits(
-      VTables.isRelativeLayout() ? 32
-                                 : Context.getTargetInfo().getPointerWidth(0));
-  CharUnits OffsetOffset = OffsetWidth * OffsetIndex;
-
+  CharUnits PointerWidth =
+    Context.toCharUnitsFromBits(Context.getTargetInfo().getPointerWidth(0));
+  CharUnits OffsetOffset = PointerWidth * OffsetIndex;
   return OffsetOffset;
 }
 
@@ -1279,13 +1271,13 @@ ThisAdjustment ItaniumVTableBuilder::ComputeThisAdjustment(
     if (VCallOffsets.empty()) {
       // We don't have vcall offsets for this virtual base, go ahead and
       // build them.
-      VCallAndVBaseOffsetBuilder Builder(
-          VTables, MostDerivedClass, MostDerivedClass,
-          /*Overriders=*/nullptr,
-          BaseSubobject(Offset.VirtualBase, CharUnits::Zero()),
-          /*BaseIsVirtual=*/true,
-          /*OffsetInLayoutClass=*/
-          CharUnits::Zero());
+      VCallAndVBaseOffsetBuilder Builder(MostDerivedClass, MostDerivedClass,
+                                         /*Overriders=*/nullptr,
+                                         BaseSubobject(Offset.VirtualBase,
+                                                       CharUnits::Zero()),
+                                         /*BaseIsVirtual=*/true,
+                                         /*OffsetInLayoutClass=*/
+                                             CharUnits::Zero());
 
       VCallOffsets = Builder.getVCallOffsets();
     }
@@ -1643,9 +1635,9 @@ void ItaniumVTableBuilder::LayoutPrimaryAndSecondaryVTables(
   VTableIndices.push_back(VTableIndex);
 
   // Add vcall and vbase offsets for this vtable.
-  VCallAndVBaseOffsetBuilder Builder(
-      VTables, MostDerivedClass, LayoutClass, &Overriders, Base,
-      BaseIsVirtualInLayoutClass, OffsetInLayoutClass);
+  VCallAndVBaseOffsetBuilder Builder(MostDerivedClass, LayoutClass, &Overriders,
+                                     Base, BaseIsVirtualInLayoutClass,
+                                     OffsetInLayoutClass);
   Components.append(Builder.components_begin(), Builder.components_end());
 
   // Check if we need to add these vcall offsets.
@@ -2208,40 +2200,12 @@ void ItaniumVTableBuilder::dumpLayout(raw_ostream &Out) {
 }
 }
 
-static VTableLayout::AddressPointsIndexMapTy
-MakeAddressPointIndices(const VTableLayout::AddressPointsMapTy &addressPoints,
-                        unsigned numVTables) {
-  VTableLayout::AddressPointsIndexMapTy indexMap(numVTables);
-
-  for (auto it = addressPoints.begin(); it != addressPoints.end(); ++it) {
-    const auto &addressPointLoc = it->second;
-    unsigned vtableIndex = addressPointLoc.VTableIndex;
-    unsigned addressPoint = addressPointLoc.AddressPointIndex;
-    if (indexMap[vtableIndex]) {
-      // Multiple BaseSubobjects can map to the same AddressPointLocation, but
-      // every vtable index should have a unique address point.
-      assert(indexMap[vtableIndex] == addressPoint &&
-             "Every vtable index should have a unique address point. Found a "
-             "vtable that has two 
diff erent address points.");
-    } else {
-      indexMap[vtableIndex] = addressPoint;
-    }
-  }
-
-  // Note that by this point, not all the address may be initialized if the
-  // AddressPoints map is empty. This is ok if the map isn't needed. See
-  // MicrosoftVTableContext::computeVTableRelatedInformation() which uses an
-  // emprt map.
-  return indexMap;
-}
-
 VTableLayout::VTableLayout(ArrayRef<size_t> VTableIndices,
                            ArrayRef<VTableComponent> VTableComponents,
                            ArrayRef<VTableThunkTy> VTableThunks,
                            const AddressPointsMapTy &AddressPoints)
     : VTableComponents(VTableComponents), VTableThunks(VTableThunks),
-      AddressPoints(AddressPoints), AddressPointIndices(MakeAddressPointIndices(
-                                        AddressPoints, VTableIndices.size())) {
+      AddressPoints(AddressPoints) {
   if (VTableIndices.size() <= 1)
     assert(VTableIndices.size() == 1 && VTableIndices[0] == 0);
   else
@@ -2257,9 +2221,8 @@ VTableLayout::VTableLayout(ArrayRef<size_t> VTableIndices,
 
 VTableLayout::~VTableLayout() { }
 
-ItaniumVTableContext::ItaniumVTableContext(
-    ASTContext &Context, VTableComponentLayout ComponentLayout)
-    : VTableContextBase(/*MS=*/false), ComponentLayout(ComponentLayout) {}
+ItaniumVTableContext::ItaniumVTableContext(ASTContext &Context)
+    : VTableContextBase(/*MS=*/false) {}
 
 ItaniumVTableContext::~ItaniumVTableContext() {}
 
@@ -2288,7 +2251,7 @@ ItaniumVTableContext::getVirtualBaseOffsetOffset(const CXXRecordDecl *RD,
   if (I != VirtualBaseClassOffsetOffsets.end())
     return I->second;
 
-  VCallAndVBaseOffsetBuilder Builder(*this, RD, RD, /*Overriders=*/nullptr,
+  VCallAndVBaseOffsetBuilder Builder(RD, RD, /*Overriders=*/nullptr,
                                      BaseSubobject(RD, CharUnits::Zero()),
                                      /*BaseIsVirtual=*/false,
                                      /*OffsetInLayoutClass=*/CharUnits::Zero());

diff  --git a/clang/lib/CodeGen/CGClass.cpp b/clang/lib/CodeGen/CGClass.cpp
index 1d78b3fccb13..c0980df40661 100644
--- a/clang/lib/CodeGen/CGClass.cpp
+++ b/clang/lib/CodeGen/CGClass.cpp
@@ -253,13 +253,8 @@ ApplyNonVirtualAndVirtualOffset(CodeGenFunction &CGF, Address addr,
   // Compute the offset from the static and dynamic components.
   llvm::Value *baseOffset;
   if (!nonVirtualOffset.isZero()) {
-    llvm::Type *OffsetType =
-        (CGF.CGM.getTarget().getCXXABI().isItaniumFamily() &&
-         CGF.CGM.getItaniumVTableContext().isRelativeLayout())
-            ? CGF.Int32Ty
-            : CGF.PtrDiffTy;
-    baseOffset =
-        llvm::ConstantInt::get(OffsetType, nonVirtualOffset.getQuantity());
+    baseOffset = llvm::ConstantInt::get(CGF.PtrDiffTy,
+                                        nonVirtualOffset.getQuantity());
     if (virtualOffset) {
       baseOffset = CGF.Builder.CreateAdd(virtualOffset, baseOffset);
     }

diff  --git a/clang/lib/CodeGen/CGVTables.cpp b/clang/lib/CodeGen/CGVTables.cpp
index 73a74ca3e47a..6a0a848a49df 100644
--- a/clang/lib/CodeGen/CGVTables.cpp
+++ b/clang/lib/CodeGen/CGVTables.cpp
@@ -618,178 +618,29 @@ void CodeGenVTables::EmitThunks(GlobalDecl GD) {
     maybeEmitThunk(GD, Thunk, /*ForVTable=*/false);
 }
 
-void CodeGenVTables::addRelativeComponent(ConstantArrayBuilder &builder,
-                                          llvm::Constant *component,
-                                          unsigned vtableAddressPoint,
-                                          bool vtableHasLocalLinkage,
-                                          bool isCompleteDtor) const {
-  // No need to get the offset of a nullptr.
-  if (component->isNullValue())
-    return builder.add(llvm::ConstantInt::get(CGM.Int32Ty, 0));
-
-  auto *globalVal =
-      cast<llvm::GlobalValue>(component->stripPointerCastsAndAliases());
-  llvm::Module &module = CGM.getModule();
-
-  // We don't want to copy the linkage of the vtable exactly because we still
-  // want the stub/proxy to be emitted for properly calculating the offset.
-  // Examples where there would be no symbol emitted are available_externally
-  // and private linkages.
-  auto stubLinkage = vtableHasLocalLinkage ? llvm::GlobalValue::InternalLinkage
-                                           : llvm::GlobalValue::ExternalLinkage;
-
-  llvm::Constant *target;
-  if (auto *func = dyn_cast<llvm::Function>(globalVal)) {
-    target = getOrCreateRelativeStub(func, stubLinkage, isCompleteDtor);
-  } else {
-    llvm::SmallString<16> rttiProxyName(globalVal->getName());
-    rttiProxyName.append(".rtti_proxy");
-
-    // The RTTI component may not always be emitted in the same linkage unit as
-    // the vtable. As a general case, we can make a dso_local proxy to the RTTI
-    // that points to the actual RTTI struct somewhere. This will result in a
-    // GOTPCREL relocation when taking the relative offset to the proxy.
-    llvm::GlobalVariable *proxy = module.getNamedGlobal(rttiProxyName);
-    if (!proxy) {
-      proxy = new llvm::GlobalVariable(module, globalVal->getType(),
-                                       /*isConstant=*/true, stubLinkage,
-                                       globalVal, rttiProxyName);
-      proxy->setDSOLocal(true);
-      proxy->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
-      if (!proxy->hasLocalLinkage()) {
-        proxy->setVisibility(llvm::GlobalValue::HiddenVisibility);
-        proxy->setComdat(module.getOrInsertComdat(rttiProxyName));
-      }
-    }
-    target = proxy;
-  }
-
-  builder.addRelativeOffsetToPosition(CGM.Int32Ty, target,
-                                      /*position=*/vtableAddressPoint);
-}
-
-llvm::Function *CodeGenVTables::getOrCreateRelativeStub(
-    llvm::Function *func, llvm::GlobalValue::LinkageTypes stubLinkage,
-    bool isCompleteDtor) const {
-  // A complete object destructor can later be substituted in the vtable for an
-  // appropriate base object destructor when optimizations are enabled. This can
-  // happen for child classes that don't have their own destructor. In the case
-  // where a parent virtual destructor is not guaranteed to be in the same
-  // linkage unit as the child vtable, it's possible for an external reference
-  // for this destructor to be substituted into the child vtable, preventing it
-  // from being in rodata. If this function is a complete virtual destructor, we
-  // can just force a stub to be emitted for it.
-  if (func->isDSOLocal() && !isCompleteDtor)
-    return func;
-
-  llvm::SmallString<16> stubName(func->getName());
-  stubName.append(".stub");
-
-  // Instead of taking the offset between the vtable and virtual function
-  // directly, we emit a dso_local stub that just contains a tail call to the
-  // original virtual function and take the offset between that and the
-  // vtable. We do this because there are some cases where the original
-  // function that would've been inserted into the vtable is not dso_local
-  // which may require some kind of dynamic relocation which prevents the
-  // vtable from being readonly. On x86_64, taking the offset between the
-  // function and the vtable gets lowered to the offset between the PLT entry
-  // for the function and the vtable which gives us a PLT32 reloc. On AArch64,
-  // right now only CALL26 and JUMP26 instructions generate PLT relocations,
-  // so we manifest them with stubs that are just jumps to the original
-  // function.
-  auto &module = CGM.getModule();
-  llvm::Function *stub = module.getFunction(stubName);
-  if (stub) {
-    assert(stub->isDSOLocal() &&
-           "The previous definition of this stub should've been dso_local.");
-    return stub;
-  }
-
-  stub = llvm::Function::Create(func->getFunctionType(), stubLinkage, stubName,
-                                module);
-
-  // Propogate function attributes.
-  stub->setAttributes(func->getAttributes());
-
-  stub->setDSOLocal(true);
-  stub->setUnnamedAddr(llvm::GlobalValue::UnnamedAddr::Global);
-  if (!stub->hasLocalLinkage()) {
-    stub->setVisibility(llvm::GlobalValue::HiddenVisibility);
-    stub->setComdat(module.getOrInsertComdat(stubName));
-  }
-
-  // Fill the stub with a tail call that will be optimized.
-  llvm::BasicBlock *block =
-      llvm::BasicBlock::Create(module.getContext(), "entry", stub);
-  llvm::IRBuilder<> block_builder(block);
-  llvm::SmallVector<llvm::Value *, 8> args;
-  for (auto &arg : stub->args())
-    args.push_back(&arg);
-  llvm::CallInst *call = block_builder.CreateCall(func, args);
-  call->setAttributes(func->getAttributes());
-  call->setTailCall();
-  if (call->getType()->isVoidTy())
-    block_builder.CreateRetVoid();
-  else
-    block_builder.CreateRet(call);
-
-  return stub;
-}
-
-bool CodeGenVTables::useRelativeLayout() const {
-  return CGM.getTarget().getCXXABI().isItaniumFamily() &&
-         CGM.getItaniumVTableContext().isRelativeLayout();
-}
-
-llvm::Type *CodeGenVTables::getVTableComponentType() const {
-  if (useRelativeLayout())
-    return CGM.Int32Ty;
-  return CGM.Int8PtrTy;
-}
-
-static void AddPointerLayoutOffset(const CodeGenModule &CGM,
-                                   ConstantArrayBuilder &builder,
-                                   CharUnits offset) {
-  builder.add(llvm::ConstantExpr::getIntToPtr(
-      llvm::ConstantInt::get(CGM.PtrDiffTy, offset.getQuantity()),
-      CGM.Int8PtrTy));
-}
+void CodeGenVTables::addVTableComponent(
+    ConstantArrayBuilder &builder, const VTableLayout &layout,
+    unsigned idx, llvm::Constant *rtti, unsigned &nextVTableThunkIndex) {
+  auto &component = layout.vtable_components()[idx];
 
-static void AddRelativeLayoutOffset(const CodeGenModule &CGM,
-                                    ConstantArrayBuilder &builder,
-                                    CharUnits offset) {
-  builder.add(llvm::ConstantInt::get(CGM.Int32Ty, offset.getQuantity()));
-}
-
-void CodeGenVTables::addVTableComponent(ConstantArrayBuilder &builder,
-                                        const VTableLayout &layout,
-                                        unsigned componentIndex,
-                                        llvm::Constant *rtti,
-                                        unsigned &nextVTableThunkIndex,
-                                        unsigned vtableAddressPoint,
-                                        bool vtableHasLocalLinkage) {
-  auto &component = layout.vtable_components()[componentIndex];
-
-  auto addOffsetConstant =
-      useRelativeLayout() ? AddRelativeLayoutOffset : AddPointerLayoutOffset;
+  auto addOffsetConstant = [&](CharUnits offset) {
+    builder.add(llvm::ConstantExpr::getIntToPtr(
+        llvm::ConstantInt::get(CGM.PtrDiffTy, offset.getQuantity()),
+        CGM.Int8PtrTy));
+  };
 
   switch (component.getKind()) {
   case VTableComponent::CK_VCallOffset:
-    return addOffsetConstant(CGM, builder, component.getVCallOffset());
+    return addOffsetConstant(component.getVCallOffset());
 
   case VTableComponent::CK_VBaseOffset:
-    return addOffsetConstant(CGM, builder, component.getVBaseOffset());
+    return addOffsetConstant(component.getVBaseOffset());
 
   case VTableComponent::CK_OffsetToTop:
-    return addOffsetConstant(CGM, builder, component.getOffsetToTop());
+    return addOffsetConstant(component.getOffsetToTop());
 
   case VTableComponent::CK_RTTI:
-    if (useRelativeLayout())
-      return addRelativeComponent(builder, rtti, vtableAddressPoint,
-                                  vtableHasLocalLinkage,
-                                  /*isCompleteDtor=*/false);
-    else
-      return builder.add(llvm::ConstantExpr::getBitCast(rtti, CGM.Int8PtrTy));
+    return builder.add(llvm::ConstantExpr::getBitCast(rtti, CGM.Int8PtrTy));
 
   case VTableComponent::CK_FunctionPointer:
   case VTableComponent::CK_CompleteDtorPointer:
@@ -823,21 +674,11 @@ void CodeGenVTables::addVTableComponent(ConstantArrayBuilder &builder,
               ? MD->hasAttr<CUDADeviceAttr>()
               : (MD->hasAttr<CUDAHostAttr>() || !MD->hasAttr<CUDADeviceAttr>());
       if (!CanEmitMethod)
-        return builder.add(llvm::ConstantExpr::getNullValue(CGM.Int8PtrTy));
+        return builder.addNullPointer(CGM.Int8PtrTy);
       // Method is acceptable, continue processing as usual.
     }
 
     auto getSpecialVirtualFn = [&](StringRef name) -> llvm::Constant * {
-      // FIXME(PR43094): When merging comdat groups, lld can select a local
-      // symbol as the signature symbol even though it cannot be accessed
-      // outside that symbol's TU. The relative vtables ABI would make
-      // __cxa_pure_virtual and __cxa_deleted_virtual local symbols, and
-      // depending on link order, the comdat groups could resolve to the one
-      // with the local symbol. As a temporary solution, fill these components
-      // with zero. We shouldn't be calling these in the first place anyway.
-      if (useRelativeLayout())
-        return llvm::ConstantPointerNull::get(CGM.Int8PtrTy);
-
       // For NVPTX devices in OpenMP emit special functon as null pointers,
       // otherwise linking ends up with unresolved references.
       if (CGM.getLangOpts().OpenMP && CGM.getLangOpts().OpenMPIsDevice &&
@@ -858,20 +699,19 @@ void CodeGenVTables::addVTableComponent(ConstantArrayBuilder &builder,
     if (cast<CXXMethodDecl>(GD.getDecl())->isPure()) {
       if (!PureVirtualFn)
         PureVirtualFn =
-            getSpecialVirtualFn(CGM.getCXXABI().GetPureVirtualCallName());
+          getSpecialVirtualFn(CGM.getCXXABI().GetPureVirtualCallName());
       fnPtr = PureVirtualFn;
 
     // Deleted virtual member functions.
     } else if (cast<CXXMethodDecl>(GD.getDecl())->isDeleted()) {
       if (!DeletedVirtualFn)
         DeletedVirtualFn =
-            getSpecialVirtualFn(CGM.getCXXABI().GetDeletedVirtualCallName());
+          getSpecialVirtualFn(CGM.getCXXABI().GetDeletedVirtualCallName());
       fnPtr = DeletedVirtualFn;
 
     // Thunks.
     } else if (nextVTableThunkIndex < layout.vtable_thunks().size() &&
-               layout.vtable_thunks()[nextVTableThunkIndex].first ==
-                   componentIndex) {
+               layout.vtable_thunks()[nextVTableThunkIndex].first == idx) {
       auto &thunkInfo = layout.vtable_thunks()[nextVTableThunkIndex].second;
 
       nextVTableThunkIndex++;
@@ -883,19 +723,13 @@ void CodeGenVTables::addVTableComponent(ConstantArrayBuilder &builder,
       fnPtr = CGM.GetAddrOfFunction(GD, fnTy, /*ForVTable=*/true);
     }
 
-    if (useRelativeLayout()) {
-      return addRelativeComponent(
-          builder, fnPtr, vtableAddressPoint, vtableHasLocalLinkage,
-          component.getKind() == VTableComponent::CK_CompleteDtorPointer);
-    } else
-      return builder.add(llvm::ConstantExpr::getBitCast(fnPtr, CGM.Int8PtrTy));
+    fnPtr = llvm::ConstantExpr::getBitCast(fnPtr, CGM.Int8PtrTy);
+    builder.add(fnPtr);
+    return;
   }
 
   case VTableComponent::CK_UnusedFunctionPointer:
-    if (useRelativeLayout())
-      return builder.add(llvm::ConstantExpr::getNullValue(CGM.Int32Ty));
-    else
-      return builder.addNullPointer(CGM.Int8PtrTy);
+    return builder.addNullPointer(CGM.Int8PtrTy);
   }
 
   llvm_unreachable("Unexpected vtable component kind");
@@ -903,41 +737,34 @@ void CodeGenVTables::addVTableComponent(ConstantArrayBuilder &builder,
 
 llvm::Type *CodeGenVTables::getVTableType(const VTableLayout &layout) {
   SmallVector<llvm::Type *, 4> tys;
-  llvm::Type *componentType = getVTableComponentType();
-  for (unsigned i = 0, e = layout.getNumVTables(); i != e; ++i)
-    tys.push_back(llvm::ArrayType::get(componentType, layout.getVTableSize(i)));
+  for (unsigned i = 0, e = layout.getNumVTables(); i != e; ++i) {
+    tys.push_back(llvm::ArrayType::get(CGM.Int8PtrTy, layout.getVTableSize(i)));
+  }
 
   return llvm::StructType::get(CGM.getLLVMContext(), tys);
 }
 
 void CodeGenVTables::createVTableInitializer(ConstantStructBuilder &builder,
                                              const VTableLayout &layout,
-                                             llvm::Constant *rtti,
-                                             bool vtableHasLocalLinkage) {
-  llvm::Type *componentType = getVTableComponentType();
-
-  const auto &addressPoints = layout.getAddressPointIndices();
+                                             llvm::Constant *rtti) {
   unsigned nextVTableThunkIndex = 0;
-  for (unsigned vtableIndex = 0, endIndex = layout.getNumVTables();
-       vtableIndex != endIndex; ++vtableIndex) {
-    auto vtableElem = builder.beginArray(componentType);
-
-    size_t vtableStart = layout.getVTableOffset(vtableIndex);
-    size_t vtableEnd = vtableStart + layout.getVTableSize(vtableIndex);
-    for (size_t componentIndex = vtableStart; componentIndex < vtableEnd;
-         ++componentIndex) {
-      addVTableComponent(vtableElem, layout, componentIndex, rtti,
-                         nextVTableThunkIndex, addressPoints[vtableIndex],
-                         vtableHasLocalLinkage);
+  for (unsigned i = 0, e = layout.getNumVTables(); i != e; ++i) {
+    auto vtableElem = builder.beginArray(CGM.Int8PtrTy);
+    size_t thisIndex = layout.getVTableOffset(i);
+    size_t nextIndex = thisIndex + layout.getVTableSize(i);
+    for (unsigned i = thisIndex; i != nextIndex; ++i) {
+      addVTableComponent(vtableElem, layout, i, rtti, nextVTableThunkIndex);
     }
     vtableElem.finishAndAddTo(builder);
   }
 }
 
-llvm::GlobalVariable *CodeGenVTables::GenerateConstructionVTable(
-    const CXXRecordDecl *RD, const BaseSubobject &Base, bool BaseIsVirtual,
-    llvm::GlobalVariable::LinkageTypes Linkage,
-    VTableAddressPointsMapTy &AddressPoints) {
+llvm::GlobalVariable *
+CodeGenVTables::GenerateConstructionVTable(const CXXRecordDecl *RD,
+                                      const BaseSubobject &Base,
+                                      bool BaseIsVirtual,
+                                   llvm::GlobalVariable::LinkageTypes Linkage,
+                                      VTableAddressPointsMapTy& AddressPoints) {
   if (CGDebugInfo *DI = CGM.getModuleDebugInfo())
     DI->completeClassData(Base.getBase());
 
@@ -954,14 +781,7 @@ llvm::GlobalVariable *CodeGenVTables::GenerateConstructionVTable(
   cast<ItaniumMangleContext>(CGM.getCXXABI().getMangleContext())
       .mangleCXXCtorVTable(RD, Base.getBaseOffset().getQuantity(),
                            Base.getBase(), Out);
-  SmallString<256> Name(OutName);
-
-  bool UsingRelativeLayout = getItaniumVTableContext().isRelativeLayout();
-  bool VTableAliasExists = UsingRelativeLayout && CGM.getModule().getNamedAlias(Name);
-  if (VTableAliasExists) {
-    // We previously made the vtable hidden and changed its name.
-    Name.append(".local");
-  }
+  StringRef Name = OutName.str();
 
   llvm::Type *VTType = getVTableType(*VTLayout);
 
@@ -988,8 +808,7 @@ llvm::GlobalVariable *CodeGenVTables::GenerateConstructionVTable(
   // Create and set the initializer.
   ConstantInitBuilder builder(CGM);
   auto components = builder.beginStruct();
-  createVTableInitializer(components, *VTLayout, RTTI,
-                          VTable->hasLocalLinkage());
+  createVTableInitializer(components, *VTLayout, RTTI);
   components.finishAndSetAsInitializer(VTable);
 
   // Set properties only after the initializer has been set to ensure that the
@@ -999,64 +818,9 @@ llvm::GlobalVariable *CodeGenVTables::GenerateConstructionVTable(
 
   CGM.EmitVTableTypeMetadata(RD, VTable, *VTLayout.get());
 
-  if (UsingRelativeLayout && !VTable->isDSOLocal())
-    GenerateRelativeVTableAlias(VTable, OutName);
-
   return VTable;
 }
 
-// If the VTable is not dso_local, then we will not be able to indicate that
-// the VTable does not need a relocation and move into rodata. An frequent
-// time this can occur is for classes that should be made public from a DSO
-// (like in libc++). For cases like these, we can make the vtable hidden or
-// private and create a public alias with the same visibility and linkage as
-// the original vtable type.
-void CodeGenVTables::GenerateRelativeVTableAlias(llvm::GlobalVariable *VTable,
-                                                 llvm::StringRef AliasName) {
-  assert(getItaniumVTableContext().isRelativeLayout() &&
-         "Can only use this if the relative vtable ABI is used");
-  assert(!VTable->isDSOLocal() && "This should be called only if the vtable is "
-                                  "not guaranteed to be dso_local");
-
-  // If the vtable is available_externally, we shouldn't (or need to) generate
-  // an alias for it in the first place since the vtable won't actually by
-  // emitted in this compilation unit.
-  if (VTable->hasAvailableExternallyLinkage())
-    return;
-
-  VTable->setName(AliasName + ".local");
-
-  auto Linkage = VTable->getLinkage();
-  assert(llvm::GlobalAlias::isValidLinkage(Linkage) &&
-         "Invalid vtable alias linkage");
-
-  llvm::GlobalAlias *VTableAlias = CGM.getModule().getNamedAlias(AliasName);
-  if (!VTableAlias) {
-    VTableAlias = llvm::GlobalAlias::create(
-        VTable->getValueType(), VTable->getAddressSpace(), Linkage, AliasName,
-        &CGM.getModule());
-  } else {
-    assert(VTableAlias->getValueType() == VTable->getValueType());
-    assert(VTableAlias->getLinkage() == Linkage);
-  }
-  VTableAlias->setVisibility(VTable->getVisibility());
-  VTableAlias->setUnnamedAddr(VTable->getUnnamedAddr());
-
-  // Both of these imply dso_local for the vtable.
-  if (!VTable->hasComdat()) {
-    // If this is in a comdat, then we shouldn't make the linkage private due to
-    // an issue in lld where private symbols can be used as the key symbol when
-    // choosing the prevelant group. This leads to "relocation refers to a
-    // symbol in a discarded section".
-    VTable->setLinkage(llvm::GlobalValue::PrivateLinkage);
-  } else {
-    // We should at least make this hidden since we don't want to expose it.
-    VTable->setVisibility(llvm::GlobalValue::HiddenVisibility);
-  }
-
-  VTableAlias->setAliasee(VTable);
-}
-
 static bool shouldEmitAvailableExternallyVTable(const CodeGenModule &CGM,
                                                 const CXXRecordDecl *RD) {
   return CGM.getCodeGenOpts().OptimizationLevel > 0 &&

diff  --git a/clang/lib/CodeGen/CGVTables.h b/clang/lib/CodeGen/CGVTables.h
index df98d7be1414..a47841bfc6c3 100644
--- a/clang/lib/CodeGen/CGVTables.h
+++ b/clang/lib/CodeGen/CGVTables.h
@@ -62,39 +62,16 @@ class CodeGenVTables {
                                  bool ForVTable);
 
   void addVTableComponent(ConstantArrayBuilder &builder,
-                          const VTableLayout &layout, unsigned componentIndex,
-                          llvm::Constant *rtti, unsigned &nextVTableThunkIndex,
-                          unsigned vtableAddressPoint,
-                          bool vtableHasLocalLinkage);
-
-  /// Add a 32-bit offset to a component relative to the vtable when using the
-  /// relative vtables ABI. The array builder points to the start of the vtable.
-  void addRelativeComponent(ConstantArrayBuilder &builder,
-                            llvm::Constant *component,
-                            unsigned vtableAddressPoint,
-                            bool vtableHasLocalLinkage,
-                            bool isCompleteDtor) const;
-
-  /// Create a dso_local stub that will be used for a relative reference in the
-  /// relative vtable layout. This stub will just be a tail call to the original
-  /// function and propagate any function attributes from the original. If the
-  /// original function is already dso_local, the original is returned instead
-  /// and a stub is not created.
-  llvm::Function *
-  getOrCreateRelativeStub(llvm::Function *func,
-                          llvm::GlobalValue::LinkageTypes stubLinkage,
-                          bool isCompleteDtor) const;
-
-  bool useRelativeLayout() const;
-
-  llvm::Type *getVTableComponentType() const;
+                          const VTableLayout &layout, unsigned idx,
+                          llvm::Constant *rtti,
+                          unsigned &nextVTableThunkIndex);
 
 public:
   /// Add vtable components for the given vtable layout to the given
   /// global initializer.
   void createVTableInitializer(ConstantStructBuilder &builder,
-                               const VTableLayout &layout, llvm::Constant *rtti,
-                               bool vtableHasLocalLinkage);
+                               const VTableLayout &layout,
+                               llvm::Constant *rtti);
 
   CodeGenVTables(CodeGenModule &CGM);
 
@@ -147,13 +124,6 @@ class CodeGenVTables {
   /// arrays of pointers, with one struct element for each vtable in the vtable
   /// group.
   llvm::Type *getVTableType(const VTableLayout &layout);
-
-  /// Generate a public facing alias for the vtable and make the vtable either
-  /// hidden or private. The alias will have the original linkage and visibility
-  /// of the vtable. This is used for cases under the relative vtables ABI
-  /// when a vtable may not be dso_local.
-  void GenerateRelativeVTableAlias(llvm::GlobalVariable *VTable,
-                                   llvm::StringRef AliasName);
 };
 
 } // end namespace CodeGen

diff  --git a/clang/lib/CodeGen/ConstantInitBuilder.cpp b/clang/lib/CodeGen/ConstantInitBuilder.cpp
index 326f079e82fa..2d63d88020be 100644
--- a/clang/lib/CodeGen/ConstantInitBuilder.cpp
+++ b/clang/lib/CodeGen/ConstantInitBuilder.cpp
@@ -128,14 +128,8 @@ void ConstantAggregateBuilderBase::addSize(CharUnits size) {
 llvm::Constant *
 ConstantAggregateBuilderBase::getRelativeOffset(llvm::IntegerType *offsetType,
                                                 llvm::Constant *target) {
-  return getRelativeOffsetToPosition(offsetType, target,
-                                     Builder.SelfReferences.size());
-}
-
-llvm::Constant *ConstantAggregateBuilderBase::getRelativeOffsetToPosition(
-    llvm::IntegerType *offsetType, llvm::Constant *target, size_t position) {
   // Compute the address of the relative-address slot.
-  auto base = getAddrOfPosition(offsetType, position);
+  auto base = getAddrOfCurrentPosition(offsetType);
 
   // Subtract.
   base = llvm::ConstantExpr::getPtrToInt(base, Builder.CGM.IntPtrTy);
@@ -150,20 +144,6 @@ llvm::Constant *ConstantAggregateBuilderBase::getRelativeOffsetToPosition(
   return offset;
 }
 
-llvm::Constant *
-ConstantAggregateBuilderBase::getAddrOfPosition(llvm::Type *type,
-                                                size_t position) {
-  // Make a global variable.  We will replace this with a GEP to this
-  // position after installing the initializer.
-  auto dummy = new llvm::GlobalVariable(Builder.CGM.getModule(), type, true,
-                                        llvm::GlobalVariable::PrivateLinkage,
-                                        nullptr, "");
-  Builder.SelfReferences.emplace_back(dummy);
-  auto &entry = Builder.SelfReferences.back();
-  (void)getGEPIndicesTo(entry.Indices, position + Begin);
-  return dummy;
-}
-
 llvm::Constant *
 ConstantAggregateBuilderBase::getAddrOfCurrentPosition(llvm::Type *type) {
   // Make a global variable.  We will replace this with a GEP to this

diff  --git a/clang/lib/CodeGen/ItaniumCXXABI.cpp b/clang/lib/CodeGen/ItaniumCXXABI.cpp
index a4f99992780c..677d6524fabd 100644
--- a/clang/lib/CodeGen/ItaniumCXXABI.cpp
+++ b/clang/lib/CodeGen/ItaniumCXXABI.cpp
@@ -703,9 +703,9 @@ CGCallee ItaniumCXXABI::EmitLoadOfMemberFunctionPointer(
       TypeId = llvm::MetadataAsValue::get(CGF.getLLVMContext(), MD);
     }
 
-    if (ShouldEmitVFEInfo) {
-      llvm::Value *VFPAddr = Builder.CreateGEP(VTable, VTableOffset);
+    llvm::Value *VFPAddr = Builder.CreateGEP(VTable, VTableOffset);
 
+    if (ShouldEmitVFEInfo) {
       // If doing VFE, load from the vtable with a type.checked.load intrinsic
       // call. Note that we use the GEP to calculate the address to load from
       // and pass 0 as the offset to the intrinsic. This is because every
@@ -722,25 +722,14 @@ CGCallee ItaniumCXXABI::EmitLoadOfMemberFunctionPointer(
       // When not doing VFE, emit a normal load, as it allows more
       // optimisations than type.checked.load.
       if (ShouldEmitCFICheck || ShouldEmitWPDInfo) {
-        llvm::Value *VFPAddr = Builder.CreateGEP(VTable, VTableOffset);
         CheckResult = Builder.CreateCall(
             CGM.getIntrinsic(llvm::Intrinsic::type_test),
             {Builder.CreateBitCast(VFPAddr, CGF.Int8PtrTy), TypeId});
       }
-
-      if (CGM.getItaniumVTableContext().isRelativeLayout()) {
-        VirtualFn = CGF.Builder.CreateCall(
-            CGM.getIntrinsic(llvm::Intrinsic::load_relative,
-                             {VTableOffset->getType()}),
-            {VTable, VTableOffset});
-        VirtualFn = CGF.Builder.CreateBitCast(VirtualFn, FTy->getPointerTo());
-      } else {
-        llvm::Value *VFPAddr = CGF.Builder.CreateGEP(VTable, VTableOffset);
-        VFPAddr = CGF.Builder.CreateBitCast(
-            VFPAddr, FTy->getPointerTo()->getPointerTo());
-        VirtualFn = CGF.Builder.CreateAlignedLoad(
-            VFPAddr, CGF.getPointerAlign(), "memptr.virtualfn");
-      }
+      VFPAddr =
+          Builder.CreateBitCast(VFPAddr, FTy->getPointerTo()->getPointerTo());
+      VirtualFn = Builder.CreateAlignedLoad(VFPAddr, CGF.getPointerAlign(),
+                                            "memptr.virtualfn");
     }
     assert(VirtualFn && "Virtual fuction pointer not created!");
     assert((!ShouldEmitCFICheck || !ShouldEmitVFEInfo || !ShouldEmitWPDInfo ||
@@ -1015,16 +1004,11 @@ llvm::Constant *ItaniumCXXABI::BuildMemberPointer(const CXXMethodDecl *MD,
   llvm::Constant *MemPtr[2];
   if (MD->isVirtual()) {
     uint64_t Index = CGM.getItaniumVTableContext().getMethodVTableIndex(MD);
-    uint64_t VTableOffset;
-    if (CGM.getItaniumVTableContext().isRelativeLayout()) {
-      // Multiply by 4-byte relative offsets.
-      VTableOffset = Index * 4;
-    } else {
-      const ASTContext &Context = getContext();
-      CharUnits PointerWidth = Context.toCharUnitsFromBits(
-          Context.getTargetInfo().getPointerWidth(0));
-      VTableOffset = Index * PointerWidth.getQuantity();
-    }
+
+    const ASTContext &Context = getContext();
+    CharUnits PointerWidth =
+      Context.toCharUnitsFromBits(Context.getTargetInfo().getPointerWidth(0));
+    uint64_t VTableOffset = (Index * PointerWidth.getQuantity());
 
     if (UseARMMethodPtrABI) {
       // ARM C++ ABI 3.2.1:
@@ -1438,19 +1422,8 @@ llvm::Value *ItaniumCXXABI::EmitTypeid(CodeGenFunction &CGF,
   llvm::Value *Value =
       CGF.GetVTablePtr(ThisPtr, StdTypeInfoPtrTy->getPointerTo(), ClassDecl);
 
-  if (CGM.getItaniumVTableContext().isRelativeLayout()) {
-    // Load the type info.
-    Value = CGF.Builder.CreateBitCast(Value, CGM.Int8PtrTy);
-    Value = CGF.Builder.CreateCall(
-        CGM.getIntrinsic(llvm::Intrinsic::load_relative, {CGM.Int32Ty}),
-        {Value, llvm::ConstantInt::get(CGM.Int32Ty, -4)});
-
-    // Setup to dereference again since this is a proxy we accessed.
-    Value = CGF.Builder.CreateBitCast(Value, StdTypeInfoPtrTy->getPointerTo());
-  } else {
-    // Load the type info.
-    Value = CGF.Builder.CreateConstInBoundsGEP1_64(Value, -1ULL);
-  }
+  // Load the type info.
+  Value = CGF.Builder.CreateConstInBoundsGEP1_64(Value, -1ULL);
   return CGF.Builder.CreateAlignedLoad(Value, CGF.getPointerAlign());
 }
 
@@ -1506,37 +1479,28 @@ llvm::Value *ItaniumCXXABI::EmitDynamicCastToVoid(CodeGenFunction &CGF,
                                                   Address ThisAddr,
                                                   QualType SrcRecordTy,
                                                   QualType DestTy) {
+  llvm::Type *PtrDiffLTy =
+      CGF.ConvertType(CGF.getContext().getPointerDiffType());
   llvm::Type *DestLTy = CGF.ConvertType(DestTy);
+
   auto *ClassDecl =
       cast<CXXRecordDecl>(SrcRecordTy->castAs<RecordType>()->getDecl());
-  llvm::Value *OffsetToTop;
-  if (CGM.getItaniumVTableContext().isRelativeLayout()) {
-    // Get the vtable pointer.
-    llvm::Value *VTable =
-        CGF.GetVTablePtr(ThisAddr, CGM.Int32Ty->getPointerTo(), ClassDecl);
-
-    // Get the offset-to-top from the vtable.
-    OffsetToTop =
-        CGF.Builder.CreateConstInBoundsGEP1_32(/*Type=*/nullptr, VTable, -2U);
-    OffsetToTop = CGF.Builder.CreateAlignedLoad(
-        OffsetToTop, CharUnits::fromQuantity(4), "offset.to.top");
-  } else {
-    llvm::Type *PtrDiffLTy =
-        CGF.ConvertType(CGF.getContext().getPointerDiffType());
+  // Get the vtable pointer.
+  llvm::Value *VTable = CGF.GetVTablePtr(ThisAddr, PtrDiffLTy->getPointerTo(),
+      ClassDecl);
 
-    // Get the vtable pointer.
-    llvm::Value *VTable =
-        CGF.GetVTablePtr(ThisAddr, PtrDiffLTy->getPointerTo(), ClassDecl);
+  // Get the offset-to-top from the vtable.
+  llvm::Value *OffsetToTop =
+      CGF.Builder.CreateConstInBoundsGEP1_64(VTable, -2ULL);
+  OffsetToTop =
+    CGF.Builder.CreateAlignedLoad(OffsetToTop, CGF.getPointerAlign(),
+                                  "offset.to.top");
 
-    // Get the offset-to-top from the vtable.
-    OffsetToTop = CGF.Builder.CreateConstInBoundsGEP1_64(VTable, -2ULL);
-    OffsetToTop = CGF.Builder.CreateAlignedLoad(
-        OffsetToTop, CGF.getPointerAlign(), "offset.to.top");
-  }
   // Finally, add the offset to the pointer.
   llvm::Value *Value = ThisAddr.getPointer();
   Value = CGF.EmitCastToVoidPtr(Value);
   Value = CGF.Builder.CreateInBoundsGEP(Value, OffsetToTop);
+
   return CGF.Builder.CreateBitCast(Value, DestLTy);
 }
 
@@ -1557,22 +1521,17 @@ ItaniumCXXABI::GetVirtualBaseClassOffset(CodeGenFunction &CGF,
   CharUnits VBaseOffsetOffset =
       CGM.getItaniumVTableContext().getVirtualBaseOffsetOffset(ClassDecl,
                                                                BaseClassDecl);
+
   llvm::Value *VBaseOffsetPtr =
     CGF.Builder.CreateConstGEP1_64(VTablePtr, VBaseOffsetOffset.getQuantity(),
                                    "vbase.offset.ptr");
+  VBaseOffsetPtr = CGF.Builder.CreateBitCast(VBaseOffsetPtr,
+                                             CGM.PtrDiffTy->getPointerTo());
+
+  llvm::Value *VBaseOffset =
+    CGF.Builder.CreateAlignedLoad(VBaseOffsetPtr, CGF.getPointerAlign(),
+                                  "vbase.offset");
 
-  llvm::Value *VBaseOffset;
-  if (CGM.getItaniumVTableContext().isRelativeLayout()) {
-    VBaseOffsetPtr =
-        CGF.Builder.CreateBitCast(VBaseOffsetPtr, CGF.Int32Ty->getPointerTo());
-    VBaseOffset = CGF.Builder.CreateAlignedLoad(
-        VBaseOffsetPtr, CharUnits::fromQuantity(4), "vbase.offset");
-  } else {
-    VBaseOffsetPtr = CGF.Builder.CreateBitCast(VBaseOffsetPtr,
-                                               CGM.PtrDiffTy->getPointerTo());
-    VBaseOffset = CGF.Builder.CreateAlignedLoad(
-        VBaseOffsetPtr, CGF.getPointerAlign(), "vbase.offset");
-  }
   return VBaseOffset;
 }
 
@@ -1720,11 +1679,10 @@ void ItaniumCXXABI::emitVTableDefinitions(CodeGenVTables &CGVT,
       CGM.GetAddrOfRTTIDescriptor(CGM.getContext().getTagDeclType(RD));
 
   // Create and set the initializer.
-  ConstantInitBuilder builder(CGM);
-  auto components = builder.beginStruct();
-  CGVT.createVTableInitializer(components, VTLayout, RTTI,
-                               llvm::GlobalValue::isLocalLinkage(Linkage));
-  components.finishAndSetAsInitializer(VTable);
+  ConstantInitBuilder Builder(CGM);
+  auto Components = Builder.beginStruct();
+  CGVT.createVTableInitializer(Components, VTLayout, RTTI);
+  Components.finishAndSetAsInitializer(VTable);
 
   // Set the correct linkage.
   VTable->setLinkage(Linkage);
@@ -1748,9 +1706,6 @@ void ItaniumCXXABI::emitVTableDefinitions(CodeGenVTables &CGVT,
 
   if (!VTable->isDeclarationForLinker())
     CGM.EmitVTableTypeMetadata(RD, VTable, VTLayout);
-
-  if (VTContext.isRelativeLayout() && !VTable->isDSOLocal())
-    CGVT.GenerateRelativeVTableAlias(VTable, VTable->getName());
 }
 
 bool ItaniumCXXABI::isVirtualOffsetNeededForVTableField(
@@ -1840,9 +1795,7 @@ llvm::GlobalVariable *ItaniumCXXABI::getAddrOfVTable(const CXXRecordDecl *RD,
   // Use pointer alignment for the vtable. Otherwise we would align them based
   // on the size of the initializer which doesn't make sense as only single
   // values are read.
-  unsigned PAlign = CGM.getItaniumVTableContext().isRelativeLayout()
-                        ? 32
-                        : CGM.getTarget().getPointerAlign(0);
+  unsigned PAlign = CGM.getTarget().getPointerAlign(0);
 
   VTable = CGM.CreateOrReplaceCXXRuntimeVariable(
       Name, VTableType, llvm::GlobalValue::ExternalLinkage,
@@ -1859,9 +1812,9 @@ CGCallee ItaniumCXXABI::getVirtualFunctionPointer(CodeGenFunction &CGF,
                                                   Address This,
                                                   llvm::Type *Ty,
                                                   SourceLocation Loc) {
+  Ty = Ty->getPointerTo()->getPointerTo();
   auto *MethodDecl = cast<CXXMethodDecl>(GD.getDecl());
-  llvm::Value *VTable = CGF.GetVTablePtr(
-      This, Ty->getPointerTo()->getPointerTo(), MethodDecl->getParent());
+  llvm::Value *VTable = CGF.GetVTablePtr(This, Ty, MethodDecl->getParent());
 
   uint64_t VTableIndex = CGM.getItaniumVTableContext().getMethodVTableIndex(GD);
   llvm::Value *VFunc;
@@ -1872,21 +1825,10 @@ CGCallee ItaniumCXXABI::getVirtualFunctionPointer(CodeGenFunction &CGF,
   } else {
     CGF.EmitTypeMetadataCodeForVCall(MethodDecl->getParent(), VTable, Loc);
 
-    llvm::Value *VFuncLoad;
-    if (CGM.getItaniumVTableContext().isRelativeLayout()) {
-      VTable = CGF.Builder.CreateBitCast(VTable, CGM.Int8PtrTy);
-      llvm::Value *Load = CGF.Builder.CreateCall(
-          CGM.getIntrinsic(llvm::Intrinsic::load_relative, {CGM.Int32Ty}),
-          {VTable, llvm::ConstantInt::get(CGM.Int32Ty, 4 * VTableIndex)});
-      VFuncLoad = CGF.Builder.CreateBitCast(Load, Ty->getPointerTo());
-    } else {
-      VTable =
-          CGF.Builder.CreateBitCast(VTable, Ty->getPointerTo()->getPointerTo());
-      llvm::Value *VTableSlotPtr =
-          CGF.Builder.CreateConstInBoundsGEP1_64(VTable, VTableIndex, "vfn");
-      VFuncLoad =
-          CGF.Builder.CreateAlignedLoad(VTableSlotPtr, CGF.getPointerAlign());
-    }
+    llvm::Value *VFuncPtr =
+        CGF.Builder.CreateConstInBoundsGEP1_64(VTable, VTableIndex, "vfn");
+    auto *VFuncLoad =
+        CGF.Builder.CreateAlignedLoad(VFuncPtr, CGF.getPointerAlign());
 
     // Add !invariant.load md to virtual function load to indicate that
     // function didn't change inside vtable.
@@ -1895,14 +1837,11 @@ CGCallee ItaniumCXXABI::getVirtualFunctionPointer(CodeGenFunction &CGF,
     // the same virtual function loads from the same vtable load, which won't
     // happen without enabled devirtualization with -fstrict-vtable-pointers.
     if (CGM.getCodeGenOpts().OptimizationLevel > 0 &&
-        CGM.getCodeGenOpts().StrictVTablePointers) {
-      if (auto *VFuncLoadInstr = dyn_cast<llvm::Instruction>(VFuncLoad)) {
-        VFuncLoadInstr->setMetadata(
-            llvm::LLVMContext::MD_invariant_load,
-            llvm::MDNode::get(CGM.getLLVMContext(),
-                              llvm::ArrayRef<llvm::Metadata *>()));
-      }
-    }
+        CGM.getCodeGenOpts().StrictVTablePointers)
+      VFuncLoad->setMetadata(
+          llvm::LLVMContext::MD_invariant_load,
+          llvm::MDNode::get(CGM.getLLVMContext(),
+                            llvm::ArrayRef<llvm::Metadata *>()));
     VFunc = VFuncLoad;
   }
 
@@ -2019,28 +1958,21 @@ static llvm::Value *performTypeAdjustment(CodeGenFunction &CGF,
   // Perform the virtual adjustment if we have one.
   llvm::Value *ResultPtr;
   if (VirtualAdjustment) {
+    llvm::Type *PtrDiffTy =
+        CGF.ConvertType(CGF.getContext().getPointerDiffType());
+
     Address VTablePtrPtr = CGF.Builder.CreateElementBitCast(V, CGF.Int8PtrTy);
     llvm::Value *VTablePtr = CGF.Builder.CreateLoad(VTablePtrPtr);
 
-    llvm::Value *Offset;
     llvm::Value *OffsetPtr =
         CGF.Builder.CreateConstInBoundsGEP1_64(VTablePtr, VirtualAdjustment);
-    if (CGF.CGM.getItaniumVTableContext().isRelativeLayout()) {
-      // Load the adjustment offset from the vtable as a 32-bit int.
-      OffsetPtr =
-          CGF.Builder.CreateBitCast(OffsetPtr, CGF.Int32Ty->getPointerTo());
-      Offset =
-          CGF.Builder.CreateAlignedLoad(OffsetPtr, CharUnits::fromQuantity(4));
-    } else {
-      llvm::Type *PtrDiffTy =
-          CGF.ConvertType(CGF.getContext().getPointerDiffType());
 
-      OffsetPtr =
-          CGF.Builder.CreateBitCast(OffsetPtr, PtrDiffTy->getPointerTo());
+    OffsetPtr = CGF.Builder.CreateBitCast(OffsetPtr, PtrDiffTy->getPointerTo());
+
+    // Load the adjustment offset from the vtable.
+    llvm::Value *Offset =
+      CGF.Builder.CreateAlignedLoad(OffsetPtr, CGF.getPointerAlign());
 
-      // Load the adjustment offset from the vtable.
-      Offset = CGF.Builder.CreateAlignedLoad(OffsetPtr, CGF.getPointerAlign());
-    }
     // Adjust our pointer.
     ResultPtr = CGF.Builder.CreateInBoundsGEP(V.getPointer(), Offset);
   } else {
@@ -3367,32 +3299,17 @@ void ItaniumRTTIBuilder::BuildVTablePointer(const Type *Ty) {
     break;
   }
 
-  llvm::Constant *VTable = nullptr;
-
-  // Check if the alias exists. If it doesn't, then get or create the global.
-  if (CGM.getItaniumVTableContext().isRelativeLayout())
-    VTable = CGM.getModule().getNamedAlias(VTableName);
-  if (!VTable)
-    VTable = CGM.getModule().getOrInsertGlobal(VTableName, CGM.Int8PtrTy);
-
+  llvm::Constant *VTable =
+    CGM.getModule().getOrInsertGlobal(VTableName, CGM.Int8PtrTy);
   CGM.setDSOLocal(cast<llvm::GlobalValue>(VTable->stripPointerCasts()));
 
   llvm::Type *PtrDiffTy =
-      CGM.getTypes().ConvertType(CGM.getContext().getPointerDiffType());
+    CGM.getTypes().ConvertType(CGM.getContext().getPointerDiffType());
 
   // The vtable address point is 2.
-  if (CGM.getItaniumVTableContext().isRelativeLayout()) {
-    // The vtable address point is 8 bytes after its start:
-    // 4 for the offset to top + 4 for the relative offset to rtti.
-    llvm::Constant *Eight = llvm::ConstantInt::get(CGM.Int32Ty, 8);
-    VTable = llvm::ConstantExpr::getBitCast(VTable, CGM.Int8PtrTy);
-    VTable =
-        llvm::ConstantExpr::getInBoundsGetElementPtr(CGM.Int8Ty, VTable, Eight);
-  } else {
-    llvm::Constant *Two = llvm::ConstantInt::get(PtrDiffTy, 2);
-    VTable = llvm::ConstantExpr::getInBoundsGetElementPtr(CGM.Int8PtrTy, VTable,
-                                                          Two);
-  }
+  llvm::Constant *Two = llvm::ConstantInt::get(PtrDiffTy, 2);
+  VTable =
+      llvm::ConstantExpr::getInBoundsGetElementPtr(CGM.Int8PtrTy, VTable, Two);
   VTable = llvm::ConstantExpr::getBitCast(VTable, CGM.Int8PtrTy);
 
   Fields.push_back(VTable);

diff  --git a/clang/lib/CodeGen/MicrosoftCXXABI.cpp b/clang/lib/CodeGen/MicrosoftCXXABI.cpp
index a9d87f135b65..76881e973f41 100644
--- a/clang/lib/CodeGen/MicrosoftCXXABI.cpp
+++ b/clang/lib/CodeGen/MicrosoftCXXABI.cpp
@@ -1688,11 +1688,10 @@ void MicrosoftCXXABI::emitVTableDefinitions(CodeGenVTables &CGVT,
                [](const VTableComponent &VTC) { return VTC.isRTTIKind(); }))
       RTTI = getMSCompleteObjectLocator(RD, *Info);
 
-    ConstantInitBuilder builder(CGM);
-    auto components = builder.beginStruct();
-    CGVT.createVTableInitializer(components, VTLayout, RTTI,
-                                 VTable->hasLocalLinkage());
-    components.finishAndSetAsInitializer(VTable);
+    ConstantInitBuilder Builder(CGM);
+    auto Components = Builder.beginStruct();
+    CGVT.createVTableInitializer(Components, VTLayout, RTTI);
+    Components.finishAndSetAsInitializer(VTable);
 
     emitVTableTypeMetadata(*Info, RD, VTable);
   }

diff  --git a/clang/lib/Frontend/CompilerInvocation.cpp b/clang/lib/Frontend/CompilerInvocation.cpp
index 3aea9164046c..29e92ceb6be1 100644
--- a/clang/lib/Frontend/CompilerInvocation.cpp
+++ b/clang/lib/Frontend/CompilerInvocation.cpp
@@ -3410,11 +3410,6 @@ static void ParseLangArgs(LangOptions &Opts, ArgList &Args, InputKind IK,
 
   Opts.CompatibilityQualifiedIdBlockParamTypeChecking =
       Args.hasArg(OPT_fcompatibility_qualified_id_block_param_type_checking);
-
-  Opts.RelativeCXXABIVTables =
-      Args.hasFlag(OPT_fexperimental_relative_cxx_abi_vtables,
-                   OPT_fno_experimental_relative_cxx_abi_vtables,
-                   /*default=*/false);
 }
 
 static bool isStrictlyPreprocessorAction(frontend::ActionKind Action) {

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/child-inheritted-from-parent-in-comdat.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/child-inheritted-from-parent-in-comdat.cpp
deleted file mode 100644
index dd068aa9c010..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/child-inheritted-from-parent-in-comdat.cpp
+++ /dev/null
@@ -1,57 +0,0 @@
-// Cross comdat example
-// Parent VTable is in a comdat section.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: $_ZN1B3fooEv.stub = comdat any
-
-// The inline function is emitted in each module with the same comdat
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-// CHECK: $_ZTS1A = comdat any
-// CHECK: $_ZTI1A = comdat any
-// CHECK: $_ZTI1B.rtti_proxy = comdat any
-
-// The VTable is emitted everywhere used
-// CHECK: $_ZTV1A = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-
-// The VTable for B is emitted here since it has a key function which is defined in this module
-// CHECK: @_ZTV1B.local = private unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-
-// The VTable for A is emitted here and in a comdat section since it has no key function, and is used in this module when creating an instance of A (in func()).
-// CHECK: @_ZTV1A.local = linkonce_odr hidden unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, comdat($_ZTV1A), align 4
-
-// CHECK: @_ZTV1B = unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1B.local
-// CHECK: @_ZTV1A = linkonce_odr unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1A.local
-
-// CHECK:      define void @_ZN1B3fooEv(%class.B* nocapture %this) unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// CHECK:      define hidden void @_ZN1B3fooEv.stub(%class.B* nocapture %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// CHECK:      define hidden void @_ZN1A3fooEv.stub(%class.A* %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1A3fooEv(%class.A* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  inline virtual void foo() {}
-};
-class B : public A {
-public:
-  void foo() override;
-};
-void A_foo(A *a);
-
-void B::foo() {}
-void func2() {
-  A a;
-  A_foo(&a);
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/child-vtable-in-comdat.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/child-vtable-in-comdat.cpp
deleted file mode 100644
index 9237b90b0f85..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/child-vtable-in-comdat.cpp
+++ /dev/null
@@ -1,66 +0,0 @@
-// Cross comdat example
-// Child VTable is in a comdat section.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: $_ZN1B3fooEv.stub = comdat any
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-
-// A comdat is emitted for B but not A
-// CHECK: $_ZTV1B = comdat any
-// CHECK: $_ZTS1B = comdat any
-// CHECK: $_ZTI1B = comdat any
-// CHECK: $_ZTI1B.rtti_proxy = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-
-// VTable for B is emitted here since we access it when creating an instance of B. The VTable is also linkonce_odr and in its own comdat.
-// CHECK: @_ZTV1B.local = linkonce_odr hidden unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, comdat($_ZTV1B), align 4
-
-// The RTTI objects aren’t that important, but it is good to know that they are emitted here since they are used in the vtable for B, and external references are used for RTTI stuff from A.
-// CHECK: @_ZTVN10__cxxabiv120__si_class_type_infoE = external global i8*
-// CHECK: @_ZTS1B = linkonce_odr constant [3 x i8] c"1B\00", comdat, align 1
-// CHECK: @_ZTI1A = external constant i8*
-// CHECK: @_ZTI1B = linkonce_odr constant { i8*, i8*, i8* } { i8* getelementptr inbounds (i8, i8* bitcast (i8** @_ZTVN10__cxxabiv120__si_class_type_infoE to i8*), i32 8), i8* getelementptr inbounds ([3 x i8], [3 x i8]* @_ZTS1B, i32 0, i32 0), i8* bitcast (i8** @_ZTI1A to i8*) }, comdat, align 8
-// CHECK: @_ZTI1B.rtti_proxy = hidden unnamed_addr constant { i8*, i8*, i8* }* @_ZTI1B, comdat
-
-// The VTable for A is available_externally, meaning it can have a definition in
-// IR, but is never emitted in this compilation unit. Because it won't be
-// emitted here, we cannot make an alias, but we won't need to in the first
-// place.
-// CHECK: @_ZTV1A = available_externally unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint (i8*** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-// CHECK: @_ZTI1A.rtti_proxy = hidden unnamed_addr constant i8** @_ZTI1A, comdat
-
-// We will emit a vtable for B here, so it does have an alias, but we will not
-// emit one for A.
-// CHECK: @_ZTV1B = linkonce_odr unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1B.local
-// CHECK-NOT: @_ZTV1A = {{.*}}alias
-
-// CHECK:      define hidden void @_ZN1B3fooEv.stub(%class.B* %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1B3fooEv(%class.B* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// CHECK: declare void @_ZN1A3fooEv(%class.A*) unnamed_addr
-
-// CHECK: define hidden void @_ZN1A3fooEv.stub(%class.A* %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1A3fooEv(%class.A* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo();
-};
-class B : public A {
-public:
-  inline void foo() override {}
-};
-void A_foo(A *a);
-
-// func() is used so that the vtable for B is accessed when creating the instance.
-void func() {
-  B b;
-  A_foo(&b);
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/cross-translation-unit-1.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/cross-translation-unit-1.cpp
deleted file mode 100644
index 97ab7eb3b2a7..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/cross-translation-unit-1.cpp
+++ /dev/null
@@ -1,39 +0,0 @@
-// Check the vtable layout for classes with key functions defined in 
diff erent
-// translation units. This TU only manifests the vtable for A.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-#include "cross-tu-header.h"
-
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-// CHECK: $_ZN1A3barEv.stub = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-
-// CHECK: @_ZTV1A.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-// @_ZTV1A = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1A.local
-
-// A::foo() is still available for other modules to use since it is not marked with private or internal linkage.
-// CHECK:      define void @_ZN1A3fooEv(%class.A* nocapture %this) unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// The proxy that we take a reference to in the vtable has hidden visibility and external linkage so it can be used only by other modules in the same DSO. A::foo() is inlined into this stub since it is defined in the same module.
-// CHECK:      define hidden void @_ZN1A3fooEv.stub(%class.A* nocapture %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// A::bar() is called within the module but not defined, even though the VTable for A is emitted here
-// CHECK: declare void @_ZN1A3barEv(%class.A*) unnamed_addr
-
-// The stub for A::bar() is made private, so it will not appear in the symbol table and is only used in this module. We tail call here because A::bar() is not defined in the same module.
-// CHECK:      define hidden void @_ZN1A3barEv.stub(%class.A* %0) unnamed_addr {{#[0-9]+}} comdat {
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1A3barEv(%class.A* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-void A::foo() {}
-void A_foo(A *a) { a->foo(); }
-void A_bar(A *a) { a->bar(); }

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/cross-translation-unit-2.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/cross-translation-unit-2.cpp
deleted file mode 100644
index 46a17b2faf5e..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/cross-translation-unit-2.cpp
+++ /dev/null
@@ -1,38 +0,0 @@
-// Check the vtable layout for classes with key functions defined in 
diff erent
-// translation units. This TU manifests the vtable for B.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-#include "cross-tu-header.h"
-
-// CHECK: $_ZN1B3fooEv.stub = comdat any
-// CHECK: $_ZN1A3barEv.stub = comdat any
-// CHECK: $_ZTI1B.rtti_proxy = comdat any
-
-// CHECK: @_ZTV1B.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-// CHECK: @_ZTV1B = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1B.local
-
-// A::bar() is defined outside of the module that defines the vtable for A
-// CHECK:      define void @_ZN1A3barEv(%class.A* nocapture %this) unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// CHECK:      define void @_ZN1B3fooEv(%class.B* nocapture %this) unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// The stubs for B::foo() and A::bar() are hidden
-// CHECK:      define hidden void @_ZN1B3fooEv.stub(%class.B* nocapture %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// CHECK:      define hidden void @_ZN1A3barEv.stub(%class.A* nocapture %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-void A::bar() {}
-void B::foo() {}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/cross-tu-header.h b/clang/test/CodeGenCXX/RelativeVTablesABI/cross-tu-header.h
deleted file mode 100644
index 73b09c055a98..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/cross-tu-header.h
+++ /dev/null
@@ -1,10 +0,0 @@
-class A {
-public:
-  virtual void foo();
-  virtual void bar();
-};
-
-class B : public A {
-public:
-  void foo() override;
-};

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/diamond-inheritance.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/diamond-inheritance.cpp
deleted file mode 100644
index 95d80d1040c2..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/diamond-inheritance.cpp
+++ /dev/null
@@ -1,57 +0,0 @@
-// Diamond inheritance.
-// A more complicated multiple inheritance example that includes longer chain of inheritance and a common ancestor.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: %class.B = type { %class.A }
-// CHECK: %class.A = type { i32 (...)** }
-// CHECK: %class.C = type { %class.A }
-// CHECK: %class.D = type { %class.B, %class.C }
-
-// VTable for B should contain offset to top (0), RTTI pointer, A::foo(), and B::barB().
-// CHECK: @_ZTV1B.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B4barBEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-
-// VTable for C should contain offset to top (0), RTTI pointer, A::foo(), and C::barC().
-// CHECK: @_ZTV1C.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1C.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1C.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1C.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.C*)* @_ZN1C4barCEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1C.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-
-// VTable for D should be similar to the mutiple inheritance example where this
-// vtable contains 2 inner vtables:
-// - 1st table containing D::foo(), B::barB(), and D::baz().
-// - 2nd table containing a thunk to D::foo() and C::barC().
-// CHECK: @_ZTV1D.local = private unnamed_addr constant { [5 x i32], [4 x i32] } { [5 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64, i8*, i64 }** @_ZTI1D.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32] }, { [5 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.D*)* @_ZN1D3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32] }, { [5 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B4barBEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32] }, { [5 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.D*)* @_ZN1D3bazEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32] }, { [5 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 0, i32 2) to i64)) to i32)], [4 x i32] [i32 -8, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64, i8*, i64 }** @_ZTI1D.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32] }, { [5 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 1, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.D*)* @_ZThn8_N1D3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32] }, { [5 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 1, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.C*)* @_ZN1C4barCEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32] }, { [5 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 1, i32 2) to i64)) to i32)] }, align 4
-
-// @_ZTV1B = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1B.local
-// @_ZTV1C = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1C.local
-// @_ZTV1D = unnamed_addr alias { [5 x i32], [4 x i32] }, { [5 x i32], [4 x i32] }* @_ZTV1D.local
-
-class A {
-public:
-  virtual void foo();
-};
-
-class B : public A {
-public:
-  virtual void barB();
-};
-
-class C : public A {
-  virtual void barC();
-};
-
-// Should be a struct with 2 arrays from 2 parents.
-// The 1st contains D::foo(), B::barB(), and D::baz().
-// The 2nd contains C::barC(), and a thunk that points to D::foo().
-class D : public B, C {
-public:
-  virtual void baz();
-  void foo() override;
-};
-
-void B::barB() {}
-void C::barC() {}
-void D::foo() {}
-void D::baz() {}
-
-void D_foo(D *d) {
-  d->foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/diamond-virtual-inheritance.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/diamond-virtual-inheritance.cpp
deleted file mode 100644
index b4f7bc5ffe0b..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/diamond-virtual-inheritance.cpp
+++ /dev/null
@@ -1,96 +0,0 @@
-// Diamond virtual inheritance.
-// This should cover virtual inheritance, construction vtables, and VTTs.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: %class.B = type { i32 (...)**, %class.A.base }
-// CHECK: %class.A.base = type <{ i32 (...)**, i32 }>
-// CHECK: %class.C = type { i32 (...)**, %class.A.base }
-// CHECK: %class.D = type { %class.B.base, %class.C.base, %class.A.base }
-// CHECK: %class.B.base = type { i32 (...)** }
-// CHECK: %class.C.base = type { i32 (...)** }
-
-// Class A contains a vtable ptr, then int, then padding
-// CHECK: %class.A = type <{ i32 (...)**, i32, [4 x i8] }>
-
-// VTable for B. Contains an extra field at the start for the virtual-base offset.
-// CHECK: @_ZTV1B.local = private unnamed_addr constant { [4 x i32], [4 x i32] } { [4 x i32] [i32 8, i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64 }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B4barBEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 3) to i64)) to i32)], [4 x i32] [i32 0, i32 -8, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64 }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1B.local, i32 0, i32 1, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1B.local, i32 0, i32 1, i32 3) to i64)) to i32)] }, align 4
-
-// VTT for B
-// CHECK: @_ZTT1B = unnamed_addr constant [2 x i8*] [i8* bitcast (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1B.local, i32 0, inrange i32 0, i32 3) to i8*), i8* bitcast (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1B.local, i32 0, inrange i32 1, i32 3) to i8*)], align 8
-
-// VTable for C
-// CHECK: @_ZTV1C.local = private unnamed_addr constant { [4 x i32], [4 x i32] } { [4 x i32] [i32 8, i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64 }** @_ZTI1C.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1C.local, i32 0, i32 0, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.C*)* @_ZN1C4barCEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1C.local, i32 0, i32 0, i32 3) to i64)) to i32)], [4 x i32] [i32 0, i32 -8, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64 }** @_ZTI1C.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1C.local, i32 0, i32 1, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1C.local, i32 0, i32 1, i32 3) to i64)) to i32)] }, align 4
-
-// VTT for C
-// CHECK: @_ZTT1C = unnamed_addr constant [2 x i8*] [i8* bitcast (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1C.local, i32 0, inrange i32 0, i32 3) to i8*), i8* bitcast (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1C.local, i32 0, inrange i32 1, i32 3) to i8*)], align 8
-
-// VTable for D
-// CHECK: @_ZTV1D.local = private unnamed_addr constant { [5 x i32], [4 x i32], [4 x i32] } { [5 x i32] [i32 16, i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64, i8*, i64 }** @_ZTI1D.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 0, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B4barBEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 0, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.D*)* @_ZN1D3bazEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 0, i32 3) to i64)) to i32)], [4 x i32] [i32 8, i32 -8, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64, i8*, i64 }** @_ZTI1D.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 1, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.C*)* @_ZN1C4barCEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 1, i32 3) to i64)) to i32)], [4 x i32] [i32 0, i32 -16, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64, i8*, i64 }** @_ZTI1D.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 2, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, i32 2, i32 3) to i64)) to i32)] }, align 4
-
-// VTT for D
-// CHECK: @_ZTT1D = unnamed_addr constant [7 x i8*] [i8* bitcast (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, inrange i32 0, i32 3) to i8*), i8* bitcast (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D0_1B.local, i32 0, inrange i32 0, i32 3) to i8*), i8* bitcast (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D0_1B.local, i32 0, inrange i32 1, i32 3) to i8*), i8* bitcast (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D8_1C.local, i32 0, inrange i32 0, i32 3) to i8*), i8* bitcast (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D8_1C.local, i32 0, inrange i32 1, i32 3) to i8*), i8* bitcast (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, inrange i32 2, i32 3) to i8*), i8* bitcast (i32* getelementptr inbounds ({ [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local, i32 0, inrange i32 1, i32 3) to i8*)], align 8
-
-// Construction vtable for B-in-D
-// CHECK: @_ZTC1D0_1B.local = private unnamed_addr constant { [4 x i32], [4 x i32] } { [4 x i32] [i32 16, i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64 }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D0_1B.local, i32 0, i32 0, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B4barBEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D0_1B.local, i32 0, i32 0, i32 3) to i64)) to i32)], [4 x i32] [i32 0, i32 -16, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64 }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D0_1B.local, i32 0, i32 1, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D0_1B.local, i32 0, i32 1, i32 3) to i64)) to i32)] }, align 4
-
-// Construction vtable for C-in-D
-// CHECK: @_ZTC1D8_1C.local = private unnamed_addr constant { [4 x i32], [4 x i32] } { [4 x i32] [i32 8, i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64 }** @_ZTI1C.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D8_1C.local, i32 0, i32 0, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.C*)* @_ZN1C4barCEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D8_1C.local, i32 0, i32 0, i32 3) to i64)) to i32)], [4 x i32] [i32 0, i32 -8, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64 }** @_ZTI1C.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D8_1C.local, i32 0, i32 1, i32 3) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D8_1C.local, i32 0, i32 1, i32 3) to i64)) to i32)] }, align 4
-
-// CHECK: @_ZTV1B = unnamed_addr alias { [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1B.local
-// CHECK: @_ZTV1C = unnamed_addr alias { [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTV1C.local
-// CHECK: @_ZTC1D0_1B = unnamed_addr alias { [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D0_1B.local
-// CHECK: @_ZTC1D8_1C = unnamed_addr alias { [4 x i32], [4 x i32] }, { [4 x i32], [4 x i32] }* @_ZTC1D8_1C.local
-// CHECK: @_ZTV1D = unnamed_addr alias { [5 x i32], [4 x i32], [4 x i32] }, { [5 x i32], [4 x i32], [4 x i32] }* @_ZTV1D.local
-
-// CHECK:      define void @_Z5D_fooP1D(%class.D* %d) local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   [[d:%[0-9]+]] = bitcast %class.D* %d to i8**
-// CHECK-NEXT:   [[vtable:%[a-z0-9]+]] = load i8*, i8** [[d]], align 8
-
-// This normally would've been -24 (8 bytes for the virtual call/base offset, 8
-// bytes for the offset to top, and 8 bytes for the RTTI pointer), but since all
-// components in the vtable are halved to 4 bytes, the offset is halved to -12.
-// CHECK-NEXT:   [[vbase_offset_ptr:%[a-z0-9.]+]] = getelementptr i8, i8* [[vtable]], i64 -12
-
-// CHECK-NEXT:   [[vbase_offset_ptr2:%[a-z0-9.]+]] = bitcast i8* [[vbase_offset_ptr]] to i32*
-// CHECK-NEXT:   [[vbase_offset:%[a-z0-9.]+]] = load i32, i32* [[vbase_offset_ptr2]], align 4
-// CHECK-NEXT:   [[d:%[0-9]+]] = bitcast %class.D* %d to i8*
-// CHECK-NEXT:   [[vbase_offset2:%.+]] = sext i32 [[vbase_offset]] to i64
-// CHECK-NEXT:   [[add_ptr:%[a-z0-9.]+]] = getelementptr inbounds i8, i8* [[d]], i64 [[vbase_offset2]]
-// CHECK-NEXT:   [[a:%[0-9]+]] = bitcast i8* [[add_ptr]] to %class.A*
-// CHECK-NEXT:   [[a_i8_ptr:%[0-9]+]] = bitcast i8* [[add_ptr]] to i8**
-// CHECK-NEXT:   [[vtable:%[a-z0-9]+]] = load i8*, i8** [[a_i8_ptr]], align 8
-// CHECK-NEXT:   [[ptr:%[0-9]+]] = call i8* @llvm.load.relative.i32(i8* [[vtable]], i32 0)
-// CHECK-NEXT:   [[method:%[0-9]+]] = bitcast i8* [[ptr]] to void (%class.A*)*
-// CHECK-NEXT:   call void [[method]](%class.A* [[a]])
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo();
-  int a;
-};
-
-class B : public virtual A {
-public:
-  virtual void barB();
-};
-
-class C : public virtual A {
-  virtual void barC();
-};
-
-class D : public B, C {
-public:
-  virtual void baz();
-};
-
-void B::barB() {}
-void C::barC() {}
-void D::baz() {}
-
-void D_foo(D *d) {
-  d->foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/dynamic-cast.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/dynamic-cast.cpp
deleted file mode 100644
index 56b56a1b9398..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/dynamic-cast.cpp
+++ /dev/null
@@ -1,78 +0,0 @@
-// dynamic_cast
-// Ensure that dynamic casting works normally
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O3 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK:      define %class.A* @_Z6upcastP1B(%class.B* readnone %b) local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   [[a:%[0-9]+]] = getelementptr %class.B, %class.B* %b, i64 0, i32 0
-// CHECK-NEXT:   ret %class.A* [[a]]
-// CHECK-NEXT: }
-
-// CHECK:      define %class.B* @_Z8downcastP1A(%class.A* readonly %a) local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   [[isnull:%[0-9]+]] = icmp eq %class.A* %a, null
-// CHECK-NEXT:   br i1 [[isnull]], label %[[dynamic_cast_end:[a-z0-9._]+]], label %[[dynamic_cast_notnull:[a-z0-9._]+]]
-// CHECK:      [[dynamic_cast_notnull]]:
-// CHECK-NEXT:   [[a:%[0-9]+]] = bitcast %class.A* %a to i8*
-// CHECK-NEXT:   [[as_b:%[0-9]+]] = tail call i8* @__dynamic_cast(i8* nonnull [[a]], i8* bitcast ({ i8*, i8* }* @_ZTI1A to i8*), i8* bitcast ({ i8*, i8*, i8* }* @_ZTI1B to i8*), i64 0)
-// CHECK-NEXT:   [[b:%[0-9]+]] = bitcast i8* [[as_b]] to %class.B*
-// CHECK-NEXT:   br label %[[dynamic_cast_end]]
-// CHECK:      [[dynamic_cast_end]]:
-// CHECK-NEXT:   [[res:%[0-9]+]] = phi %class.B* [ [[b]], %[[dynamic_cast_notnull]] ], [ null, %entry ]
-// CHECK-NEXT:   ret %class.B* [[res]]
-// CHECK-NEXT: }
-
-// CHECK: declare i8* @__dynamic_cast(i8*, i8*, i8*, i64) local_unnamed_addr
-
-// CHECK:      define %class.B* @_Z8selfcastP1B(%class.B* readnone returned %b) local_unnamed_addr
-// CHECK-NEXT: entry
-// CHECK-NEXT:   ret %class.B* %b
-// CHECK-NEXT: }
-
-// CHECK: define i8* @_Z9void_castP1B(%class.B* readonly %b) local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   [[isnull:%[0-9]+]] = icmp eq %class.B* %b, null
-// CHECK-NEXT:   br i1 [[isnull]], label %[[dynamic_cast_end:[a-z0-9._]+]], label %[[dynamic_cast_notnull:[a-z0-9._]+]]
-// CHECK:      [[dynamic_cast_notnull]]:
-// CHECK-NEXT:   [[b2:%[0-9]+]] = bitcast %class.B* %b to i32**
-// CHECK-NEXT:   [[vtable:%[a-z0-9]+]] = load i32*, i32** [[b2]], align 8
-// CHECK-NEXT:   [[offset_ptr:%.+]] = getelementptr inbounds i32, i32* [[vtable]], i64 -2
-// CHECK-NEXT:   [[offset_to_top:%.+]] = load i32, i32* [[offset_ptr]], align 4
-// CHECK-NEXT:   [[b:%[0-9]+]] = bitcast %class.B* %b to i8*
-// CHECK-NEXT:   [[offset_to_top2:%.+]] = sext i32 [[offset_to_top]] to i64
-// CHECK-NEXT:   [[casted:%.+]] = getelementptr inbounds i8, i8* [[b]], i64 [[offset_to_top2]]
-// CHECK-NEXT:   br label %[[dynamic_cast_end]]
-// CHECK:      [[dynamic_cast_end]]:
-// CHECK-NEXT:   [[res:%[0-9]+]] = phi i8* [ [[casted]], %[[dynamic_cast_notnull]] ], [ null, %entry ]
-// CHECK-NEXT:   ret i8* [[res]]
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo();
-};
-
-class B : public A {
-public:
-  void foo() override;
-};
-
-void A::foo() {}
-void B::foo() {}
-
-A *upcast(B *b) {
-  return dynamic_cast<A *>(b);
-}
-
-B *downcast(A *a) {
-  return dynamic_cast<B *>(a);
-}
-
-B *selfcast(B *b) {
-  return dynamic_cast<B *>(b);
-}
-
-void *void_cast(B *b) {
-  return dynamic_cast<void *>(b);
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/inheritted-virtual-function.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/inheritted-virtual-function.cpp
deleted file mode 100644
index 3eee8f0d07bb..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/inheritted-virtual-function.cpp
+++ /dev/null
@@ -1,29 +0,0 @@
-// Check the layout of the vtable for a child class that inherits a virtual
-// function but does not override it.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-class A {
-public:
-  virtual void foo();
-};
-
-// The VTable for B should look similar to the vtable for A but the component for foo() should point to A::foo() and the component for bar() should point to B::bar().
-// CHECK: @_ZTV1B.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-// CHECK: @_ZTV1B = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1B.local
-
-class B : public A {
-public:
-  virtual void bar();
-};
-
-void A::foo() {}
-void B::bar() {}
-
-void A_foo(A *a) {
-  a->foo();
-}
-
-void B_foo(B *b) {
-  b->foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/inline-virtual-function.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/inline-virtual-function.cpp
deleted file mode 100644
index 9f8439d7100f..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/inline-virtual-function.cpp
+++ /dev/null
@@ -1,27 +0,0 @@
-// The VTable is not in a comdat but the inline methods are.
-// This doesn’t affect the vtable or the stubs we emit.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-// CHECK: $_ZN1A3barEv.stub = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-
-// The vtable has a key function (A::foo()) so it does not have a comdat
-// CHECK: @_ZTV1A.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-// CHECK: @_ZTV1A = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1A.local
-
-// We do not declare the stub with linkonce_odr so it can be emitted as .globl.
-// CHECK:      define hidden void @_ZN1A3barEv.stub(%class.A* %0) unnamed_addr #{{[0-9]+}} comdat {
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1A3barEv(%class.A* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo(); // Key func
-  inline virtual void bar() {}
-};
-
-void A::foo() {}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/inlined-key-function.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/inlined-key-function.cpp
deleted file mode 100644
index 7775cd8ac6e0..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/inlined-key-function.cpp
+++ /dev/null
@@ -1,33 +0,0 @@
-// Inline comdat method definition example.
-// The VTable is in a comdat and defined anywhere the inline definition is.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-// CHECK: $_ZTV1A = comdat any
-// CHECK: $_ZTS1A = comdat any
-// CHECK: $_ZTI1A = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-
-// The VTable is linkonce_odr and in a comdat here bc it’s key function is inline defined.
-// CHECK: @_ZTV1A.local = linkonce_odr hidden unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, comdat($_ZTV1A), align 4
-// CHECK: @_ZTV1A = linkonce_odr unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1A.local
-
-// CHECK:      define hidden void @_ZN1A3fooEv.stub(%class.A* %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1A3fooEv(%class.A* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo();
-};
-void A_foo(A *a);
-
-inline void A::foo() {}
-
-void func() {
-  A a;
-  A_foo(&a);
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/member-function-pointer.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/member-function-pointer.cpp
deleted file mode 100644
index 396dd15c482b..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/member-function-pointer.cpp
+++ /dev/null
@@ -1,47 +0,0 @@
-// Member pointer to virtual function.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O3 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK:      define void @_Z4funcP1AMS_FvvE(%class.A* %a, [2 x i64] %fn.coerce) local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   [[fn_ptr:%.+]] = extractvalue [2 x i64] %fn.coerce, 0
-// CHECK-NEXT:   [[adjust:%.+]] = extractvalue [2 x i64] %fn.coerce, 1
-// CHECK-NEXT:   [[this:%.+]] = bitcast %class.A* %a to i8*
-// CHECK-NEXT:   [[this_adj:%.+]] = getelementptr inbounds i8, i8* [[this]], i64 [[adjust]]
-// CHECK-NEXT:   [[virtbit:%.+]] = and i64 [[fn_ptr]], 1
-// CHECK-NEXT:   [[isvirt:%.+]] = icmp eq i64 [[virtbit]], 0
-// CHECK-NEXT:   br i1 [[isvirt]], label %[[nonvirt:.+]], label %[[virt:.+]]
-// CHECK:      [[virt]]:
-
-// The loading of the virtual function here should be replaced with a llvm.load.relative() call.
-// CHECK-NEXT:   [[this:%.+]] = bitcast i8* [[this_adj]] to i8**
-// CHECK-NEXT:   [[vtable:%.+]] = load i8*, i8** [[this]], align 8
-// CHECK-NEXT:   [[offset:%.+]] = add i64 [[fn_ptr]], -1
-// CHECK-NEXT:   [[ptr:%.+]] = tail call i8* @llvm.load.relative.i64(i8* [[vtable]], i64 [[offset]])
-// CHECK-NEXT:   [[method:%.+]] = bitcast i8* [[ptr]] to void (%class.A*)*
-// CHECK-NEXT:   br label %[[memptr_end:.+]]
-// CHECK:      [[nonvirt]]:
-// CHECK-NEXT:   [[method2:%.+]] = inttoptr i64 [[fn_ptr]] to void (%class.A*)*
-// CHECK-NEXT:   br label %[[memptr_end]]
-// CHECK:      [[memptr_end]]:
-// CHECK-NEXT:   [[method3:%.+]] = phi void (%class.A*)* [ [[method]], %[[virt]] ], [ [[method2]], %[[nonvirt]] ]
-// CHECK-NEXT:   [[a:%.+]] = bitcast i8* [[this_adj]] to %class.A*
-// CHECK-NEXT:   tail call void [[method3]](%class.A* [[a]])
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo();
-};
-
-class B : public A {
-public:
-  void foo() override;
-};
-
-typedef void (A::*A_foo)();
-
-void func(A *a, A_foo fn) {
-  (a->*fn)();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/multiple-inheritance.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/multiple-inheritance.cpp
deleted file mode 100644
index 76125c299686..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/multiple-inheritance.cpp
+++ /dev/null
@@ -1,55 +0,0 @@
-// Multiple inheritance.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: %class.C = type { %class.A, %class.B }
-// CHECK: %class.A = type { i32 (...)** }
-// CHECK: %class.B = type { i32 (...)** }
-
-// VTable for C contains 2 sub-vtables (represented as 2 structs). The first contains the components for B and the second contains the components for C. The RTTI ptr in both arrays still point to the RTTI struct for C.
-// The component for bar() instead points to a thunk which redirects to C::bar() which overrides B::bar().
-// Now that we have a class with 2 parents, the offset to top in the second array is non-zero.
-// CHECK: @_ZTV1C.local = private unnamed_addr constant { [4 x i32], [3 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64, i8*, i64 }** @_ZTI1C.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [3 x i32] }, { [4 x i32], [3 x i32] }* @_ZTV1C.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.C*)* @_ZN1C3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [3 x i32] }, { [4 x i32], [3 x i32] }* @_ZTV1C.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.C*)* @_ZN1C3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [3 x i32] }, { [4 x i32], [3 x i32] }* @_ZTV1C.local, i32 0, i32 0, i32 2) to i64)) to i32)], [3 x i32] [i32 -8, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i32, i32, i8*, i64, i8*, i64 }** @_ZTI1C.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [3 x i32] }, { [4 x i32], [3 x i32] }* @_ZTV1C.local, i32 0, i32 1, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.C*)* @_ZThn8_N1C3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32], [3 x i32] }, { [4 x i32], [3 x i32] }* @_ZTV1C.local, i32 0, i32 1, i32 2) to i64)) to i32)] }, align 4
-
-// CHECK: @_ZTV1C = unnamed_addr alias { [4 x i32], [3 x i32] }, { [4 x i32], [3 x i32] }* @_ZTV1C.local
-
-// CHECK:      define void @_Z8C_foobarP1C(%class.C* %c) local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   [[c:%[0-9]+]] = bitcast %class.C* %c to i8**
-// CHECK-NEXT:   [[vtable:%[a-z0-9]+]] = load i8*, i8** [[c]], align 8
-
-// Offset 0 to get first method
-// CHECK-NEXT:   [[ptr1:%[0-9]+]] = call i8* @llvm.load.relative.i32(i8* [[vtable]], i32 0)
-// CHECK-NEXT:   [[method1:%[0-9]+]] = bitcast i8* [[ptr1]] to void (%class.C*)*
-// CHECK-NEXT:   call void [[method1]](%class.C* %c)
-// CHECK-NEXT:   [[vtable:%[a-z0-9]+]] = load i8*, i8** [[c]], align 8
-
-// Offset by 4 to get the next bar()
-// CHECK-NEXT:   [[ptr2:%[0-9]+]] = call i8* @llvm.load.relative.i32(i8* [[vtable]], i32 4)
-// CHECK-NEXT:   [[method2:%[0-9]+]] = bitcast i8* [[ptr2]] to void (%class.C*)*
-// CHECK-NEXT:   call void [[method2]](%class.C* %c)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo();
-};
-
-class B {
-  virtual void bar();
-};
-
-class C : public A, public B {
-public:
-  void foo() override;
-  void bar() override;
-};
-
-void C::foo() {}
-void C::bar() {}
-
-void C_foobar(C *c) {
-  c->foo();
-  c->bar();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/no-alias-when-dso-local.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/no-alias-when-dso-local.cpp
deleted file mode 100644
index e9ee4b7722d7..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/no-alias-when-dso-local.cpp
+++ /dev/null
@@ -1,16 +0,0 @@
-// Check that no alias is emitted when the vtable is already dso_local. This can
-// happen if the class is hidden.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s --check-prefix=DEFAULT-VIS
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables -fvisibility hidden | FileCheck %s --check-prefix=HIDDEN-VIS
-
-// DEFAULT-VIS: @_ZTV1A.local = private unnamed_addr constant
-// DEFAULT-VIS: @_ZTV1A = unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1A.local
-// HIDDEN-VIS-NOT: @_ZTV1A.local
-// HIDDEN-VIS: @_ZTV1A = hidden unnamed_addr constant
-class A {
- public:
-  virtual void func();
-};
-
-void A::func() {}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/no-stub-when-dso-local.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/no-stub-when-dso-local.cpp
deleted file mode 100644
index bb4b6ae94a03..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/no-stub-when-dso-local.cpp
+++ /dev/null
@@ -1,49 +0,0 @@
-// Check that we do not emit a stub for a virtual function if it is already
-// known to be in the same linkage unit as the vtable.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s --check-prefixes=CHECK,NO-OPT
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables -O3 | FileCheck %s --check-prefixes=CHECK,OPT
-
-// The vtable offset is relative to _ZN1A3fooEv instead of a stub. We can do
-// this since hidden functions are implicitly dso_local.
-// CHECK: @_ZTV1A.local = private unnamed_addr constant { [5 x i32] } { [5 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32] }, { [5 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32] }, { [5 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (%class.A* (%class.A*)* @_ZN1AD1Ev.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32] }, { [5 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1AD0Ev.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32] }, { [5 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-
-// Despite the complete object destructor being hidden, we should still emit a
-// stub for it because it's possible, when optimizations are enabled, for the
-// dtor to be "devirtualized" into the destructor for a parent class if the
-// child class doesn't implement its own dtor. For complete destructors, we
-// always emit and use a stub.
-// @_ZTV1B = hidden unnamed_addr constant { [5 x i32] } { [5 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32] }, { [5 x i32] }* @_ZTV1B, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3fooEv to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32] }, { [5 x i32] }* @_ZTV1B, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (%class.B* (%class.B*)* @_ZN1BD1Ev.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32] }, { [5 x i32] }* @_ZTV1B, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1BD0Ev to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [5 x i32] }, { [5 x i32] }* @_ZTV1B, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-
-// CHECK: @_ZTV1A = unnamed_addr alias { [5 x i32] }, { [5 x i32] }* @_ZTV1A.local
-
-// CHECK: @_ZN1A3fooEv
-// CHECK-NOT: @_ZN1A3fooEv.stub
-
-// The complete object destructor is hidden.
-// NO-OPT: define linkonce_odr hidden %class.B* @_ZN1BD1Ev
-// OPT-NOT: @_ZN1BD1Ev
-// CHECK: @_ZN1BD1Ev.stub
-
-#define HIDDEN __attribute__((visibility("hidden")))
-
-class A {
-public:
-  HIDDEN virtual void foo();
-  virtual ~A();
-};
-
-class HIDDEN B : public A {
-public:
-  virtual void foo();
-};
-
-void A::foo() {}
-
-void A_foo(A *a) {
-  a->foo();
-}
-
-void B::foo() {
-  A::foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/override-pure-virtual-method.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/override-pure-virtual-method.cpp
deleted file mode 100644
index 1388a5a0b990..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/override-pure-virtual-method.cpp
+++ /dev/null
@@ -1,34 +0,0 @@
-// Override pure virtual function.
-// We instead emit zero for the pure virtual function component. See PR43094 for
-// details.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: @_ZTV1A.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 0, i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-
-// CHECK: @_ZTV1B.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-
-// CHECK: @_ZTV1A = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1A.local
-// CHECK: @_ZTV1B = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1B.local
-
-// CHECK-NOT: declare void @__cxa_pure_virtual() unnamed_addr
-
-class A {
-public:
-  virtual void foo() = 0;
-  virtual void bar();
-};
-
-class B : public A {
-public:
-  void foo() override;
-  void bar() override;
-};
-
-void A::bar() {}
-void B::foo() {}
-void B::bar() {}
-
-void A_foo(A *a) {
-  a->foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/overriden-virtual-function.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/overriden-virtual-function.cpp
deleted file mode 100644
index e3b3bb62f27b..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/overriden-virtual-function.cpp
+++ /dev/null
@@ -1,30 +0,0 @@
-// Check the layout of the vtable for a child class that inherits a virtual
-// function but does override it.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: @_ZTV1B.local = private unnamed_addr constant { [4 x i32] } { [4 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3barEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [4 x i32] }, { [4 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-
-// CHECK: @_ZTV1B = unnamed_addr alias { [4 x i32] }, { [4 x i32] }* @_ZTV1B.local
-
-class A {
-public:
-  virtual void foo();
-};
-
-class B : public A {
-public:
-  void foo() override;
-  virtual void bar();
-};
-
-void A::foo() {}
-void B::foo() {}
-
-void A_foo(A *a) {
-  a->foo();
-}
-
-void B_foo(B *b) {
-  b->foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/parent-and-child-in-comdats.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/parent-and-child-in-comdats.cpp
deleted file mode 100644
index 70a65825a5db..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/parent-and-child-in-comdats.cpp
+++ /dev/null
@@ -1,62 +0,0 @@
-// Cross comdat example
-// Both the parent and child VTablea are in their own comdat sections.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// Comdats are emitted for both A and B in this module and for their respective implementations of foo().
-// CHECK: $_ZN1A3fooEv = comdat any
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-// CHECK: $_ZN1B3fooEv = comdat any
-// CHECK: $_ZN1B3fooEv.stub = comdat any
-// CHECK: $_ZTV1A = comdat any
-// CHECK: $_ZTS1A = comdat any
-// CHECK: $_ZTI1A = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-// CHECK: $_ZTV1B = comdat any
-// CHECK: $_ZTS1B = comdat any
-// CHECK: $_ZTI1B = comdat any
-// CHECK: $_ZTI1B.rtti_proxy = comdat any
-
-// Both the vtables for A and B are emitted and in their own comdats.
-// CHECK: @_ZTV1A.local = linkonce_odr hidden unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, comdat($_ZTV1A), align 4
-// CHECK: @_ZTV1B.local = linkonce_odr hidden unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8*, i8* }** @_ZTI1B.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.B*)* @_ZN1B3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1B.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, comdat($_ZTV1B), align 4
-
-// CHECK: @_ZTV1A = linkonce_odr unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1A.local
-// CHECK: @_ZTV1B = linkonce_odr unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1B.local
-
-// CHECK: declare void @_Z5A_fooP1A(%class.A*)
-
-// The stubs and implementations for foo() are in their own comdat sections.
-// CHECK:      define linkonce_odr void @_ZN1A3fooEv(%class.A* %this) unnamed_addr #{{[0-9]+}} comdat
-
-// CHECK:      define hidden void @_ZN1A3fooEv.stub(%class.A* %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1A3fooEv(%class.A* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// CHECK:      define linkonce_odr void @_ZN1B3fooEv(%class.B* %this) unnamed_addr #{{[0-9]+}} comdat
-
-// CHECK:      define hidden void @_ZN1B3fooEv.stub(%class.B* %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1B3fooEv(%class.B* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  inline virtual void foo() {}
-};
-class B : public A {
-public:
-  inline void foo() override {}
-};
-void A_foo(A *a);
-
-// func() is used so that the vtable for B is accessed when creating the instance.
-void func() {
-  A a;
-  B b;
-  A_foo(&a);
-  A_foo(&b);
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/parent-vtable-in-comdat.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/parent-vtable-in-comdat.cpp
deleted file mode 100644
index d22cf802689f..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/parent-vtable-in-comdat.cpp
+++ /dev/null
@@ -1,48 +0,0 @@
-// Cross comdat example
-// Parent VTable is in a comdat section.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// A::foo() has a comdat since it is an inline function
-// CHECK: $_ZN1A3fooEv = comdat any
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-// CHECK: $_ZTV1A = comdat any
-// CHECK: $_ZTS1A = comdat any
-
-// The VTable for A has its own comdat section bc it has no key function
-// CHECK: $_ZTI1A = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-
-// The VTable for A is emitted here and in a comdat section since it has no key function, and is used in this module when creating an instance of A.
-// CHECK: @_ZTV1A.local = linkonce_odr hidden unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, comdat($_ZTV1A), align 4
-// CHECK: @_ZTVN10__cxxabiv117__class_type_infoE = external global i8*
-// CHECK: @_ZTS1A = linkonce_odr constant [3 x i8] c"1A\00", comdat, align 1
-// CHECK: @_ZTI1A = linkonce_odr constant { i8*, i8* } { i8* getelementptr inbounds (i8, i8* bitcast (i8** @_ZTVN10__cxxabiv117__class_type_infoE to i8*), i32 8), i8* getelementptr inbounds ([3 x i8], [3 x i8]* @_ZTS1A, i32 0, i32 0) }, comdat, align 8
-// CHECK: @_ZTI1A.rtti_proxy = hidden unnamed_addr constant { i8*, i8* }* @_ZTI1A, comdat
-// CHECK: @_ZTV1A = linkonce_odr unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1A.local
-
-// CHECK:      define linkonce_odr void @_ZN1A3fooEv(%class.A* %this) unnamed_addr #{{[0-9]+}} comdat
-
-// CHECK:      define hidden void @_ZN1A3fooEv.stub(%class.A* %0) unnamed_addr #{{[0-9]+}} comdat {
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN1A3fooEv(%class.A* %0)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  inline virtual void foo() {}
-};
-class B : public A {
-public:
-  void foo() override;
-};
-void A_foo(A *a);
-
-void A_foo(A *a) { a->foo(); }
-
-// func() is only used to emit a vtable.
-void func() {
-  A a;
-  A_foo(&a);
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/pass-byval-attributes.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/pass-byval-attributes.cpp
deleted file mode 100644
index 43bd234e5f83..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/pass-byval-attributes.cpp
+++ /dev/null
@@ -1,37 +0,0 @@
-// ByVal attributes should propogate through to produce proper assembly and
-// avoid "unpacking" structs within the stubs on x86_64.
-
-// RUN: %clang_cc1 %s -triple=x86_64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-struct LargeStruct {
-  char x[24];
-  virtual ~LargeStruct() {}
-};
-
-struct fidl_string {
-  unsigned long long size;
-  char *data;
-};
-static_assert(sizeof(fidl_string) == 16, "");
-
-class Base {
-public:
-  virtual void func(LargeStruct, fidl_string, LargeStruct, fidl_string) = 0;
-};
-
-class Derived : public Base {
-public:
-  void func(LargeStruct, fidl_string, LargeStruct, fidl_string) override;
-};
-
-// The original function takes a byval pointer.
-// CHECK: define void @_ZN7Derived4funcE11LargeStruct11fidl_stringS0_S1_(%class.Derived* %this, %struct.LargeStruct* %ls, i64 %sv1.coerce0, i8* %sv1.coerce1, %struct.LargeStruct* %ls2, %struct.fidl_string* byval(%struct.fidl_string) align 8 %sv2) unnamed_addr
-
-// So the stub should take and pass one also.
-// CHECK:      define hidden void @_ZN7Derived4funcE11LargeStruct11fidl_stringS0_S1_.stub(%class.Derived* %0, %struct.LargeStruct* %1, i64 %2, i8* %3, %struct.LargeStruct* %4, %struct.fidl_string* byval(%struct.fidl_string) align 8 %5) unnamed_addr {{#[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   tail call void @_ZN7Derived4funcE11LargeStruct11fidl_stringS0_S1_(%class.Derived* %0, %struct.LargeStruct* %1, i64 %2, i8* %3, %struct.LargeStruct* %4, %struct.fidl_string* byval(%struct.fidl_string) align 8 %5)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-void Derived::func(LargeStruct ls, fidl_string sv1, LargeStruct ls2, fidl_string sv2) {}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/relative-vtables-flag.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/relative-vtables-flag.cpp
deleted file mode 100644
index 01cef5055dd5..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/relative-vtables-flag.cpp
+++ /dev/null
@@ -1,24 +0,0 @@
-// Check the layout of the vtable for a normal class.
-// The Fuchsia relative vtables ABI will be hidden behind a flag for now as part
-// of a soft incremental rollout. This ABI should only be used if the flag for
-// it is passed on Fuchsia.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck --check-prefix=RELATIVE-ABI %s
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fno-experimental-relative-c++-abi-vtables | FileCheck --check-prefix=DEFAULT-ABI %s
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm | FileCheck --check-prefix=DEFAULT-ABI %s
-
-// VTable contains offsets and references to the hidden symbols
-// RELATIVE-ABI: @_ZTV1A.local = private unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-// RELATIVE-ABI: @_ZTV1A = unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1A.local
-// DEFAULT-ABI: @_ZTV1A = unnamed_addr constant { [3 x i8*] } { [3 x i8*] [i8* null, i8* bitcast ({ i8*, i8* }* @_ZTI1A to i8*), i8* bitcast (void (%class.A*)* @_ZN1A3fooEv to i8*)] }, align 8
-
-class A {
-public:
-  virtual void foo();
-};
-
-void A::foo() {}
-
-void A_foo(A *a) {
-  a->foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/simple-vtable-definition.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/simple-vtable-definition.cpp
deleted file mode 100644
index 99e63313ac38..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/simple-vtable-definition.cpp
+++ /dev/null
@@ -1,43 +0,0 @@
-// Check the layout of the vtable for a normal class.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// We should be emitting comdats for each of the virtual function stubs and RTTI proxies
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-
-// VTable contains offsets and references to the hidden symbols
-// The vtable definition itself is private so we can take relative references to
-// it. The vtable symbol will be exposed through a public alias.
-// CHECK: @_ZTV1A.local = private unnamed_addr constant { [3 x i32] } { [3 x i32] [i32 0, i32 trunc (i64 sub (i64 ptrtoint ({ i8*, i8* }** @_ZTI1A.rtti_proxy to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32), i32 trunc (i64 sub (i64 ptrtoint (void (%class.A*)* @_ZN1A3fooEv.stub to i64), i64 ptrtoint (i32* getelementptr inbounds ({ [3 x i32] }, { [3 x i32] }* @_ZTV1A.local, i32 0, i32 0, i32 2) to i64)) to i32)] }, align 4
-// CHECK: @_ZTVN10__cxxabiv117__class_type_infoE = external global i8*
-// CHECK: @_ZTS1A = constant [3 x i8] c"1A\00", align 1
-// CHECK: @_ZTI1A = constant { i8*, i8* } { i8* getelementptr inbounds (i8, i8* bitcast (i8** @_ZTVN10__cxxabiv117__class_type_infoE to i8*), i32 8), i8* getelementptr inbounds ([3 x i8], [3 x i8]* @_ZTS1A, i32 0, i32 0) }, align 8
-
-// The stub should be in a comdat
-// CHECK: @_ZTI1A.rtti_proxy = hidden unnamed_addr constant { i8*, i8* }* @_ZTI1A, comdat
-
-// The vtable symbol is exposed through an alias.
-// @_ZTV1A = dso_local unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1A.local
-
-// CHECK:      define void @_ZN1A3fooEv(%class.A* nocapture %this) unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-// This function should be in a comdat
-// CHECK:      define hidden void @_ZN1A3fooEv.stub(%class.A* nocapture %0) unnamed_addr #{{[0-9]+}} comdat
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo();
-};
-
-void A::foo() {}
-
-void A_foo(A *a) {
-  a->foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/stub-linkages.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/stub-linkages.cpp
deleted file mode 100644
index 53360091bf55..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/stub-linkages.cpp
+++ /dev/null
@@ -1,51 +0,0 @@
-// If the linkage of the class is internal, then the stubs and proxies should
-// also be internally linked.
-
-// RUN: %clang_cc1 %s -triple=x86_64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// External linkage.
-// CHECK: @_ZTI8External.rtti_proxy = hidden unnamed_addr constant { i8*, i8* }* @_ZTI8External, comdat
-
-class External {
-public:
-  virtual void func();
-};
-
-void External::func() {}
-
-// Internal linkage.
-// CHECK: @_ZTIN12_GLOBAL__N_18InternalE.rtti_proxy = internal unnamed_addr constant { i8*, i8* }* @_ZTIN12_GLOBAL__N_18InternalE
-namespace {
-
-class Internal {
-public:
-  virtual void func();
-};
-
-void Internal::func() {}
-
-} // namespace
-
-// This gets the same treatment as an externally available vtable.
-// CHECK: @_ZTI11LinkOnceODR.rtti_proxy = hidden unnamed_addr constant { i8*, i8* }* @_ZTI11LinkOnceODR, comdat
-class LinkOnceODR {
-public:
-  virtual void func() {} // A method defined in the class definition results in this linkage for the vtable.
-};
-
-// Force an emission of a vtable for Internal by using it here.
-void manifest_internal() {
-  Internal internal;
-  (void)internal;
-  LinkOnceODR linkonceodr;
-  (void)linkonceodr;
-}
-
-// Aliases are typically emitted after the vtable definitions but before the
-// function definitions.
-// CHECK: @_ZTV8External = unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV8External.local
-// CHECK: @_ZTV11LinkOnceODR = linkonce_odr unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV11LinkOnceODR.local
-
-// CHECK: define void @_ZN8External4funcEv
-// CHECK: define internal void @_ZN12_GLOBAL__N_18Internal4funcEv.stub
-// CHECK: define hidden void @_ZN11LinkOnceODR4funcEv.stub

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/thunk-mangling.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/thunk-mangling.cpp
deleted file mode 100644
index fb1da64e93f4..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/thunk-mangling.cpp
+++ /dev/null
@@ -1,31 +0,0 @@
-// Check that virtual thunks are unaffected by the relative ABI.
-// The offset of thunks is mangled into the symbol name, which could result in
-// linking errors for binaries that want to look for symbols in SOs made with
-// this ABI.
-// Running that linked binary still won't work since we're using conflicting
-// ABIs, but we should still be able to link.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O1 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// This would be normally n24 (3 ptr widths) but is 12 since the vtable is
-// entierely made of i32s now.
-// CHECK: _ZTv0_n12_N7Derived1fEi
-
-class Base {
-public:
-  virtual int f(int x);
-
-private:
-  long x;
-};
-
-class Derived : public virtual Base {
-public:
-  virtual int f(int x);
-
-private:
-  long y;
-};
-
-int Base::f(int x) { return x + 1; }
-int Derived::f(int x) { return x + 2; }

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/type-info.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/type-info.cpp
deleted file mode 100644
index 86b73193c08c..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/type-info.cpp
+++ /dev/null
@@ -1,77 +0,0 @@
-// Check typeid() + type_info
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O3 -S -o - -emit-llvm -fcxx-exceptions -fexceptions -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: %class.A = type { i32 (...)** }
-// CHECK: %class.B = type { %class.A }
-// CHECK: %"class.std::type_info" = type { i32 (...)**, i8* }
-
-// CHECK: $_ZN1A3fooEv.stub = comdat any
-// CHECK: $_ZN1B3fooEv.stub = comdat any
-// CHECK: $_ZTI1A.rtti_proxy = comdat any
-// CHECK: $_ZTI1B.rtti_proxy = comdat any
-
-// CHECK: @_ZTVN10__cxxabiv117__class_type_infoE = external global i8*
-// CHECK: @_ZTS1A = constant [3 x i8] c"1A\00", align 1
-// CHECK: @_ZTI1A = constant { i8*, i8* } { i8* getelementptr inbounds (i8, i8* bitcast (i8** @_ZTVN10__cxxabiv117__class_type_infoE to i8*), i32 8), i8* getelementptr inbounds ([3 x i8], [3 x i8]* @_ZTS1A, i32 0, i32 0) }, align 8
-// CHECK: @_ZTVN10__cxxabiv120__si_class_type_infoE = external global i8*
-// CHECK: @_ZTS1B = constant [3 x i8] c"1B\00", align 1
-// CHECK: @_ZTI1B = constant { i8*, i8*, i8* } { i8* getelementptr inbounds (i8, i8* bitcast (i8** @_ZTVN10__cxxabiv120__si_class_type_infoE to i8*), i32 8), i8* getelementptr inbounds ([3 x i8], [3 x i8]* @_ZTS1B, i32 0, i32 0), i8* bitcast ({ i8*, i8* }* @_ZTI1A to i8*) }, align 8
-// CHECK: @_ZTI1A.rtti_proxy = hidden unnamed_addr constant { i8*, i8* }* @_ZTI1A, comdat
-// CHECK: @_ZTI1B.rtti_proxy = hidden unnamed_addr constant { i8*, i8*, i8* }* @_ZTI1B, comdat
-
-// CHECK:      define {{.*}}%"class.std::type_info"* @_Z11getTypeInfov() local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret %"class.std::type_info"* bitcast ({ i8*, i8* }* @_ZTI1A to %"class.std::type_info"*)
-// CHECK-NEXT: }
-
-// CHECK:      define i8* @_Z7getNamev() local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   ret i8* getelementptr inbounds ([3 x i8], [3 x i8]* @_ZTS1A, i64 0, i64 0)
-// CHECK-NEXT: }
-
-// CHECK:      define i1 @_Z5equalP1A(%class.A* readonly %a) local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   [[isnull:%[0-9]+]] = icmp eq %class.A* %a, null
-// CHECK-NEXT:   br i1 [[isnull]], label %[[bad_typeid:[a-z0-9._]+]], label %[[end:[a-z0-9.+]+]]
-// CHECK:      [[bad_typeid]]:
-// CHECK-NEXT:   tail call void @__cxa_bad_typeid()
-// CHECK-NEXT:   unreachable
-// CHECK:      [[end]]:
-// CHECK-NEXT:   [[type_info_ptr3:%[0-9]+]] = bitcast %class.A* %a to i8**
-// CHECK-NEXT:   [[vtable:%[a-z0-9]+]] = load i8*, i8** [[type_info_ptr3]]
-// CHECK-NEXT:   [[type_info_ptr:%[0-9]+]] = tail call i8* @llvm.load.relative.i32(i8* [[vtable]], i32 -4)
-// CHECK-NEXT:   [[type_info_ptr2:%[0-9]+]] = bitcast i8* [[type_info_ptr]] to %"class.std::type_info"**
-// CHECK-NEXT:   [[type_info_ptr:%[0-9]+]] = load %"class.std::type_info"*, %"class.std::type_info"** [[type_info_ptr2]], align 8
-// CHECK-NEXT:   [[name_ptr:%[a-z0-9._]+]] = getelementptr inbounds %"class.std::type_info", %"class.std::type_info"* [[type_info_ptr]], i64 0, i32 1
-// CHECK-NEXT:   [[name:%[0-9]+]] = load i8*, i8** [[name_ptr]], align 8
-// CHECK-NEXT:   [[eq:%[a-z0-9.]+]] = icmp eq i8* [[name]], getelementptr inbounds ([3 x i8], [3 x i8]* @_ZTS1B, i64 0, i64 0)
-// CHECK-NEXT:   ret i1 [[eq]]
-// CHECK-NEXT: }
-
-#include "../typeinfo"
-
-class A {
-public:
-  virtual void foo();
-};
-
-class B : public A {
-public:
-  void foo() override;
-};
-
-void A::foo() {}
-void B::foo() {}
-
-const auto &getTypeInfo() {
-  return typeid(A);
-}
-
-const char *getName() {
-  return typeid(A).name();
-}
-
-bool equal(A *a) {
-  return typeid(B) == typeid(*a);
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/vbase-offset.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/vbase-offset.cpp
deleted file mode 100644
index 178f453deac3..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/vbase-offset.cpp
+++ /dev/null
@@ -1,36 +0,0 @@
-// Check that the pointer adjustment from the virtual base offset is loaded as a
-// 32-bit int.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK-LABEL: @_ZTv0_n12_N7Derived1fEi(
-// CHECK-NEXT:  entry:
-// CHECK:        [[this:%.+]] = bitcast %class.Derived* %this1 to i8*
-// CHECK-NEXT:   [[this2:%.+]] = bitcast i8* [[this]] to i8**
-// CHECK-NEXT:   [[vtable:%.+]] = load i8*, i8** [[this2]], align 8
-// CHECK-NEXT:   [[vbase_offset_ptr:%.+]] = getelementptr inbounds i8, i8* [[vtable]], i64 -12
-// CHECK-NEXT:   [[vbase_offset_ptr2:%.+]] = bitcast i8* [[vbase_offset_ptr]] to i32*
-// CHECK-NEXT:   [[vbase_offset:%.+]] = load i32, i32* [[vbase_offset_ptr2]], align 4
-// CHECK-NEXT:   [[adj_this:%.+]] = getelementptr inbounds i8, i8* [[this]], i32 [[vbase_offset]]
-// CHECK-NEXT:   [[adj_this2:%.+]] = bitcast i8* [[adj_this]] to %class.Derived*
-// CHECK:        [[call:%.+]] = tail call i32 @_ZN7Derived1fEi(%class.Derived* [[adj_this2]], i32 {{.*}})
-// CHECK:        ret i32 [[call]]
-
-class Base {
-public:
-  virtual int f(int x);
-
-private:
-  long x;
-};
-
-class Derived : public virtual Base {
-public:
-  virtual int f(int x);
-
-private:
-  long y;
-};
-
-int Base::f(int x) { return x + 1; }
-int Derived::f(int x) { return x + 2; }

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/virtual-function-call.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/virtual-function-call.cpp
deleted file mode 100644
index 0b0b5bd5faa7..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/virtual-function-call.cpp
+++ /dev/null
@@ -1,22 +0,0 @@
-// Check that we call llvm.load.relative() on a vtable function call.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -O3 -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK:      define void @_Z5A_fooP1A(%class.A* %a) local_unnamed_addr
-// CHECK-NEXT: entry:
-// CHECK-NEXT:   [[this:%[0-9]+]] = bitcast %class.A* %a to i8**
-// CHECK-NEXT:   %vtable1 = load i8*, i8** [[this]]
-// CHECK-NEXT:   [[func_ptr:%[0-9]+]] = tail call i8* @llvm.load.relative.i32(i8* %vtable1, i32 0)
-// CHECK-NEXT:   [[func:%[0-9]+]] = bitcast i8* [[func_ptr]] to void (%class.A*)*
-// CHECK-NEXT:   tail call void [[func]](%class.A* %a)
-// CHECK-NEXT:   ret void
-// CHECK-NEXT: }
-
-class A {
-public:
-  virtual void foo();
-};
-
-void A_foo(A *a) {
-  a->foo();
-}

diff  --git a/clang/test/CodeGenCXX/RelativeVTablesABI/vtable-hidden-when-in-comdat.cpp b/clang/test/CodeGenCXX/RelativeVTablesABI/vtable-hidden-when-in-comdat.cpp
deleted file mode 100644
index 9b2b3a5c1c80..000000000000
--- a/clang/test/CodeGenCXX/RelativeVTablesABI/vtable-hidden-when-in-comdat.cpp
+++ /dev/null
@@ -1,19 +0,0 @@
-// Check that a vtable is made hidden instead of private if the original vtable
-// is not dso_local. The vtable will need to be hidden and not private so it can
-// be used as acomdat key signature.
-
-// RUN: %clang_cc1 %s -triple=aarch64-unknown-fuchsia -S -o - -emit-llvm -fexperimental-relative-c++-abi-vtables | FileCheck %s
-
-// CHECK: @_ZTV1B.local = linkonce_odr hidden unnamed_addr constant
-// CHECK: @_ZTV1B = linkonce_odr unnamed_addr alias { [3 x i32] }, { [3 x i32] }* @_ZTV1B.local
-
-// The VTable will be in a comdat here since it has no key function.
-class B {
- public:
-  inline virtual void func() {}
-};
-
-// This is here just to manifest the vtable for B.
-void func() {
-  B b;
-}


        


More information about the cfe-commits mailing list