11#if SWIFT_PACKAGE
22import cllvm
3+ import llvmshims
34#endif
45
56/// A `Function` represents a named function body in LLVM IR source. Functions
67/// in LLVM IR encapsulate a list of parameters and a sequence of basic blocks
78/// and provide a way to append to that sequence to build out its body.
9+ ///
10+ /// A LLVM function definition contains a list of basic blocks, starting with
11+ /// a privileged first block called the "entry block", and proceeding its
12+ /// terminating instruction to zero or more other basic blocks. The path the
13+ /// flow of control can potentially take, from each block to its terminator
14+ /// and back again, forms the "Control Flow Graph" (CFG) for the function.
15+ ///
16+ /// Additional basic blocks may be created and appended to the function at
17+ /// any time.
18+ ///
19+ /// let module = Module(name: "Example")
20+ /// let builder = IRBuilder(module: module)
21+ /// let fun = builder.addFunction("example",
22+ /// type: FunctionType(argTypes: [],
23+ /// returnType: VoidType()))
24+ /// // Create and append the entry block
25+ /// let entryBB = fun.appendBasicBlock(named: "entry")
26+ /// // Create and append a standalone basic block
27+ /// let freestanding = BasicBlock(name: "freestanding")
28+ /// fun.append(freestanding)
29+ ///
30+ /// A LLVM function always has the type `FunctionType`. This type is used to
31+ /// determine the number and kind of parameters to the function as well as its
32+ /// return value, if any. The parameter values, which would normally enter
33+ /// the entry block, are instead attached to the function and are accessible
34+ /// via the `parameters` property.
35+ ///
36+ /// Calling Convention
37+ /// ==================
38+ ///
39+ /// By default, all functions in LLVM are invoked with the C calling convention
40+ /// but the exact calling convention of both a function declaration and a
41+ /// `call` instruction are fully configurable.
42+ ///
43+ /// let module = Module(name: "Example")
44+ /// let builder = IRBuilder(module: module)
45+ /// let fun = builder.addFunction("example",
46+ /// type: FunctionType(argTypes: [],
47+ /// returnType: VoidType()))
48+ /// // Switch to swiftcc
49+ /// fun.callingConvention = .swift
50+ ///
51+ /// The calling convention of a function and a corresponding call instruction
52+ /// must match or the result is undefined.
53+ ///
54+ /// Sections
55+ /// ========
56+ ///
57+ /// A function may optionally state the section in the object file the function
58+ /// should reside in through the use of a metadata attachment. This can be
59+ /// useful to satisfy target-specific data layout constraints, or to provide
60+ /// some hints to optimizers and linkers. LLVMSwift provides a convenience
61+ /// object called an `MDBuilder` to assist in the creation of this metadata.
62+ ///
63+ /// let mdBuilder = MDBuilder()
64+ /// // __attribute__((hot))
65+ /// let hotAttr = mdBuilder.buildFunctionSectionPrefix(".hot")
66+ ///
67+ /// let module = Module(name: "Example")
68+ /// let builder = IRBuilder(module: module)
69+ /// let fun = builder.addFunction("example",
70+ /// type: FunctionType(argTypes: [],
71+ /// returnType: VoidType()))
72+ /// // Attach the metadata
73+ /// fun.addMetadata(hotAttr, kind: .sectionPrefix)
74+ ///
75+ /// For targets that support it, a function may also specify a COMDAT section.
76+ ///
77+ /// fun.comdat = module.comdat(named: "example")
78+ ///
79+ /// Debug Information
80+ /// =================
81+ ///
82+ /// A function may also carry debug information through special subprogram
83+ /// nodes. These nodes are intended to capture the structure of the function
84+ /// as it appears in the source so that it is available for inspection by a
85+ /// debugger. See `DIBuilderr.buildFunction` for more information.
886public class Function : IRGlobal {
987 internal let llvm : LLVMValueRef
1088 internal init ( llvm: LLVMValueRef ) {
@@ -26,17 +104,6 @@ public class Function: IRGlobal {
26104 }
27105
28106 /// Retrieves the entry block of this function.
29- ///
30- /// The first basic block in a function is special in two ways: it is
31- /// immediately executed on entrance to the function, and it is not allowed to
32- /// have predecessor basic blocks (i.e. there can not be any branches to the
33- /// entry block of a function). Because the block can have no predecessors, it
34- /// also cannot have any PHI nodes.
35- ///
36- /// The entry block is also special in that any static allocas emitted into it
37- /// influence the layout of the stack frame of the function at code generation
38- /// time. It is therefore often more efficient to emit static allocas in the
39- /// entry block than anywhere else in the function.
40107 public var entryBlock : BasicBlock ? {
41108 guard let blockRef = LLVMGetEntryBasicBlock ( llvm) else { return nil }
42109 return BasicBlock ( llvm: blockRef)
@@ -78,7 +145,7 @@ public class Function: IRGlobal {
78145
79146 /// Computes the address of the specified basic block in this function.
80147 ///
81- /// Taking the address of the entry block is illegal.
148+ /// - WARNING: Taking the address of the entry block is illegal.
82149 ///
83150 /// This value only has defined behavior when used as an operand to the
84151 /// `indirectbr` instruction, or for comparisons against null. Pointer
@@ -170,6 +237,13 @@ public class Function: IRGlobal {
170237 return BasicBlock ( llvm: block)
171238 }
172239
240+ /// Appends the named basic block to the body of this function.
241+ ///
242+ /// - parameter basicBlock: The block to append.
243+ public func append( _ basicBlock: BasicBlock ) {
244+ LLVMAppendExistingBasicBlock ( llvm, basicBlock. asLLVM ( ) )
245+ }
246+
173247 /// Deletes the function from its containing module.
174248 /// - note: This does not remove calls to this function from the
175249 /// module. Ensure you have removed all instructions that reference
0 commit comments