diff options
-rw-r--r-- | src/mesa/state_tracker/st_glsl_to_llvm.cpp | 61 |
1 files changed, 56 insertions, 5 deletions
diff --git a/src/mesa/state_tracker/st_glsl_to_llvm.cpp b/src/mesa/state_tracker/st_glsl_to_llvm.cpp index d077fc496e..0f3020f17f 100644 --- a/src/mesa/state_tracker/st_glsl_to_llvm.cpp +++ b/src/mesa/state_tracker/st_glsl_to_llvm.cpp @@ -1,6 +1,8 @@ #include <llvm/Module.h> #include <llvm/LLVMContext.h> #include <llvm/Support/IRBuilder.h> +#include <llvm/GlobalVariable.h> +#include <llvm/Metadata.h> #include "st_glsl_to_llvm.h" #include "ir_hierarchical_visitor.h" @@ -50,6 +52,8 @@ public: virtual ir_visitor_status visit_enter(ir_assignment *); virtual ir_visitor_status visit_enter(ir_function *); virtual ir_visitor_status visit_leave(ir_function *); + virtual ir_visitor_status visit_enter(ir_expression *); + virtual ir_visitor_status visit_leave(ir_swizzle *); void dump() const; }; @@ -74,6 +78,7 @@ glsl_to_llvm_visitor::find_variable_storage(ir_variable *var) llvm::Type* glsl_to_llvm_visitor::get_type(const glsl_type *const type) { + printf ("type is %s\n", type->name); switch (type->base_type) { case GLSL_TYPE_FLOAT: return llvm::Type::getFloatTy(llvm::getGlobalContext()); @@ -81,6 +86,7 @@ glsl_to_llvm_visitor::get_type(const glsl_type *const type) return llvm::Type::getInt32Ty(llvm::getGlobalContext()); } + return NULL; } @@ -95,9 +101,22 @@ glsl_to_llvm_visitor::visit(ir_variable *ir) { variable_info * res = find_variable_storage(ir); if (!res) { - llvm::Instruction *inst = builder.CreateAlloca(get_type(ir->type), 0, ir->name); - append(inst); - hash_table_insert(variables, new variable_info(ir, PROGRAM_TEMPORARY, 0, inst), ir); + llvm::Value *v; + + switch (ir->mode) { + case ir_var_uniform: + case ir_var_in: + case ir_var_out: + case ir_var_inout: + new llvm::GlobalVariable(module, get_type(ir->type),false, llvm::GlobalVariable::ExternalLinkage, NULL, ir->name); + v = module.getGlobalVariable(ir->name); + module.getOrInsertNamedMetadata("varying")->addOperand(llvm::MDNode::get(llvm::getGlobalContext(), v)); + break; + case ir_var_temporary: + v = builder.CreateAlloca(get_type(ir->type), 0, ir->name); + break; + } + hash_table_insert(variables, new variable_info(ir, PROGRAM_TEMPORARY, 0, v), ir); } return visit_continue; } @@ -107,7 +126,7 @@ ir_visitor_status glsl_to_llvm_visitor::visit(ir_dereference_variable *ir) { variable_info *vi = find_variable_storage(ir->var); - current_value = builder.CreateLoad(vi->val, vi->var->name); + current_value = builder.CreateLoad(vi->val); return visit_continue; } @@ -140,6 +159,38 @@ glsl_to_llvm_visitor::visit_enter(ir_assignment *ir) return visit_continue_with_parent; } +ir_visitor_status +glsl_to_llvm_visitor::visit_enter(ir_expression *ir) +{ + switch (ir->operation) { + case ir_binop_add: + ir->operands[0]->accept(this); + llvm::Value *op1 = current_value; + ir->operands[1]->accept(this); + llvm::Value *op2 = current_value; + current_value = builder.CreateFAdd(op1, op2); + break; + } + + return visit_continue_with_parent; +} + +ir_visitor_status +glsl_to_llvm_visitor::visit_leave(ir_swizzle *ir) +{ + std::vector<llvm::Constant*> mask; + + mask.push_back( llvm::ConstantInt::get(llvm::Type::getInt32Ty(llvm::getGlobalContext()), ir->mask.x)); + mask.push_back( llvm::ConstantInt::get(llvm::Type::getInt32Ty(llvm::getGlobalContext()), ir->mask.y)); + mask.push_back( llvm::ConstantInt::get(llvm::Type::getInt32Ty(llvm::getGlobalContext()), ir->mask.z)); + mask.push_back( llvm::ConstantInt::get(llvm::Type::getInt32Ty(llvm::getGlobalContext()), ir->mask.w)); + mask.resize(ir->type->vector_elements); + + llvm::Value* msk =llvm::ConstantVector::get(mask); + current_value = builder.CreateShuffleVector(msk,current_value,llvm::UndefValue::get(current_value->getType())); + return visit_continue_with_parent; +} + void glsl_to_llvm_visitor::dump() const { @@ -161,5 +212,5 @@ void st_glsl_to_llvm_visit(const exec_list *ir) printf("\n"); } - v.dump(); + v.module.dump(); } |