@@ -200,10 +200,8 @@ public enum AtomicOrdering: Comparable {
200200 . sequentiallyConsistent: LLVMAtomicOrderingSequentiallyConsistent,
201201 ]
202202
203- public static func == ( lhs: AtomicOrdering , rhs: AtomicOrdering ) -> Bool {
204- return lhs. llvm == rhs. llvm
205- }
206-
203+ /// Returns whether the left atomic ordering is strictly weaker than the
204+ /// right atomic order.
207205 public static func < ( lhs: AtomicOrdering , rhs: AtomicOrdering ) -> Bool {
208206 return lhs. llvm. rawValue < rhs. llvm. rawValue
209207 }
@@ -1094,25 +1092,40 @@ public class IRBuilder {
10941092 return LLVMBuildAlloca ( llvm, type. asLLVM ( ) , name)
10951093 }
10961094
1097- /// Build a store instruction that stores the first value into the location
1095+ /// Builds a store instruction that stores the first value into the location
10981096 /// given in the second value.
10991097 ///
1098+ /// - parameter val: The source value.
1099+ /// - parameter ptr: The destination pointer to store into.
1100+ /// - parameter ordering: The ordering effect of the fence for this store,
1101+ /// if any. Defaults to a nonatomic store.
1102+ /// - parameter volatile: Whether this is a store to a volatile memory location.
1103+ ///
11001104 /// - returns: A value representing `void`.
11011105 @discardableResult
1102- public func buildStore( _ val: IRValue , to ptr: IRValue ) -> IRValue {
1103- return LLVMBuildStore ( llvm, val. asLLVM ( ) , ptr. asLLVM ( ) )
1106+ public func buildStore( _ val: IRValue , to ptr: IRValue , ordering: AtomicOrdering = . notAtomic, volatile: Bool = false ) -> IRValue {
1107+ let storeInst = LLVMBuildStore ( llvm, val. asLLVM ( ) , ptr. asLLVM ( ) ) !
1108+ LLVMSetOrdering ( storeInst, ordering. llvm)
1109+ LLVMSetVolatile ( storeInst, volatile. llvm)
1110+ return storeInst
11041111 }
11051112
11061113 /// Builds a load instruction that loads a value from the location in the
11071114 /// given value.
11081115 ///
11091116 /// - parameter ptr: The pointer value to load from.
1117+ /// - parameter ordering: The ordering effect of the fence for this load,
1118+ /// if any. Defaults to a nonatomic load.
1119+ /// - parameter volatile: Whether this is a load from a volatile memory location.
11101120 /// - parameter name: The name for the newly inserted instruction.
11111121 ///
11121122 /// - returns: A value representing the result of a load from the given
11131123 /// pointer value.
1114- public func buildLoad( _ ptr: IRValue , name: String = " " ) -> IRValue {
1115- return LLVMBuildLoad ( llvm, ptr. asLLVM ( ) , name)
1124+ public func buildLoad( _ ptr: IRValue , ordering: AtomicOrdering = . notAtomic, volatile: Bool = false , name: String = " " ) -> IRValue {
1125+ let loadInst = LLVMBuildLoad ( llvm, ptr. asLLVM ( ) , name) !
1126+ LLVMSetOrdering ( loadInst, ordering. llvm)
1127+ LLVMSetVolatile ( loadInst, volatile. llvm)
1128+ return loadInst
11161129 }
11171130
11181131 /// Builds a `GEP` (Get Element Pointer) instruction with a resultant value
@@ -1706,6 +1719,48 @@ public class IRBuilder {
17061719 return Alias ( llvm: LLVMAddAlias ( module. llvm, type. asLLVM ( ) , aliasee. asLLVM ( ) , name) )
17071720 }
17081721
1722+ // MARK: Inline Assembly
1723+
1724+ /// Builds a value representing an inline assembly expression (as opposed to
1725+ /// module-level inline assembly).
1726+ ///
1727+ /// LLVM represents inline assembler as a template string (containing the
1728+ /// instructions to emit), a list of operand constraints (stored as a string),
1729+ /// and some flags.
1730+ ///
1731+ /// The template string supports argument substitution of the operands using
1732+ /// "$" followed by a number, to indicate substitution of the given
1733+ /// register/memory location, as specified by the constraint string.
1734+ /// "${NUM:MODIFIER}" may also be used, where MODIFIER is a target-specific
1735+ /// annotation for how to print the operand (see [Asm Template Argument
1736+ /// Modifiers](https://llvm.org/docs/LangRef.html#inline-asm-modifiers)).
1737+ ///
1738+ /// LLVM’s support for inline asm is modeled closely on the requirements of
1739+ /// Clang’s GCC-compatible inline-asm support. Thus, the feature-set and the
1740+ /// constraint and modifier codes are similar or identical to those in GCC’s
1741+ /// inline asm support.
1742+ ///
1743+ /// However, the syntax of the template and constraint strings is not the
1744+ /// same as the syntax accepted by GCC and Clang, and, while most constraint
1745+ /// letters are passed through as-is by Clang, some get translated to other
1746+ /// codes when converting from the C source to the LLVM assembly.
1747+ ///
1748+ /// - parameter asm: The inline assembly expression template string.
1749+ /// - parameter type: The type of the parameters and return value of the
1750+ /// assembly expression string.
1751+ /// - parameter constraints: A comma-separated string, each element containing
1752+ /// one or more constraint codes.
1753+ /// - parameter hasSideEffects: Whether this inline asm expression has
1754+ /// side effects. Defaults to `false`.
1755+ /// - parameter needsAlignedStack: Whether the function containing the
1756+ /// asm needs to align its stack conservatively. Defaults to `true`.
1757+ ///
1758+ /// - returns: A representation of the newly created inline assembly
1759+ /// expression.
1760+ public func buildInlineAssembly( _ asm: String , type: FunctionType , constraints: String = " " , hasSideEffects: Bool = true , needsAlignedStack: Bool = true ) -> IRValue {
1761+ return LLVMConstInlineAsm ( type. asLLVM ( ) , asm, constraints, hasSideEffects. llvm, needsAlignedStack. llvm)
1762+ }
1763+
17091764 deinit {
17101765 LLVMDisposeBuilder ( llvm)
17111766 }
0 commit comments