From: Zack Rusin Date: Fri, 15 Feb 2008 04:50:39 +0000 (-0500) Subject: redo indirection X-Git-Url: https://git.libre-soc.org/?a=commitdiff_plain;h=cf51d5c4210d3301c96947e6e80e71c252bc04d1;p=mesa.git redo indirection make all load's respect indirection --- diff --git a/src/mesa/pipe/llvm/instructionssoa.cpp b/src/mesa/pipe/llvm/instructionssoa.cpp index 1e144393e0f..9c38c64bd10 100644 --- a/src/mesa/pipe/llvm/instructionssoa.cpp +++ b/src/mesa/pipe/llvm/instructionssoa.cpp @@ -43,14 +43,26 @@ std::vector InstructionsSoa::arl(const std::vector i { std::vector res(4); - //Extract the first x (all 4 should be the same) - llvm::Value *x = m_builder.CreateExtractElement(in[0], - m_storage->constantInt(0), - name("extractX")); + //Extract x's + llvm::Value *x1 = m_builder.CreateExtractElement(in[0], + m_storage->constantInt(0), + name("extractX")); + llvm::Value *x2 = m_builder.CreateExtractElement(in[0], + m_storage->constantInt(1), + name("extractX")); + llvm::Value *x3 = m_builder.CreateExtractElement(in[0], + m_storage->constantInt(2), + name("extractX")); + llvm::Value *x4 = m_builder.CreateExtractElement(in[0], + m_storage->constantInt(3), + name("extractX")); //cast it to an unsigned int - x = m_builder.CreateFPToUI(x, IntegerType::get(32), name("xIntCast")); + x1 = m_builder.CreateFPToUI(x1, IntegerType::get(32), name("x1IntCast")); + x2 = m_builder.CreateFPToUI(x2, IntegerType::get(32), name("x2IntCast")); + x3 = m_builder.CreateFPToUI(x3, IntegerType::get(32), name("x3IntCast")); + x4 = m_builder.CreateFPToUI(x4, IntegerType::get(32), name("x4IntCast")); - res[0] = x; + res[0] = vectorFromVals(x1, x2, x3, x4); //only x is valid. the others shouldn't be necessary /* res[1] = Constant::getNullValue(m_floatVecType); @@ -100,3 +112,22 @@ std::vector InstructionsSoa::madd(const std::vector std::vector res = mul(in1, in2); return add(res, in3); } + +std::vector InstructionsSoa::extractVector(llvm::Value *vector) +{ + std::vector res(4); + res[0] = m_builder.CreateExtractElement(vector, + m_storage->constantInt(0), + name("extract1X")); + res[1] = m_builder.CreateExtractElement(vector, + m_storage->constantInt(1), + name("extract2X")); + res[2] = m_builder.CreateExtractElement(vector, + m_storage->constantInt(2), + name("extract3X")); + res[3] = m_builder.CreateExtractElement(vector, + m_storage->constantInt(3), + name("extract4X")); + + return res; +} diff --git a/src/mesa/pipe/llvm/instructionssoa.h b/src/mesa/pipe/llvm/instructionssoa.h index 25ff4ac712a..4169dcbb2eb 100644 --- a/src/mesa/pipe/llvm/instructionssoa.h +++ b/src/mesa/pipe/llvm/instructionssoa.h @@ -57,6 +57,7 @@ public: const std::vector in2); void end(); + std::vector extractVector(llvm::Value *vector); private: const char * name(const char *prefix) const; llvm::Value *vectorFromVals(llvm::Value *x, llvm::Value *y, diff --git a/src/mesa/pipe/llvm/storagesoa.cpp b/src/mesa/pipe/llvm/storagesoa.cpp index f8f4193fd7f..314ffe62dc3 100644 --- a/src/mesa/pipe/llvm/storagesoa.cpp +++ b/src/mesa/pipe/llvm/storagesoa.cpp @@ -136,10 +136,17 @@ std::vector StorageSoa::inputElement(int idx, llvm::Value *indIdx) { std::vector res(4); - res[0] = element(m_input, idx, 0); - res[1] = element(m_input, idx, 1); - res[2] = element(m_input, idx, 2); - res[3] = element(m_input, idx, 3); + if (!indIdx) { + res[0] = element(m_input, idx, 0); + res[1] = element(m_input, idx, 1); + res[2] = element(m_input, idx, 2); + res[3] = element(m_input, idx, 3); + } else { + res[0] = indirectElement(m_input, indIdx, 0); + res[1] = indirectElement(m_input, indIdx, 1); + res[2] = indirectElement(m_input, indIdx, 2); + res[3] = indirectElement(m_input, indIdx, 3); + } return res; } @@ -147,10 +154,18 @@ std::vector StorageSoa::inputElement(int idx, llvm::Value *indIdx) std::vector StorageSoa::constElement(int idx, llvm::Value *indIdx) { std::vector res(4); - llvm::Value *xChannel = elementPointer(m_consts, idx, 0); - llvm::Value *yChannel = elementPointer(m_consts, idx, 1); - llvm::Value *zChannel = elementPointer(m_consts, idx, 2); - llvm::Value *wChannel = elementPointer(m_consts, idx, 3); + llvm::Value *xChannel, *yChannel, *zChannel, *wChannel; + if (!indIdx) { + xChannel = elementPointer(m_consts, idx, 0); + yChannel = elementPointer(m_consts, idx, 1); + zChannel = elementPointer(m_consts, idx, 2); + wChannel = elementPointer(m_consts, idx, 3); + } else { + xChannel = indirectElementPointer(m_consts, indIdx, 0); + yChannel = indirectElementPointer(m_consts, indIdx, 1); + zChannel = indirectElementPointer(m_consts, indIdx, 2); + wChannel = indirectElementPointer(m_consts, indIdx, 3); + } res[0] = alignedArrayLoad(xChannel); res[1] = alignedArrayLoad(yChannel); @@ -164,10 +179,17 @@ std::vector StorageSoa::outputElement(int idx, llvm::Value *indIdx { std::vector res(4); - res[0] = element(m_output, idx, 0); - res[1] = element(m_output, idx, 1); - res[2] = element(m_output, idx, 2); - res[3] = element(m_output, idx, 3); + if (!indIdx) { + res[0] = element(m_output, idx, 0); + res[1] = element(m_output, idx, 1); + res[2] = element(m_output, idx, 2); + res[3] = element(m_output, idx, 3); + } else { + res[0] = indirectElement(m_output, indIdx, 0); + res[1] = indirectElement(m_output, indIdx, 1); + res[2] = indirectElement(m_output, indIdx, 2); + res[3] = indirectElement(m_output, indIdx, 3); + } return res; } @@ -176,22 +198,36 @@ std::vector StorageSoa::tempElement(int idx, llvm::Value *indIdx) { std::vector res(4); - res[0] = element(m_temps, idx, 0); - res[1] = element(m_temps, idx, 1); - res[2] = element(m_temps, idx, 2); - res[3] = element(m_temps, idx, 3); + if (!indIdx) { + res[0] = element(m_temps, idx, 0); + res[1] = element(m_temps, idx, 1); + res[2] = element(m_temps, idx, 2); + res[3] = element(m_temps, idx, 3); + } else { + res[0] = indirectElement(m_temps, indIdx, 0); + res[1] = indirectElement(m_temps, indIdx, 1); + res[2] = indirectElement(m_temps, indIdx, 2); + res[3] = indirectElement(m_temps, indIdx, 3); + } return res; } -std::vector StorageSoa::immediateElement(int idx) +std::vector StorageSoa::immediateElement(int idx, llvm::Value *indIdx) { std::vector res(4); - res[0] = element(m_immediates, idx, 0); - res[1] = element(m_immediates, idx, 1); - res[2] = element(m_immediates, idx, 2); - res[3] = element(m_immediates, idx, 3); + if (!indIdx) { + res[0] = element(m_immediates, idx, 0); + res[1] = element(m_immediates, idx, 1); + res[2] = element(m_immediates, idx, 2); + res[3] = element(m_immediates, idx, 3); + } else { + res[0] = indirectElement(m_immediates, indIdx, 0); + res[1] = indirectElement(m_immediates, indIdx, 1); + res[2] = indirectElement(m_immediates, indIdx, 2); + res[3] = indirectElement(m_immediates, indIdx, 3); + } return res; } @@ -295,7 +331,7 @@ std::vector StorageSoa::load(Argument type, int idx, int swizzle, val = constElement(idx, indIdx); break; case Immediate: - val = immediateElement(idx); + val = immediateElement(idx, indIdx); break; case Address: debug_printf("Address not handled in the load phase!\n"); @@ -365,16 +401,43 @@ void StorageSoa::store(Argument type, int idx, const std::vector & void StorageSoa::addAddress(int idx) { + VectorType *vectorType = VectorType::get(Type::FloatTy, 4); GlobalVariable *val = new GlobalVariable( - /*Type=*/IntegerType::get(32), + /*Type=*/vectorType, /*isConstant=*/false, /*Linkage=*/GlobalValue::ExternalLinkage, /*Initializer=*/0, // has initializer, specified below /*Name=*/name("address"), currentModule()); //val->setInitializer(Constant::getNullValue(IntegerType::get(32))); - val->setInitializer(constantInt(1)); + //val->setInitializer(constantInt(1)); debug_printf("adding to %d\n", idx); m_addresses[idx] = val; } + +llvm::Value * StorageSoa::indirectElementPointer(llvm::Value *ptr, llvm::Value *indIdx, + int channel) const +{ + std::vector indices; + if (m_immediates == ptr) + indices.push_back(constantInt(0)); + indices.push_back(indIdx); + indices.push_back(constantInt(channel)); + + GetElementPtrInst *getElem = new GetElementPtrInst(ptr, + indices.begin(), + indices.end(), + name("ptr"), + m_block); + return getElem; +} + +llvm::Value * StorageSoa::indirectElement(llvm::Value *ptr, llvm::Value *indIdx, + int channel) const +{ + llvm::Value *res = indirectElementPointer(ptr, indIdx, channel); + LoadInst *load = new LoadInst(res, name("element"), false, m_block); + //load->setAlignment(8); + return load; +} diff --git a/src/mesa/pipe/llvm/storagesoa.h b/src/mesa/pipe/llvm/storagesoa.h index ea5db2b4276..ca8fee63407 100644 --- a/src/mesa/pipe/llvm/storagesoa.h +++ b/src/mesa/pipe/llvm/storagesoa.h @@ -80,6 +80,10 @@ private: int channel) const; llvm::Value *element(llvm::Value *ptr, int index, int channel) const; + llvm::Value *indirectElementPointer(llvm::Value *ptr, llvm::Value *indIdx, + int channel) const; + llvm::Value *indirectElement(llvm::Value *ptr, llvm::Value *indIdx, + int channel) const; const char *name(const char *prefix) const; llvm::Value *alignedArrayLoad(llvm::Value *val); llvm::Module *currentModule() const; @@ -89,7 +93,7 @@ private: std::vector constElement(int idx, llvm::Value *indIdx =0); std::vector outputElement(int idx, llvm::Value *indIdx =0); std::vector tempElement(int idx, llvm::Value *indIdx =0); - std::vector immediateElement(int idx); + std::vector immediateElement(int idx, llvm::Value *indIdx =0); private: llvm::BasicBlock *m_block;