summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/mesa/state_tracker/st_glsl_to_llvm.cpp61
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();
}