mirror of
https://git.freebsd.org/ports.git
synced 2025-07-18 01:39:16 -04:00
Add all patches from base llvm/clang/lld/lldb 6.0 to devel/llvm60
This adds all the patches that were applied in the past to head, under contrib/llvm. After these, there only minimal diffs left between the port sources and the base sources. Most of these remaining diffs are due to #ifdef shortcuts in the base sources, because we don't compile certain features in. Other diffs are because the port has applied a few changes that we don't have in base. While here, use Makefile.LICENSE from the devel/llvm-devel port. Approved by: brooks (maintainer) Reviewed by: brooks PR: 212343, 225128, 225471, 226388, 226658, 226872, 229050, 230444, 230604, 231355 MFH: 2018Q4 Differential Revision: https://reviews.freebsd.org/D17702
This commit is contained in:
parent
133a6110fa
commit
a702c15488
Notes:
svn2git
2021-03-31 03:12:20 +00:00
svn path=/head/; revision=483054
24 changed files with 1835 additions and 5 deletions
|
@ -2,7 +2,7 @@
|
|||
|
||||
PORTNAME= llvm
|
||||
DISTVERSION= 6.0.1
|
||||
PORTREVISION= 2
|
||||
PORTREVISION= 3
|
||||
CATEGORIES= devel lang
|
||||
MASTER_SITES= http://${PRE_}releases.llvm.org/${LLVM_RELEASE}/${RCDIR}
|
||||
PKGNAMESUFFIX= ${LLVM_SUFFIX}
|
||||
|
@ -12,10 +12,7 @@ DISTFILES= ${PORTNAME}-${DISTVERSION}.src${EXTRACT_SUFX}
|
|||
MAINTAINER= brooks@FreeBSD.org
|
||||
COMMENT= LLVM and Clang
|
||||
|
||||
LICENSE= LLVM
|
||||
LICENSE_NAME= LLVM Release License
|
||||
LICENSE_FILE= ${WRKSRC}/LICENSE.TXT
|
||||
LICENSE_PERMS= dist-mirror dist-sell pkg-mirror pkg-sell auto-accept
|
||||
.include "${.CURDIR}/../llvm-devel/Makefile.LICENSE"
|
||||
|
||||
LLVM_RELEASE= ${DISTVERSION:C/rc.*//}
|
||||
LLVM_MAJOR= ${LLVM_RELEASE:C/\.[0-9]$//}
|
||||
|
@ -84,10 +81,12 @@ LIT_DESC= Install lit and FileCheck test tools
|
|||
LIT_VARS= _USES_PYTHON=python:2.7
|
||||
LLD_DESC= Install lld, the LLVM linker
|
||||
LLD_DISTFILES= lld-${DISTVERSION}.src${EXTRACT_SUFX}
|
||||
LLD_EXTRA_PATCHES= ${PATCHDIR}/lld
|
||||
LLDB_BUILD_DEPENDS= swig3.0:devel/swig30 \
|
||||
${PY_ENUM34}
|
||||
LLDB_DESC= Install lldb, the LLVM debugger
|
||||
LLDB_DISTFILES= lldb-${DISTVERSION}.src${EXTRACT_SUFX}
|
||||
LLDB_EXTRA_PATCHES= ${PATCHDIR}/lldb
|
||||
LLDB_IMPLIES= CLANG
|
||||
LLDB_VARS= _USES_PYTHON=python:2.7
|
||||
OPENMP_DESC= Install libomp, the LLVM OpenMP runtime library
|
||||
|
@ -228,6 +227,7 @@ CLANG_PATTERN= (c-index-test|clang|scan-|Reporter.py|ScanView.py|scanview.css|so
|
|||
SHEBANG_FILES+= tools/clang/tools/scan-view/bin/scan-view \
|
||||
tools/clang/tools/clang-format/git-clang-format \
|
||||
tools/clang/tools/clang-format/clang-format-diff.py
|
||||
USES+= gnome
|
||||
.endif
|
||||
|
||||
.if ${PORT_OPTIONS:MCOMPILER_RT}
|
||||
|
|
40
devel/llvm60/files/clang/patch-head-r331066.diff
Normal file
40
devel/llvm60/files/clang/patch-head-r331066.diff
Normal file
|
@ -0,0 +1,40 @@
|
|||
r331066 | dim | 2018-03-16 19:04:13 +0100 (Fri, 16 Mar 2018) | 19 lines
|
||||
|
||||
Pull in r321999 from upstream clang trunk (by Ivan A. Kosarev):
|
||||
|
||||
[CodeGen] Fix TBAA info for accesses to members of base classes
|
||||
|
||||
Resolves:
|
||||
Bug 35724 - regression (r315984): fatal error: error in backend:
|
||||
Broken function found (Did not see access type in access path!)
|
||||
https://bugs.llvm.org/show_bug.cgi?id=35724
|
||||
|
||||
Differential Revision: https://reviews.llvm.org/D41547
|
||||
|
||||
This fixes "Did not see access type in access path" fatal errors when
|
||||
building the devel/gdb port (version 8.1).
|
||||
|
||||
Reported by: jbeich
|
||||
PR: 226658
|
||||
MFC after: 3 months
|
||||
X-MFC-With: r327952
|
||||
|
||||
Index: tools/clang/lib/CodeGen/CGExpr.cpp
|
||||
===================================================================
|
||||
--- tools/clang/lib/CodeGen/CGExpr.cpp (revision 331065)
|
||||
+++ tools/clang/lib/CodeGen/CGExpr.cpp (revision 331066)
|
||||
@@ -1034,8 +1034,12 @@ Address CodeGenFunction::EmitPointerWithAlignment(
|
||||
// Derived-to-base conversions.
|
||||
case CK_UncheckedDerivedToBase:
|
||||
case CK_DerivedToBase: {
|
||||
- Address Addr = EmitPointerWithAlignment(CE->getSubExpr(), BaseInfo,
|
||||
- TBAAInfo);
|
||||
+ // TODO: Support accesses to members of base classes in TBAA. For now, we
|
||||
+ // conservatively pretend that the complete object is of the base class
|
||||
+ // type.
|
||||
+ if (TBAAInfo)
|
||||
+ *TBAAInfo = CGM.getTBAAAccessInfo(E->getType());
|
||||
+ Address Addr = EmitPointerWithAlignment(CE->getSubExpr(), BaseInfo);
|
||||
auto Derived = CE->getSubExpr()->getType()->getPointeeCXXRecordDecl();
|
||||
return GetAddressOfBaseClass(Addr, Derived,
|
||||
CE->path_begin(), CE->path_end(),
|
42
devel/llvm60/files/clang/patch-head-r336227.diff
Normal file
42
devel/llvm60/files/clang/patch-head-r336227.diff
Normal file
|
@ -0,0 +1,42 @@
|
|||
r336227 | dim | 2018-07-12 21:02:59 +0200 (Thu, 12 Jul 2018) | 27 lines
|
||||
|
||||
Pull in r336008 from upstream clang trunk:
|
||||
|
||||
Request init/fini array on FreeBSD 12 and later
|
||||
|
||||
Summary:
|
||||
|
||||
It seems a bad idea to change the default in the middle of a release
|
||||
branch due to possible changes in global ctor / dtor ordering between
|
||||
.ctors and .init_array. With FreeBSD 11.0's release imminent lets
|
||||
change the default now for FreeBSD 12 (the current development
|
||||
stream) and later.
|
||||
|
||||
FreeBSD rtld has supported .init_array / .fini_array for many years.
|
||||
As of Jan 1 2017 all supported FreeBSD releases and branches will
|
||||
have support.
|
||||
|
||||
Reviewers: dim, brooks, arichardson
|
||||
|
||||
Reviewed By: dim, brooks, arichardson
|
||||
|
||||
Subscribers: bsdjhb, krytarowski, emaste, cfe-commits
|
||||
|
||||
Differential Revision: https://reviews.llvm.org/D24867
|
||||
|
||||
Requested by: jhb
|
||||
MFC after: 3 days
|
||||
|
||||
Index: tools/clang/lib/Driver/ToolChains/Gnu.cpp
|
||||
===================================================================
|
||||
--- tools/clang/lib/Driver/ToolChains/Gnu.cpp (revision 336226)
|
||||
+++ tools/clang/lib/Driver/ToolChains/Gnu.cpp (revision 336227)
|
||||
@@ -2375,6 +2375,8 @@ void Generic_ELF::addClangTargetOptions(const ArgL
|
||||
bool UseInitArrayDefault =
|
||||
getTriple().getArch() == llvm::Triple::aarch64 ||
|
||||
getTriple().getArch() == llvm::Triple::aarch64_be ||
|
||||
+ (getTriple().getOS() == llvm::Triple::FreeBSD &&
|
||||
+ getTriple().getOSMajorVersion() >= 12) ||
|
||||
(getTriple().getOS() == llvm::Triple::Linux &&
|
||||
((!GCCInstallation.isValid() || !V.isOlderThan(4, 7, 0)) ||
|
||||
getTriple().isAndroid())) ||
|
104
devel/llvm60/files/clang/patch-head-r338697.diff
Normal file
104
devel/llvm60/files/clang/patch-head-r338697.diff
Normal file
|
@ -0,0 +1,104 @@
|
|||
r338697 | dim | 2018-09-15 23:22:50 +0200 (Sat, 15 Sep 2018) | 21 lines
|
||||
|
||||
Pull in r325478 from upstream clang trunk (by Ivan A. Kosarev):
|
||||
|
||||
[CodeGen] Initialize large arrays by copying from a global
|
||||
|
||||
Currently, clang compiles explicit initializers for array elements
|
||||
into series of store instructions. For large arrays of built-in types
|
||||
this results in bloated output code and significant amount of time
|
||||
spent on the instruction selection phase. This patch fixes the issue
|
||||
by initializing such arrays with global constants that store the
|
||||
binary image of the initializer.
|
||||
|
||||
Differential Revision: https://reviews.llvm.org/D43181
|
||||
|
||||
This should fix a compiler hang (and excessive memory usage) while
|
||||
building the science/rmg port.
|
||||
|
||||
Approved by: re (kib)
|
||||
Reported by: yuri@tsoft.com
|
||||
See also: https://bugs.llvm.org/show_bug.cgi?id=38798
|
||||
MFC after: 3 days
|
||||
|
||||
Index: tools/clang/lib/CodeGen/CGExprAgg.cpp
|
||||
===================================================================
|
||||
--- tools/clang/lib/CodeGen/CGExprAgg.cpp (revision 338696)
|
||||
+++ tools/clang/lib/CodeGen/CGExprAgg.cpp (revision 338697)
|
||||
@@ -14,6 +14,7 @@
|
||||
#include "CodeGenFunction.h"
|
||||
#include "CGObjCRuntime.h"
|
||||
#include "CodeGenModule.h"
|
||||
+#include "ConstantEmitter.h"
|
||||
#include "clang/AST/ASTContext.h"
|
||||
#include "clang/AST/DeclCXX.h"
|
||||
#include "clang/AST/DeclTemplate.h"
|
||||
@@ -85,7 +86,7 @@ class AggExprEmitter : public StmtVisitor<AggExprE
|
||||
void EmitMoveFromReturnSlot(const Expr *E, RValue Src);
|
||||
|
||||
void EmitArrayInit(Address DestPtr, llvm::ArrayType *AType,
|
||||
- QualType elementType, InitListExpr *E);
|
||||
+ QualType ArrayQTy, InitListExpr *E);
|
||||
|
||||
AggValueSlot::NeedsGCBarriers_t needsGC(QualType T) {
|
||||
if (CGF.getLangOpts().getGC() && TypeRequiresGCollection(T))
|
||||
@@ -392,12 +393,15 @@ static bool isTrivialFiller(Expr *E) {
|
||||
|
||||
/// \brief Emit initialization of an array from an initializer list.
|
||||
void AggExprEmitter::EmitArrayInit(Address DestPtr, llvm::ArrayType *AType,
|
||||
- QualType elementType, InitListExpr *E) {
|
||||
+ QualType ArrayQTy, InitListExpr *E) {
|
||||
uint64_t NumInitElements = E->getNumInits();
|
||||
|
||||
uint64_t NumArrayElements = AType->getNumElements();
|
||||
assert(NumInitElements <= NumArrayElements);
|
||||
|
||||
+ QualType elementType =
|
||||
+ CGF.getContext().getAsArrayType(ArrayQTy)->getElementType();
|
||||
+
|
||||
// DestPtr is an array*. Construct an elementType* by drilling
|
||||
// down a level.
|
||||
llvm::Value *zero = llvm::ConstantInt::get(CGF.SizeTy, 0);
|
||||
@@ -409,6 +413,29 @@ void AggExprEmitter::EmitArrayInit(Address DestPtr
|
||||
CharUnits elementAlign =
|
||||
DestPtr.getAlignment().alignmentOfArrayElement(elementSize);
|
||||
|
||||
+ // Consider initializing the array by copying from a global. For this to be
|
||||
+ // more efficient than per-element initialization, the size of the elements
|
||||
+ // with explicit initializers should be large enough.
|
||||
+ if (NumInitElements * elementSize.getQuantity() > 16 &&
|
||||
+ elementType.isTriviallyCopyableType(CGF.getContext())) {
|
||||
+ CodeGen::CodeGenModule &CGM = CGF.CGM;
|
||||
+ ConstantEmitter Emitter(CGM);
|
||||
+ LangAS AS = ArrayQTy.getAddressSpace();
|
||||
+ if (llvm::Constant *C = Emitter.tryEmitForInitializer(E, AS, ArrayQTy)) {
|
||||
+ auto GV = new llvm::GlobalVariable(
|
||||
+ CGM.getModule(), C->getType(),
|
||||
+ CGM.isTypeConstant(ArrayQTy, /* ExcludeCtorDtor= */ true),
|
||||
+ llvm::GlobalValue::PrivateLinkage, C, "constinit",
|
||||
+ /* InsertBefore= */ nullptr, llvm::GlobalVariable::NotThreadLocal,
|
||||
+ CGM.getContext().getTargetAddressSpace(AS));
|
||||
+ Emitter.finalize(GV);
|
||||
+ CharUnits Align = CGM.getContext().getTypeAlignInChars(ArrayQTy);
|
||||
+ GV->setAlignment(Align.getQuantity());
|
||||
+ EmitFinalDestCopy(ArrayQTy, CGF.MakeAddrLValue(GV, ArrayQTy, Align));
|
||||
+ return;
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
// Exception safety requires us to destroy all the
|
||||
// already-constructed members if an initializer throws.
|
||||
// For that, we'll need an EH cleanup.
|
||||
@@ -1156,11 +1183,8 @@ void AggExprEmitter::VisitInitListExpr(InitListExp
|
||||
|
||||
// Handle initialization of an array.
|
||||
if (E->getType()->isArrayType()) {
|
||||
- QualType elementType =
|
||||
- CGF.getContext().getAsArrayType(E->getType())->getElementType();
|
||||
-
|
||||
auto AType = cast<llvm::ArrayType>(Dest.getAddress().getElementType());
|
||||
- EmitArrayInit(Dest.getAddress(), AType, elementType, E);
|
||||
+ EmitArrayInit(Dest.getAddress(), AType, E->getType(), E);
|
||||
return;
|
||||
}
|
||||
|
30
devel/llvm60/files/clang/patch-head-r339019.diff
Normal file
30
devel/llvm60/files/clang/patch-head-r339019.diff
Normal file
|
@ -0,0 +1,30 @@
|
|||
r339019 | emaste | 2018-09-29 22:01:23 +0200 (Sat, 29 Sep 2018) | 15 lines
|
||||
|
||||
clang: allow ifunc resolvers to accept arguments
|
||||
|
||||
Previously Clang required ifunc resolution functions to take no
|
||||
arguments, presumably because GCC documented ifunc resolvers as taking
|
||||
no arguments. However, GCC accepts resolvers accepting arguments, and
|
||||
our rtld passes CPU ID information (cpuid, hwcap, etc.) to ifunc
|
||||
resolvers. Just remove the check from the in-tree compiler for our in-
|
||||
tree compiler; a different (per-OS) approach may be required upstream.
|
||||
|
||||
Reported by: mjg
|
||||
Approved by: re (rgrimes)
|
||||
MFC after: 1 week
|
||||
Relnotes: Yes
|
||||
Sponsored by: The FreeBSD Foundation
|
||||
|
||||
Index: tools/clang/lib/CodeGen/CodeGenModule.cpp
|
||||
===================================================================
|
||||
--- tools/clang/lib/CodeGen/CodeGenModule.cpp (revision 339018)
|
||||
+++ tools/clang/lib/CodeGen/CodeGenModule.cpp (revision 339019)
|
||||
@@ -321,8 +321,6 @@ void CodeGenModule::checkAliases() {
|
||||
assert(FTy);
|
||||
if (!FTy->getReturnType()->isPointerTy())
|
||||
Diags.Report(Location, diag::err_ifunc_resolver_return);
|
||||
- if (FTy->getNumParams())
|
||||
- Diags.Report(Location, diag::err_ifunc_resolver_params);
|
||||
}
|
||||
|
||||
llvm::Constant *Aliasee = Alias->getIndirectSymbol();
|
67
devel/llvm60/files/lld/patch-head-r331731.diff
Normal file
67
devel/llvm60/files/lld/patch-head-r331731.diff
Normal file
|
@ -0,0 +1,67 @@
|
|||
r331731 | dim | 2018-03-29 15:55:23 +0200 (Thu, 29 Mar 2018) | 22 lines
|
||||
|
||||
Pull in r328738 from upstream lld trunk (by Rafael Espindola):
|
||||
|
||||
Strip @VER suffices from the LTO output.
|
||||
|
||||
This fixes pr36623.
|
||||
|
||||
The problem is that we have to parse versions out of names before LTO
|
||||
so that LTO can use that information.
|
||||
|
||||
When we get the LTO produced .o files, we replace the previous symbols
|
||||
with the LTO produced ones, but they still have @ in their names.
|
||||
|
||||
We could just trim the name directly, but calling parseSymbolVersion
|
||||
to do it is simpler.
|
||||
|
||||
This is a follow-up to r331366, since we discovered that lld could
|
||||
append version strings to symbols twice, when using Link Time
|
||||
Optimization.
|
||||
|
||||
MFC after: 3 months
|
||||
X-MFC-With: r327952
|
||||
|
||||
Index: tools/lld/ELF/InputFiles.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/InputFiles.cpp (revision 331730)
|
||||
+++ tools/lld/ELF/InputFiles.cpp (revision 331731)
|
||||
@@ -281,6 +281,10 @@ template <class ELFT> ArrayRef<Symbol *> ObjFile<E
|
||||
return makeArrayRef(this->Symbols).slice(1, this->FirstNonLocal - 1);
|
||||
}
|
||||
|
||||
+template <class ELFT> ArrayRef<Symbol *> ObjFile<ELFT>::getGlobalSymbols() {
|
||||
+ return makeArrayRef(this->Symbols).slice(this->FirstNonLocal);
|
||||
+}
|
||||
+
|
||||
template <class ELFT>
|
||||
void ObjFile<ELFT>::parse(DenseSet<CachedHashStringRef> &ComdatGroups) {
|
||||
// Read section and symbol tables.
|
||||
Index: tools/lld/ELF/InputFiles.h
|
||||
===================================================================
|
||||
--- tools/lld/ELF/InputFiles.h (revision 331730)
|
||||
+++ tools/lld/ELF/InputFiles.h (revision 331731)
|
||||
@@ -167,6 +167,7 @@ template <class ELFT> class ObjFile : public ELFFi
|
||||
static bool classof(const InputFile *F) { return F->kind() == Base::ObjKind; }
|
||||
|
||||
ArrayRef<Symbol *> getLocalSymbols();
|
||||
+ ArrayRef<Symbol *> getGlobalSymbols();
|
||||
|
||||
ObjFile(MemoryBufferRef M, StringRef ArchiveName);
|
||||
void parse(llvm::DenseSet<llvm::CachedHashStringRef> &ComdatGroups);
|
||||
Index: tools/lld/ELF/SymbolTable.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/SymbolTable.cpp (revision 331730)
|
||||
+++ tools/lld/ELF/SymbolTable.cpp (revision 331731)
|
||||
@@ -130,7 +130,10 @@ template <class ELFT> void SymbolTable::addCombine
|
||||
|
||||
for (InputFile *File : LTO->compile()) {
|
||||
DenseSet<CachedHashStringRef> DummyGroups;
|
||||
- cast<ObjFile<ELFT>>(File)->parse(DummyGroups);
|
||||
+ auto *Obj = cast<ObjFile<ELFT>>(File);
|
||||
+ Obj->parse(DummyGroups);
|
||||
+ for (Symbol *Sym : Obj->getGlobalSymbols())
|
||||
+ Sym->parseSymbolVersion();
|
||||
ObjectFiles.push_back(File);
|
||||
}
|
||||
}
|
34
devel/llvm60/files/lld/patch-head-r333401.diff
Normal file
34
devel/llvm60/files/lld/patch-head-r333401.diff
Normal file
|
@ -0,0 +1,34 @@
|
|||
r333401 | emaste | 2018-05-09 13:17:01 +0200 (Wed, 09 May 2018) | 19 lines
|
||||
|
||||
lld: Omit PT_NOTE for SHT_NOTE without SHF_ALLOC
|
||||
|
||||
A non-alloc note section should not have a PT_NOTE program header.
|
||||
|
||||
Found while linking ghc (Haskell compiler) with lld on FreeBSD. Haskell
|
||||
emits a .debug-ghc-link-info note section (as the name suggests, it
|
||||
contains link info) as a SHT_NOTE section without SHF_ALLOC set.
|
||||
|
||||
For this case ld.bfd does not emit a PT_NOTE segment for
|
||||
.debug-ghc-link-info. lld previously emitted a PT_NOTE with p_vaddr = 0
|
||||
and FreeBSD's rtld segfaulted when trying to parse a note at address 0.
|
||||
|
||||
LLVM PR: https://llvm.org/pr37361
|
||||
LLVM review: https://reviews.llvm.org/D46623
|
||||
|
||||
PR: 226872
|
||||
Reviewed by: dim
|
||||
Sponsored by: The FreeBSD Foundation
|
||||
|
||||
Index: tools/lld/ELF/Writer.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Writer.cpp (revision 333400)
|
||||
+++ tools/lld/ELF/Writer.cpp (revision 333401)
|
||||
@@ -1708,7 +1708,7 @@ template <class ELFT> std::vector<PhdrEntry *> Wri
|
||||
// Create one PT_NOTE per a group of contiguous .note sections.
|
||||
PhdrEntry *Note = nullptr;
|
||||
for (OutputSection *Sec : OutputSections) {
|
||||
- if (Sec->Type == SHT_NOTE) {
|
||||
+ if (Sec->Type == SHT_NOTE && (Sec->Flags & SHF_ALLOC)) {
|
||||
if (!Note || Sec->LMAExpr)
|
||||
Note = AddHdr(PT_NOTE, PF_R);
|
||||
Note->add(Sec);
|
52
devel/llvm60/files/lld/patch-head-r336664.diff
Normal file
52
devel/llvm60/files/lld/patch-head-r336664.diff
Normal file
|
@ -0,0 +1,52 @@
|
|||
r336664 | emaste | 2018-07-24 13:35:22 +0200 (Tue, 24 Jul 2018) | 11 lines
|
||||
|
||||
lld: fix addends with partial linking
|
||||
|
||||
[ELF] Update addends in non-allocatable sections for REL targets when
|
||||
creating a relocatable output.
|
||||
|
||||
LLVM PR: 37735
|
||||
LLVM Differential Revision: https://reviews.llvm.org/D48929
|
||||
|
||||
PR: 225128
|
||||
Obtained from: LLVM r336799 by Igor Kudrin
|
||||
|
||||
Index: tools/lld/ELF/InputSection.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/InputSection.cpp (revision 336663)
|
||||
+++ tools/lld/ELF/InputSection.cpp (revision 336664)
|
||||
@@ -686,6 +686,23 @@ void InputSection::relocateNonAlloc(uint8_t *Buf,
|
||||
}
|
||||
}
|
||||
|
||||
+// This is used when '-r' is given.
|
||||
+// For REL targets, InputSection::copyRelocations() may store artificial
|
||||
+// relocations aimed to update addends. They are handled in relocateAlloc()
|
||||
+// for allocatable sections, and this function does the same for
|
||||
+// non-allocatable sections, such as sections with debug information.
|
||||
+static void relocateNonAllocForRelocatable(InputSection *Sec, uint8_t *Buf) {
|
||||
+ const unsigned Bits = Config->Is64 ? 64 : 32;
|
||||
+
|
||||
+ for (const Relocation &Rel : Sec->Relocations) {
|
||||
+ // InputSection::copyRelocations() adds only R_ABS relocations.
|
||||
+ assert(Rel.Expr == R_ABS);
|
||||
+ uint8_t *BufLoc = Buf + Rel.Offset + Sec->OutSecOff;
|
||||
+ uint64_t TargetVA = SignExtend64(Rel.Sym->getVA(Rel.Addend), Bits);
|
||||
+ Target->relocateOne(BufLoc, Rel.Type, TargetVA);
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
template <class ELFT>
|
||||
void InputSectionBase::relocate(uint8_t *Buf, uint8_t *BufEnd) {
|
||||
if (Flags & SHF_ALLOC) {
|
||||
@@ -694,7 +711,9 @@ void InputSectionBase::relocate(uint8_t *Buf, uint
|
||||
}
|
||||
|
||||
auto *Sec = cast<InputSection>(this);
|
||||
- if (Sec->AreRelocsRela)
|
||||
+ if (Config->Relocatable)
|
||||
+ relocateNonAllocForRelocatable(Sec, Buf);
|
||||
+ else if (Sec->AreRelocsRela)
|
||||
Sec->relocateNonAlloc<ELFT>(Buf, Sec->template relas<ELFT>());
|
||||
else
|
||||
Sec->relocateNonAlloc<ELFT>(Buf, Sec->template rels<ELFT>());
|
146
devel/llvm60/files/lld/patch-head-r336972.diff
Normal file
146
devel/llvm60/files/lld/patch-head-r336972.diff
Normal file
|
@ -0,0 +1,146 @@
|
|||
r336972 | emaste | 2018-07-31 17:25:03 +0200 (Tue, 31 Jul 2018) | 37 lines
|
||||
|
||||
lld: [ELF][ARM] Implement support for Tag_ABI_VFP_args
|
||||
|
||||
The Tag_ABI_VFP_args build attribute controls the procedure call
|
||||
standard used for floating point parameters on ARM. The values are:
|
||||
|
||||
0 - Base AAPCS (FP Parameters passed in Core (Integer) registers
|
||||
1 - VFP AAPCS (FP Parameters passed in FP registers)
|
||||
2 - Toolchain specific (Neither Base or VFP)
|
||||
3 - Compatible with all (No use of floating point parameters)
|
||||
|
||||
If the Tag_ABI_VFP_args build attribute is missing it has an implicit
|
||||
value of 0.
|
||||
|
||||
We use the attribute in two ways:
|
||||
|
||||
* Detect a clash in calling convention between Base, VFP and Toolchain.
|
||||
|
||||
we follow ld.bfd's lead and do not error if there is a clash between an
|
||||
implicit Base AAPCS caused by a missing attribute. Many projects
|
||||
including the hard-float (VFP AAPCS) version of glibc contain assembler
|
||||
files that do not use floating point but do not have Tag_ABI_VFP_args.
|
||||
|
||||
* Set the EF_ARM_ABI_FLOAT_SOFT or EF_ARM_ABI_FLOAT_HARD ELF header flag
|
||||
|
||||
for Base or VFP AAPCS respectively. This flag is used by some ELF
|
||||
loaders.
|
||||
|
||||
References:
|
||||
* Addenda to, and Errata in, the ABI for the ARM Architecture for
|
||||
Tag_ABI_VFP_args
|
||||
* Elf for the ARM Architecture for ELF header flags
|
||||
|
||||
Fixes LLVM PR36009
|
||||
|
||||
PR: 229050
|
||||
Obtained from: llvm r338377 by Peter Smith
|
||||
|
||||
Index: tools/lld/ELF/Arch/ARM.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Arch/ARM.cpp (revision 336971)
|
||||
+++ tools/lld/ELF/Arch/ARM.cpp (revision 336972)
|
||||
@@ -97,10 +97,19 @@ ARM::ARM() {
|
||||
}
|
||||
|
||||
uint32_t ARM::calcEFlags() const {
|
||||
+ // The ABIFloatType is used by loaders to detect the floating point calling
|
||||
+ // convention.
|
||||
+ uint32_t ABIFloatType = 0;
|
||||
+ if (Config->ARMVFPArgs == ARMVFPArgKind::Base ||
|
||||
+ Config->ARMVFPArgs == ARMVFPArgKind::Default)
|
||||
+ ABIFloatType = EF_ARM_ABI_FLOAT_SOFT;
|
||||
+ else if (Config->ARMVFPArgs == ARMVFPArgKind::VFP)
|
||||
+ ABIFloatType = EF_ARM_ABI_FLOAT_HARD;
|
||||
+
|
||||
// We don't currently use any features incompatible with EF_ARM_EABI_VER5,
|
||||
// but we don't have any firm guarantees of conformance. Linux AArch64
|
||||
// kernels (as of 2016) require an EABI version to be set.
|
||||
- return EF_ARM_EABI_VER5;
|
||||
+ return EF_ARM_EABI_VER5 | ABIFloatType;
|
||||
}
|
||||
|
||||
RelExpr ARM::getRelExpr(RelType Type, const Symbol &S,
|
||||
Index: tools/lld/ELF/Config.h
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Config.h (revision 336971)
|
||||
+++ tools/lld/ELF/Config.h (revision 336972)
|
||||
@@ -54,6 +54,9 @@ enum class SortSectionPolicy { Default, None, Alig
|
||||
// For --target2
|
||||
enum class Target2Policy { Abs, Rel, GotRel };
|
||||
|
||||
+// For tracking ARM Float Argument PCS
|
||||
+enum class ARMVFPArgKind { Default, Base, VFP, ToolChain };
|
||||
+
|
||||
struct SymbolVersion {
|
||||
llvm::StringRef Name;
|
||||
bool IsExternCpp;
|
||||
@@ -169,6 +172,7 @@ struct Configuration {
|
||||
StripPolicy Strip;
|
||||
UnresolvedPolicy UnresolvedSymbols;
|
||||
Target2Policy Target2;
|
||||
+ ARMVFPArgKind ARMVFPArgs = ARMVFPArgKind::Default;
|
||||
BuildIdKind BuildId = BuildIdKind::None;
|
||||
ELFKind EKind = ELFNoneKind;
|
||||
uint16_t DefaultSymbolVersion = llvm::ELF::VER_NDX_GLOBAL;
|
||||
Index: tools/lld/ELF/InputFiles.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/InputFiles.cpp (revision 336971)
|
||||
+++ tools/lld/ELF/InputFiles.cpp (revision 336972)
|
||||
@@ -441,6 +441,46 @@ void ObjFile<ELFT>::initializeSections(
|
||||
}
|
||||
}
|
||||
|
||||
+// For ARM only, to set the EF_ARM_ABI_FLOAT_SOFT or EF_ARM_ABI_FLOAT_HARD
|
||||
+// flag in the ELF Header we need to look at Tag_ABI_VFP_args to find out how
|
||||
+// the input objects have been compiled.
|
||||
+static void updateARMVFPArgs(const ARMAttributeParser &Attributes,
|
||||
+ const InputFile *F) {
|
||||
+ if (!Attributes.hasAttribute(ARMBuildAttrs::ABI_VFP_args))
|
||||
+ // If an ABI tag isn't present then it is implicitly given the value of 0
|
||||
+ // which maps to ARMBuildAttrs::BaseAAPCS. However many assembler files,
|
||||
+ // including some in glibc that don't use FP args (and should have value 3)
|
||||
+ // don't have the attribute so we do not consider an implicit value of 0
|
||||
+ // as a clash.
|
||||
+ return;
|
||||
+
|
||||
+ unsigned VFPArgs = Attributes.getAttributeValue(ARMBuildAttrs::ABI_VFP_args);
|
||||
+ ARMVFPArgKind Arg;
|
||||
+ switch (VFPArgs) {
|
||||
+ case ARMBuildAttrs::BaseAAPCS:
|
||||
+ Arg = ARMVFPArgKind::Base;
|
||||
+ break;
|
||||
+ case ARMBuildAttrs::HardFPAAPCS:
|
||||
+ Arg = ARMVFPArgKind::VFP;
|
||||
+ break;
|
||||
+ case ARMBuildAttrs::ToolChainFPPCS:
|
||||
+ // Tool chain specific convention that conforms to neither AAPCS variant.
|
||||
+ Arg = ARMVFPArgKind::ToolChain;
|
||||
+ break;
|
||||
+ case ARMBuildAttrs::CompatibleFPAAPCS:
|
||||
+ // Object compatible with all conventions.
|
||||
+ return;
|
||||
+ default:
|
||||
+ error(toString(F) + ": unknown Tag_ABI_VFP_args value: " + Twine(VFPArgs));
|
||||
+ return;
|
||||
+ }
|
||||
+ // Follow ld.bfd and error if there is a mix of calling conventions.
|
||||
+ if (Config->ARMVFPArgs != Arg && Config->ARMVFPArgs != ARMVFPArgKind::Default)
|
||||
+ error(toString(F) + ": incompatible Tag_ABI_VFP_args");
|
||||
+ else
|
||||
+ Config->ARMVFPArgs = Arg;
|
||||
+}
|
||||
+
|
||||
// The ARM support in lld makes some use of instructions that are not available
|
||||
// on all ARM architectures. Namely:
|
||||
// - Use of BLX instruction for interworking between ARM and Thumb state.
|
||||
@@ -520,6 +560,8 @@ InputSectionBase *ObjFile<ELFT>::createInputSectio
|
||||
ArrayRef<uint8_t> Contents = check(this->getObj().getSectionContents(&Sec));
|
||||
Attributes.Parse(Contents, /*isLittle*/ Config->EKind == ELF32LEKind);
|
||||
updateSupportedARMFeatures(Attributes);
|
||||
+ updateARMVFPArgs(Attributes, this);
|
||||
+
|
||||
// FIXME: Retain the first attribute section we see. The eglibc ARM
|
||||
// dynamic loaders require the presence of an attribute section for dlopen
|
||||
// to work. In a full implementation we would merge all attribute sections.
|
39
devel/llvm60/files/lld/patch-head-r337282.diff
Normal file
39
devel/llvm60/files/lld/patch-head-r337282.diff
Normal file
|
@ -0,0 +1,39 @@
|
|||
r337282 | alc | 2018-08-04 04:30:51 +0200 (Sat, 04 Aug 2018) | 7 lines
|
||||
|
||||
Set the default image base on arm64 and i386 to a superpage-aligned
|
||||
address.
|
||||
|
||||
Reviewed by: emaste, markj
|
||||
Discussed with: dim
|
||||
Differential Revision: https://reviews.freebsd.org/D16385
|
||||
|
||||
Index: tools/lld/ELF/Arch/AArch64.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Arch/AArch64.cpp (revision 337281)
|
||||
+++ tools/lld/ELF/Arch/AArch64.cpp (revision 337282)
|
||||
@@ -66,6 +66,10 @@ AArch64::AArch64() {
|
||||
PltHeaderSize = 32;
|
||||
DefaultMaxPageSize = 65536;
|
||||
|
||||
+ // Align to the 2 MiB page size (known as a superpage or huge page).
|
||||
+ // FreeBSD automatically promotes 2 MiB-aligned allocations.
|
||||
+ DefaultImageBase = 0x200000;
|
||||
+
|
||||
// It doesn't seem to be documented anywhere, but tls on aarch64 uses variant
|
||||
// 1 of the tls structures and the tcb size is 16.
|
||||
TcbSize = 16;
|
||||
Index: tools/lld/ELF/Arch/X86.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Arch/X86.cpp (revision 337281)
|
||||
+++ tools/lld/ELF/Arch/X86.cpp (revision 337282)
|
||||
@@ -61,6 +61,10 @@ X86::X86() {
|
||||
PltHeaderSize = 16;
|
||||
TlsGdRelaxSkip = 2;
|
||||
TrapInstr = 0xcccccccc; // 0xcc = INT3
|
||||
+
|
||||
+ // Align to the non-PAE large page size (known as a superpage or huge page).
|
||||
+ // FreeBSD automatically promotes large, superpage-aligned allocations.
|
||||
+ DefaultImageBase = 0x400000;
|
||||
}
|
||||
|
||||
static bool hasBaseReg(uint8_t ModRM) { return (ModRM & 0xc7) != 0x5; }
|
123
devel/llvm60/files/lld/patch-head-r338251.diff
Normal file
123
devel/llvm60/files/lld/patch-head-r338251.diff
Normal file
|
@ -0,0 +1,123 @@
|
|||
r338251 | markj | 2018-08-23 16:58:19 +0200 (Thu, 23 Aug 2018) | 29 lines
|
||||
|
||||
Add an lld option to emit PC-relative relocations for ifunc calls.
|
||||
|
||||
The current kernel ifunc implementation creates a PLT entry for each
|
||||
ifunc definition. ifunc calls therefore consist of a call to the
|
||||
PLT entry followed by an indirect jump. The jump target is written
|
||||
during boot when the kernel linker resolves R_[*]_IRELATIVE relocations.
|
||||
This implementation is defined by requirements for userland code, where
|
||||
text relocations are avoided. This requirement is not present for the
|
||||
kernel, so the implementation has avoidable overhead (namely, an extra
|
||||
indirect jump per call).
|
||||
|
||||
Address this for now by adding a special option to the static linker
|
||||
to inhibit PLT creation for ifuncs. Instead, relocations to ifunc call
|
||||
sites are passed through to the output file, so the kernel linker can
|
||||
enumerate such call sites and apply PC-relative relocations directly
|
||||
to the text section. Thus the overhead of an ifunc call becomes exactly
|
||||
the same as that of an ordinary function call. This option is only for
|
||||
use by the kernel and will not work for regular programs.
|
||||
|
||||
The final form of this optimization is up for debate; for now, this
|
||||
change is simple and static enough to be acceptable as an interim
|
||||
solution.
|
||||
|
||||
Reviewed by: emaste
|
||||
Discussed with: arichardson, dim
|
||||
MFC after: 1 month
|
||||
Sponsored by: The FreeBSD Foundation
|
||||
Differential Revision: https://reviews.freebsd.org/D16748
|
||||
|
||||
Index: tools/lld/ELF/Config.h
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Config.h (revision 338250)
|
||||
+++ tools/lld/ELF/Config.h (revision 338251)
|
||||
@@ -155,6 +155,7 @@ struct Configuration {
|
||||
bool ZCombreloc;
|
||||
bool ZExecstack;
|
||||
bool ZHazardplt;
|
||||
+ bool ZIfuncnoplt;
|
||||
bool ZNocopyreloc;
|
||||
bool ZNodelete;
|
||||
bool ZNodlopen;
|
||||
Index: tools/lld/ELF/Driver.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Driver.cpp (revision 338250)
|
||||
+++ tools/lld/ELF/Driver.cpp (revision 338251)
|
||||
@@ -669,6 +669,7 @@ void LinkerDriver::readConfigs(opt::InputArgList &
|
||||
Config->ZCombreloc = !hasZOption(Args, "nocombreloc");
|
||||
Config->ZExecstack = hasZOption(Args, "execstack");
|
||||
Config->ZHazardplt = hasZOption(Args, "hazardplt");
|
||||
+ Config->ZIfuncnoplt = hasZOption(Args, "ifunc-noplt");
|
||||
Config->ZNocopyreloc = hasZOption(Args, "nocopyreloc");
|
||||
Config->ZNodelete = hasZOption(Args, "nodelete");
|
||||
Config->ZNodlopen = hasZOption(Args, "nodlopen");
|
||||
Index: tools/lld/ELF/Relocations.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Relocations.cpp (revision 338250)
|
||||
+++ tools/lld/ELF/Relocations.cpp (revision 338251)
|
||||
@@ -374,6 +374,9 @@ static bool isStaticLinkTimeConstant(RelExpr E, Re
|
||||
R_PPC_PLT_OPD, R_TLSDESC_CALL, R_TLSDESC_PAGE, R_HINT>(E))
|
||||
return true;
|
||||
|
||||
+ if (Sym.isGnuIFunc() && Config->ZIfuncnoplt)
|
||||
+ return false;
|
||||
+
|
||||
// These never do, except if the entire file is position dependent or if
|
||||
// only the low bits are used.
|
||||
if (E == R_GOT || E == R_PLT || E == R_TLSDESC)
|
||||
@@ -921,7 +924,9 @@ static void scanRelocs(InputSectionBase &Sec, Arra
|
||||
// Strenghten or relax a PLT access.
|
||||
//
|
||||
// GNU ifunc symbols must be accessed via PLT because their addresses
|
||||
- // are determined by runtime.
|
||||
+ // are determined by runtime. If the -z ifunc-noplt option is specified,
|
||||
+ // we permit the optimization of ifunc calls by omitting the PLT entry
|
||||
+ // and preserving relocations at ifunc call sites.
|
||||
//
|
||||
// On the other hand, if we know that a PLT entry will be resolved within
|
||||
// the same ELF module, we can skip PLT access and directly jump to the
|
||||
@@ -929,7 +934,7 @@ static void scanRelocs(InputSectionBase &Sec, Arra
|
||||
// all dynamic symbols that can be resolved within the executable will
|
||||
// actually be resolved that way at runtime, because the main exectuable
|
||||
// is always at the beginning of a search list. We can leverage that fact.
|
||||
- if (Sym.isGnuIFunc())
|
||||
+ if (Sym.isGnuIFunc() && !Config->ZIfuncnoplt)
|
||||
Expr = toPlt(Expr);
|
||||
else if (!Preemptible && Expr == R_GOT_PC && !isAbsoluteValue(Sym))
|
||||
Expr =
|
||||
@@ -1034,6 +1039,16 @@ static void scanRelocs(InputSectionBase &Sec, Arra
|
||||
continue;
|
||||
}
|
||||
|
||||
+ // Preserve relocations against ifuncs if we were asked to do so.
|
||||
+ if (Sym.isGnuIFunc() && Config->ZIfuncnoplt) {
|
||||
+ if (Config->IsRela)
|
||||
+ InX::RelaDyn->addReloc({Type, &Sec, Offset, false, &Sym, Addend});
|
||||
+ else
|
||||
+ // Preserve the existing addend.
|
||||
+ InX::RelaDyn->addReloc({Type, &Sec, Offset, false, &Sym, 0});
|
||||
+ continue;
|
||||
+ }
|
||||
+
|
||||
// If the output being produced is position independent, the final value
|
||||
// is still not known. In that case we still need some help from the
|
||||
// dynamic linker. We can however do better than just copying the incoming
|
||||
Index: tools/lld/ELF/Writer.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Writer.cpp (revision 338250)
|
||||
+++ tools/lld/ELF/Writer.cpp (revision 338251)
|
||||
@@ -1400,8 +1400,11 @@ template <class ELFT> void Writer<ELFT>::finalizeS
|
||||
applySynthetic({InX::EhFrame},
|
||||
[](SyntheticSection *SS) { SS->finalizeContents(); });
|
||||
|
||||
- for (Symbol *S : Symtab->getSymbols())
|
||||
+ for (Symbol *S : Symtab->getSymbols()) {
|
||||
S->IsPreemptible |= computeIsPreemptible(*S);
|
||||
+ if (S->isGnuIFunc() && Config->ZIfuncnoplt)
|
||||
+ S->ExportDynamic = true;
|
||||
+ }
|
||||
|
||||
// Scan relocations. This must be done after every symbol is declared so that
|
||||
// we can correctly decide if a dynamic relocation is needed.
|
55
devel/llvm60/files/lld/patch-head-r338682.diff
Normal file
55
devel/llvm60/files/lld/patch-head-r338682.diff
Normal file
|
@ -0,0 +1,55 @@
|
|||
r338682 | emaste | 2018-09-14 17:15:16 +0200 (Fri, 14 Sep 2018) | 16 lines
|
||||
|
||||
lld: add -z interpose support
|
||||
|
||||
-z interpose sets the DF_1_INTERPOSE flag, marking the object as an
|
||||
interposer.
|
||||
|
||||
Committed upstream as LLVM r342239.
|
||||
|
||||
PR: 230604
|
||||
Reported by: jbeich
|
||||
Reviewed by: markj
|
||||
Approved by: re (kib)
|
||||
MFC after: 1 week
|
||||
Relnotes: Yes
|
||||
Sponsored by: The FreeBSD Foundation
|
||||
Differential Revision: https://reviews.freebsd.org/D17172
|
||||
|
||||
Index: tools/lld/ELF/Config.h
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Config.h (revision 338681)
|
||||
+++ tools/lld/ELF/Config.h (revision 338682)
|
||||
@@ -156,6 +156,7 @@ struct Configuration {
|
||||
bool ZExecstack;
|
||||
bool ZHazardplt;
|
||||
bool ZIfuncnoplt;
|
||||
+ bool ZInterpose;
|
||||
bool ZNocopyreloc;
|
||||
bool ZNodelete;
|
||||
bool ZNodlopen;
|
||||
Index: tools/lld/ELF/Driver.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Driver.cpp (revision 338681)
|
||||
+++ tools/lld/ELF/Driver.cpp (revision 338682)
|
||||
@@ -670,6 +670,7 @@ void LinkerDriver::readConfigs(opt::InputArgList &
|
||||
Config->ZExecstack = hasZOption(Args, "execstack");
|
||||
Config->ZHazardplt = hasZOption(Args, "hazardplt");
|
||||
Config->ZIfuncnoplt = hasZOption(Args, "ifunc-noplt");
|
||||
+ Config->ZInterpose = hasZOption(Args, "interpose");
|
||||
Config->ZNocopyreloc = hasZOption(Args, "nocopyreloc");
|
||||
Config->ZNodelete = hasZOption(Args, "nodelete");
|
||||
Config->ZNodlopen = hasZOption(Args, "nodlopen");
|
||||
Index: tools/lld/ELF/SyntheticSections.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/SyntheticSections.cpp (revision 338681)
|
||||
+++ tools/lld/ELF/SyntheticSections.cpp (revision 338682)
|
||||
@@ -1034,6 +1034,8 @@ template <class ELFT> void DynamicSection<ELFT>::f
|
||||
uint32_t DtFlags1 = 0;
|
||||
if (Config->Bsymbolic)
|
||||
DtFlags |= DF_SYMBOLIC;
|
||||
+ if (Config->ZInterpose)
|
||||
+ DtFlags1 |= DF_1_INTERPOSE;
|
||||
if (Config->ZNodelete)
|
||||
DtFlags1 |= DF_1_NODELETE;
|
||||
if (Config->ZNodlopen)
|
39
devel/llvm60/files/lld/patch-head-r339013.diff
Normal file
39
devel/llvm60/files/lld/patch-head-r339013.diff
Normal file
|
@ -0,0 +1,39 @@
|
|||
r339013 | dim | 2018-09-29 16:12:03 +0200 (Sat, 29 Sep 2018) | 24 lines
|
||||
|
||||
Pull in r329557 from upstream lld trunk (by George Rimar):
|
||||
|
||||
[ELF] - Allow LLD to produce file symbols.
|
||||
|
||||
This is for PR36716 and
|
||||
this enables emitting STT_FILE symbols.
|
||||
|
||||
Output size affect is minor:
|
||||
lld binary size changes from 52,883,408 to 52,949,400
|
||||
clang binary size changes from 83,136,456 to 83,219,600
|
||||
|
||||
Differential revision: https://reviews.llvm.org/D45261
|
||||
|
||||
This fixes a regression in lld that made it stop emitting STT_FILE
|
||||
symbols, which ctfmerge relies upon to uniquify function table entries
|
||||
that reference STB_LOCAL symbols. Consequently, ctfmerge stopped
|
||||
emitting entries for static functions into the function table, and
|
||||
dtrace no longer gets type info for them.
|
||||
|
||||
Approved by: re (kib)
|
||||
Reported by: markj
|
||||
PR: 230444
|
||||
MFC after: 3 days
|
||||
|
||||
Index: tools/lld/ELF/Writer.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/Writer.cpp (revision 339012)
|
||||
+++ tools/lld/ELF/Writer.cpp (revision 339013)
|
||||
@@ -487,7 +487,7 @@ template <class ELFT> void Writer<ELFT>::run() {
|
||||
|
||||
static bool shouldKeepInSymtab(SectionBase *Sec, StringRef SymName,
|
||||
const Symbol &B) {
|
||||
- if (B.isFile() || B.isSection())
|
||||
+ if (B.isSection())
|
||||
return false;
|
||||
|
||||
// If sym references a section in a discarded group, don't keep it.
|
37
devel/llvm60/files/lld/patch-head-r339304.diff
Normal file
37
devel/llvm60/files/lld/patch-head-r339304.diff
Normal file
|
@ -0,0 +1,37 @@
|
|||
r339304 | emaste | 2018-10-11 15:19:17 +0200 (Thu, 11 Oct 2018) | 13 lines
|
||||
|
||||
lld: set sh_link and sh_info for .rela.plt sections
|
||||
|
||||
ELF spec says that for SHT_REL and SHT_RELA sh_link should reference the
|
||||
associated string table and sh_info should reference the "section to
|
||||
which the relocation applies." ELF Tool Chain's elfcopy / strip use
|
||||
this (in part) to control whether or not the relocation entry is copied
|
||||
to the output.
|
||||
|
||||
LLVM PR 37538 https://bugs.llvm.org/show_bug.cgi?id=37538
|
||||
|
||||
Approved by: re (kib)
|
||||
Obtained from: llvm r344226 (backported for 6.0)
|
||||
|
||||
Index: tools/lld/ELF/SyntheticSections.cpp
|
||||
===================================================================
|
||||
--- tools/lld/ELF/SyntheticSections.cpp (revision 339303)
|
||||
+++ tools/lld/ELF/SyntheticSections.cpp (revision 339304)
|
||||
@@ -1213,11 +1213,13 @@ void RelocationBaseSection::addReloc(const Dynamic
|
||||
void RelocationBaseSection::finalizeContents() {
|
||||
// If all relocations are R_*_RELATIVE they don't refer to any
|
||||
// dynamic symbol and we don't need a dynamic symbol table. If that
|
||||
- // is the case, just use 0 as the link.
|
||||
- Link = InX::DynSymTab ? InX::DynSymTab->getParent()->SectionIndex : 0;
|
||||
+ // is the case, just use the index of the regular symbol table section.
|
||||
+ getParent()->Link = InX::DynSymTab ?
|
||||
+ InX::DynSymTab->getParent()->SectionIndex :
|
||||
+ InX::SymTab->getParent()->SectionIndex;
|
||||
|
||||
- // Set required output section properties.
|
||||
- getParent()->Link = Link;
|
||||
+ if (InX::RelaIplt == this || InX::RelaPlt == this)
|
||||
+ getParent()->Info = InX::GotPlt->getParent()->SectionIndex;
|
||||
}
|
||||
|
||||
template <class ELFT>
|
38
devel/llvm60/files/lldb/patch-head-r332849.diff
Normal file
38
devel/llvm60/files/lldb/patch-head-r332849.diff
Normal file
|
@ -0,0 +1,38 @@
|
|||
r332849 | emaste | 2018-04-21 02:34:46 +0200 (Sat, 21 Apr 2018) | 20 lines
|
||||
|
||||
lldb: propagate error to user if memory read fails
|
||||
|
||||
Previously, an attempt to read an unreadable access reported zeros:
|
||||
|
||||
(lldb) memory read -format hex -size 8 0
|
||||
0x00000000: 0x0000000000000000 0x0000000000000000
|
||||
0x00000010: 0x0000000000000000 0x0000000000000000
|
||||
...
|
||||
|
||||
Now, if DoReadMemory encounters error then return 0 (bytes read) so we
|
||||
report the error to the user:
|
||||
|
||||
(lldb) memory read -format hex -size 8 0
|
||||
error: Bad address
|
||||
|
||||
LLVM PR: 37190
|
||||
|
||||
MFC after: 1 week
|
||||
Sponsored by: The FreeBSD Foundation
|
||||
|
||||
Index: tools/lldb/source/Plugins/Process/FreeBSD/ProcessMonitor.cpp
|
||||
===================================================================
|
||||
--- tools/lldb/source/Plugins/Process/FreeBSD/ProcessMonitor.cpp (revision 332848)
|
||||
+++ tools/lldb/source/Plugins/Process/FreeBSD/ProcessMonitor.cpp (revision 332849)
|
||||
@@ -163,8 +163,10 @@ static size_t DoReadMemory(lldb::pid_t pid, lldb::
|
||||
pi_desc.piod_addr = buf;
|
||||
pi_desc.piod_len = size;
|
||||
|
||||
- if (PTRACE(PT_IO, pid, (caddr_t)&pi_desc, 0) < 0)
|
||||
+ if (PTRACE(PT_IO, pid, (caddr_t)&pi_desc, 0) < 0) {
|
||||
error.SetErrorToErrno();
|
||||
+ return 0;
|
||||
+ }
|
||||
return pi_desc.piod_len;
|
||||
}
|
||||
|
22
devel/llvm60/files/lldb/patch-head-r332965.diff
Normal file
22
devel/llvm60/files/lldb/patch-head-r332965.diff
Normal file
|
@ -0,0 +1,22 @@
|
|||
r332965 | emaste | 2018-04-24 21:26:58 +0200 (Tue, 24 Apr 2018) | 8 lines
|
||||
|
||||
lldb: remove assertion that target_arch is FreeBSD
|
||||
|
||||
The target is not necessarily a FreeBSD binary - for example, it may be
|
||||
a Linux binary running under the linuxulator. Basic ptrace (live)
|
||||
debugging already worked in this case, except for the assertion.
|
||||
|
||||
Sponsored by: Turing Robotic Industries Inc.
|
||||
|
||||
Index: tools/lldb/source/Plugins/Process/FreeBSD/FreeBSDThread.cpp
|
||||
===================================================================
|
||||
--- tools/lldb/source/Plugins/Process/FreeBSD/FreeBSDThread.cpp (revision 332964)
|
||||
+++ tools/lldb/source/Plugins/Process/FreeBSD/FreeBSDThread.cpp (revision 332965)
|
||||
@@ -169,7 +169,6 @@ lldb::RegisterContextSP FreeBSDThread::GetRegister
|
||||
RegisterInfoInterface *reg_interface = NULL;
|
||||
const ArchSpec &target_arch = GetProcess()->GetTarget().GetArchitecture();
|
||||
|
||||
- assert(target_arch.GetTriple().getOS() == llvm::Triple::FreeBSD);
|
||||
switch (target_arch.GetMachine()) {
|
||||
case llvm::Triple::aarch64:
|
||||
reg_interface = new RegisterInfoPOSIX_arm64(target_arch);
|
33
devel/llvm60/files/patch-head-r308867.diff
Normal file
33
devel/llvm60/files/patch-head-r308867.diff
Normal file
|
@ -0,0 +1,33 @@
|
|||
r308867 | dim | 2016-11-19 22:05:17 +0100 (Sat, 19 Nov 2016) | 15 lines
|
||||
|
||||
Work around LLVM PR30879, which is about a bad interaction between X86
|
||||
Call Frame Optimization on i386 and libunwind, by disallowing the
|
||||
optimization for i386-freebsd12.
|
||||
|
||||
This should fix some instances of broken exception handling when frame
|
||||
pointers are omitted, in particular some unittests run during the build
|
||||
of editors/libreoffice.
|
||||
|
||||
This hack will be removed as soon as upstream has implemented a more
|
||||
permanent fix for this problem.
|
||||
|
||||
Upstream PR: https://llvm.org/bugs/show_bug.cgi?id=30879
|
||||
Reviewed by: emaste
|
||||
PR: 212343
|
||||
|
||||
Index: lib/Target/X86/X86CallFrameOptimization.cpp
|
||||
===================================================================
|
||||
--- lib/Target/X86/X86CallFrameOptimization.cpp (revision 308866)
|
||||
+++ lib/Target/X86/X86CallFrameOptimization.cpp (revision 308867)
|
||||
@@ -125,6 +125,11 @@ bool X86CallFrameOptimization::isLegal(MachineFunc
|
||||
if (NoX86CFOpt.getValue())
|
||||
return false;
|
||||
|
||||
+ // Work around LLVM PR30879 (bad interaction between CFO and libunwind)
|
||||
+ if (STI->isTargetFreeBSD() && STI->is32Bit() &&
|
||||
+ STI->getTargetTriple().getOSMajorVersion() >= 12)
|
||||
+ return false;
|
||||
+
|
||||
// We can't encode multiple DW_CFA_GNU_args_size or DW_CFA_def_cfa_offset
|
||||
// in the compact unwind encoding that Darwin uses. So, bail if there
|
||||
// is a danger of that being generated.
|
80
devel/llvm60/files/patch-head-r330686.diff
Normal file
80
devel/llvm60/files/patch-head-r330686.diff
Normal file
|
@ -0,0 +1,80 @@
|
|||
r330686 | dim | 2018-03-09 10:21:22 +0100 (Fri, 09 Mar 2018) | 20 lines
|
||||
|
||||
Pull in r326882 from upstream llvm trunk (by Sjoerd Meijer):
|
||||
|
||||
[ARM] Fix for PR36577
|
||||
|
||||
Don't PerformSHLSimplify if the given node is used by a node that
|
||||
also uses a constant because we may get stuck in an infinite combine
|
||||
loop.
|
||||
|
||||
bugzilla: https://bugs.llvm.org/show_bug.cgi?id=36577
|
||||
|
||||
Patch by Sam Parker.
|
||||
|
||||
Differential Revision: https://reviews.llvm.org/D44097
|
||||
|
||||
This fixes a hang when compiling one particular file in java/openjdk8
|
||||
for armv6 and armv7.
|
||||
|
||||
Reported by: swills
|
||||
PR: 226388
|
||||
|
||||
Index: lib/Target/ARM/ARMISelLowering.cpp
|
||||
===================================================================
|
||||
--- lib/Target/ARM/ARMISelLowering.cpp (revision 330685)
|
||||
+++ lib/Target/ARM/ARMISelLowering.cpp (revision 330686)
|
||||
@@ -10201,7 +10201,14 @@ static SDValue PerformSHLSimplify(SDNode *N,
|
||||
case ISD::XOR:
|
||||
case ISD::SETCC:
|
||||
case ARMISD::CMP:
|
||||
- // Check that its not already using a shl.
|
||||
+ // Check that the user isn't already using a constant because there
|
||||
+ // aren't any instructions that support an immediate operand and a
|
||||
+ // shifted operand.
|
||||
+ if (isa<ConstantSDNode>(U->getOperand(0)) ||
|
||||
+ isa<ConstantSDNode>(U->getOperand(1)))
|
||||
+ return SDValue();
|
||||
+
|
||||
+ // Check that it's not already using a shift.
|
||||
if (U->getOperand(0).getOpcode() == ISD::SHL ||
|
||||
U->getOperand(1).getOpcode() == ISD::SHL)
|
||||
return SDValue();
|
||||
@@ -10223,8 +10230,6 @@ static SDValue PerformSHLSimplify(SDNode *N,
|
||||
if (!C1ShlC2 || !C2)
|
||||
return SDValue();
|
||||
|
||||
- DEBUG(dbgs() << "Trying to simplify shl: "; N->dump());
|
||||
-
|
||||
APInt C2Int = C2->getAPIntValue();
|
||||
APInt C1Int = C1ShlC2->getAPIntValue();
|
||||
|
||||
@@ -10238,12 +10243,12 @@ static SDValue PerformSHLSimplify(SDNode *N,
|
||||
C1Int.lshrInPlace(C2Int);
|
||||
|
||||
// The immediates are encoded as an 8-bit value that can be rotated.
|
||||
- unsigned Zeros = C1Int.countLeadingZeros() + C1Int.countTrailingZeros();
|
||||
- if (C1Int.getBitWidth() - Zeros > 8)
|
||||
- return SDValue();
|
||||
+ auto LargeImm = [](const APInt &Imm) {
|
||||
+ unsigned Zeros = Imm.countLeadingZeros() + Imm.countTrailingZeros();
|
||||
+ return Imm.getBitWidth() - Zeros > 8;
|
||||
+ };
|
||||
|
||||
- Zeros = C2Int.countLeadingZeros() + C2Int.countTrailingZeros();
|
||||
- if (C2Int.getBitWidth() - Zeros > 8)
|
||||
+ if (LargeImm(C1Int) || LargeImm(C2Int))
|
||||
return SDValue();
|
||||
|
||||
SelectionDAG &DAG = DCI.DAG;
|
||||
@@ -10254,6 +10259,10 @@ static SDValue PerformSHLSimplify(SDNode *N,
|
||||
// Shift left to compensate for the lshr of C1Int.
|
||||
SDValue Res = DAG.getNode(ISD::SHL, dl, MVT::i32, BinOp, SHL.getOperand(1));
|
||||
|
||||
+ DEBUG(dbgs() << "Simplify shl use:\n"; SHL.getOperand(0).dump(); SHL.dump();
|
||||
+ N->dump());
|
||||
+ DEBUG(dbgs() << "Into:\n"; X.dump(); BinOp.dump(); Res.dump());
|
||||
+
|
||||
DAG.ReplaceAllUsesWith(SDValue(N, 0), Res);
|
||||
return SDValue(N, 0);
|
||||
}
|
88
devel/llvm60/files/patch-head-r331065.diff
Normal file
88
devel/llvm60/files/patch-head-r331065.diff
Normal file
|
@ -0,0 +1,88 @@
|
|||
r331065 | dim | 2018-03-16 18:50:44 +0100 (Fri, 16 Mar 2018) | 17 lines
|
||||
|
||||
Pull in r327638 from upstream llvm trunk (by Matthew Simpson):
|
||||
|
||||
[ConstantFolding, InstSimplify] Handle more vector GEPs
|
||||
|
||||
This patch addresses some additional cases where the compiler crashes
|
||||
upon encountering vector GEPs. This should fix PR36116.
|
||||
|
||||
Differential Revision: https://reviews.llvm.org/D44219
|
||||
Reference: https://bugs.llvm.org/show_bug.cgi?id=36116
|
||||
|
||||
This fixes an assertion when building the emulators/snes9x port.
|
||||
|
||||
Reported by: jbeich
|
||||
PR: 225471
|
||||
MFC after: 3 months
|
||||
X-MFC-With: r327952
|
||||
|
||||
Index: lib/Analysis/InstructionSimplify.cpp
|
||||
===================================================================
|
||||
--- lib/Analysis/InstructionSimplify.cpp (revision 331064)
|
||||
+++ lib/Analysis/InstructionSimplify.cpp (revision 331065)
|
||||
@@ -3697,7 +3697,7 @@ static Value *SimplifyGEPInst(Type *SrcTy, ArrayRe
|
||||
|
||||
if (Ops.size() == 2) {
|
||||
// getelementptr P, 0 -> P.
|
||||
- if (match(Ops[1], m_Zero()))
|
||||
+ if (match(Ops[1], m_Zero()) && Ops[0]->getType() == GEPTy)
|
||||
return Ops[0];
|
||||
|
||||
Type *Ty = SrcTy;
|
||||
@@ -3706,7 +3706,7 @@ static Value *SimplifyGEPInst(Type *SrcTy, ArrayRe
|
||||
uint64_t C;
|
||||
uint64_t TyAllocSize = Q.DL.getTypeAllocSize(Ty);
|
||||
// getelementptr P, N -> P if P points to a type of zero size.
|
||||
- if (TyAllocSize == 0)
|
||||
+ if (TyAllocSize == 0 && Ops[0]->getType() == GEPTy)
|
||||
return Ops[0];
|
||||
|
||||
// The following transforms are only safe if the ptrtoint cast
|
||||
Index: lib/IR/ConstantFold.cpp
|
||||
===================================================================
|
||||
--- lib/IR/ConstantFold.cpp (revision 331064)
|
||||
+++ lib/IR/ConstantFold.cpp (revision 331065)
|
||||
@@ -2018,8 +2018,16 @@ static bool isInBoundsIndices(ArrayRef<IndexTy> Id
|
||||
|
||||
// If the first index is one and all the rest are zero, it's in bounds,
|
||||
// by the one-past-the-end rule.
|
||||
- if (!cast<ConstantInt>(Idxs[0])->isOne())
|
||||
- return false;
|
||||
+ if (auto *CI = dyn_cast<ConstantInt>(Idxs[0])) {
|
||||
+ if (!CI->isOne())
|
||||
+ return false;
|
||||
+ } else {
|
||||
+ auto *CV = cast<ConstantDataVector>(Idxs[0]);
|
||||
+ CI = dyn_cast_or_null<ConstantInt>(CV->getSplatValue());
|
||||
+ if (!CI || !CI->isOne())
|
||||
+ return false;
|
||||
+ }
|
||||
+
|
||||
for (unsigned i = 1, e = Idxs.size(); i != e; ++i)
|
||||
if (!cast<Constant>(Idxs[i])->isNullValue())
|
||||
return false;
|
||||
@@ -2049,15 +2057,18 @@ Constant *llvm::ConstantFoldGetElementPtr(Type *Po
|
||||
ArrayRef<Value *> Idxs) {
|
||||
if (Idxs.empty()) return C;
|
||||
|
||||
- if (isa<UndefValue>(C)) {
|
||||
- Type *GEPTy = GetElementPtrInst::getGEPReturnType(
|
||||
- C, makeArrayRef((Value * const *)Idxs.data(), Idxs.size()));
|
||||
+ Type *GEPTy = GetElementPtrInst::getGEPReturnType(
|
||||
+ C, makeArrayRef((Value *const *)Idxs.data(), Idxs.size()));
|
||||
+
|
||||
+ if (isa<UndefValue>(C))
|
||||
return UndefValue::get(GEPTy);
|
||||
- }
|
||||
|
||||
Constant *Idx0 = cast<Constant>(Idxs[0]);
|
||||
if (Idxs.size() == 1 && (Idx0->isNullValue() || isa<UndefValue>(Idx0)))
|
||||
- return C;
|
||||
+ return GEPTy->isVectorTy() && !C->getType()->isVectorTy()
|
||||
+ ? ConstantVector::getSplat(
|
||||
+ cast<VectorType>(GEPTy)->getNumElements(), C)
|
||||
+ : C;
|
||||
|
||||
if (C->isNullValue()) {
|
||||
bool isNull = true;
|
609
devel/llvm60/files/patch-head-r331366.diff
Normal file
609
devel/llvm60/files/patch-head-r331366.diff
Normal file
|
@ -0,0 +1,609 @@
|
|||
r331366 | dim | 2018-03-22 19:58:34 +0100 (Thu, 22 Mar 2018) | 61 lines
|
||||
|
||||
Pull in r327101 from upstream llvm trunk (by Rafael Espindola):
|
||||
|
||||
Don't treat .symver as a regular alias definition.
|
||||
|
||||
This patch starts simplifying the handling of .symver.
|
||||
|
||||
For now it just moves the responsibility for creating an alias down to
|
||||
the streamer. With that the asm streamer can pass a .symver unchanged,
|
||||
which is nice since gas cannot parse "foo@bar = zed".
|
||||
|
||||
In a followup I hope to move the handling down to the writer so that
|
||||
we don't need special hacks for avoiding breaking names with @@@ on
|
||||
windows.
|
||||
|
||||
Pull in r327160 from upstream llvm trunk (by Rafael Espindola):
|
||||
|
||||
Delay creating an alias for @@@.
|
||||
|
||||
With this we only create an alias for @@@ once we know if it should
|
||||
use @ or @@. This avoids last minutes renames and hacks to handle MS
|
||||
names.
|
||||
|
||||
This only handles the ELF writer. LTO still has issues with @@@
|
||||
aliases.
|
||||
|
||||
Pull in r327928 from upstream llvm trunk (by Vitaly Buka):
|
||||
|
||||
Object: Move attribute calculation into RecordStreamer. NFC
|
||||
|
||||
Summary: Preparation for D44274
|
||||
|
||||
Reviewers: pcc, espindola
|
||||
|
||||
Subscribers: hiraditya
|
||||
|
||||
Differential Revision: https://reviews.llvm.org/D44276
|
||||
|
||||
Pull in r327930 from upstream llvm trunk (by Vitaly Buka):
|
||||
|
||||
Object: Fix handling of @@@ in .symver directive
|
||||
|
||||
Summary:
|
||||
name@@@nodename is going to be replaced with name@@nodename if symbols is
|
||||
defined in the assembled file, or name@nodename if undefined.
|
||||
https://sourceware.org/binutils/docs/as/Symver.html
|
||||
|
||||
Fixes PR36623
|
||||
|
||||
Reviewers: pcc, espindola
|
||||
|
||||
Subscribers: mehdi_amini, hiraditya
|
||||
|
||||
Differential Revision: https://reviews.llvm.org/D44274
|
||||
|
||||
Together, these changes fix handling of @@@ in .symver directives when
|
||||
doing Link Time Optimization.
|
||||
|
||||
Reported by: Shawn Webb <shawn.webb@hardenedbsd.org>
|
||||
MFC after: 3 months
|
||||
X-MFC-With: r327952
|
||||
|
||||
Index: include/llvm/MC/MCAssembler.h
|
||||
===================================================================
|
||||
--- include/llvm/MC/MCAssembler.h (revision 331365)
|
||||
+++ include/llvm/MC/MCAssembler.h (revision 331366)
|
||||
@@ -206,6 +206,8 @@ class MCAssembler {
|
||||
handleFixup(const MCAsmLayout &Layout, MCFragment &F, const MCFixup &Fixup);
|
||||
|
||||
public:
|
||||
+ std::vector<std::pair<StringRef, const MCSymbol *>> Symvers;
|
||||
+
|
||||
/// Construct a new assembler instance.
|
||||
//
|
||||
// FIXME: How are we going to parameterize this? Two obvious options are stay
|
||||
Index: include/llvm/MC/MCELFStreamer.h
|
||||
===================================================================
|
||||
--- include/llvm/MC/MCELFStreamer.h (revision 331365)
|
||||
+++ include/llvm/MC/MCELFStreamer.h (revision 331366)
|
||||
@@ -51,6 +51,8 @@ class MCELFStreamer : public MCObjectStreamer {
|
||||
unsigned ByteAlignment) override;
|
||||
|
||||
void emitELFSize(MCSymbol *Symbol, const MCExpr *Value) override;
|
||||
+ void emitELFSymverDirective(StringRef AliasName,
|
||||
+ const MCSymbol *Aliasee) override;
|
||||
|
||||
void EmitLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
|
||||
unsigned ByteAlignment) override;
|
||||
Index: include/llvm/MC/MCStreamer.h
|
||||
===================================================================
|
||||
--- include/llvm/MC/MCStreamer.h (revision 331365)
|
||||
+++ include/llvm/MC/MCStreamer.h (revision 331366)
|
||||
@@ -519,9 +519,10 @@ class MCStreamer {
|
||||
///
|
||||
/// This corresponds to an assembler statement such as:
|
||||
/// .symver _start, foo@@SOME_VERSION
|
||||
- /// \param Alias - The versioned alias (i.e. "foo@@SOME_VERSION")
|
||||
+ /// \param AliasName - The versioned alias (i.e. "foo@@SOME_VERSION")
|
||||
/// \param Aliasee - The aliased symbol (i.e. "_start")
|
||||
- virtual void emitELFSymverDirective(MCSymbol *Alias, const MCSymbol *Aliasee);
|
||||
+ virtual void emitELFSymverDirective(StringRef AliasName,
|
||||
+ const MCSymbol *Aliasee);
|
||||
|
||||
/// \brief Emit a Linker Optimization Hint (LOH) directive.
|
||||
/// \param Args - Arguments of the LOH.
|
||||
Index: lib/MC/ELFObjectWriter.cpp
|
||||
===================================================================
|
||||
--- lib/MC/ELFObjectWriter.cpp (revision 331365)
|
||||
+++ lib/MC/ELFObjectWriter.cpp (revision 331366)
|
||||
@@ -128,8 +128,6 @@ class ELFObjectWriter : public MCObjectWriter {
|
||||
/// @name Symbol Table Data
|
||||
/// @{
|
||||
|
||||
- BumpPtrAllocator Alloc;
|
||||
- StringSaver VersionSymSaver{Alloc};
|
||||
StringTableBuilder StrTabBuilder{StringTableBuilder::ELF};
|
||||
|
||||
/// @}
|
||||
@@ -391,27 +389,29 @@ void ELFObjectWriter::executePostLayoutBinding(MCA
|
||||
const MCAsmLayout &Layout) {
|
||||
// The presence of symbol versions causes undefined symbols and
|
||||
// versions declared with @@@ to be renamed.
|
||||
- for (const MCSymbol &A : Asm.symbols()) {
|
||||
- const auto &Alias = cast<MCSymbolELF>(A);
|
||||
- // Not an alias.
|
||||
- if (!Alias.isVariable())
|
||||
- continue;
|
||||
- auto *Ref = dyn_cast<MCSymbolRefExpr>(Alias.getVariableValue());
|
||||
- if (!Ref)
|
||||
- continue;
|
||||
- const auto &Symbol = cast<MCSymbolELF>(Ref->getSymbol());
|
||||
-
|
||||
- StringRef AliasName = Alias.getName();
|
||||
+ for (const std::pair<StringRef, const MCSymbol *> &P : Asm.Symvers) {
|
||||
+ StringRef AliasName = P.first;
|
||||
+ const auto &Symbol = cast<MCSymbolELF>(*P.second);
|
||||
size_t Pos = AliasName.find('@');
|
||||
- if (Pos == StringRef::npos)
|
||||
- continue;
|
||||
+ assert(Pos != StringRef::npos);
|
||||
|
||||
+ StringRef Prefix = AliasName.substr(0, Pos);
|
||||
+ StringRef Rest = AliasName.substr(Pos);
|
||||
+ StringRef Tail = Rest;
|
||||
+ if (Rest.startswith("@@@"))
|
||||
+ Tail = Rest.substr(Symbol.isUndefined() ? 2 : 1);
|
||||
+
|
||||
+ auto *Alias =
|
||||
+ cast<MCSymbolELF>(Asm.getContext().getOrCreateSymbol(Prefix + Tail));
|
||||
+ Asm.registerSymbol(*Alias);
|
||||
+ const MCExpr *Value = MCSymbolRefExpr::create(&Symbol, Asm.getContext());
|
||||
+ Alias->setVariableValue(Value);
|
||||
+
|
||||
// Aliases defined with .symvar copy the binding from the symbol they alias.
|
||||
// This is the first place we are able to copy this information.
|
||||
- Alias.setExternal(Symbol.isExternal());
|
||||
- Alias.setBinding(Symbol.getBinding());
|
||||
+ Alias->setExternal(Symbol.isExternal());
|
||||
+ Alias->setBinding(Symbol.getBinding());
|
||||
|
||||
- StringRef Rest = AliasName.substr(Pos);
|
||||
if (!Symbol.isUndefined() && !Rest.startswith("@@@"))
|
||||
continue;
|
||||
|
||||
@@ -420,7 +420,7 @@ void ELFObjectWriter::executePostLayoutBinding(MCA
|
||||
!Rest.startswith("@@@"))
|
||||
report_fatal_error("A @@ version cannot be undefined");
|
||||
|
||||
- Renames.insert(std::make_pair(&Symbol, &Alias));
|
||||
+ Renames.insert(std::make_pair(&Symbol, Alias));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -836,44 +836,7 @@ void ELFObjectWriter::computeSymbolTable(
|
||||
HasLargeSectionIndex = true;
|
||||
}
|
||||
|
||||
- // The @@@ in symbol version is replaced with @ in undefined symbols and @@
|
||||
- // in defined ones.
|
||||
- //
|
||||
- // FIXME: All name handling should be done before we get to the writer,
|
||||
- // including dealing with GNU-style version suffixes. Fixing this isn't
|
||||
- // trivial.
|
||||
- //
|
||||
- // We thus have to be careful to not perform the symbol version replacement
|
||||
- // blindly:
|
||||
- //
|
||||
- // The ELF format is used on Windows by the MCJIT engine. Thus, on
|
||||
- // Windows, the ELFObjectWriter can encounter symbols mangled using the MS
|
||||
- // Visual Studio C++ name mangling scheme. Symbols mangled using the MSVC
|
||||
- // C++ name mangling can legally have "@@@" as a sub-string. In that case,
|
||||
- // the EFLObjectWriter should not interpret the "@@@" sub-string as
|
||||
- // specifying GNU-style symbol versioning. The ELFObjectWriter therefore
|
||||
- // checks for the MSVC C++ name mangling prefix which is either "?", "@?",
|
||||
- // "__imp_?" or "__imp_@?".
|
||||
- //
|
||||
- // It would have been interesting to perform the MS mangling prefix check
|
||||
- // only when the target triple is of the form *-pc-windows-elf. But, it
|
||||
- // seems that this information is not easily accessible from the
|
||||
- // ELFObjectWriter.
|
||||
StringRef Name = Symbol.getName();
|
||||
- SmallString<32> Buf;
|
||||
- if (!Name.startswith("?") && !Name.startswith("@?") &&
|
||||
- !Name.startswith("__imp_?") && !Name.startswith("__imp_@?")) {
|
||||
- // This symbol isn't following the MSVC C++ name mangling convention. We
|
||||
- // can thus safely interpret the @@@ in symbol names as specifying symbol
|
||||
- // versioning.
|
||||
- size_t Pos = Name.find("@@@");
|
||||
- if (Pos != StringRef::npos) {
|
||||
- Buf += Name.substr(0, Pos);
|
||||
- unsigned Skip = MSD.SectionIndex == ELF::SHN_UNDEF ? 2 : 1;
|
||||
- Buf += Name.substr(Pos + Skip);
|
||||
- Name = VersionSymSaver.save(Buf.c_str());
|
||||
- }
|
||||
- }
|
||||
|
||||
// Sections have their own string table
|
||||
if (Symbol.getType() != ELF::STT_SECTION) {
|
||||
Index: lib/MC/MCAsmStreamer.cpp
|
||||
===================================================================
|
||||
--- lib/MC/MCAsmStreamer.cpp (revision 331365)
|
||||
+++ lib/MC/MCAsmStreamer.cpp (revision 331366)
|
||||
@@ -129,6 +129,9 @@ class MCAsmStreamer final : public MCStreamer {
|
||||
|
||||
void ChangeSection(MCSection *Section, const MCExpr *Subsection) override;
|
||||
|
||||
+ void emitELFSymverDirective(StringRef AliasName,
|
||||
+ const MCSymbol *Aliasee) override;
|
||||
+
|
||||
void EmitLOHDirective(MCLOHType Kind, const MCLOHArgs &Args) override;
|
||||
void EmitLabel(MCSymbol *Symbol, SMLoc Loc = SMLoc()) override;
|
||||
|
||||
@@ -411,6 +414,14 @@ void MCAsmStreamer::ChangeSection(MCSection *Secti
|
||||
}
|
||||
}
|
||||
|
||||
+void MCAsmStreamer::emitELFSymverDirective(StringRef AliasName,
|
||||
+ const MCSymbol *Aliasee) {
|
||||
+ OS << ".symver ";
|
||||
+ Aliasee->print(OS, MAI);
|
||||
+ OS << ", " << AliasName;
|
||||
+ EmitEOL();
|
||||
+}
|
||||
+
|
||||
void MCAsmStreamer::EmitLabel(MCSymbol *Symbol, SMLoc Loc) {
|
||||
MCStreamer::EmitLabel(Symbol, Loc);
|
||||
|
||||
Index: lib/MC/MCELFStreamer.cpp
|
||||
===================================================================
|
||||
--- lib/MC/MCELFStreamer.cpp (revision 331365)
|
||||
+++ lib/MC/MCELFStreamer.cpp (revision 331366)
|
||||
@@ -337,6 +337,11 @@ void MCELFStreamer::emitELFSize(MCSymbol *Symbol,
|
||||
cast<MCSymbolELF>(Symbol)->setSize(Value);
|
||||
}
|
||||
|
||||
+void MCELFStreamer::emitELFSymverDirective(StringRef AliasName,
|
||||
+ const MCSymbol *Aliasee) {
|
||||
+ getAssembler().Symvers.push_back({AliasName, Aliasee});
|
||||
+}
|
||||
+
|
||||
void MCELFStreamer::EmitLocalCommonSymbol(MCSymbol *S, uint64_t Size,
|
||||
unsigned ByteAlignment) {
|
||||
auto *Symbol = cast<MCSymbolELF>(S);
|
||||
Index: lib/MC/MCParser/ELFAsmParser.cpp
|
||||
===================================================================
|
||||
--- lib/MC/MCParser/ELFAsmParser.cpp (revision 331365)
|
||||
+++ lib/MC/MCParser/ELFAsmParser.cpp (revision 331366)
|
||||
@@ -767,12 +767,8 @@ bool ELFAsmParser::ParseDirectiveSymver(StringRef,
|
||||
if (AliasName.find('@') == StringRef::npos)
|
||||
return TokError("expected a '@' in the name");
|
||||
|
||||
- MCSymbol *Alias = getContext().getOrCreateSymbol(AliasName);
|
||||
MCSymbol *Sym = getContext().getOrCreateSymbol(Name);
|
||||
- const MCExpr *Value = MCSymbolRefExpr::create(Sym, getContext());
|
||||
-
|
||||
- getStreamer().EmitAssignment(Alias, Value);
|
||||
- getStreamer().emitELFSymverDirective(Alias, Sym);
|
||||
+ getStreamer().emitELFSymverDirective(AliasName, Sym);
|
||||
return false;
|
||||
}
|
||||
|
||||
Index: lib/MC/MCStreamer.cpp
|
||||
===================================================================
|
||||
--- lib/MC/MCStreamer.cpp (revision 331365)
|
||||
+++ lib/MC/MCStreamer.cpp (revision 331366)
|
||||
@@ -925,7 +925,7 @@ void MCStreamer::EmitCOFFSymbolType(int Type) {
|
||||
llvm_unreachable("this directive only supported on COFF targets");
|
||||
}
|
||||
void MCStreamer::emitELFSize(MCSymbol *Symbol, const MCExpr *Value) {}
|
||||
-void MCStreamer::emitELFSymverDirective(MCSymbol *Alias,
|
||||
+void MCStreamer::emitELFSymverDirective(StringRef AliasName,
|
||||
const MCSymbol *Aliasee) {}
|
||||
void MCStreamer::EmitLocalCommonSymbol(MCSymbol *Symbol, uint64_t Size,
|
||||
unsigned ByteAlignment) {}
|
||||
Index: lib/Object/ModuleSymbolTable.cpp
|
||||
===================================================================
|
||||
--- lib/Object/ModuleSymbolTable.cpp (revision 331365)
|
||||
+++ lib/Object/ModuleSymbolTable.cpp (revision 331366)
|
||||
@@ -24,7 +24,6 @@
|
||||
#include "llvm/IR/GlobalAlias.h"
|
||||
#include "llvm/IR/GlobalValue.h"
|
||||
#include "llvm/IR/GlobalVariable.h"
|
||||
-#include "llvm/IR/Mangler.h"
|
||||
#include "llvm/IR/Module.h"
|
||||
#include "llvm/MC/MCAsmInfo.h"
|
||||
#include "llvm/MC/MCContext.h"
|
||||
@@ -69,81 +68,6 @@ void ModuleSymbolTable::addModule(Module *M) {
|
||||
});
|
||||
}
|
||||
|
||||
-// Ensure ELF .symver aliases get the same binding as the defined symbol
|
||||
-// they alias with.
|
||||
-static void handleSymverAliases(const Module &M, RecordStreamer &Streamer) {
|
||||
- if (Streamer.symverAliases().empty())
|
||||
- return;
|
||||
-
|
||||
- // The name in the assembler will be mangled, but the name in the IR
|
||||
- // might not, so we first compute a mapping from mangled name to GV.
|
||||
- Mangler Mang;
|
||||
- SmallString<64> MangledName;
|
||||
- StringMap<const GlobalValue *> MangledNameMap;
|
||||
- auto GetMangledName = [&](const GlobalValue &GV) {
|
||||
- if (!GV.hasName())
|
||||
- return;
|
||||
-
|
||||
- MangledName.clear();
|
||||
- MangledName.reserve(GV.getName().size() + 1);
|
||||
- Mang.getNameWithPrefix(MangledName, &GV, /*CannotUsePrivateLabel=*/false);
|
||||
- MangledNameMap[MangledName] = &GV;
|
||||
- };
|
||||
- for (const Function &F : M)
|
||||
- GetMangledName(F);
|
||||
- for (const GlobalVariable &GV : M.globals())
|
||||
- GetMangledName(GV);
|
||||
- for (const GlobalAlias &GA : M.aliases())
|
||||
- GetMangledName(GA);
|
||||
-
|
||||
- // Walk all the recorded .symver aliases, and set up the binding
|
||||
- // for each alias.
|
||||
- for (auto &Symver : Streamer.symverAliases()) {
|
||||
- const MCSymbol *Aliasee = Symver.first;
|
||||
- MCSymbolAttr Attr = MCSA_Invalid;
|
||||
-
|
||||
- // First check if the aliasee binding was recorded in the asm.
|
||||
- RecordStreamer::State state = Streamer.getSymbolState(Aliasee);
|
||||
- switch (state) {
|
||||
- case RecordStreamer::Global:
|
||||
- case RecordStreamer::DefinedGlobal:
|
||||
- Attr = MCSA_Global;
|
||||
- break;
|
||||
- case RecordStreamer::UndefinedWeak:
|
||||
- case RecordStreamer::DefinedWeak:
|
||||
- Attr = MCSA_Weak;
|
||||
- break;
|
||||
- default:
|
||||
- break;
|
||||
- }
|
||||
-
|
||||
- // If we don't have a symbol attribute from assembly, then check if
|
||||
- // the aliasee was defined in the IR.
|
||||
- if (Attr == MCSA_Invalid) {
|
||||
- const auto *GV = M.getNamedValue(Aliasee->getName());
|
||||
- if (!GV) {
|
||||
- auto MI = MangledNameMap.find(Aliasee->getName());
|
||||
- if (MI != MangledNameMap.end())
|
||||
- GV = MI->second;
|
||||
- else
|
||||
- continue;
|
||||
- }
|
||||
- if (GV->hasExternalLinkage())
|
||||
- Attr = MCSA_Global;
|
||||
- else if (GV->hasLocalLinkage())
|
||||
- Attr = MCSA_Local;
|
||||
- else if (GV->isWeakForLinker())
|
||||
- Attr = MCSA_Weak;
|
||||
- }
|
||||
- if (Attr == MCSA_Invalid)
|
||||
- continue;
|
||||
-
|
||||
- // Set the detected binding on each alias with this aliasee.
|
||||
- for (auto &Alias : Symver.second)
|
||||
- Streamer.EmitSymbolAttribute(Alias, Attr);
|
||||
- }
|
||||
-}
|
||||
-
|
||||
void ModuleSymbolTable::CollectAsmSymbols(
|
||||
const Module &M,
|
||||
function_ref<void(StringRef, BasicSymbolRef::Flags)> AsmSymbol) {
|
||||
@@ -176,7 +100,7 @@ void ModuleSymbolTable::CollectAsmSymbols(
|
||||
MCObjectFileInfo MOFI;
|
||||
MCContext MCCtx(MAI.get(), MRI.get(), &MOFI);
|
||||
MOFI.InitMCObjectFileInfo(TT, /*PIC*/ false, MCCtx);
|
||||
- RecordStreamer Streamer(MCCtx);
|
||||
+ RecordStreamer Streamer(MCCtx, M);
|
||||
T->createNullTargetStreamer(Streamer);
|
||||
|
||||
std::unique_ptr<MemoryBuffer> Buffer(MemoryBuffer::getMemBuffer(InlineAsm));
|
||||
@@ -195,7 +119,7 @@ void ModuleSymbolTable::CollectAsmSymbols(
|
||||
if (Parser->Run(false))
|
||||
return;
|
||||
|
||||
- handleSymverAliases(M, Streamer);
|
||||
+ Streamer.flushSymverDirectives();
|
||||
|
||||
for (auto &KV : Streamer) {
|
||||
StringRef Key = KV.first();
|
||||
Index: lib/Object/RecordStreamer.cpp
|
||||
===================================================================
|
||||
--- lib/Object/RecordStreamer.cpp (revision 331365)
|
||||
+++ lib/Object/RecordStreamer.cpp (revision 331366)
|
||||
@@ -8,6 +8,9 @@
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
||||
#include "RecordStreamer.h"
|
||||
+#include "llvm/IR/Mangler.h"
|
||||
+#include "llvm/IR/Module.h"
|
||||
+#include "llvm/MC/MCContext.h"
|
||||
#include "llvm/MC/MCSymbol.h"
|
||||
|
||||
using namespace llvm;
|
||||
@@ -70,7 +73,8 @@ void RecordStreamer::markUsed(const MCSymbol &Symb
|
||||
|
||||
void RecordStreamer::visitUsedSymbol(const MCSymbol &Sym) { markUsed(Sym); }
|
||||
|
||||
-RecordStreamer::RecordStreamer(MCContext &Context) : MCStreamer(Context) {}
|
||||
+RecordStreamer::RecordStreamer(MCContext &Context, const Module &M)
|
||||
+ : MCStreamer(Context), M(M) {}
|
||||
|
||||
RecordStreamer::const_iterator RecordStreamer::begin() {
|
||||
return Symbols.begin();
|
||||
@@ -112,7 +116,109 @@ void RecordStreamer::EmitCommonSymbol(MCSymbol *Sy
|
||||
markDefined(*Symbol);
|
||||
}
|
||||
|
||||
-void RecordStreamer::emitELFSymverDirective(MCSymbol *Alias,
|
||||
+RecordStreamer::State RecordStreamer::getSymbolState(const MCSymbol *Sym) {
|
||||
+ auto SI = Symbols.find(Sym->getName());
|
||||
+ if (SI == Symbols.end())
|
||||
+ return NeverSeen;
|
||||
+ return SI->second;
|
||||
+}
|
||||
+
|
||||
+void RecordStreamer::emitELFSymverDirective(StringRef AliasName,
|
||||
const MCSymbol *Aliasee) {
|
||||
- SymverAliasMap[Aliasee].push_back(Alias);
|
||||
+ SymverAliasMap[Aliasee].push_back(AliasName);
|
||||
}
|
||||
+
|
||||
+void RecordStreamer::flushSymverDirectives() {
|
||||
+ // Mapping from mangled name to GV.
|
||||
+ StringMap<const GlobalValue *> MangledNameMap;
|
||||
+ // The name in the assembler will be mangled, but the name in the IR
|
||||
+ // might not, so we first compute a mapping from mangled name to GV.
|
||||
+ Mangler Mang;
|
||||
+ SmallString<64> MangledName;
|
||||
+ for (const GlobalValue &GV : M.global_values()) {
|
||||
+ if (!GV.hasName())
|
||||
+ continue;
|
||||
+ MangledName.clear();
|
||||
+ MangledName.reserve(GV.getName().size() + 1);
|
||||
+ Mang.getNameWithPrefix(MangledName, &GV, /*CannotUsePrivateLabel=*/false);
|
||||
+ MangledNameMap[MangledName] = &GV;
|
||||
+ }
|
||||
+
|
||||
+ // Walk all the recorded .symver aliases, and set up the binding
|
||||
+ // for each alias.
|
||||
+ for (auto &Symver : SymverAliasMap) {
|
||||
+ const MCSymbol *Aliasee = Symver.first;
|
||||
+ MCSymbolAttr Attr = MCSA_Invalid;
|
||||
+ bool IsDefined = false;
|
||||
+
|
||||
+ // First check if the aliasee binding was recorded in the asm.
|
||||
+ RecordStreamer::State state = getSymbolState(Aliasee);
|
||||
+ switch (state) {
|
||||
+ case RecordStreamer::Global:
|
||||
+ case RecordStreamer::DefinedGlobal:
|
||||
+ Attr = MCSA_Global;
|
||||
+ break;
|
||||
+ case RecordStreamer::UndefinedWeak:
|
||||
+ case RecordStreamer::DefinedWeak:
|
||||
+ Attr = MCSA_Weak;
|
||||
+ break;
|
||||
+ default:
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ switch (state) {
|
||||
+ case RecordStreamer::Defined:
|
||||
+ case RecordStreamer::DefinedGlobal:
|
||||
+ case RecordStreamer::DefinedWeak:
|
||||
+ IsDefined = true;
|
||||
+ break;
|
||||
+ case RecordStreamer::NeverSeen:
|
||||
+ case RecordStreamer::Global:
|
||||
+ case RecordStreamer::Used:
|
||||
+ case RecordStreamer::UndefinedWeak:
|
||||
+ break;
|
||||
+ }
|
||||
+
|
||||
+ if (Attr == MCSA_Invalid || !IsDefined) {
|
||||
+ const GlobalValue *GV = M.getNamedValue(Aliasee->getName());
|
||||
+ if (!GV) {
|
||||
+ auto MI = MangledNameMap.find(Aliasee->getName());
|
||||
+ if (MI != MangledNameMap.end())
|
||||
+ GV = MI->second;
|
||||
+ }
|
||||
+ if (GV) {
|
||||
+ // If we don't have a symbol attribute from assembly, then check if
|
||||
+ // the aliasee was defined in the IR.
|
||||
+ if (Attr == MCSA_Invalid) {
|
||||
+ if (GV->hasExternalLinkage())
|
||||
+ Attr = MCSA_Global;
|
||||
+ else if (GV->hasLocalLinkage())
|
||||
+ Attr = MCSA_Local;
|
||||
+ else if (GV->isWeakForLinker())
|
||||
+ Attr = MCSA_Weak;
|
||||
+ }
|
||||
+ IsDefined = IsDefined || !GV->isDeclarationForLinker();
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ // Set the detected binding on each alias with this aliasee.
|
||||
+ for (auto AliasName : Symver.second) {
|
||||
+ std::pair<StringRef, StringRef> Split = AliasName.split("@@@");
|
||||
+ SmallString<128> NewName;
|
||||
+ if (!Split.second.empty() && !Split.second.startswith("@")) {
|
||||
+ // Special processing for "@@@" according
|
||||
+ // https://sourceware.org/binutils/docs/as/Symver.html
|
||||
+ const char *Separator = IsDefined ? "@@" : "@";
|
||||
+ AliasName =
|
||||
+ (Split.first + Separator + Split.second).toStringRef(NewName);
|
||||
+ }
|
||||
+ MCSymbol *Alias = getContext().getOrCreateSymbol(AliasName);
|
||||
+ // TODO: Handle "@@@". Depending on SymbolAttribute value it needs to be
|
||||
+ // converted into @ or @@.
|
||||
+ const MCExpr *Value = MCSymbolRefExpr::create(Aliasee, getContext());
|
||||
+ EmitAssignment(Alias, Value);
|
||||
+ if (Attr != MCSA_Invalid)
|
||||
+ EmitSymbolAttribute(Alias, Attr);
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
Index: lib/Object/RecordStreamer.h
|
||||
===================================================================
|
||||
--- lib/Object/RecordStreamer.h (revision 331365)
|
||||
+++ lib/Object/RecordStreamer.h (revision 331366)
|
||||
@@ -20,6 +20,9 @@
|
||||
|
||||
namespace llvm {
|
||||
|
||||
+class GlobalValue;
|
||||
+class Module;
|
||||
+
|
||||
class RecordStreamer : public MCStreamer {
|
||||
public:
|
||||
enum State { NeverSeen, Global, Defined, DefinedGlobal, DefinedWeak, Used,
|
||||
@@ -26,12 +29,16 @@ class RecordStreamer : public MCStreamer {
|
||||
UndefinedWeak};
|
||||
|
||||
private:
|
||||
+ const Module &M;
|
||||
StringMap<State> Symbols;
|
||||
// Map of aliases created by .symver directives, saved so we can update
|
||||
// their symbol binding after parsing complete. This maps from each
|
||||
// aliasee to its list of aliases.
|
||||
- DenseMap<const MCSymbol *, std::vector<MCSymbol *>> SymverAliasMap;
|
||||
+ DenseMap<const MCSymbol *, std::vector<StringRef>> SymverAliasMap;
|
||||
|
||||
+ /// Get the state recorded for the given symbol.
|
||||
+ State getSymbolState(const MCSymbol *Sym);
|
||||
+
|
||||
void markDefined(const MCSymbol &Symbol);
|
||||
void markGlobal(const MCSymbol &Symbol, MCSymbolAttr Attribute);
|
||||
void markUsed(const MCSymbol &Symbol);
|
||||
@@ -38,7 +45,7 @@ class RecordStreamer : public MCStreamer {
|
||||
void visitUsedSymbol(const MCSymbol &Sym) override;
|
||||
|
||||
public:
|
||||
- RecordStreamer(MCContext &Context);
|
||||
+ RecordStreamer(MCContext &Context, const Module &M);
|
||||
|
||||
using const_iterator = StringMap<State>::const_iterator;
|
||||
|
||||
@@ -54,20 +61,11 @@ class RecordStreamer : public MCStreamer {
|
||||
void EmitCommonSymbol(MCSymbol *Symbol, uint64_t Size,
|
||||
unsigned ByteAlignment) override;
|
||||
/// Record .symver aliases for later processing.
|
||||
- void emitELFSymverDirective(MCSymbol *Alias,
|
||||
+ void emitELFSymverDirective(StringRef AliasName,
|
||||
const MCSymbol *Aliasee) override;
|
||||
- /// Return the map of .symver aliasee to associated aliases.
|
||||
- DenseMap<const MCSymbol *, std::vector<MCSymbol *>> &symverAliases() {
|
||||
- return SymverAliasMap;
|
||||
- }
|
||||
-
|
||||
- /// Get the state recorded for the given symbol.
|
||||
- State getSymbolState(const MCSymbol *Sym) {
|
||||
- auto SI = Symbols.find(Sym->getName());
|
||||
- if (SI == Symbols.end())
|
||||
- return NeverSeen;
|
||||
- return SI->second;
|
||||
- }
|
||||
+ // Emit ELF .symver aliases and ensure they have the same binding as the
|
||||
+ // defined symbol they alias with.
|
||||
+ void flushSymverDirectives();
|
||||
};
|
||||
|
||||
} // end namespace llvm
|
32
devel/llvm60/files/patch-head-r336969.diff
Normal file
32
devel/llvm60/files/patch-head-r336969.diff
Normal file
|
@ -0,0 +1,32 @@
|
|||
r336969 | emaste | 2018-07-31 16:12:09 +0200 (Tue, 31 Jul 2018) | 13 lines
|
||||
|
||||
llvm: [ELF][ARM] Add Arm ABI names for float ABI ELF Header flags
|
||||
|
||||
The ELF for the Arm architecture document defines, for EF_ARM_EABI_VER5
|
||||
and above, the flags EF_ARM_ABI_FLOAT_HARD and EF_ARM_ABI_FLOAT_SOFT.
|
||||
These have been defined to be compatible with the existing
|
||||
EF_ARM_VFP_FLOAT and EF_ARM_SOFT_FLOAT used by gcc for
|
||||
EF_ARM_EABI_UNKNOWN.
|
||||
|
||||
This patch adds the flags in addition to the existing ones so that any
|
||||
code depending on the old names will still work.
|
||||
|
||||
Obtained from: llvm r338370 by Peter Smith
|
||||
|
||||
Index: include/llvm/BinaryFormat/ELF.h
|
||||
===================================================================
|
||||
--- include/llvm/BinaryFormat/ELF.h (revision 336968)
|
||||
+++ include/llvm/BinaryFormat/ELF.h (revision 336969)
|
||||
@@ -418,8 +418,10 @@ enum {
|
||||
|
||||
// ARM Specific e_flags
|
||||
enum : unsigned {
|
||||
- EF_ARM_SOFT_FLOAT = 0x00000200U,
|
||||
- EF_ARM_VFP_FLOAT = 0x00000400U,
|
||||
+ EF_ARM_SOFT_FLOAT = 0x00000200U, // Legacy pre EABI_VER5
|
||||
+ EF_ARM_ABI_FLOAT_SOFT = 0x00000200U, // EABI_VER5
|
||||
+ EF_ARM_VFP_FLOAT = 0x00000400U, // Legacy pre EABI_VER5
|
||||
+ EF_ARM_ABI_FLOAT_HARD = 0x00000400U, // EABI_VER5
|
||||
EF_ARM_EABI_UNKNOWN = 0x00000000U,
|
||||
EF_ARM_EABI_VER1 = 0x01000000U,
|
||||
EF_ARM_EABI_VER2 = 0x02000000U,
|
24
devel/llvm60/files/patch-head-r336970.diff
Normal file
24
devel/llvm60/files/patch-head-r336970.diff
Normal file
|
@ -0,0 +1,24 @@
|
|||
r336970 | emaste | 2018-07-31 16:14:41 +0200 (Tue, 31 Jul 2018) | 9 lines
|
||||
|
||||
llvm: [ARM] Complete enumeration values for Tag_ABI_VFP_args
|
||||
|
||||
The LLD implementation of Tag_ABI_VFP_args needs to check the rarely
|
||||
seen values of 3 (toolchain specific) and 4 compatible with both Base
|
||||
and VFP. Add the missing enumeration values so that LLD can refer to
|
||||
them without having to use the raw numbers.
|
||||
|
||||
Obtained from: llvm r338373 by Peter Smith
|
||||
|
||||
Index: include/llvm/Support/ARMBuildAttributes.h
|
||||
===================================================================
|
||||
--- include/llvm/Support/ARMBuildAttributes.h (revision 336969)
|
||||
+++ include/llvm/Support/ARMBuildAttributes.h (revision 336970)
|
||||
@@ -213,6 +213,8 @@ enum {
|
||||
// Tag_ABI_VFP_args, (=28), uleb128
|
||||
BaseAAPCS = 0,
|
||||
HardFPAAPCS = 1,
|
||||
+ ToolChainFPPCS = 2,
|
||||
+ CompatibleFPAAPCS = 3,
|
||||
|
||||
// Tag_FP_HP_extension, (=36), uleb128
|
||||
AllowHPFP = 1, // Allow use of Half Precision FP
|
64
devel/llvm60/files/patch-head-r337615.diff
Normal file
64
devel/llvm60/files/patch-head-r337615.diff
Normal file
|
@ -0,0 +1,64 @@
|
|||
r337615 | dim | 2018-08-11 12:42:12 +0200 (Sat, 11 Aug 2018) | 43 lines
|
||||
|
||||
Pull in r338481 from upstream llvm trunk (by Chandler Carruth):
|
||||
|
||||
[x86] Fix a really subtle miscompile due to a somewhat glaring bug in
|
||||
EFLAGS copy lowering.
|
||||
|
||||
If you have a branch of LLVM, you may want to cherrypick this. It is
|
||||
extremely unlikely to hit this case empirically, but it will likely
|
||||
manifest as an "impossible" branch being taken somewhere, and will be
|
||||
... very hard to debug.
|
||||
|
||||
Hitting this requires complex conditions living across complex
|
||||
control flow combined with some interesting memory (non-stack)
|
||||
initialized with the results of a comparison. Also, because you have
|
||||
to arrange for an EFLAGS copy to be in *just* the right place, almost
|
||||
anything you do to the code will hide the bug. I was unable to reduce
|
||||
anything remotely resembling a "good" test case from the place where
|
||||
I hit it, and so instead I have constructed synthetic MIR testing
|
||||
that directly exercises the bug in question (as well as the good
|
||||
behavior for completeness).
|
||||
|
||||
The issue is that we would mistakenly assume any SETcc with a valid
|
||||
condition and an initial operand that was a register and a virtual
|
||||
register at that to be a register *defining* SETcc...
|
||||
|
||||
It isn't though....
|
||||
|
||||
This would in turn cause us to test some other bizarre register,
|
||||
typically the base pointer of some memory. Now, testing this register
|
||||
and using that to branch on doesn't make any sense. It even fails the
|
||||
machine verifier (if you are running it) due to the wrong register
|
||||
class. But it will make it through LLVM, assemble, and it *looks*
|
||||
fine... But wow do you get a very unsual and surprising branch taken
|
||||
in your actual code.
|
||||
|
||||
The fix is to actually check what kind of SETcc instruction we're
|
||||
dealing with. Because there are a bunch of them, I just test the
|
||||
may-store bit in the instruction. I've also added an assert for
|
||||
sanity that ensure we are, in fact, *defining* the register operand.
|
||||
=D
|
||||
|
||||
Noticed by: kib
|
||||
MFC after: 1 week
|
||||
|
||||
Index: lib/Target/X86/X86FlagsCopyLowering.cpp
|
||||
===================================================================
|
||||
--- lib/Target/X86/X86FlagsCopyLowering.cpp (revision 337614)
|
||||
+++ lib/Target/X86/X86FlagsCopyLowering.cpp (revision 337615)
|
||||
@@ -608,9 +608,12 @@ X86FlagsCopyLoweringPass::collectCondsInRegs(Machi
|
||||
for (MachineInstr &MI : llvm::reverse(
|
||||
llvm::make_range(MBB.instr_begin(), CopyDefI.getIterator()))) {
|
||||
X86::CondCode Cond = X86::getCondFromSETOpc(MI.getOpcode());
|
||||
- if (Cond != X86::COND_INVALID && MI.getOperand(0).isReg() &&
|
||||
- TRI->isVirtualRegister(MI.getOperand(0).getReg()))
|
||||
+ if (Cond != X86::COND_INVALID && !MI.mayStore() && MI.getOperand(0).isReg() &&
|
||||
+ TRI->isVirtualRegister(MI.getOperand(0).getReg())) {
|
||||
+ assert(MI.getOperand(0).isDef() &&
|
||||
+ "A non-storing SETcc should always define a register!");
|
||||
CondRegs[Cond] = MI.getOperand(0).getReg();
|
||||
+ }
|
||||
|
||||
// Stop scanning when we see the first definition of the EFLAGS as prior to
|
||||
// this we would potentially capture the wrong flag state.
|
32
devel/llvm60/files/patch-head-r338689.diff
Normal file
32
devel/llvm60/files/patch-head-r338689.diff
Normal file
|
@ -0,0 +1,32 @@
|
|||
r338689 | dim | 2018-09-14 21:25:23 +0200 (Fri, 14 Sep 2018) | 12 lines
|
||||
|
||||
Pull in r335365 from upstream llvm trunk (by Krzysztof Parzyszek):
|
||||
|
||||
Initialize LiveRegs once in BranchFolder::mergeCommonTails
|
||||
|
||||
This should fix '(TRI && "LivePhysRegs is not initialized."' assertions
|
||||
when building the lang/qt5-qml port in certain configurations.
|
||||
|
||||
Approved by: re (kib)
|
||||
Reported by: Piotr Kubaj <pkubaj@anongoth.pl>
|
||||
PR: 231355
|
||||
MFC after: 3 days
|
||||
|
||||
Index: lib/CodeGen/BranchFolding.cpp
|
||||
===================================================================
|
||||
--- lib/CodeGen/BranchFolding.cpp (revision 338688)
|
||||
+++ lib/CodeGen/BranchFolding.cpp (revision 338689)
|
||||
@@ -884,11 +884,12 @@ void BranchFolder::mergeCommonTails(unsigned commo
|
||||
if (UpdateLiveIns) {
|
||||
LivePhysRegs NewLiveIns(*TRI);
|
||||
computeLiveIns(NewLiveIns, *MBB);
|
||||
+ LiveRegs.init(*TRI);
|
||||
|
||||
// The flag merging may lead to some register uses no longer using the
|
||||
// <undef> flag, add IMPLICIT_DEFs in the predecessors as necessary.
|
||||
for (MachineBasicBlock *Pred : MBB->predecessors()) {
|
||||
- LiveRegs.init(*TRI);
|
||||
+ LiveRegs.clear();
|
||||
LiveRegs.addLiveOuts(*Pred);
|
||||
MachineBasicBlock::iterator InsertBefore = Pred->getFirstTerminator();
|
||||
for (unsigned Reg : NewLiveIns) {
|
Loading…
Add table
Reference in a new issue