Skip to content

Commit

Permalink
Update to LLVM 9.0
Browse files Browse the repository at this point in the history
  • Loading branch information
dduan committed Aug 10, 2020
1 parent 188bfbb commit bc303e0
Show file tree
Hide file tree
Showing 19 changed files with 123 additions and 439 deletions.
27 changes: 15 additions & 12 deletions .travis.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,40 +5,43 @@ matrix:
include:
- os: osx
language: objective-c
osx_image: xcode10.2
osx_image: xcode11.5
before_install:
- export PATH=/usr/local/opt/llvm/bin:"${PATH}"
- brew update
- brew install llvm
- brew install llvm@9
- echo 'export PATH="/usr/local/opt/llvm@9/bin:$PATH"' >> /Users/travis/.bash_profile
- source /Users/travis/.bash_profile
- sudo swift utils/make-pkgconfig.swift
script:
- swift test -Xlinker -w
- os: linux
language: generic
sudo: required
dist: trusty
dist: focal
env:
- LLVM_API_VERSION=8
- LLVM_API_VERSION=9
before_install:
- export PKG_CONFIG_PATH=/usr/local/lib/pkgconfig:"${PKG_CONFIG_PATH}"
- wget -O - http://apt.llvm.org/llvm-snapshot.gpg.key | sudo apt-key add -
- sudo apt-add-repository "deb http://apt.llvm.org/trusty/ llvm-toolchain-trusty-${LLVM_API_VERSION} main"
- sudo apt-add-repository "deb http://apt.llvm.org/focal/ llvm-toolchain-focal-${LLVM_API_VERSION} main"
- sudo apt-add-repository -y "ppa:ubuntu-toolchain-r/test"
- sudo apt-get update
- sudo apt-get install -y llvm-${LLVM_API_VERSION} libc++1
- sudo apt-get install -y binutils git gnupg2 libc6-dev libcurl4 libedit2 libgcc-9-dev libpython2.7 libsqlite3-0 libstdc++-9-dev libxml2 libz3-dev pkg-config tzdata zlib1g-dev
- sudo apt-get install -y llvm-${LLVM_API_VERSION} llvm-${LLVM_API_VERSION}-dev libc++1 libtinfo5 libncurses5
- sudo cp /usr/lib/x86_64-linux-gnu/libc++.so.1.0 /usr/lib/
- sudo ln -sf /usr/lib/libc++.so.1.0 /usr/lib/libc++.so
- sudo rm -rf /usr/local/clang-*/bin/llvm-config
- ls -l /usr/bin/llvm-config*
- sudo rm -f /usr/bin/llvm-config
- sudo ln -s /usr/bin/llvm-config-${LLVM_API_VERSION} /usr/bin/llvm-config
- ls /usr/lib/llvm-9/include/llvm-c
- wget -q -O - https://swift.org/keys/all-keys.asc | gpg --import -
- wget https://swift.org/builds/swift-5.0-release/ubuntu1404/swift-5.0-RELEASE/swift-5.0-RELEASE-ubuntu14.04.tar.gz
- tar xzf swift-5.0-RELEASE-ubuntu14.04.tar.gz
- export PATH=${PWD}/swift-5.0-RELEASE-ubuntu14.04/usr/bin:"${PATH}"
- sudo ./swift-5.0-RELEASE-ubuntu14.04/usr/bin/swift utils/make-pkgconfig.swift
- wget https://swift.org/builds/swift-5.2.5-release/ubuntu1804/swift-5.2.5-RELEASE/swift-5.2.5-RELEASE-ubuntu18.04.tar.gz
- tar xzf swift-5.2.5-RELEASE-ubuntu18.04.tar.gz
- export PATH=${PWD}/swift-5.2.5-RELEASE-ubuntu18.04/usr/bin:"${PATH}"
- sudo ./swift-5.2.5-RELEASE-ubuntu18.04/usr/bin/swift utils/make-pkgconfig.swift
script:
- ./swift-5.0-RELEASE-ubuntu14.04/usr/bin/swift test
- sudo ./swift-5.2.5-RELEASE-ubuntu18.04/usr/bin/swift test
notifications:
slack:
secure: ek/+U+e44bqP8+QCHojy2LhrN9iwY3N/TNNqNG5FZrp09Vidrd5KXWJOXFxlGrpeWdgTpi089YbEdTfxpcDIudUqDqLwPzS7wePiG2cEC1OT6l3yrhI4AvOe7EsNSOX8gzkuEnmrZVHwLLGe7JeR7JIQKoHMZsBcPYDnO8kRP0Ei3zOh47YUn75SE87egAgZOVBDbZYO3GWRa4WX64s8gaQYQ9a7EoUY0oX9rQ48FJs3rmEIhvIXdcOj9bGX7+o0j7l+IFial/Qh+B6bp4XkZU/tUVP6cuNVI1vxE1weVGCBhgt5wLhXTMewzoE5D1IgMZHVuzIBcDbBthSzQRttLSlYar6xTjXtRtOnb8tqZMWfUj3HBYCFYqtz7PGnZ3IflEVsPJW6tgSsoeB6egjzb8APP9mvhm8+zb1jQG1dqXLWErMjWqhlyPVPmHrxU2w/OLWLAJPY94GVmLnSuOw2pSz41spuEY80JcVVzoRbAOQWrwAujq2S3k93yvKpGq4eaT72Mt8g1CyZesByvzcLk99LEJSpqOIxUqXBd4RwHhay/sq8LllyyqY8ORsxEgwQluOAjEhATO/t/HUsu2ndn1k38U1c4HqXW7FDs1hffYEzZ/PGxciCS6Vt1bfST+iq34pzqpanENQCnX6mSR+D+M7mHlCWdsUihmxEcs5knuM=
66 changes: 66 additions & 0 deletions Sources/LLVM/AddressSpace.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,66 @@
#if SWIFT_PACKAGE
import cllvm
#endif

/// An address space is an identifier for a target-specific range of address values. An address space is a
/// fundamental part of the type of a pointer value and the type of operations that manipulate memory.
///
/// LLVM affords a default address space (numbered zero) and places a number of assumptions on pointer
/// values within that address space:
/// - The pointer must have a fixed integral value
/// - The null pointer has a bit-value of 0
///
/// These assumptions are not guaranteed to hold in any other address space. In particular, a target may
/// allow pointers in non-default address spaces to have *non-integral* types. Non-integral pointer types
/// represent pointers that have an unspecified bitwise representation; that is, the integral representation may
/// be target dependent or have an unstable value. Further, outside of the default address space, it is not
/// always the case that the `null` pointer value, especially as returned by
/// `IRType.constPointerNull()` has a bit value of 0. e.g. A non-default address space may use
/// an offset-based or segment-based addressing mode in which 0 is a valid, addressable pointer value.
///
/// Target-Level Address Space Overrides
/// ====================================
///
/// A target may choose to override the default address space for code, data, and local allocations through the
/// data layout string. This has multiple uses. For example, the address space of an `alloca` is *only*
/// configurable via the data layout string, because it is a target-dependent property. There are also
/// use-cases for overriding language standards e.g. the C standard requires the address-of operator applied
/// to values on the stack to result in a pointer in the default address space. However, many OpenCL-based
/// targets consider the stack to be a private region, and place such pointers in a non-default address space.
///
/// Care must be taken when interacting with these non-standard targets. The IR printer currently does not
/// print anything when the default address space is attached to an instruction or value, and values will still
/// report being assigned to that space. However, these values are still subject to the backend's interpretation
/// of the data layout string overrides and as such may not always reside in the default address space when
/// it comes time to codegen them.
///
/// Restrictions
/// ============
///
/// There are currently a number of artificial restrictions on values and operations that have non-default
/// address spaces:
/// - A `bitcast` between two pointer values residing in different address spaces, even if those two
/// values have the same size, is always an illegal operation. Use an `addrspacecast` instead or
/// always use `IRBuilder.buildPointerCast(of:to:name:)` to get the correct operation.
/// - The so-called "null pointer" has a bit value that may differ from address space to address space. This
/// exposes bugs in optimizer passes and lowerings that did not consider this possibility.
/// - A pointer value may not necessarily "round-trip" when converted between address spaces, even if
/// annotated `nonnull` and `dereferenceable`. This is especially true of non-integral pointer types.
/// - Though the zero address space is the default, many backends and some errant passes interpret this to
/// mean a "lack of address space" and may miscompile code with pointers in mixed address spaces.
/// - A number of intriniscs that operate on memory currently do not support a non-default address space.
/// - The address space is ultimately an integer value and in theory an address space identifier may take on
/// any value. In practice, LLVM guarantees only 24 bits of precision, though higher address space
/// identifiers may succeed in being properly represented.
public struct AddressSpace: Equatable {
let rawValue: Int

/// LLVM's default address space.
public static let zero = AddressSpace(0)

/// Creates and initializes an address space with the given identifier.
/// - Parameter identifier: The raw, integral address space identifier.
public init(_ identifier: Int) {
self.rawValue = identifier
}
}
3 changes: 3 additions & 0 deletions Sources/LLVM/AttachedMetadata.swift
Original file line number Diff line number Diff line change
Expand Up @@ -336,6 +336,9 @@ public class AttachedMetadata {
/// attribute may only be applied to pointer typed parameters. This is not
/// checked or enforced by LLVM; if the parameter or return pointer is null,
/// the behavior is undefined.
///
/// Note that the concept of a "null" pointer is address space dependent. it is
/// not necessarily the 0 bit-pattern.
case nonnull = 11
/// Dereferenceable metadata.
///
Expand Down
6 changes: 3 additions & 3 deletions Sources/LLVM/DIBuilder.swift
Original file line number Diff line number Diff line change
Expand Up @@ -664,17 +664,17 @@ extension DIBuilder {
/// - pointee: Type pointed by this pointer.
/// - size: The size of the pointer value.
/// - alignment: The alignment of the pointer.
/// - addressSpace: DWARF address space.
/// - addressSpace: The address space the pointer type reside in.
/// - name: The name of the pointer type.
public func buildPointerType(
pointee: DIType, size: Size, alignment: Alignment = .zero,
addressSpace: UInt32 = 0, name: String = ""
addressSpace: AddressSpace = .zero, name: String = ""
) -> DIType {
let radix = UInt32(self.module.dataLayout.intPointerType().width)
guard let ty = LLVMDIBuilderCreatePointerType(
self.llvm, pointee.asMetadata(),
size.valueInBits(radix: UInt64(radix)), alignment.rawValue * radix,
addressSpace, name, name.count)
UInt32(addressSpace.rawValue), name, name.count)
else {
fatalError("Failed to allocate metadata")
}
Expand Down
10 changes: 8 additions & 2 deletions Sources/LLVM/IRBuilder.swift
Original file line number Diff line number Diff line change
Expand Up @@ -1038,6 +1038,9 @@ extension IRBuilder {
/// choose to align the allocation on any convenient boundary compatible with
/// the type.
///
/// The returned value is allocated in the address space specified in the data layout string for the target. If
/// no such value is specified, the value is allocated in the default address space.
///
/// - parameter type: The sized type used to determine the amount of stack
/// memory to allocate.
/// - parameter count: An optional number of slots to allocate, to simulate a
Expand Down Expand Up @@ -1277,6 +1280,9 @@ extension IRBuilder {
/// `bitcast` instruction. Note that if the address space conversion is legal
/// then both result and operand refer to the same memory location.
///
/// This instruction must be used in lieu of a `bitcast` even if the cast is between
/// types of the same size.
///
/// The address spaces of the value and the destination pointer types must
/// be distinct.
public func buildAddrSpaceCast(_ val: IRValue, type: IRType, name: String = "") -> IRValue {
Expand Down Expand Up @@ -1791,7 +1797,7 @@ extension IRBuilder {
/// variable resides.
///
/// - returns: A value representing the newly inserted global variable.
public func addGlobal(_ name: String, type: IRType, addressSpace: Int? = nil) -> Global {
public func addGlobal(_ name: String, type: IRType, addressSpace: AddressSpace = .zero) -> Global {
return self.module.addGlobal(name, type: type, addressSpace: addressSpace)
}

Expand All @@ -1803,7 +1809,7 @@ extension IRBuilder {
/// variable resides.
///
/// - returns: A value representing the newly inserted global variable.
public func addGlobal(_ name: String, initializer: IRValue, addressSpace: Int? = nil) -> Global {
public func addGlobal(_ name: String, initializer: IRValue, addressSpace: AddressSpace = .zero) -> Global {
return self.module.addGlobal(name, initializer: initializer, addressSpace: addressSpace)
}

Expand Down
2 changes: 1 addition & 1 deletion Sources/LLVM/IRMetadata.swift
Original file line number Diff line number Diff line change
Expand Up @@ -438,7 +438,7 @@ public struct MDNode: IRMetadata {
public init(in context: Context = .global, operands: [IRMetadata]) {
var operands = operands.map { $0.asMetadata() as Optional }
self.llvm = operands.withUnsafeMutableBufferPointer { buf in
return LLVMMDNodeInContext2(context.llvm, buf.baseAddress!, UInt32(buf.count))
return LLVMMDNodeInContext2(context.llvm, buf.baseAddress!, buf.count)
}
}

Expand Down
2 changes: 1 addition & 1 deletion Sources/LLVM/IRType.swift
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ internal func convertType(_ type: LLVMTypeRef) -> IRType {
case LLVMPointerTypeKind:
let pointee = convertType(LLVMGetElementType(type))
let addressSpace = Int(LLVMGetPointerAddressSpace(type))
return PointerType(pointee: pointee, addressSpace: addressSpace)
return PointerType(pointee: pointee, addressSpace: AddressSpace(addressSpace))
case LLVMVectorTypeKind:
let elementType = convertType(LLVMGetElementType(type))
let count = Int(LLVMGetVectorSize(type))
Expand Down
2 changes: 2 additions & 0 deletions Sources/LLVM/IRValue.swift
Original file line number Diff line number Diff line change
Expand Up @@ -107,6 +107,8 @@ public enum IRValueKind {
/// The value is a constant floating pointer value.
case constantFloat
/// The value is a constant pointer to null.
///
/// Note that this pointer is a zero bit-value pointer. Its semantics are dependent upon the address space.
case constantPointerNull
/// The value is a constant none-token value.
case constantTokenNone
Expand Down
7 changes: 2 additions & 5 deletions Sources/LLVM/MetadataAttributes.swift
Original file line number Diff line number Diff line change
Expand Up @@ -496,8 +496,6 @@ public struct DIFlags : OptionSet {
public static let bitField = DIFlags(rawValue: LLVMDIFlagBitField.rawValue)
/// Denotes a `noreturn` function.
public static let noReturn = DIFlags(rawValue: LLVMDIFlagNoReturn.rawValue)
/// Denotes the subprogram for main.
public static let mainSubprogram = DIFlags(rawValue: LLVMDIFlagMainSubprogram.rawValue)
/// Denotes a parameter that is passed by value according to the target's
/// calling convention.
public static let passByValue = DIFlags(rawValue: LLVMDIFlagTypePassByValue.rawValue)
Expand All @@ -508,9 +506,8 @@ public struct DIFlags : OptionSet {
public static let enumClass = DIFlags(rawValue: LLVMDIFlagEnumClass.rawValue)
/// Denotes a thunk function.
public static let thunk = DIFlags(rawValue: LLVMDIFlagThunk.rawValue)
/// Denotes a class that has a trivial default constructor and is trivially
/// copiable.
public static let trivial = DIFlags(rawValue: LLVMDIFlagTrivial.rawValue)
/// Denotes a class that has a non-trivial default constructor or is not trivially copiable.
public static let nonTrivial = DIFlags(rawValue: LLVMDIFlagNonTrivial.rawValue)
/// Denotes an indirect virtual base class.
public static let indirectVirtualBase = DIFlags(rawValue: LLVMDIFlagIndirectVirtualBase.rawValue)
/// The mask for `public`, `private`, and `protected` accessibility.
Expand Down
11 changes: 4 additions & 7 deletions Sources/LLVM/Module.swift
Original file line number Diff line number Diff line change
Expand Up @@ -502,12 +502,9 @@ extension Module {
/// variable resides.
///
/// - returns: A value representing the newly inserted global variable.
public func addGlobal(_ name: String, type: IRType, addressSpace: Int? = nil) -> Global {
let val: LLVMValueRef
if let addressSpace = addressSpace {
val = LLVMAddGlobalInAddressSpace(llvm, type.asLLVM(), name, UInt32(addressSpace))
} else {
val = LLVMAddGlobal(llvm, type.asLLVM(), name)
public func addGlobal(_ name: String, type: IRType, addressSpace: AddressSpace = .zero) -> Global {
guard let val = LLVMAddGlobalInAddressSpace(llvm, type.asLLVM(), name, UInt32(addressSpace.rawValue)) else {
fatalError()
}
return Global(llvm: val)
}
Expand All @@ -520,7 +517,7 @@ extension Module {
/// variable resides.
///
/// - returns: A value representing the newly inserted global variable.
public func addGlobal(_ name: String, initializer: IRValue, addressSpace: Int? = nil) -> Global {
public func addGlobal(_ name: String, initializer: IRValue, addressSpace: AddressSpace = .zero) -> Global {
let global = addGlobal(name, type: initializer.type)
global.initializer = initializer
return global
Expand Down
2 changes: 1 addition & 1 deletion Sources/LLVM/ObjectFile.swift
Original file line number Diff line number Diff line change
Expand Up @@ -184,7 +184,7 @@ public final class MachOUniversalBinaryFile: BinaryFile {
public func objectFile(for architecture: Triple.Architecture) throws -> Slice {
var error: UnsafeMutablePointer<Int8>?
let archName = architecture.rawValue
let archFile: LLVMBinaryRef = LLVMUniversalBinaryCopyObjectForArchitecture(self.llvm, archName, archName.count, &error)
let archFile: LLVMBinaryRef = LLVMMachOUniversalBinaryCopyObjectForArch(self.llvm, archName, archName.count, &error)
if let error = error {
defer { LLVMDisposeMessage(error) }
throw BinaryFileError.couldNotCreate(String(cString: error))
Expand Down
3 changes: 2 additions & 1 deletion Sources/LLVM/PassManager.swift
Original file line number Diff line number Diff line change
Expand Up @@ -212,7 +212,8 @@ public enum Pass {
/// Return a new pass object which transforms invoke instructions into calls,
/// if the callee can *not* unwind the stack.
case pruneEH

/// This transformation attempts to discovery `alloca` allocations of aggregates that can be
/// broken down into component scalar values.
case scalarReplacementOfAggregates
/// This pass removes any function declarations (prototypes) that are not used.
case stripDeadPrototypes
Expand Down
6 changes: 3 additions & 3 deletions Sources/LLVM/PointerType.swift
Original file line number Diff line number Diff line change
Expand Up @@ -16,15 +16,15 @@ public struct PointerType: IRType {
/// Retrieves the type of the value being pointed to.
public let pointee: IRType
/// Retrieves the address space where the pointed-to object resides.
public let addressSpace: Int
public let addressSpace: AddressSpace

/// Creates a `PointerType` from a pointee type and an optional address space.
///
/// - parameter pointee: The type of the pointed-to object.
/// - parameter addressSpace: The optional address space where the pointed-to
/// object resides.
/// - note: The context of this type is taken from it's pointee
public init(pointee: IRType, addressSpace: Int = 0) {
public init(pointee: IRType, addressSpace: AddressSpace = .zero) {
// FIXME: This class of invalid reference is not caught by Module.verify(),
// only `lli`.
if pointee is VoidType {
Expand All @@ -40,7 +40,7 @@ public struct PointerType: IRType {

/// Retrieves the underlying LLVM type object.
public func asLLVM() -> LLVMTypeRef {
return LLVMPointerType(pointee.asLLVM(), UInt32(addressSpace))
return LLVMPointerType(pointee.asLLVM(), UInt32(addressSpace.rawValue))
}
}

Expand Down
24 changes: 6 additions & 18 deletions Sources/LLVM/TargetData.swift
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ public class TargetData {
/// Computes the byte offset of the indexed struct element for a target.
///
/// - parameter element: The index of the element in the given structure to
// compute.
/// compute.
/// - parameter type: The type of the structure to compute the offset with.
///
/// - returns: The offset of the given element within the structure.
Expand Down Expand Up @@ -66,17 +66,9 @@ public class TargetData {
/// - addressSpace: The address space in which to derive the type.
/// - returns: An IntegerType that is the same size as the pointer type
/// on this target.
public func intPointerType(context: Context? = nil, addressSpace: Int? = nil) -> IntType {
let type: LLVMTypeRef
switch (context, addressSpace) {
case let (context?, addressSpace?):
type = LLVMIntPtrTypeForASInContext(context.llvm, llvm, UInt32(addressSpace))
case let (nil, addressSpace?):
type = LLVMIntPtrTypeForAS(llvm, UInt32(addressSpace))
case let (context?, nil):
type = LLVMIntPtrTypeInContext(context.llvm, llvm)
case (nil, nil):
type = LLVMIntPtrType(llvm)
public func intPointerType(context: Context = .global, addressSpace: AddressSpace = .zero) -> IntType {
guard let type = LLVMIntPtrTypeForASInContext(context.llvm, llvm, UInt32(addressSpace.rawValue)) else {
fatalError()
}
return convertType(type) as! IntType // Guaranteed to succeed
}
Expand Down Expand Up @@ -137,12 +129,8 @@ public class TargetData {
/// - parameter addressSpace: The address space in which to compute
/// pointer size.
/// - returns: The size of a pointer in the target address space.
public func pointerSize(addressSpace: Int? = nil) -> Size {
if let addressSpace = addressSpace {
return Size(UInt64(LLVMPointerSizeForAS(llvm, UInt32(addressSpace))))
} else {
return Size(UInt64(LLVMPointerSize(llvm)))
}
public func pointerSize(addressSpace: AddressSpace = .zero) -> Size {
return Size(UInt64(LLVMPointerSizeForAS(llvm, UInt32(addressSpace.rawValue))))
}

/// Returns the offset in bytes between successive objects of the
Expand Down
1 change: 0 additions & 1 deletion Sources/cllvm/shim.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@
#include <llvm-c/LinkTimeOptimizer.h>
#include <llvm-c/lto.h>
#include <llvm-c/Object.h>
#include <llvm-c/OptRemarks.h>
#include <llvm-c/OrcBindings.h>
#include <llvm-c/Support.h>
#include <llvm-c/Target.h>
Expand Down
Loading

0 comments on commit bc303e0

Please sign in to comment.