Changeset 6069


Ignore:
Timestamp:
Jun 7, 2018, 5:16:10 PM (2 months ago)
Author:
cameron
Message:

S2P_21 kernel for transposition of UTF-32; steps toward little-endian bit numbering throughout

Location:
icGREP/icgrep-devel/icgrep
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • icGREP/icgrep-devel/icgrep/cc/cc_compiler.cpp

    r5962 r6069  
    224224    llvm::report_fatal_error(std::string("Invalid Character Set Range: [") + std::to_string(lo) + "," + std::to_string(hi) + "]");
    225225}
     226//#define LITTLE_ENDIAN_BIT_NUMBERING
    226227
    227228inline PabloAST * Parabix_CC_Compiler::getBasisVar(const unsigned i) const {
    228229    assert (i < mEncodingBits);
     230#ifndef LITTLE_ENDIAN_BIT_NUMBERING
    229231    const unsigned index = mEncodingBits - i - 1; assert (index < mEncodingBits);
     232#else
     233    const unsigned index = i;
     234#endif
    230235    assert (mBasisBit[index]);
    231236    return mBasisBit[index];
  • icGREP/icgrep-devel/icgrep/kernels/s2p_kernel.cpp

    r6060 r6069  
    3333    p1 = iBuilder->simd_if(1, hi_mask, iBuilder->simd_slli(16, t0, shift), t1);
    3434}
     35//#define LITTLE_ENDIAN_BIT_NUMBERING
    3536
    3637void s2p(const std::unique_ptr<KernelBuilder> & iBuilder, Value * input[], Value * output[]) {
     
    5354                 iBuilder->simd_himask(4), 2, bit11115555[j], bit33337777[j]);
    5455    }
     56#ifndef LITTLE_ENDIAN_BIT_NUMBERING
    5557    s2p_step(iBuilder, bit00004444[0], bit00004444[1], iBuilder->simd_himask(8), 4, output[0], output[4]);
    5658    s2p_step(iBuilder, bit11115555[0], bit11115555[1], iBuilder->simd_himask(8), 4, output[1], output[5]);
    5759    s2p_step(iBuilder, bit22226666[0], bit22226666[1], iBuilder->simd_himask(8), 4, output[2], output[6]);
    5860    s2p_step(iBuilder, bit33337777[0], bit33337777[1], iBuilder->simd_himask(8), 4, output[3], output[7]);
     61#else
     62    s2p_step(iBuilder, bit00004444[0], bit00004444[1], iBuilder->simd_himask(8), 4, output[7], output[3]);
     63    s2p_step(iBuilder, bit11115555[0], bit11115555[1], iBuilder->simd_himask(8), 4, output[6], output[2]);
     64    s2p_step(iBuilder, bit22226666[0], bit22226666[1], iBuilder->simd_himask(8), 4, output[5], output[1]);
     65    s2p_step(iBuilder, bit33337777[0], bit33337777[1], iBuilder->simd_himask(8), 4, output[4], output[0]);
     66#endif   
    5967}
    6068
     
    159167    }
    160168}
     169   
     170S2P_21Kernel::S2P_21Kernel(const std::unique_ptr<KernelBuilder> & b)
     171: MultiBlockKernel("s2p_21",
     172                   {Binding{b->getStreamSetTy(1, 32), "codeUnitStream", FixedRate(), Principal()}},
     173                   {Binding{b->getStreamSetTy(21, 1), "basisBits"}}, {}, {}, {}) {
     174}
     175
     176
     177void S2P_21Kernel::generateMultiBlockLogic(const std::unique_ptr<KernelBuilder> & kb, Value * const numOfBlocks) {
     178    BasicBlock * entry = kb->GetInsertBlock();
     179    BasicBlock * processBlock = kb->CreateBasicBlock("s2p21_loop");
     180    BasicBlock * s2pDone = kb->CreateBasicBlock("s2p21_done");
     181    Constant * const ZERO = kb->getSize(0);
     182   
     183    kb->CreateBr(processBlock);
     184    kb->SetInsertPoint(processBlock);
     185    PHINode * blockOffsetPhi = kb->CreatePHI(kb->getSizeTy(), 2); // block offset from the base block, e.g. 0, 1, 2, ...
     186    blockOffsetPhi->addIncoming(ZERO, entry);
     187    Value * u32byte0[8];
     188    Value * u32byte1[8];
     189    Value * u32byte2[8];
     190    for (unsigned i = 0; i < 8; i++) {
     191        Value * UTF32units[4];
     192        for (unsigned j = 0; j < 4; j++) {
     193            UTF32units[j] = kb->loadInputStreamPack("codeUnitStream", ZERO, kb->getInt32(4*i + j), blockOffsetPhi);
     194        }
     195        Value * u32lo16_0 = kb->hsimd_packl(32, UTF32units[0], UTF32units[1]);
     196        Value * u32lo16_1 = kb->hsimd_packl(32, UTF32units[2], UTF32units[3]);
     197        Value * u32hi16_0 = kb->hsimd_packh(32, UTF32units[0], UTF32units[1]);
     198        Value * u32hi16_1 = kb->hsimd_packh(32, UTF32units[2], UTF32units[3]);
     199        u32byte0[i] = kb->hsimd_packl(16, u32lo16_0, u32lo16_1);
     200        u32byte1[i] = kb->hsimd_packh(16, u32lo16_0, u32lo16_1);
     201        u32byte2[i] = kb->hsimd_packl(16, u32hi16_0, u32hi16_1);
     202    #ifdef VALIDATE_U32
     203        //  Validation should ensure that none of the high 11 bits are
     204        //  set for any UTF-32 code unit.   We simply combine the bits
     205        //  of code units together with bitwise-or, and then perform a
     206        //  single check at the end.
     207        u32_check = simd_or(u32_check, simd_or(u32hi16_0, u32hi16_1));
     208    #endif
     209    }
     210    Value * basisbits[24];
     211    s2p(kb, u32byte0, basisbits);
     212    s2p(kb, u32byte1, &basisbits[8]);
     213    s2p(kb, u32byte2, &basisbits[16]);
     214    for (unsigned i = 0; i < 21; ++i) {
     215#ifndef LITTLE_ENDIAN_BIT_NUMBERING
     216        const unsigned idx = (i/3) * 3 + 7 - (i & 7);
     217        kb->storeOutputStreamBlock("basisBits", kb->getInt32(idx), blockOffsetPhi, basisbits[i]);
     218#else
     219        kb->storeOutputStreamBlock("basisBits", kb->getInt32(i), blockOffsetPhi, basisbits[i]);
     220#endif
     221    }
     222    Value * nextBlk = kb->CreateAdd(blockOffsetPhi, kb->getSize(1));
     223    blockOffsetPhi->addIncoming(nextBlk, processBlock);
     224    Value * moreToDo = kb->CreateICmpNE(nextBlk, numOfBlocks);
     225    kb->CreateCondBr(moreToDo, processBlock, s2pDone);
     226    kb->SetInsertPoint(s2pDone);
     227}
     228
    161229void S2P_PabloKernel::generatePabloMethod() {
    162230    pablo::PabloBlock * const pb = getEntryScope();
     
    177245    }
    178246    for (unsigned bit = 0; bit < mCodeUnitWidth; bit++) {
     247#ifndef LITTLE_ENDIAN_BIT_NUMBERING
    179248        pb->createAssign(pb->createExtract(getOutputStreamVar("basisBits"), pb->getInteger(bit)), streamSet[steps][mCodeUnitWidth-1-bit]);
     249#else
     250        pb->createAssign(pb->createExtract(getOutputStreamVar("basisBits"), pb->getInteger(bit)), streamSet[steps][bit]);
     251#endif
    180252    }
    181253}
  • icGREP/icgrep-devel/icgrep/kernels/s2p_kernel.h

    r6060 r6069  
    2727};
    2828
     29class S2P_21Kernel final : public MultiBlockKernel {
     30public:
     31    S2P_21Kernel(const std::unique_ptr<kernel::KernelBuilder> & b);
     32    bool isCachable() const override { return true; }
     33    bool hasSignature() const override { return false; }
     34protected:
     35    void generateMultiBlockLogic(const std::unique_ptr<KernelBuilder> & kb, llvm::Value * const numOfStrides) override;
     36};
     37
    2938class S2P_PabloKernel final : public pablo::PabloKernel {
    3039public:
Note: See TracChangeset for help on using the changeset viewer.