LLVMValueRef
+lp_declare_intrinsic(LLVMModuleRef module,
+ const char *name,
+ LLVMTypeRef ret_type,
+ LLVMTypeRef *arg_types,
+ unsigned num_args)
+{
+ LLVMTypeRef function_type;
+ LLVMValueRef function;
+
+ assert(!LLVMGetNamedFunction(module, name));
+
+ function_type = LLVMFunctionType(ret_type, arg_types, num_args, 0);
+ function = LLVMAddFunction(module, name, function_type);
+
+ LLVMSetFunctionCallConv(function, LLVMCCallConv);
+ LLVMSetLinkage(function, LLVMExternalLinkage);
+
+ assert(LLVMIsDeclaration(function));
+
+ if(name[0] == 'l' &&
+ name[1] == 'l' &&
+ name[2] == 'v' &&
+ name[3] == 'm' &&
+ name[4] == '.')
+ assert(LLVMGetIntrinsicID(function));
+
+ return function;
+}
+
+
+LLVMValueRef
lp_build_intrinsic(LLVMBuilderRef builder,
const char *name,
LLVMTypeRef ret_type,
LLVMModuleRef module = LLVMGetGlobalParent(LLVMGetBasicBlockParent(LLVMGetInsertBlock(builder)));
LLVMValueRef function;
- assert(num_args <= LP_MAX_FUNC_ARGS);
-
function = LLVMGetNamedFunction(module, name);
if(!function) {
LLVMTypeRef arg_types[LP_MAX_FUNC_ARGS];
unsigned i;
+
+ assert(num_args <= LP_MAX_FUNC_ARGS);
+
for(i = 0; i < num_args; ++i) {
assert(args[i]);
arg_types[i] = LLVMTypeOf(args[i]);
}
- function = LLVMAddFunction(module, name, LLVMFunctionType(ret_type, arg_types, num_args, 0));
- LLVMSetFunctionCallConv(function, LLVMCCallConv);
- LLVMSetLinkage(function, LLVMExternalLinkage);
- }
- assert(LLVMIsDeclaration(function));
- if(name[0] == 'l' &&
- name[1] == 'l' &&
- name[2] == 'v' &&
- name[3] == 'm' &&
- name[4] == '.')
- assert(LLVMGetIntrinsicID(function));
+ function = lp_declare_intrinsic(module, name, ret_type, arg_types, num_args);
+ }
return LLVMBuildCall(builder, function, args, num_args, "");
}
LLVMValueRef
+lp_declare_intrinsic(LLVMModuleRef module,
+ const char *name,
+ LLVMTypeRef ret_type,
+ LLVMTypeRef *arg_types,
+ unsigned num_args);
+
+LLVMValueRef
lp_build_intrinsic(LLVMBuilderRef builder,
const char *name,
LLVMTypeRef ret_type,
struct tgsi_token;
+struct tgsi_sampler;
union lp_type;
struct lp_build_context;
struct lp_build_mask_context;
#include "util/u_memory.h"
#include "lp_screen.h"
+#include "lp_bld_intr.h"
+#include "lp_bld_tgsi.h" /* for lp_build_tgsi_fetch_texel_soa */
#include "lp_jit.h"
static void
-lp_jit_init_types(struct llvmpipe_screen *screen)
+lp_jit_init_globals(struct llvmpipe_screen *screen)
{
/* struct lp_jit_context */
{
screen->context_ptr_type = LLVMPointerType(context_type, 0);
}
+ /* fetch_texel
+ */
+ {
+ LLVMTypeRef ret_type;
+ LLVMTypeRef arg_types[3];
+ LLVMValueRef fetch_texel;
+
+ ret_type = LLVMVoidType();
+ arg_types[0] = LLVMPointerType(LLVMInt8Type(), 0); /* samplers */
+ arg_types[1] = LLVMInt32Type(); /* unit */
+ arg_types[2] = LLVMPointerType(LLVMVectorType(LLVMFloatType(), 4), 0); /* store */
+
+ fetch_texel = lp_declare_intrinsic(screen->module, "fetch_texel",
+ ret_type, arg_types, Elements(arg_types));
+
+ LLVMAddGlobalMapping(screen->engine, fetch_texel, lp_build_tgsi_fetch_texel_soa);
+ }
+
#ifdef DEBUG
LLVMDumpModule(screen->module);
#endif
LLVMAddGVNPass(screen->pass);
LLVMAddCFGSimplificationPass(screen->pass);
- lp_jit_init_types(screen);
+ lp_jit_init_globals(screen);
}
LLVMValueRef fs_out_color[NUM_CHANNELS][LP_MAX_VECTOR_LENGTH];
LLVMValueRef blend_mask;
LLVMValueRef blend_in_color[NUM_CHANNELS];
- LLVMValueRef fetch_texel;
unsigned num_fs;
unsigned i;
unsigned chan;
abort();
}
- /* Tell where the fetch_texel function is, if the shader refers to it.
- * TODO: this should be done elsewhere.
- */
- fetch_texel = LLVMGetNamedFunction(screen->module, "fetch_texel");
- if(fetch_texel) {
- static boolean first_time = TRUE;
- if(first_time) {
- LLVMAddGlobalMapping(screen->engine, fetch_texel, lp_build_tgsi_fetch_texel_soa);
- first_time = FALSE;
- }
- }
-
variant->jit_function = (lp_jit_frag_func)LLVMGetPointerToGlobal(screen->engine, variant->function);
#ifdef DEBUG