Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
Skip to content

Commit 7ec0d80

Browse files
committed
Add helpers for emitting LLVM IR.
These basically just help to make code a bit more concise and pgindent proof. Author: Andres Freund Discussion: https://postgr.es/m/20170901064131.tazjxwus3k2w3ybh@alap3.anarazel.de
1 parent 250bca7 commit 7ec0d80

File tree

2 files changed

+194
-0
lines changed

2 files changed

+194
-0
lines changed

src/include/jit/llvmjit_emit.h

Lines changed: 193 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,193 @@
1+
/*
2+
* llvmjit_emit.h
3+
* Helpers to make emitting LLVM IR a it more concise and pgindent proof.
4+
*
5+
* Copyright (c) 2018, PostgreSQL Global Development Group
6+
*
7+
* src/include/lib/llvmjit_emit.h
8+
*/
9+
#ifndef LLVMJIT_EMIT_H
10+
#define LLVMJIT_EMIT_H
11+
12+
13+
#include <llvm-c/Core.h>
14+
15+
16+
/*
17+
* Emit a non-LLVM pointer as an LLVM constant.
18+
*/
19+
static inline LLVMValueRef
20+
l_ptr_const(void *ptr, LLVMTypeRef type)
21+
{
22+
LLVMValueRef c = LLVMConstInt(TypeSizeT, (uintptr_t) ptr, false);
23+
24+
return LLVMConstIntToPtr(c, type);
25+
}
26+
27+
/*
28+
* Emit pointer.
29+
*/
30+
static inline LLVMTypeRef
31+
l_ptr(LLVMTypeRef t)
32+
{
33+
return LLVMPointerType(t, 0);
34+
}
35+
36+
/*
37+
* Emit constant integer.
38+
*/
39+
static inline LLVMValueRef
40+
l_int8_const(int8 i)
41+
{
42+
return LLVMConstInt(LLVMInt8Type(), i, false);
43+
}
44+
45+
/*
46+
* Emit constant integer.
47+
*/
48+
static inline LLVMValueRef
49+
l_int16_const(int16 i)
50+
{
51+
return LLVMConstInt(LLVMInt16Type(), i, false);
52+
}
53+
54+
/*
55+
* Emit constant integer.
56+
*/
57+
static inline LLVMValueRef
58+
l_int32_const(int32 i)
59+
{
60+
return LLVMConstInt(LLVMInt32Type(), i, false);
61+
}
62+
63+
/*
64+
* Emit constant integer.
65+
*/
66+
static inline LLVMValueRef
67+
l_int64_const(int64 i)
68+
{
69+
return LLVMConstInt(LLVMInt64Type(), i, false);
70+
}
71+
72+
/*
73+
* Emit constant integer.
74+
*/
75+
static inline LLVMValueRef
76+
l_sizet_const(size_t i)
77+
{
78+
return LLVMConstInt(TypeSizeT, i, false);
79+
}
80+
81+
/*
82+
* Load a pointer member idx from a struct.
83+
*/
84+
static inline LLVMValueRef
85+
l_load_struct_gep(LLVMBuilderRef b, LLVMValueRef v, int32 idx, const char *name)
86+
{
87+
LLVMValueRef v_ptr = LLVMBuildStructGEP(b, v, idx, "");
88+
89+
return LLVMBuildLoad(b, v_ptr, name);
90+
}
91+
92+
/*
93+
* Load value of a pointer, after applying one index operation.
94+
*/
95+
static inline LLVMValueRef
96+
l_load_gep1(LLVMBuilderRef b, LLVMValueRef v, LLVMValueRef idx, const char *name)
97+
{
98+
LLVMValueRef v_ptr = LLVMBuildGEP(b, v, &idx, 1, "");
99+
100+
return LLVMBuildLoad(b, v_ptr, name);
101+
}
102+
103+
/* separate, because pg_attribute_printf(2, 3) can't appear in definition */
104+
static inline LLVMBasicBlockRef l_bb_before_v(LLVMBasicBlockRef r, const char *fmt,...) pg_attribute_printf(2, 3);
105+
106+
/*
107+
* Insert a new basic block, just before r, the name being determined by fmt
108+
* and arguments.
109+
*/
110+
static inline LLVMBasicBlockRef
111+
l_bb_before_v(LLVMBasicBlockRef r, const char *fmt,...)
112+
{
113+
char buf[512];
114+
va_list args;
115+
116+
va_start(args, fmt);
117+
vsnprintf(buf, sizeof(buf), fmt, args);
118+
va_end(args);
119+
120+
return LLVMInsertBasicBlock(r, buf);
121+
}
122+
123+
/* separate, because pg_attribute_printf(2, 3) can't appear in definition */
124+
static inline LLVMBasicBlockRef l_bb_append_v(LLVMValueRef f, const char *fmt,...) pg_attribute_printf(2, 3);
125+
126+
/*
127+
* Insert a new basic block after previous basic blocks, the name being
128+
* determined by fmt and arguments.
129+
*/
130+
static inline LLVMBasicBlockRef
131+
l_bb_append_v(LLVMValueRef f, const char *fmt,...)
132+
{
133+
char buf[512];
134+
va_list args;
135+
136+
va_start(args, fmt);
137+
vsnprintf(buf, sizeof(buf), fmt, args);
138+
va_end(args);
139+
140+
return LLVMAppendBasicBlock(f, buf);
141+
}
142+
143+
/*
144+
* Mark a callsite as readonly.
145+
*/
146+
static inline void
147+
l_callsite_ro(LLVMValueRef f)
148+
{
149+
const char argname[] = "readonly";
150+
LLVMAttributeRef ref;
151+
152+
ref = LLVMCreateStringAttribute(LLVMGetGlobalContext(),
153+
argname,
154+
sizeof(argname) - 1,
155+
NULL, 0);
156+
157+
LLVMAddCallSiteAttribute(f, LLVMAttributeFunctionIndex, ref);
158+
}
159+
160+
/*
161+
* Mark a callsite as alwaysinline.
162+
*/
163+
static inline void
164+
l_callsite_alwaysinline(LLVMValueRef f)
165+
{
166+
const char argname[] = "alwaysinline";
167+
int id;
168+
LLVMAttributeRef attr;
169+
170+
id = LLVMGetEnumAttributeKindForName(argname,
171+
sizeof(argname) - 1);
172+
attr = LLVMCreateEnumAttribute(LLVMGetGlobalContext(), id, 0);
173+
LLVMAddCallSiteAttribute(f, LLVMAttributeFunctionIndex, attr);
174+
}
175+
176+
/*
177+
* Emit code to switch memory context.
178+
*/
179+
static inline LLVMValueRef
180+
l_mcxt_switch(LLVMModuleRef mod, LLVMBuilderRef b, LLVMValueRef nc)
181+
{
182+
const char *cmc = "CurrentMemoryContext";
183+
LLVMValueRef cur;
184+
LLVMValueRef ret;
185+
186+
if (!(cur = LLVMGetNamedGlobal(mod, cmc)))
187+
cur = LLVMAddGlobal(mod, l_ptr(StructMemoryContextData), cmc);
188+
ret = LLVMBuildLoad(b, cur, cmc);
189+
LLVMBuildStore(b, nc, cur);
190+
191+
return ret;
192+
}
193+
#endif

src/tools/pgindent/typedefs.list

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1102,6 +1102,7 @@ LDAPMessage
11021102
LDAPURLDesc
11031103
LDAP_TIMEVAL
11041104
LINE
1105+
LLVMBuilderRef
11051106
LLVMJitContext
11061107
LLVMJitHandle
11071108
LLVMTypeRef

0 commit comments

Comments
 (0)