source: icGREP/icgrep-devel/icgrep/editd/editd_cpu_kernel.cpp @ 5238

Last change on this file since 5238 was 5238, checked in by cameron, 2 years ago

IR_Gen subdirectory for all IR generation utility functions

File size: 6.3 KB
Line 
1/*
2 *  Copyright (c) 2016 International Characters.
3 *  This software is licensed to the public under the Open Software License 3.0.
4 */
5#include "editd_cpu_kernel.h"
6#include <kernels/kernel.h>
7#include <IR_Gen/idisa_builder.h>
8#include <llvm/Support/raw_ostream.h>
9#include <iostream>
10
11namespace kernel {
12using namespace llvm;
13
14void editdCPUKernel::bitblock_advance_ci_co(Value * val, unsigned shift, Value * stideCarryArr, unsigned carryIdx, std::vector<std::vector<Value *>> & adv, std::vector<std::vector<int>> & calculated, int i, int j){   
15    if(!calculated[i][j]){
16        Value * ptr = iBuilder->CreateGEP(stideCarryArr, {iBuilder->getInt32(0), iBuilder->getInt32(carryIdx)});
17        Value * ci = iBuilder->CreateLoad(ptr);
18        std::pair<Value *, Value *> rslt = iBuilder->bitblock_advance(val, ci, shift);
19        iBuilder->CreateStore(std::get<0>(rslt), ptr);
20        adv[i][j] = std::get<1>(rslt);
21        calculated[i][j] = 1;
22    }
23    return;
24}
25
26void editdCPUKernel::generateFinalBlockMethod() {
27    IDISA::IDISA_Builder::InsertPoint savePoint = iBuilder->saveIP();
28    Module * m = iBuilder->getModule();
29    Function * doBlockFunction = m->getFunction(mKernelName + doBlock_suffix);
30    Function * finalBlockFunction = m->getFunction(mKernelName + finalBlock_suffix);
31    iBuilder->SetInsertPoint(BasicBlock::Create(iBuilder->getContext(), "fb_entry", finalBlockFunction, 0));
32    // Final Block arguments: self, remaining, then the standard DoBlock args.
33    Function::arg_iterator args = finalBlockFunction->arg_begin();
34    Value * self = &*(args++);
35    Value * remaining = &*(args++);
36    std::vector<Value *> doBlockArgs = {self};
37    while (args != finalBlockFunction->arg_end()){
38        doBlockArgs.push_back(&*args++);
39    }
40    setScalarField(self, "EOFmask", iBuilder->bitblock_mask_from(remaining));
41    iBuilder->CreateCall(doBlockFunction, doBlockArgs);
42    /* Adjust the produced item count */
43    Value * produced = getProducedItemCount(self);
44    produced = iBuilder->CreateSub(produced, ConstantInt::get(iBuilder->getSizeTy(), iBuilder->getStride()));
45    setProducedItemCount(self, iBuilder->CreateAdd(produced, remaining));
46    iBuilder->CreateRetVoid();
47    iBuilder->restoreIP(savePoint);
48}
49   
50void editdCPUKernel::generateDoBlockMethod() {
51    IDISA::IDISA_Builder::InsertPoint savePoint = iBuilder->saveIP();
52    Module * m = iBuilder->getModule(); 
53
54    Type * const int32ty = iBuilder->getInt32Ty();
55    Type * const int8ty = iBuilder->getInt8Ty();
56
57    Function * doBlockFunction = m->getFunction(mKernelName + doBlock_suffix);
58       
59    BasicBlock * entryBlock = BasicBlock::Create(iBuilder->getContext(), "entry", doBlockFunction, 0);
60   
61    iBuilder->SetInsertPoint(entryBlock);
62
63    Value * kernelStuctParam = getParameter(doBlockFunction, "self");
64    Value * pattStartPtr = getScalarField(kernelStuctParam, "pattStream");
65    Value * stideCarryArr = getScalarField(kernelStuctParam, "srideCarry");
66    Value * blockNo = getScalarField(kernelStuctParam, blockNoScalar);
67    Value * ccStreamPtr = getStreamSetBlockPtr(kernelStuctParam, "CCStream", blockNo);
68    Value * resultStreamPtr = getStreamSetBlockPtr(kernelStuctParam, "ResultStream", blockNo);
69    Value * pattPos = ConstantInt::get(int32ty, 0);
70   
71    unsigned carryIdx = 0;
72
73    std::vector<std::vector<Value *>> e(mPatternLen+1, std::vector<Value *>(mEditDistance+1));
74    std::vector<std::vector<Value *>> adv(mPatternLen, std::vector<Value *>(mEditDistance+1));
75    std::vector<std::vector<int>> calculated(mPatternLen, std::vector<int>(mEditDistance+1));
76    for(unsigned i=0; i<mPatternLen; i++)
77        for(unsigned j=0; j<=mEditDistance; j++)
78            calculated[i][j] = 0;
79    Value * pattPtr = iBuilder->CreateGEP(pattStartPtr, {pattPos});
80    Value * pattCh = iBuilder->CreateLoad(pattPtr);
81    Value * pattIdx = iBuilder->CreateAnd(iBuilder->CreateLShr(pattCh, 1), ConstantInt::get(int8ty, 3));
82    Value * pattStreamPtr = iBuilder->CreateGEP(ccStreamPtr, {iBuilder->getInt32(0), iBuilder->CreateZExt(pattIdx, int32ty)});
83    Value * pattStream = iBuilder->CreateLoad(pattStreamPtr);
84    pattPos = iBuilder->CreateAdd(pattPos, ConstantInt::get(int32ty, 1));
85
86    e[0][0] = pattStream;
87    for(unsigned j = 1; j <= mEditDistance; j++){
88      e[0][j] = iBuilder->allOnes();
89    }
90
91    for(unsigned i = 1; i<mPatternLen; i++){     
92        pattPtr = iBuilder->CreateGEP(pattStartPtr, {pattPos});
93        pattCh = iBuilder->CreateLoad(pattPtr);
94        pattIdx = iBuilder->CreateAnd(iBuilder->CreateLShr(pattCh, 1), ConstantInt::get(int8ty, 3));
95        pattStreamPtr = iBuilder->CreateGEP(ccStreamPtr, {iBuilder->getInt32(0), iBuilder->CreateZExt(pattIdx, int32ty)});
96        pattStream = iBuilder->CreateLoad(pattStreamPtr);
97
98        bitblock_advance_ci_co(e[i-1][0], 1, stideCarryArr, carryIdx++, adv, calculated, i-1, 0);
99        e[i][0] = iBuilder->CreateAnd(adv[i-1][0], pattStream); 
100        for(unsigned j = 1; j<= mEditDistance; j++){
101            bitblock_advance_ci_co(e[i-1][j], 1, stideCarryArr, carryIdx++, adv, calculated, i-1, j);
102            bitblock_advance_ci_co(e[i-1][j-1], 1, stideCarryArr, carryIdx++, adv, calculated, i-1, j-1);
103            bitblock_advance_ci_co(e[i][j-1], 1, stideCarryArr, carryIdx++, adv, calculated, i, j-1);
104            Value * tmp1 = iBuilder->CreateAnd(adv[i-1][j], pattStream);
105            Value * tmp2 = iBuilder->CreateAnd(adv[i-1][j-1], iBuilder->CreateNot(pattStream));
106            Value * tmp3 = iBuilder->CreateOr(adv[i][j-1], e[i-1][j-1]);
107            e[i][j] = iBuilder->CreateOr(iBuilder->CreateOr(tmp1, tmp2), tmp3);
108
109        }
110        pattPos = iBuilder->CreateAdd(pattPos, ConstantInt::get(int32ty, 1));
111    }
112   
113    Value * ptr = iBuilder->CreateGEP(resultStreamPtr, {iBuilder->getInt32(0), iBuilder->getInt32(0)});
114    iBuilder->CreateStore(e[mPatternLen-1][0], ptr);
115    for(unsigned j = 1; j<= mEditDistance; j++){
116        ptr = iBuilder->CreateGEP(resultStreamPtr, {iBuilder->getInt32(0), iBuilder->getInt32(j)});
117        iBuilder->CreateStore(iBuilder->CreateAnd(e[mPatternLen-1][j], iBuilder->CreateNot(e[mPatternLen-1][j-1])), ptr);
118    }
119
120    Value * produced = getProducedItemCount(kernelStuctParam);
121    produced = iBuilder->CreateAdd(produced, ConstantInt::get(iBuilder->getSizeTy(), iBuilder->getStride()));
122    setProducedItemCount(kernelStuctParam, produced); 
123       
124    iBuilder->CreateRetVoid();
125    iBuilder->restoreIP(savePoint);
126}
127
128}
129
130
Note: See TracBrowser for help on using the repository browser.