Changeset 4892


Ignore:
Timestamp:
Dec 14, 2015, 2:01:49 PM (2 years ago)
Author:
cameron
Message:

Move AVX2 specific IDISA function implementations into subclassed builder

Location:
icGREP/icgrep-devel/icgrep
Files:
2 added
5 edited

Legend:

Unmodified
Added
Removed
  • icGREP/icgrep-devel/icgrep/CMakeLists.txt

    r4885 r4892  
    6262
    6363SET(PABLO_SRC pablo/pabloAST.cpp pablo/ps_if.cpp pablo/ps_while.cpp pablo/function.cpp pablo/codegenstate.cpp pablo/builder.cpp pablo/symbol_generator.cpp pablo/printer_pablos.cpp)
    64 SET(PABLO_SRC ${PABLO_SRC} pablo/pablo_compiler.cpp pablo/carry_manager.cpp pablo/carry_data.cpp IDISA/idisa_builder.cpp)
     64SET(PABLO_SRC ${PABLO_SRC} pablo/pablo_compiler.cpp pablo/carry_manager.cpp pablo/carry_data.cpp IDISA/idisa_builder.cpp IDISA/idisa_avx_builder.cpp)
    6565SET(PABLO_SRC ${PABLO_SRC} pablo/analysis/pabloverifier.cpp)
    6666SET(PABLO_SRC ${PABLO_SRC} pablo/optimizers/pablo_simplifier.cpp pablo/optimizers/codemotionpass.cpp pablo/optimizers/distributivepass.cpp pablo/passes/flattenassociativedfg.cpp pablo/passes/factorizedfg.cpp)
  • icGREP/icgrep-devel/icgrep/IDISA/idisa_builder.cpp

    r4891 r4892  
    148148}
    149149
    150 Value * IDISA_Builder:: esimd_bitspread(unsigned fw, Value * bitmask) {
     150Value * IDISA_Builder::esimd_bitspread(unsigned fw, Value * bitmask) {
    151151    unsigned field_count = mBitBlockWidth/fw;
    152152    Type * field_type = mLLVMBuilder->getIntNTy(fw);
     
    193193}
    194194
    195 #if (BLOCK_SIZE==256)
    196 #define SIGNMASK_AVX2
    197 #endif
    198 
    199195Value * IDISA_Builder::hsimd_signmask(unsigned fw, Value * a) {
    200 #ifdef SIGNMASK_AVX2
    201     if (fw == 64) {
    202         Value * signmask_f64func = Intrinsic::getDeclaration(mMod, Intrinsic::x86_avx_movmsk_pd_256);
    203         Type * bitBlock_f64type = VectorType::get(mLLVMBuilder->getDoubleTy(), mBitBlockWidth/64);
    204         Value * a_as_pd = mLLVMBuilder->CreateBitCast(a, bitBlock_f64type);
    205         Value * mask = mLLVMBuilder->CreateCall(signmask_f64func, std::vector<Value *>({a_as_pd}));
    206         return mask;
    207     }
    208     else if (fw == 32) {
    209         Value * signmask_f32func = Intrinsic::getDeclaration(mMod, Intrinsic::x86_avx_movmsk_ps_256);
    210         Type * bitBlock_f32type = VectorType::get(mLLVMBuilder->getFloatTy(), mBitBlockWidth/32);
    211         Value * a_as_ps = mLLVMBuilder->CreateBitCast(a, bitBlock_f32type);
    212         Value * mask = mLLVMBuilder->CreateCall(signmask_f32func, std::vector<Value *>({a_as_ps}));
    213         return mask;
    214     }
    215 #endif
    216196    Value * mask = mLLVMBuilder->CreateICmpSLT(fwCast(fw, a), ConstantAggregateZero::get(fwVectorType(fw)));
    217     return mLLVMBuilder->CreateBitCast(mask, mLLVMBuilder->getIntNTy(mBitBlockWidth/fw));
     197    return mLLVMBuilder->CreateZExt(mLLVMBuilder->CreateBitCast(mask, mLLVMBuilder->getIntNTy(mBitBlockWidth/fw)), mLLVMBuilder->getInt32Ty());
    218198}
    219199
  • icGREP/icgrep-devel/icgrep/IDISA/idisa_builder.h

    r4891 r4892  
    3030
    3131    }
     32    virtual ~IDISA_Builder() {};
    3233
    3334    void initialize(Module * m, IRBuilder <> * b) {
     
    4647    Constant * allOnes() {return mOneInitializer;}
    4748       
    48     Value * simd_add(unsigned fw, Value * a, Value * b);
    49     Value * simd_sub(unsigned fw, Value * a, Value * b);
    50     Value * simd_mult(unsigned fw, Value * a, Value * b);
    51     Value * simd_eq(unsigned fw, Value * a, Value * b);
    52     Value * simd_gt(unsigned fw, Value * a, Value * b);
    53     Value * simd_ugt(unsigned fw, Value * a, Value * b);
    54     Value * simd_lt(unsigned fw, Value * a, Value * b);
    55     Value * simd_ult(unsigned fw, Value * a, Value * b);
    56     Value * simd_max(unsigned fw, Value * a, Value * b);
    57     Value * simd_umax(unsigned fw, Value * a, Value * b);
    58     Value * simd_min(unsigned fw, Value * a, Value * b);
    59     Value * simd_umin(unsigned fw, Value * a, Value * b);
     49    virtual Value * simd_add(unsigned fw, Value * a, Value * b);
     50    virtual Value * simd_sub(unsigned fw, Value * a, Value * b);
     51    virtual Value * simd_mult(unsigned fw, Value * a, Value * b);
     52    virtual Value * simd_eq(unsigned fw, Value * a, Value * b);
     53    virtual Value * simd_gt(unsigned fw, Value * a, Value * b);
     54    virtual Value * simd_ugt(unsigned fw, Value * a, Value * b);
     55    virtual Value * simd_lt(unsigned fw, Value * a, Value * b);
     56    virtual Value * simd_ult(unsigned fw, Value * a, Value * b);
     57    virtual Value * simd_max(unsigned fw, Value * a, Value * b);
     58    virtual Value * simd_umax(unsigned fw, Value * a, Value * b);
     59    virtual Value * simd_min(unsigned fw, Value * a, Value * b);
     60    virtual Value * simd_umin(unsigned fw, Value * a, Value * b);
     61    virtual Value * simd_if(unsigned fw, Value * cond, Value * a, Value * b);
    6062    Value * simd_if(unsigned fw, Value * cond, Value * a, Value * b);
    6163   
    62     Value * simd_slli(unsigned fw, Value * a, unsigned shift);
    63     Value * simd_srli(unsigned fw, Value * a, unsigned shift);
    64     Value * simd_srai(unsigned fw, Value * a, unsigned shift);
     64    virtual Value * simd_slli(unsigned fw, Value * a, unsigned shift);
     65    virtual Value * simd_srli(unsigned fw, Value * a, unsigned shift);
     66    virtual Value * simd_srai(unsigned fw, Value * a, unsigned shift);
    6567   
    66     Value * simd_cttz(unsigned fw, Value * a);
    67     Value * simd_popcount(unsigned fw, Value * a);
     68    virtual Value * simd_cttz(unsigned fw, Value * a);
     69    virtual Value * simd_popcount(unsigned fw, Value * a);
    6870   
    69     Value * esimd_mergeh(unsigned fw, Value * a, Value * b);
    70     Value * esimd_mergel(unsigned fw, Value * a, Value * b);
    71     Value * esimd_bitspread(unsigned fw, Value * bitmask);
     71    virtual Value * esimd_mergeh(unsigned fw, Value * a, Value * b);
     72    virtual Value * esimd_mergel(unsigned fw, Value * a, Value * b);
     73    virtual Value * esimd_bitspread(unsigned fw, Value * bitmask);
    7274   
    73     Value * hsimd_packh(unsigned fw, Value * a, Value * b);
    74     Value * hsimd_packl(unsigned fw, Value * a, Value * b);
    75     Value * hsimd_signmask(unsigned fw, Value * a);
     75    virtual Value * hsimd_packh(unsigned fw, Value * a, Value * b);
     76    virtual Value * hsimd_packl(unsigned fw, Value * a, Value * b);
     77    virtual Value * hsimd_signmask(unsigned fw, Value * a);
    7678
    7779   
    78     Value * mvmd_extract(unsigned fw, Value * a, unsigned fieldIndex);
    79     Value * mvmd_insert(unsigned fw, Value * blk, Value * elt, unsigned fieldIndex);
    80     Value * mvmd_dslli(unsigned fw, Value * a, Value * b, unsigned shift);
     80    virtual Value * mvmd_extract(unsigned fw, Value * a, unsigned fieldIndex);
     81    virtual Value * mvmd_insert(unsigned fw, Value * blk, Value * elt, unsigned fieldIndex);
     82    virtual Value * mvmd_dslli(unsigned fw, Value * a, Value * b, unsigned shift);
    8183   
    82     Value * bitblock_any(Value * a);
     84    virtual Value * bitblock_any(Value * a);
    8385    Value * simd_and(Value * a, Value * b);
    8486    Value * simd_or(Value * a, Value * b);
     
    8789    Value * fwCast(unsigned fw, Value * a);
    8890   
    89 private:
     91protected:
    9092    Module * mMod;
    9193    IRBuilder <> * mLLVMBuilder;
  • icGREP/icgrep-devel/icgrep/pablo/pablo_compiler.cpp

    r4873 r4892  
    1616#include <sstream>
    1717#include <IDISA/idisa_builder.h>
     18#include <IDISA/idisa_avx_builder.h>
    1819#include <llvm/IR/Verifier.h>
    1920#include <llvm/Pass.h>
     
    6061, mCarryManager(nullptr)
    6162, mBitBlockType(bitBlockType)
    62 , iBuilder(mBitBlockType)
     63, iBuilder(nullptr)
    6364, mInputType(nullptr)
    6465, mWhileDepth(0)
     
    6869, mOutputAddressPtr(nullptr)
    6970, mMaxWhileDepth(0) {
     71   
     72   
    7073
    7174}
     
    9093}
    9194
     95// Dynamic AVX2 confirmation
     96#if (BLOCK_SIZE == 256)
     97#define ISPC_LLVM_VERSION ISPC_LLVM_3_6
     98#include <ispc.cpp>
     99#endif
     100   
    92101llvm::Function * PabloCompiler::compile(PabloFunction * function, Module * module) {
    93102
     
    103112    mBuilder = new IRBuilder<>(mMod->getContext());
    104113
    105     iBuilder.initialize(mMod, mBuilder);
    106 
    107     mCarryManager = new CarryManager(mBuilder, &iBuilder);
     114#if (BLOCK_SIZE == 256)
     115    if ((strncmp(lGetSystemISA(), "avx2", 4) == 0)) {
     116        iBuilder = new IDISA::IDISA_AVX2_Builder(mBitBlockType);
     117        //std::cerr << "IDISA_AVX2_Builder selected\n";
     118    }
     119    else{
     120        iBuilder = new IDISA::IDISA_Builder(mBitBlockType);
     121        //std::cerr << "Generic IDISA_Builder selected\n";
     122    }
     123#else   
     124    iBuilder = new IDISA::IDISA_Builder(mBitBlockType);
     125#endif
     126    iBuilder->initialize(mMod, mBuilder);
     127
     128    mCarryManager = new CarryManager(mBuilder, iBuilder);
    108129   
    109130    GenerateFunction(*function);
     
    115136        Value* indices[] = {mBuilder->getInt64(0), mBuilder->getInt32(i)};
    116137        Value * gep = mBuilder->CreateGEP(mInputAddressPtr, indices);
    117         LoadInst * basisBit = mBuilder->CreateAlignedLoad(gep, iBuilder.getBitBlockWidth()/8, false, function->getParameter(i)->getName()->to_string());
     138        LoadInst * basisBit = mBuilder->CreateAlignedLoad(gep, iBuilder->getBitBlockWidth()/8, false, function->getParameter(i)->getName()->to_string());
    118139        mMarkerMap[function->getParameter(i)] = basisBit;
    119140        if (DumpTrace) {
    120             iBuilder.genPrintRegister(function->getParameter(i)->getName()->to_string(), basisBit);
     141            iBuilder->genPrintRegister(function->getParameter(i)->getName()->to_string(), basisBit);
    121142        }
    122143    }
     
    135156
    136157    if (DumpTrace) {
    137         iBuilder.genPrintRegister("mBlockNo", mBuilder->CreateAlignedLoad(mBuilder->CreateBitCast(mCarryManager->getBlockNoPtr(), PointerType::get(mBitBlockType, 0)), iBuilder.getBitBlockWidth()/8, false));
     158        iBuilder->genPrintRegister("mBlockNo", mBuilder->CreateAlignedLoad(mBuilder->CreateBitCast(mCarryManager->getBlockNoPtr(), PointerType::get(mBitBlockType, 0)), iBuilder->getBitBlockWidth()/8, false));
    138159    }
    139160   
     
    149170    // Clean up
    150171    delete mCarryManager; mCarryManager = nullptr;
     172    delete iBuilder; iBuilder = nullptr;
    151173    delete mBuilder; mBuilder = nullptr;
    152174    mMod = nullptr; // don't delete this. It's either owned by the ExecutionEngine or the calling function.
     
    260282        auto f = mMarkerMap.find(assign);
    261283        assert (f != mMarkerMap.end());
    262         phi->addIncoming(iBuilder.allZeroes(), ifEntryBlock);
     284        phi->addIncoming(iBuilder->allZeroes(), ifEntryBlock);
    263285        phi->addIncoming(f->second, ifBodyFinalBlock);
    264286        mMarkerMap[assign] = phi;
     
    323345
    324346    // Terminate the while loop body with a conditional branch back.
    325     mBuilder->CreateCondBr(iBuilder.bitblock_any(compileExpression(whileStatement->getCondition())), whileBodyBlock, whileEndBlock);
     347    mBuilder->CreateCondBr(iBuilder->bitblock_any(compileExpression(whileStatement->getCondition())), whileBodyBlock, whileEndBlock);
    326348
    327349    // and for any Next nodes in the loop body
     
    388410        mBuilder->CreateCall2(externalFunction, mInputAddressPtr, outputStruct);
    389411        Value * outputPtr = mBuilder->CreateGEP(outputStruct, std::vector<Value *>({ mBuilder->getInt32(0), mBuilder->getInt32(0) }));
    390         expr = mBuilder->CreateAlignedLoad(outputPtr, iBuilder.getBitBlockWidth() / 8, false);
     412        expr = mBuilder->CreateAlignedLoad(outputPtr, iBuilder->getBitBlockWidth() / 8, false);
    391413    }
    392414    else if (const And * pablo_and = dyn_cast<And>(stmt)) {
    393         expr = iBuilder.simd_and(compileExpression(pablo_and->getOperand(0)), compileExpression(pablo_and->getOperand(1)));
     415        expr = iBuilder->simd_and(compileExpression(pablo_and->getOperand(0)), compileExpression(pablo_and->getOperand(1)));
    394416    }
    395417    else if (const Or * pablo_or = dyn_cast<Or>(stmt)) {
    396         expr = iBuilder.simd_or(compileExpression(pablo_or->getOperand(0)), compileExpression(pablo_or->getOperand(1)));
     418        expr = iBuilder->simd_or(compileExpression(pablo_or->getOperand(0)), compileExpression(pablo_or->getOperand(1)));
    397419    }
    398420    else if (const Xor * pablo_xor = dyn_cast<Xor>(stmt)) {
    399         expr = iBuilder.simd_xor(compileExpression(pablo_xor->getOperand(0)), compileExpression(pablo_xor->getOperand(1)));
     421        expr = iBuilder->simd_xor(compileExpression(pablo_xor->getOperand(0)), compileExpression(pablo_xor->getOperand(1)));
    400422    }
    401423    else if (const Sel * sel = dyn_cast<Sel>(stmt)) {
    402424        Value* ifMask = compileExpression(sel->getCondition());
    403         Value* ifTrue = iBuilder.simd_and(ifMask, compileExpression(sel->getTrueExpr()));
    404         Value* ifFalse = iBuilder.simd_and(iBuilder.simd_not(ifMask), compileExpression(sel->getFalseExpr()));
    405         expr = iBuilder.simd_or(ifTrue, ifFalse);
     425        Value* ifTrue = iBuilder->simd_and(ifMask, compileExpression(sel->getTrueExpr()));
     426        Value* ifFalse = iBuilder->simd_and(iBuilder->simd_not(ifMask), compileExpression(sel->getFalseExpr()));
     427        expr = iBuilder->simd_or(ifTrue, ifFalse);
    406428    }
    407429    else if (const Not * pablo_not = dyn_cast<Not>(stmt)) {
    408         expr = iBuilder.simd_not(compileExpression(pablo_not->getExpr()));
     430        expr = iBuilder->simd_not(compileExpression(pablo_not->getExpr()));
    409431    }
    410432    else if (const Advance * adv = dyn_cast<Advance>(stmt)) {
     
    417439        Value* strm_value = compileExpression(adv->getExpr());
    418440        int shift = adv->getAdvanceAmount();
    419         expr = iBuilder.simd_slli(64, strm_value, shift);
     441        expr = iBuilder->simd_slli(64, strm_value, shift);
    420442    }
    421443    else if (const MatchStar * mstar = dyn_cast<MatchStar>(stmt)) {
    422444        Value * marker = compileExpression(mstar->getMarker());
    423445        Value * cc = compileExpression(mstar->getCharClass());
    424         Value * marker_and_cc = iBuilder.simd_and(marker, cc);
     446        Value * marker_and_cc = iBuilder->simd_and(marker, cc);
    425447        unsigned carry_index = mstar->getLocalCarryIndex();
    426448        Value * sum = mCarryManager->addCarryInCarryOut(carry_index, marker_and_cc, cc);
    427         expr = iBuilder.simd_or(iBuilder.simd_xor(sum, cc), marker);
     449        expr = iBuilder->simd_or(iBuilder->simd_xor(sum, cc), marker);
    428450    }
    429451    else if (const Mod64MatchStar * mstar = dyn_cast<Mod64MatchStar>(stmt)) {
    430452        Value * marker = compileExpression(mstar->getMarker());
    431453        Value * cc = compileExpression(mstar->getCharClass());
    432         Value * marker_and_cc = iBuilder.simd_and(marker, cc);
    433         Value * sum = iBuilder.simd_add(64, marker_and_cc, cc);
    434         expr = iBuilder.simd_or(iBuilder.simd_xor(sum, cc), marker);
     454        Value * marker_and_cc = iBuilder->simd_and(marker, cc);
     455        Value * sum = iBuilder->simd_add(64, marker_and_cc, cc);
     456        expr = iBuilder->simd_or(iBuilder->simd_xor(sum, cc), marker);
    435457    }
    436458    else if (const ScanThru * sthru = dyn_cast<ScanThru>(stmt)) {
     
    439461        unsigned carry_index = sthru->getLocalCarryIndex();
    440462        Value * sum = mCarryManager->addCarryInCarryOut(carry_index, marker_expr, cc_expr);
    441         expr = iBuilder.simd_and(sum, iBuilder.simd_not(cc_expr));
     463        expr = iBuilder->simd_and(sum, iBuilder->simd_not(cc_expr));
    442464    }
    443465    else if (const Mod64ScanThru * sthru = dyn_cast<Mod64ScanThru>(stmt)) {
    444466        Value * marker_expr = compileExpression(sthru->getScanFrom());
    445467        Value * cc_expr = compileExpression(sthru->getScanThru());
    446         Value * sum = iBuilder.simd_add(64, marker_expr, cc_expr);
    447         expr = iBuilder.simd_and(sum, iBuilder.simd_not(cc_expr));
     468        Value * sum = iBuilder->simd_add(64, marker_expr, cc_expr);
     469        expr = iBuilder->simd_and(sum, iBuilder->simd_not(cc_expr));
    448470    }
    449471    else if (const Count * c = dyn_cast<Count>(stmt)) {
     
    459481    mMarkerMap[stmt] = expr;
    460482    if (DumpTrace) {
    461         iBuilder.genPrintRegister(stmt->getName()->to_string(), expr);
     483        iBuilder->genPrintRegister(stmt->getName()->to_string(), expr);
    462484    }
    463485   
     
    466488Value * PabloCompiler::compileExpression(const PabloAST * expr) {
    467489    if (isa<Ones>(expr)) {
    468         return iBuilder.allOnes();
     490        return iBuilder->allOnes();
    469491    }
    470492    else if (isa<Zeroes>(expr)) {
    471         return iBuilder.allZeroes();
     493        return iBuilder->allZeroes();
    472494    }
    473495    auto f = mMarkerMap.find(expr);
     
    488510    }
    489511    if (LLVM_UNLIKELY(marker->getType()->isPointerTy())) {
    490         marker = mBuilder->CreateAlignedLoad(marker, iBuilder.getBitBlockWidth()/8, false);
     512        marker = mBuilder->CreateAlignedLoad(marker, iBuilder->getBitBlockWidth()/8, false);
    491513    }
    492514    Value* indices[] = {mBuilder->getInt64(0), mBuilder->getInt32(index)};
     
    495517        marker = mBuilder->CreateBitCast(marker, mBitBlockType);
    496518    }
    497     mBuilder->CreateAlignedStore(marker, gep, iBuilder.getBitBlockWidth()/8, false);
    498 }
    499 
    500 }
     519    mBuilder->CreateAlignedStore(marker, gep, iBuilder->getBitBlockWidth()/8, false);
     520}
     521
     522}
  • icGREP/icgrep-devel/icgrep/pablo/pablo_compiler.h

    r4870 r4892  
    103103
    104104    Type* const                   mBitBlockType;
    105     IDISA::IDISA_Builder                iBuilder;
     105    IDISA::IDISA_Builder *              iBuilder;
    106106    PointerType*                        mInputType;
    107107
Note: See TracChangeset for help on using the changeset viewer.