Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 1 | #include "llvmtgsi.h" |
| 2 | |
Zack Rusin | b0f8069 | 2007-10-17 11:28:26 -0400 | [diff] [blame] | 3 | #include "instructions.h" |
| 4 | #include "storage.h" |
| 5 | |
Zack Rusin | 5ffdada | 2007-10-15 09:59:19 -0400 | [diff] [blame] | 6 | #include "pipe/p_context.h" |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 7 | #include "pipe/tgsi/exec/tgsi_exec.h" |
| 8 | #include "pipe/tgsi/exec/tgsi_token.h" |
| 9 | #include "pipe/tgsi/exec/tgsi_build.h" |
| 10 | #include "pipe/tgsi/exec/tgsi_util.h" |
| 11 | #include "pipe/tgsi/exec/tgsi_parse.h" |
| 12 | #include "pipe/tgsi/exec/tgsi_dump.h" |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 13 | |
| 14 | #include <llvm/Module.h> |
| 15 | #include <llvm/CallingConv.h> |
| 16 | #include <llvm/Constants.h> |
| 17 | #include <llvm/DerivedTypes.h> |
| 18 | #include <llvm/Instructions.h> |
| 19 | #include <llvm/ModuleProvider.h> |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 20 | #include <llvm/Pass.h> |
| 21 | #include <llvm/PassManager.h> |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 22 | #include <llvm/ParameterAttributes.h> |
| 23 | #include <llvm/Support/PatternMatch.h> |
| 24 | #include <llvm/ExecutionEngine/JIT.h> |
| 25 | #include <llvm/ExecutionEngine/Interpreter.h> |
| 26 | #include <llvm/ExecutionEngine/GenericValue.h> |
| 27 | #include <llvm/Support/MemoryBuffer.h> |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 28 | #include <llvm/LinkAllPasses.h> |
| 29 | #include <llvm/Analysis/Verifier.h> |
| 30 | #include <llvm/Analysis/LoopPass.h> |
| 31 | #include <llvm/Target/TargetData.h> |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 32 | #include <llvm/Bitcode/ReaderWriter.h> |
Zack Rusin | ba88751 | 2007-10-22 08:46:28 -0400 | [diff] [blame] | 33 | |
| 34 | #include <sstream> |
Zack Rusin | b04430e | 2007-10-22 11:00:28 -0400 | [diff] [blame] | 35 | #include <fstream> |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 36 | #include <iostream> |
| 37 | |
Zack Rusin | d76a7b6 | 2007-10-24 08:34:01 -0400 | [diff] [blame^] | 38 | #ifdef MESA_LLVM |
Zack Rusin | ba88751 | 2007-10-22 08:46:28 -0400 | [diff] [blame] | 39 | |
Zack Rusin | b04430e | 2007-10-22 11:00:28 -0400 | [diff] [blame] | 40 | struct ga_llvm_prog { |
| 41 | void *module; |
| 42 | void *function; |
| 43 | int num_consts; |
| 44 | int id; |
| 45 | }; |
| 46 | |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 47 | using namespace llvm; |
| 48 | #include "llvm_base_shader.cpp" |
| 49 | |
| 50 | |
Zack Rusin | ba88751 | 2007-10-22 08:46:28 -0400 | [diff] [blame] | 51 | static int GLOBAL_ID = 0; |
| 52 | |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 53 | static inline void addPass(PassManager &PM, Pass *P) { |
| 54 | // Add the pass to the pass manager... |
| 55 | PM.add(P); |
| 56 | } |
| 57 | |
| 58 | static inline void AddStandardCompilePasses(PassManager &PM) { |
| 59 | PM.add(createVerifierPass()); // Verify that input is correct |
| 60 | |
| 61 | addPass(PM, createLowerSetJmpPass()); // Lower llvm.setjmp/.longjmp |
| 62 | |
| 63 | // If the -strip-debug command line option was specified, do it. |
| 64 | //if (StripDebug) |
| 65 | // addPass(PM, createStripSymbolsPass(true)); |
| 66 | |
| 67 | addPass(PM, createRaiseAllocationsPass()); // call %malloc -> malloc inst |
| 68 | addPass(PM, createCFGSimplificationPass()); // Clean up disgusting code |
| 69 | addPass(PM, createPromoteMemoryToRegisterPass());// Kill useless allocas |
| 70 | addPass(PM, createGlobalOptimizerPass()); // Optimize out global vars |
| 71 | addPass(PM, createGlobalDCEPass()); // Remove unused fns and globs |
| 72 | addPass(PM, createIPConstantPropagationPass());// IP Constant Propagation |
| 73 | addPass(PM, createDeadArgEliminationPass()); // Dead argument elimination |
| 74 | addPass(PM, createInstructionCombiningPass()); // Clean up after IPCP & DAE |
| 75 | addPass(PM, createCFGSimplificationPass()); // Clean up after IPCP & DAE |
| 76 | |
| 77 | addPass(PM, createPruneEHPass()); // Remove dead EH info |
| 78 | |
| 79 | //if (!DisableInline) |
| 80 | addPass(PM, createFunctionInliningPass()); // Inline small functions |
| 81 | addPass(PM, createArgumentPromotionPass()); // Scalarize uninlined fn args |
| 82 | |
| 83 | addPass(PM, createTailDuplicationPass()); // Simplify cfg by copying code |
| 84 | addPass(PM, createInstructionCombiningPass()); // Cleanup for scalarrepl. |
| 85 | addPass(PM, createCFGSimplificationPass()); // Merge & remove BBs |
| 86 | addPass(PM, createScalarReplAggregatesPass()); // Break up aggregate allocas |
| 87 | addPass(PM, createInstructionCombiningPass()); // Combine silly seq's |
| 88 | addPass(PM, createCondPropagationPass()); // Propagate conditionals |
| 89 | |
| 90 | addPass(PM, createTailCallEliminationPass()); // Eliminate tail calls |
| 91 | addPass(PM, createCFGSimplificationPass()); // Merge & remove BBs |
| 92 | addPass(PM, createReassociatePass()); // Reassociate expressions |
| 93 | addPass(PM, createLoopRotatePass()); |
| 94 | addPass(PM, createLICMPass()); // Hoist loop invariants |
| 95 | addPass(PM, createLoopUnswitchPass()); // Unswitch loops. |
| 96 | addPass(PM, createLoopIndexSplitPass()); // Index split loops. |
| 97 | addPass(PM, createInstructionCombiningPass()); // Clean up after LICM/reassoc |
| 98 | addPass(PM, createIndVarSimplifyPass()); // Canonicalize indvars |
| 99 | addPass(PM, createLoopUnrollPass()); // Unroll small loops |
| 100 | addPass(PM, createInstructionCombiningPass()); // Clean up after the unroller |
| 101 | addPass(PM, createGVNPass()); // Remove redundancies |
| 102 | addPass(PM, createSCCPPass()); // Constant prop with SCCP |
| 103 | |
| 104 | // Run instcombine after redundancy elimination to exploit opportunities |
| 105 | // opened up by them. |
| 106 | addPass(PM, createInstructionCombiningPass()); |
| 107 | addPass(PM, createCondPropagationPass()); // Propagate conditionals |
| 108 | |
| 109 | addPass(PM, createDeadStoreEliminationPass()); // Delete dead stores |
| 110 | addPass(PM, createAggressiveDCEPass()); // SSA based 'Aggressive DCE' |
| 111 | addPass(PM, createCFGSimplificationPass()); // Merge & remove BBs |
| 112 | addPass(PM, createSimplifyLibCallsPass()); // Library Call Optimizations |
| 113 | addPass(PM, createDeadTypeEliminationPass()); // Eliminate dead types |
| 114 | addPass(PM, createConstantMergePass()); // Merge dup global constants |
| 115 | } |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 116 | |
| 117 | static void |
| 118 | translate_declaration(llvm::Module *module, |
| 119 | struct tgsi_full_declaration *decl, |
| 120 | struct tgsi_full_declaration *fd) |
| 121 | { |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 122 | /* i think this is going to be a noop */ |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 123 | } |
| 124 | |
| 125 | |
| 126 | static void |
| 127 | translate_immediate(llvm::Module *module, |
| 128 | struct tgsi_full_immediate *imm) |
| 129 | { |
| 130 | } |
| 131 | |
| 132 | |
| 133 | static void |
| 134 | translate_instruction(llvm::Module *module, |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 135 | Storage *storage, |
| 136 | Instructions *instr, |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 137 | struct tgsi_full_instruction *inst, |
| 138 | struct tgsi_full_instruction *fi) |
| 139 | { |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 140 | llvm::Value *inputs[4]; |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 141 | inputs[0] = 0; |
| 142 | inputs[1] = 0; |
| 143 | inputs[2] = 0; |
| 144 | inputs[3] = 0; |
Zack Rusin | b04430e | 2007-10-22 11:00:28 -0400 | [diff] [blame] | 145 | |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 146 | for (int i = 0; i < inst->Instruction.NumSrcRegs; ++i) { |
| 147 | struct tgsi_full_src_register *src = &inst->FullSrcRegisters[i]; |
| 148 | llvm::Value *val = 0; |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 149 | llvm::Value *indIdx = 0; |
| 150 | |
| 151 | if (src->SrcRegister.Indirect) { |
| 152 | indIdx = storage->addrElement(src->SrcRegisterInd.Index); |
| 153 | indIdx = storage->extractIndex(indIdx); |
| 154 | } |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 155 | if (src->SrcRegister.File == TGSI_FILE_CONSTANT) { |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 156 | val = storage->constElement(src->SrcRegister.Index, indIdx); |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 157 | } else if (src->SrcRegister.File == TGSI_FILE_INPUT) { |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 158 | val = storage->inputElement(src->SrcRegister.Index, indIdx); |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 159 | } else if (src->SrcRegister.File == TGSI_FILE_TEMPORARY) { |
| 160 | val = storage->tempElement(src->SrcRegister.Index); |
| 161 | } else { |
Zack Rusin | d76a7b6 | 2007-10-24 08:34:01 -0400 | [diff] [blame^] | 162 | fprintf(stderr, "ERROR: not supported llvm source\n"); |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 163 | return; |
| 164 | } |
| 165 | |
| 166 | if (src->SrcRegister.Extended) { |
| 167 | if (src->SrcRegisterExtSwz.ExtSwizzleX != TGSI_EXTSWIZZLE_X || |
| 168 | src->SrcRegisterExtSwz.ExtSwizzleY != TGSI_EXTSWIZZLE_Y || |
| 169 | src->SrcRegisterExtSwz.ExtSwizzleZ != TGSI_EXTSWIZZLE_Z || |
| 170 | src->SrcRegisterExtSwz.ExtSwizzleW != TGSI_EXTSWIZZLE_W) { |
Zack Rusin | 1248b97 | 2007-10-22 14:01:52 -0400 | [diff] [blame] | 171 | int swizzle = 0; |
| 172 | |
| 173 | if (src->SrcRegisterExtSwz.ExtSwizzleX != TGSI_EXTSWIZZLE_X) |
| 174 | swizzle = src->SrcRegisterExtSwz.ExtSwizzleX * 1000; |
| 175 | else |
| 176 | swizzle = src->SrcRegister.SwizzleX * 1000; |
| 177 | if (src->SrcRegisterExtSwz.ExtSwizzleY != TGSI_EXTSWIZZLE_Y) |
| 178 | swizzle += src->SrcRegisterExtSwz.ExtSwizzleY * 100; |
| 179 | else |
| 180 | swizzle += src->SrcRegister.SwizzleY * 100; |
| 181 | if (src->SrcRegisterExtSwz.ExtSwizzleZ != TGSI_EXTSWIZZLE_Z) |
| 182 | swizzle += src->SrcRegisterExtSwz.ExtSwizzleZ * 10; |
| 183 | else |
| 184 | swizzle += src->SrcRegister.SwizzleZ * 10; |
| 185 | if (src->SrcRegisterExtSwz.ExtSwizzleW != TGSI_EXTSWIZZLE_W) |
| 186 | swizzle += src->SrcRegisterExtSwz.ExtSwizzleW * 1; |
| 187 | else |
| 188 | swizzle += src->SrcRegister.SwizzleW * 1; |
| 189 | /*fprintf(stderr, "EXT XXXXXXXX swizzle x = %d\n", swizzle);*/ |
| 190 | |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 191 | val = storage->shuffleVector(val, swizzle); |
| 192 | } |
| 193 | } else if (src->SrcRegister.SwizzleX != TGSI_SWIZZLE_X || |
| 194 | src->SrcRegister.SwizzleY != TGSI_SWIZZLE_Y || |
| 195 | src->SrcRegister.SwizzleZ != TGSI_SWIZZLE_Z || |
| 196 | src->SrcRegister.SwizzleW != TGSI_SWIZZLE_W) { |
| 197 | int swizzle = src->SrcRegister.SwizzleX * 1000; |
| 198 | swizzle += src->SrcRegister.SwizzleY * 100; |
| 199 | swizzle += src->SrcRegister.SwizzleZ * 10; |
| 200 | swizzle += src->SrcRegister.SwizzleW * 1; |
Zack Rusin | 1248b97 | 2007-10-22 14:01:52 -0400 | [diff] [blame] | 201 | /*fprintf(stderr, "XXXXXXXX swizzle = %d\n", swizzle);*/ |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 202 | val = storage->shuffleVector(val, swizzle); |
| 203 | } |
| 204 | inputs[i] = val; |
| 205 | } |
| 206 | |
Zack Rusin | ba88751 | 2007-10-22 08:46:28 -0400 | [diff] [blame] | 207 | /*if (inputs[0]) |
Zack Rusin | 1248b97 | 2007-10-22 14:01:52 -0400 | [diff] [blame] | 208 | instr->printVector(inputs[0]); |
| 209 | if (inputs[1]) |
| 210 | instr->printVector(inputs[1]);*/ |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 211 | llvm::Value *out = 0; |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 212 | switch (inst->Instruction.Opcode) { |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 213 | case TGSI_OPCODE_ARL: { |
| 214 | out = instr->arl(inputs[0]); |
| 215 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 216 | break; |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 217 | case TGSI_OPCODE_MOV: { |
| 218 | out = inputs[0]; |
| 219 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 220 | break; |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 221 | case TGSI_OPCODE_LIT: { |
Zack Rusin | 3b772a2 | 2007-10-20 16:59:37 -0400 | [diff] [blame] | 222 | out = instr->lit(inputs[0]); |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 223 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 224 | break; |
Zack Rusin | e20294b | 2007-10-17 13:27:25 -0400 | [diff] [blame] | 225 | case TGSI_OPCODE_RCP: { |
| 226 | out = instr->rcp(inputs[0]); |
| 227 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 228 | break; |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 229 | case TGSI_OPCODE_RSQ: { |
| 230 | out = instr->rsq(inputs[0]); |
| 231 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 232 | break; |
| 233 | case TGSI_OPCODE_EXP: |
| 234 | break; |
| 235 | case TGSI_OPCODE_LOG: |
| 236 | break; |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 237 | case TGSI_OPCODE_MUL: { |
| 238 | out = instr->mul(inputs[0], inputs[1]); |
| 239 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 240 | break; |
Zack Rusin | fcbde5e | 2007-10-17 12:13:33 -0400 | [diff] [blame] | 241 | case TGSI_OPCODE_ADD: { |
| 242 | out = instr->add(inputs[0], inputs[1]); |
| 243 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 244 | break; |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 245 | case TGSI_OPCODE_DP3: { |
| 246 | out = instr->dp3(inputs[0], inputs[1]); |
| 247 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 248 | break; |
Zack Rusin | 7abe336 | 2007-10-17 13:34:25 -0400 | [diff] [blame] | 249 | case TGSI_OPCODE_DP4: { |
| 250 | out = instr->dp4(inputs[0], inputs[1]); |
| 251 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 252 | break; |
Zack Rusin | bd38f4d | 2007-10-17 13:46:00 -0400 | [diff] [blame] | 253 | case TGSI_OPCODE_DST: { |
| 254 | out = instr->dst(inputs[0], inputs[1]); |
| 255 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 256 | break; |
Zack Rusin | e9a623d | 2007-10-18 08:12:48 -0400 | [diff] [blame] | 257 | case TGSI_OPCODE_MIN: { |
| 258 | out = instr->min(inputs[0], inputs[1]); |
| 259 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 260 | break; |
Zack Rusin | e9a623d | 2007-10-18 08:12:48 -0400 | [diff] [blame] | 261 | case TGSI_OPCODE_MAX: { |
| 262 | out = instr->max(inputs[0], inputs[1]); |
| 263 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 264 | break; |
Zack Rusin | 743e96e | 2007-10-22 11:27:34 -0400 | [diff] [blame] | 265 | case TGSI_OPCODE_SLT: { |
| 266 | out = instr->slt(inputs[0], inputs[1]); |
| 267 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 268 | break; |
Zack Rusin | 743e96e | 2007-10-22 11:27:34 -0400 | [diff] [blame] | 269 | case TGSI_OPCODE_SGE: { |
| 270 | out = instr->sge(inputs[0], inputs[1]); |
| 271 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 272 | break; |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 273 | case TGSI_OPCODE_MAD: { |
| 274 | out = instr->madd(inputs[0], inputs[1], inputs[2]); |
| 275 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 276 | break; |
Zack Rusin | e20294b | 2007-10-17 13:27:25 -0400 | [diff] [blame] | 277 | case TGSI_OPCODE_SUB: { |
| 278 | out = instr->sub(inputs[0], inputs[1]); |
| 279 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 280 | break; |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 281 | case TGSI_OPCODE_LERP: { |
| 282 | out = instr->lerp(inputs[0], inputs[1], inputs[2]); |
| 283 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 284 | break; |
| 285 | case TGSI_OPCODE_CND: |
| 286 | break; |
| 287 | case TGSI_OPCODE_CND0: |
| 288 | break; |
| 289 | case TGSI_OPCODE_DOT2ADD: |
| 290 | break; |
| 291 | case TGSI_OPCODE_INDEX: |
| 292 | break; |
| 293 | case TGSI_OPCODE_NEGATE: |
| 294 | break; |
Zack Rusin | c6a1beb | 2007-10-18 07:03:37 -0400 | [diff] [blame] | 295 | case TGSI_OPCODE_FRAC: { |
| 296 | out = instr->frc(inputs[0]); |
| 297 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 298 | break; |
| 299 | case TGSI_OPCODE_CLAMP: |
| 300 | break; |
Zack Rusin | c6a1beb | 2007-10-18 07:03:37 -0400 | [diff] [blame] | 301 | case TGSI_OPCODE_FLOOR: { |
| 302 | out = instr->floor(inputs[0]); |
| 303 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 304 | break; |
| 305 | case TGSI_OPCODE_ROUND: |
| 306 | break; |
Zack Rusin | 1c95517 | 2007-10-18 05:51:01 -0400 | [diff] [blame] | 307 | case TGSI_OPCODE_EXPBASE2: { |
| 308 | out = instr->ex2(inputs[0]); |
| 309 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 310 | break; |
Zack Rusin | 3ae767d | 2007-10-18 07:20:27 -0400 | [diff] [blame] | 311 | case TGSI_OPCODE_LOGBASE2: { |
| 312 | out = instr->lg2(inputs[0]); |
| 313 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 314 | break; |
Zack Rusin | e20294b | 2007-10-17 13:27:25 -0400 | [diff] [blame] | 315 | case TGSI_OPCODE_POWER: { |
| 316 | out = instr->pow(inputs[0], inputs[1]); |
| 317 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 318 | break; |
Zack Rusin | ba823b3 | 2007-10-23 07:11:39 -0400 | [diff] [blame] | 319 | case TGSI_OPCODE_CROSSPRODUCT: { |
| 320 | out = instr->cross(inputs[0], inputs[1]); |
| 321 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 322 | break; |
| 323 | case TGSI_OPCODE_MULTIPLYMATRIX: |
| 324 | break; |
Zack Rusin | ba823b3 | 2007-10-23 07:11:39 -0400 | [diff] [blame] | 325 | case TGSI_OPCODE_ABS: { |
| 326 | out = instr->abs(inputs[0]); |
| 327 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 328 | break; |
| 329 | case TGSI_OPCODE_RCC: |
| 330 | break; |
Zack Rusin | 3c558e1 | 2007-10-17 13:38:53 -0400 | [diff] [blame] | 331 | case TGSI_OPCODE_DPH: { |
| 332 | out = instr->dph(inputs[0], inputs[1]); |
| 333 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 334 | break; |
| 335 | case TGSI_OPCODE_COS: |
| 336 | break; |
| 337 | case TGSI_OPCODE_DDX: |
| 338 | break; |
| 339 | case TGSI_OPCODE_DDY: |
| 340 | break; |
| 341 | case TGSI_OPCODE_KILP: |
| 342 | break; |
| 343 | case TGSI_OPCODE_PK2H: |
| 344 | break; |
| 345 | case TGSI_OPCODE_PK2US: |
| 346 | break; |
| 347 | case TGSI_OPCODE_PK4B: |
| 348 | break; |
| 349 | case TGSI_OPCODE_PK4UB: |
| 350 | break; |
| 351 | case TGSI_OPCODE_RFL: |
| 352 | break; |
| 353 | case TGSI_OPCODE_SEQ: |
| 354 | break; |
| 355 | case TGSI_OPCODE_SFL: |
| 356 | break; |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 357 | case TGSI_OPCODE_SGT: { |
| 358 | out = instr->sgt(inputs[0], inputs[1]); |
| 359 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 360 | break; |
| 361 | case TGSI_OPCODE_SIN: |
| 362 | break; |
| 363 | case TGSI_OPCODE_SLE: |
| 364 | break; |
| 365 | case TGSI_OPCODE_SNE: |
| 366 | break; |
| 367 | case TGSI_OPCODE_STR: |
| 368 | break; |
| 369 | case TGSI_OPCODE_TEX: |
| 370 | break; |
| 371 | case TGSI_OPCODE_TXD: |
| 372 | break; |
| 373 | case TGSI_OPCODE_TXP: |
| 374 | break; |
| 375 | case TGSI_OPCODE_UP2H: |
| 376 | break; |
| 377 | case TGSI_OPCODE_UP2US: |
| 378 | break; |
| 379 | case TGSI_OPCODE_UP4B: |
| 380 | break; |
| 381 | case TGSI_OPCODE_UP4UB: |
| 382 | break; |
| 383 | case TGSI_OPCODE_X2D: |
| 384 | break; |
| 385 | case TGSI_OPCODE_ARA: |
| 386 | break; |
| 387 | case TGSI_OPCODE_ARR: |
| 388 | break; |
| 389 | case TGSI_OPCODE_BRA: |
| 390 | break; |
| 391 | case TGSI_OPCODE_CAL: |
| 392 | break; |
| 393 | case TGSI_OPCODE_RET: |
| 394 | break; |
| 395 | case TGSI_OPCODE_SSG: |
| 396 | break; |
| 397 | case TGSI_OPCODE_CMP: |
| 398 | break; |
| 399 | case TGSI_OPCODE_SCS: |
| 400 | break; |
| 401 | case TGSI_OPCODE_TXB: |
| 402 | break; |
| 403 | case TGSI_OPCODE_NRM: |
| 404 | break; |
| 405 | case TGSI_OPCODE_DIV: |
| 406 | break; |
| 407 | case TGSI_OPCODE_DP2: |
| 408 | break; |
| 409 | case TGSI_OPCODE_TXL: |
| 410 | break; |
| 411 | case TGSI_OPCODE_BRK: |
| 412 | break; |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 413 | case TGSI_OPCODE_IF: { |
| 414 | instr->ifop(inputs[0]); |
| 415 | storage->setCurrentBlock(instr->currentBlock()); |
| 416 | return; //just update the state |
| 417 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 418 | break; |
| 419 | case TGSI_OPCODE_LOOP: |
| 420 | break; |
| 421 | case TGSI_OPCODE_REP: |
| 422 | break; |
| 423 | case TGSI_OPCODE_ELSE: |
| 424 | break; |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 425 | case TGSI_OPCODE_ENDIF: { |
| 426 | instr->endif(); |
| 427 | storage->setCurrentBlock(instr->currentBlock()); |
| 428 | storage->popPhiNode(); |
| 429 | return; //just update the state |
| 430 | } |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 431 | break; |
| 432 | case TGSI_OPCODE_ENDLOOP: |
| 433 | break; |
| 434 | case TGSI_OPCODE_ENDREP: |
| 435 | break; |
| 436 | case TGSI_OPCODE_PUSHA: |
| 437 | break; |
| 438 | case TGSI_OPCODE_POPA: |
| 439 | break; |
| 440 | case TGSI_OPCODE_CEIL: |
| 441 | break; |
| 442 | case TGSI_OPCODE_I2F: |
| 443 | break; |
| 444 | case TGSI_OPCODE_NOT: |
| 445 | break; |
| 446 | case TGSI_OPCODE_TRUNC: |
| 447 | break; |
| 448 | case TGSI_OPCODE_SHL: |
| 449 | break; |
| 450 | case TGSI_OPCODE_SHR: |
| 451 | break; |
| 452 | case TGSI_OPCODE_AND: |
| 453 | break; |
| 454 | case TGSI_OPCODE_OR: |
| 455 | break; |
| 456 | case TGSI_OPCODE_MOD: |
| 457 | break; |
| 458 | case TGSI_OPCODE_XOR: |
| 459 | break; |
| 460 | case TGSI_OPCODE_SAD: |
| 461 | break; |
| 462 | case TGSI_OPCODE_TXF: |
| 463 | break; |
| 464 | case TGSI_OPCODE_TXQ: |
| 465 | break; |
| 466 | case TGSI_OPCODE_CONT: |
| 467 | break; |
| 468 | case TGSI_OPCODE_EMIT: |
| 469 | break; |
| 470 | case TGSI_OPCODE_ENDPRIM: |
| 471 | break; |
| 472 | case TGSI_OPCODE_BGNLOOP2: |
| 473 | break; |
| 474 | case TGSI_OPCODE_BGNSUB: |
| 475 | break; |
| 476 | case TGSI_OPCODE_ENDLOOP2: |
| 477 | break; |
| 478 | case TGSI_OPCODE_ENDSUB: |
| 479 | break; |
| 480 | case TGSI_OPCODE_NOISE1: |
| 481 | break; |
| 482 | case TGSI_OPCODE_NOISE2: |
| 483 | break; |
| 484 | case TGSI_OPCODE_NOISE3: |
| 485 | break; |
| 486 | case TGSI_OPCODE_NOISE4: |
| 487 | break; |
| 488 | case TGSI_OPCODE_NOP: |
| 489 | break; |
| 490 | case TGSI_OPCODE_TEXBEM: |
| 491 | break; |
| 492 | case TGSI_OPCODE_TEXBEML: |
| 493 | break; |
| 494 | case TGSI_OPCODE_TEXREG2AR: |
| 495 | break; |
| 496 | case TGSI_OPCODE_TEXM3X2PAD: |
| 497 | break; |
| 498 | case TGSI_OPCODE_TEXM3X2TEX: |
| 499 | break; |
| 500 | case TGSI_OPCODE_TEXM3X3PAD: |
| 501 | break; |
| 502 | case TGSI_OPCODE_TEXM3X3TEX: |
| 503 | break; |
| 504 | case TGSI_OPCODE_TEXM3X3SPEC: |
| 505 | break; |
| 506 | case TGSI_OPCODE_TEXM3X3VSPEC: |
| 507 | break; |
| 508 | case TGSI_OPCODE_TEXREG2GB: |
| 509 | break; |
| 510 | case TGSI_OPCODE_TEXREG2RGB: |
| 511 | break; |
| 512 | case TGSI_OPCODE_TEXDP3TEX: |
| 513 | break; |
| 514 | case TGSI_OPCODE_TEXDP3: |
| 515 | break; |
| 516 | case TGSI_OPCODE_TEXM3X3: |
| 517 | break; |
| 518 | case TGSI_OPCODE_TEXM3X2DEPTH: |
| 519 | break; |
| 520 | case TGSI_OPCODE_TEXDEPTH: |
| 521 | break; |
| 522 | case TGSI_OPCODE_BEM: |
| 523 | break; |
| 524 | case TGSI_OPCODE_M4X3: |
| 525 | break; |
| 526 | case TGSI_OPCODE_M3X4: |
| 527 | break; |
| 528 | case TGSI_OPCODE_M3X3: |
| 529 | break; |
| 530 | case TGSI_OPCODE_M3X2: |
| 531 | break; |
| 532 | case TGSI_OPCODE_NRM4: |
| 533 | break; |
| 534 | case TGSI_OPCODE_CALLNZ: |
| 535 | break; |
| 536 | case TGSI_OPCODE_IFC: |
| 537 | break; |
| 538 | case TGSI_OPCODE_BREAKC: |
| 539 | break; |
| 540 | case TGSI_OPCODE_KIL: |
| 541 | break; |
| 542 | case TGSI_OPCODE_END: |
Zack Rusin | fcbde5e | 2007-10-17 12:13:33 -0400 | [diff] [blame] | 543 | return; |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 544 | break; |
| 545 | default: |
| 546 | fprintf(stderr, "ERROR: Unknown opcode %d\n", |
| 547 | inst->Instruction.Opcode); |
| 548 | assert(0); |
| 549 | break; |
| 550 | } |
| 551 | |
Zack Rusin | fcbde5e | 2007-10-17 12:13:33 -0400 | [diff] [blame] | 552 | if (!out) { |
| 553 | fprintf(stderr, "ERROR: unsupported opcode %d\n", |
| 554 | inst->Instruction.Opcode); |
| 555 | assert(!"Unsupported opcode"); |
| 556 | } |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 557 | |
Zack Rusin | 11bc1f0 | 2007-10-10 07:21:02 -0400 | [diff] [blame] | 558 | switch( inst->Instruction.Saturate ) { |
| 559 | case TGSI_SAT_NONE: |
| 560 | break; |
| 561 | case TGSI_SAT_ZERO_ONE: |
| 562 | /*TXT( "_SAT" );*/ |
| 563 | break; |
| 564 | case TGSI_SAT_MINUS_PLUS_ONE: |
| 565 | /*TXT( "_SAT[-1,1]" );*/ |
| 566 | break; |
| 567 | default: |
| 568 | assert( 0 ); |
| 569 | } |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 570 | |
| 571 | for (int i = 0; i < inst->Instruction.NumDstRegs; ++i) { |
| 572 | struct tgsi_full_dst_register *dst = &inst->FullDstRegisters[i]; |
| 573 | |
| 574 | if (dst->DstRegister.File == TGSI_FILE_OUTPUT) { |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 575 | storage->store(dst->DstRegister.Index, out, dst->DstRegister.WriteMask); |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 576 | } else if (dst->DstRegister.File == TGSI_FILE_TEMPORARY) { |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 577 | storage->setTempElement(dst->DstRegister.Index, out, dst->DstRegister.WriteMask); |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 578 | } else if (dst->DstRegister.File == TGSI_FILE_ADDRESS) { |
| 579 | storage->setAddrElement(dst->DstRegister.Index, out, dst->DstRegister.WriteMask); |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 580 | } else { |
| 581 | fprintf(stderr, "ERROR: unsupported LLVM destination!"); |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 582 | assert(!"wrong destination"); |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 583 | } |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 584 | } |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 585 | } |
| 586 | |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 587 | static llvm::Module * |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 588 | tgsi_to_llvm(struct ga_llvm_prog *prog, const struct tgsi_token *tokens) |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 589 | { |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 590 | llvm::Module *mod = createBaseShader(); |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 591 | struct tgsi_parse_context parse; |
| 592 | struct tgsi_full_instruction fi; |
| 593 | struct tgsi_full_declaration fd; |
| 594 | |
Zack Rusin | 5e02050 | 2007-10-16 05:41:06 -0400 | [diff] [blame] | 595 | Function* shader = mod->getFunction("execute_shader"); |
Zack Rusin | ba88751 | 2007-10-22 08:46:28 -0400 | [diff] [blame] | 596 | std::ostringstream stream; |
| 597 | stream << "execute_shader"; |
| 598 | stream << prog->id; |
| 599 | std::string func_name = stream.str(); |
| 600 | shader->setName(func_name.c_str()); |
Zack Rusin | 5e02050 | 2007-10-16 05:41:06 -0400 | [diff] [blame] | 601 | |
| 602 | Function::arg_iterator args = shader->arg_begin(); |
| 603 | Value *ptr_OUT = args++; |
| 604 | ptr_OUT->setName("OUT"); |
| 605 | Value *ptr_IN = args++; |
| 606 | ptr_IN->setName("IN"); |
| 607 | Value *ptr_CONST = args++; |
| 608 | ptr_CONST->setName("CONST"); |
| 609 | |
| 610 | BasicBlock *label_entry = new BasicBlock("entry", shader, 0); |
| 611 | |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 612 | tgsi_parse_init(&parse, tokens); |
| 613 | |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 614 | fi = tgsi_default_full_instruction(); |
| 615 | fd = tgsi_default_full_declaration(); |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 616 | Storage storage(label_entry, ptr_OUT, ptr_IN, ptr_CONST); |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 617 | Instructions instr(mod, shader, label_entry); |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 618 | while(!tgsi_parse_end_of_tokens(&parse)) { |
| 619 | tgsi_parse_token(&parse); |
| 620 | |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 621 | switch (parse.FullToken.Token.Type) { |
| 622 | case TGSI_TOKEN_TYPE_DECLARATION: |
| 623 | translate_declaration(mod, |
| 624 | &parse.FullToken.FullDeclaration, |
| 625 | &fd); |
| 626 | break; |
| 627 | |
| 628 | case TGSI_TOKEN_TYPE_IMMEDIATE: |
| 629 | translate_immediate(mod, |
| 630 | &parse.FullToken.FullImmediate); |
| 631 | break; |
| 632 | |
| 633 | case TGSI_TOKEN_TYPE_INSTRUCTION: |
Zack Rusin | 3975f34 | 2007-10-17 11:27:46 -0400 | [diff] [blame] | 634 | translate_instruction(mod, &storage, &instr, |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 635 | &parse.FullToken.FullInstruction, |
| 636 | &fi); |
| 637 | break; |
| 638 | |
| 639 | default: |
| 640 | assert(0); |
| 641 | } |
| 642 | } |
| 643 | |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 644 | new ReturnInst(instr.currentBlock()); |
Zack Rusin | 5e02050 | 2007-10-16 05:41:06 -0400 | [diff] [blame] | 645 | |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 646 | tgsi_parse_free(&parse); |
| 647 | |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 648 | prog->num_consts = storage.numConsts(); |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 649 | return mod; |
| 650 | } |
| 651 | |
| 652 | struct ga_llvm_prog * |
Zack Rusin | 5ffdada | 2007-10-15 09:59:19 -0400 | [diff] [blame] | 653 | ga_llvm_from_tgsi(struct pipe_context *pipe, const struct tgsi_token *tokens) |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 654 | { |
Zack Rusin | 6815a9a | 2007-10-21 11:16:01 -0400 | [diff] [blame] | 655 | std::cout << "Creating llvm from: " <<std::endl; |
Zack Rusin | ba88751 | 2007-10-22 08:46:28 -0400 | [diff] [blame] | 656 | ++GLOBAL_ID; |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 657 | struct ga_llvm_prog *ga_llvm = |
| 658 | (struct ga_llvm_prog *)malloc(sizeof(struct ga_llvm_prog)); |
Zack Rusin | ba88751 | 2007-10-22 08:46:28 -0400 | [diff] [blame] | 659 | ga_llvm->id = GLOBAL_ID; |
Zack Rusin | 7abe336 | 2007-10-17 13:34:25 -0400 | [diff] [blame] | 660 | tgsi_dump(tokens, 0); |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 661 | llvm::Module *mod = tgsi_to_llvm(ga_llvm, tokens); |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 662 | ga_llvm->module = mod; |
| 663 | ga_llvm_prog_dump(ga_llvm, 0); |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 664 | /* Run optimization passes over it */ |
| 665 | PassManager passes; |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 666 | passes.add(new TargetData(mod)); |
| 667 | AddStandardCompilePasses(passes); |
Zack Rusin | 6815a9a | 2007-10-21 11:16:01 -0400 | [diff] [blame] | 668 | passes.run(*mod); |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 669 | |
Zack Rusin | 6815a9a | 2007-10-21 11:16:01 -0400 | [diff] [blame] | 670 | llvm::ExistingModuleProvider *mp = new llvm::ExistingModuleProvider(mod); |
Zack Rusin | 5ffdada | 2007-10-15 09:59:19 -0400 | [diff] [blame] | 671 | llvm::ExecutionEngine *ee = 0; |
| 672 | if (!pipe->llvm_execution_engine) { |
| 673 | ee = llvm::ExecutionEngine::create(mp, false); |
| 674 | pipe->llvm_execution_engine = ee; |
| 675 | } else { |
| 676 | ee = (llvm::ExecutionEngine*)pipe->llvm_execution_engine; |
| 677 | ee->addModuleProvider(mp); |
| 678 | } |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 679 | ga_llvm->module = mod; |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 680 | |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 681 | Function *func = mod->getFunction("run_vertex_shader"); |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 682 | ga_llvm->function = ee->getPointerToFunctionOrStub(func); |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 683 | |
Zack Rusin | b04430e | 2007-10-22 11:00:28 -0400 | [diff] [blame] | 684 | ga_llvm_prog_dump(ga_llvm, 0); |
| 685 | |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 686 | return ga_llvm; |
| 687 | } |
| 688 | |
| 689 | void ga_llvm_prog_delete(struct ga_llvm_prog *prog) |
| 690 | { |
| 691 | llvm::Module *mod = static_cast<llvm::Module*>(prog->module); |
| 692 | delete mod; |
| 693 | prog->module = 0; |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 694 | prog->function = 0; |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 695 | free(prog); |
| 696 | } |
| 697 | |
Zack Rusin | 5e02050 | 2007-10-16 05:41:06 -0400 | [diff] [blame] | 698 | typedef void (*vertex_shader_runner)(float (*ainputs)[PIPE_MAX_SHADER_INPUTS][4], |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 699 | float (*dests)[PIPE_MAX_SHADER_INPUTS][4], |
| 700 | float (*aconsts)[4], |
| 701 | int num_vertices, |
| 702 | int num_inputs, |
| 703 | int num_attribs, |
| 704 | int num_consts); |
Zack Rusin | 5ffdada | 2007-10-15 09:59:19 -0400 | [diff] [blame] | 705 | |
Zack Rusin | 2dbba8b | 2007-10-12 13:57:53 -0400 | [diff] [blame] | 706 | int ga_llvm_prog_exec(struct ga_llvm_prog *prog, |
Zack Rusin | 5e02050 | 2007-10-16 05:41:06 -0400 | [diff] [blame] | 707 | float (*inputs)[PIPE_MAX_SHADER_INPUTS][4], |
| 708 | float (*dests)[PIPE_MAX_SHADER_INPUTS][4], |
Zack Rusin | 2dbba8b | 2007-10-12 13:57:53 -0400 | [diff] [blame] | 709 | float (*consts)[4], |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 710 | int num_vertices, |
| 711 | int num_inputs, |
Zack Rusin | 9e6d58f | 2007-10-15 08:12:22 -0400 | [diff] [blame] | 712 | int num_attribs) |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 713 | { |
Zack Rusin | 5ffdada | 2007-10-15 09:59:19 -0400 | [diff] [blame] | 714 | vertex_shader_runner runner = reinterpret_cast<vertex_shader_runner>(prog->function); |
Zack Rusin | d4d8d7c | 2007-10-20 16:55:23 -0400 | [diff] [blame] | 715 | runner(inputs, dests, consts, num_vertices, num_inputs, |
| 716 | num_attribs, prog->num_consts); |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 717 | |
Zack Rusin | b2e5299 | 2007-10-08 10:24:35 -0400 | [diff] [blame] | 718 | return 0; |
| 719 | } |
Zack Rusin | b04430e | 2007-10-22 11:00:28 -0400 | [diff] [blame] | 720 | |
| 721 | void ga_llvm_prog_dump(struct ga_llvm_prog *prog, const char *file_prefix) |
| 722 | { |
| 723 | llvm::Module *mod; |
| 724 | if (!prog || !prog->module) |
| 725 | return; |
| 726 | |
| 727 | mod = static_cast<llvm::Module*>(prog->module); |
| 728 | |
| 729 | if (file_prefix) { |
| 730 | std::ostringstream stream; |
| 731 | stream << file_prefix; |
| 732 | stream << prog->id; |
| 733 | stream << ".ll"; |
| 734 | std::string name = stream.str(); |
| 735 | std::ofstream out(name.c_str()); |
| 736 | if (!out) { |
| 737 | std::cerr<<"Can't open file : "<<stream.str()<<std::endl;; |
| 738 | return; |
| 739 | } |
| 740 | out << (*mod); |
| 741 | out.close(); |
| 742 | } else { |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 743 | std::ostringstream stream; |
| 744 | stream << "execute_shader"; |
| 745 | stream << prog->id; |
| 746 | std::string func_name = stream.str(); |
| 747 | llvm::Function *func = mod->getFunction(func_name.c_str()); |
| 748 | assert(func); |
Zack Rusin | b04430e | 2007-10-22 11:00:28 -0400 | [diff] [blame] | 749 | std::cout<<"; ---------- Start shader "<<prog->id<<std::endl; |
Zack Rusin | 5040eef | 2007-10-24 07:49:24 -0400 | [diff] [blame] | 750 | std::cout<<*func<<std::endl; |
Zack Rusin | b04430e | 2007-10-22 11:00:28 -0400 | [diff] [blame] | 751 | std::cout<<"; ---------- End shader "<<prog->id<<std::endl; |
| 752 | } |
| 753 | } |
Zack Rusin | d76a7b6 | 2007-10-24 08:34:01 -0400 | [diff] [blame^] | 754 | |
| 755 | #endif /* MESA_LLVM */ |