fragment shaders through llvm.
##### RULES #####
.c.o:
- $(CC) -c $(INCLUDES) $(CFLAGS) $(DRIVER_DEFINES) $< -o $@
+ $(CC) -c $(INCLUDES) $(LLVM_CFLAGS) $(CFLAGS) $(DRIVER_DEFINES) $< -o $@
.S.o:
$(CC) -c $(INCLUDES) $(CFLAGS) $(DRIVER_DEFINES) $< -o $@
#include "x86/rtasm/x86sse.h"
#include "pipe/tgsi/exec/tgsi_core.h"
-#include "pipe/llvm/llvmtgsi.h"
+#include "pipe/llvm/gallivm.h"
#define DBG_VS 0
#endif
#ifdef MESA_LLVM
vs->llvm_prog = gallivm_from_tgsi(shader->tokens);
- if (!draw->engine)
+ draw->engine = gallivm_global_cpu_engine();
+ if (!draw->engine) {
draw->engine = gallivm_cpu_engine_create(vs->llvm_prog);
+ }
else
gallivm_cpu_jit_compile(draw->engine, vs->llvm_prog);
#endif
#ifdef MESA_LLVM
-#include "pipe/llvm/llvmtgsi.h"
+#include "pipe/llvm/gallivm.h"
#include "pipe/tgsi/exec/tgsi_core.h"
#define DBG 0
*/
#ifdef MESA_LLVM
-#include "llvmtgsi.h"
+#include "gallivm.h"
#include "instructions.h"
#include "storage.h"
}
+static struct gallivm_cpu_engine *CPU = 0;
/*!
This function creates a CPU based execution engine for the given gallivm_prog.
gallivm_cpu_engine should be used as a singleton throughout the library. Before
llvm::Function *func = mod->getFunction("run_vertex_shader");
prog->function = ee->getPointerToFunctionOrStub(func);
+ CPU = cpu;
return cpu;
}
free(cpu);
}
+struct gallivm_cpu_engine * gallivm_global_cpu_engine()
+{
+ return CPU;
+}
+
#endif /* MESA_LLVM */
+
struct gallivm_cpu_engine *gallivm_cpu_engine_create(struct gallivm_prog *prog);
+struct gallivm_cpu_engine *gallivm_global_cpu_engine();
void gallivm_cpu_jit_compile(struct gallivm_cpu_engine *ee, struct gallivm_prog *prog);
void gallivm_cpu_engine_delete(struct gallivm_cpu_engine *ee);
}
}
+#if 0
+static void
+shade_quad_llvm(struct quad_stage *qs,
+ struct quad_header *quad)
+{
+ struct quad_shade_stage *qss = quad_shade_stage(qs);
+ struct softpipe_context *softpipe = qs->softpipe;
+ const float fx = (float) quad->x0;
+ const float fy = (float) quad->y0;
+
+ /* Consts does not require 16 byte alignment. */
+ machine->Consts = softpipe->mapped_constants[PIPE_SHADER_FRAGMENT];
+
+ machine->SamplerUnits = softpipe->sampler_units;
+ machine->InterpCoefs = quad->coef;
+
+ machine->Inputs[0].xyzw[0].f[0] = fx;
+ machine->Inputs[0].xyzw[0].f[1] = fx + 1.0f;
+ machine->Inputs[0].xyzw[0].f[2] = fx;
+ machine->Inputs[0].xyzw[0].f[3] = fx + 1.0f;
+
+ machine->Inputs[0].xyzw[1].f[0] = fy;
+ machine->Inputs[0].xyzw[1].f[1] = fy;
+ machine->Inputs[0].xyzw[1].f[2] = fy + 1.0f;
+ machine->Inputs[0].xyzw[1].f[3] = fy + 1.0f;
+
+ /* run shader */
+#if defined(__i386__) || defined(__386__)
+ machine->Inputs,
+ machine->Outputs,
+ machine->Consts,
+ machine->Temps,
+ machine->InterpCoefs );
+ quad->mask &= ~(machine->Temps[TGSI_EXEC_TEMP_KILMASK_I].xyzw[TGSI_EXEC_TEMP_KILMASK_C].u[0]);
+#endif
+ ga_llvm_prog_exec(softpipe->fs->llvm_prog);
+
+ /* store result color */
+ if (qss->colorOutSlot >= 0) {
+ /* XXX need to handle multiple color outputs someday */
+ assert(qss->stage.softpipe->fs->shader.output_semantic_name[qss->colorOutSlot]
+ == TGSI_SEMANTIC_COLOR);
+ memcpy(
+ quad->outputs.color,
+ &machine->Outputs[qss->colorOutSlot].xyzw[0].f[0],
+ sizeof( quad->outputs.color ) );
+ }
+
+ /* store result Z */
+ if (qss->depthOutSlot >= 0) {
+ /* output[slot] is new Z */
+ uint i;
+ for (i = 0; i < 4; i++) {
+ quad->outputs.depth[i] = machine->Outputs[0].xyzw[2].f[i];
+ }
+ }
+ else {
+ /* copy input Z (which was interpolated by the executor) to output Z */
+ uint i;
+ for (i = 0; i < 4; i++) {
+ quad->outputs.depth[i] = machine->Inputs[0].xyzw[2].f[i];
+ }
+ }
+
+ /* shader may cull fragments */
+ if( quad->mask ) {
+ qs->next->run( qs->next, quad );
+ }
+}
+#endif
/**
* Per-primitive (or per-begin?) setup
#include "x86/rtasm/x86sse.h"
+#ifdef MESA_LLVM
+struct gallivm_prog;
+#endif
+
/**
* Softpipe fs state is derived from pipe_shader_state.
*/
#if defined(__i386__) || defined(__386__)
struct x86_function sse2_program;
#endif
+#ifdef MESA_LLVM
+ struct gallivm_prog *llvm_prog;
+#endif
};
void *
#include "pipe/p_winsys.h"
#include "pipe/draw/draw_context.h"
#include "pipe/tgsi/exec/tgsi_core.h"
+#include "pipe/llvm/gallivm.h"
void * softpipe_create_fs_state(struct pipe_context *pipe,
}
#endif
+#ifdef MESA_LLVM
+ fprintf(stderr, "+++++++++++++++++++++++++++++++++++++++++++++++++\n");
+ state->llvm_prog = gallivm_from_tgsi(state->shader.tokens);
+ if (!gallivm_global_cpu_engine()) {
+ gallivm_cpu_engine_create(state->llvm_prog);
+ }
+ else
+ gallivm_cpu_jit_compile(gallivm_global_cpu_engine(), state->llvm_prog);
+ fprintf(stderr, "+++++++++++++++++++++++++++++++++++++++++++++++++\n");
+#endif
+
return state;
}
LLVMTGSI_SOURCES = \
- pipe/llvm/llvmtgsi.cpp \
+ pipe/llvm/gallivm.cpp \
pipe/llvm/storage.cpp \
pipe/llvm/instructions.cpp
#include "pipe/p_defines.h"
#include "pipe/draw/draw_context.h"
#include "pipe/tgsi/exec/tgsi_core.h"
-#include "pipe/llvm/llvmtgsi.h"
#include "st_context.h"
#include "st_cache.h"
tokensOut, maxTokens);
fs.tokens = tokensOut;
-#ifdef MESA_LLVM
- /*fs.llvm_prog = gallivm_from_tgsi(st->pipe, fs.tokens);*/
-#endif
+
cso = st_cached_fs_state(st, &fs);
stfp->fs = cso;