source: icGREP/icgrep-devel/icgrep/pablo/pablo_kernel.cpp @ 5233

Last change on this file since 5233 was 5233, checked in by nmedfort, 3 years ago

Bug fixes for Carry Manager and issues reported by Fahad

File size: 5.2 KB
RevLine 
[5057]1/*
2 *  Copyright (c) 2016 International Characters.
3 *  This software is licensed to the public under the Open Software License 3.0.
4 */
5
6#include <pablo/pablo_kernel.h>
[5227]7#include <pablo/codegenstate.h>
[5059]8#include <pablo/pablo_compiler.h>
[5230]9// #include <llvm/Support/Debug.h>
[5202]10#include <pablo/pe_var.h>
11#include <llvm/IR/Verifier.h>
[5217]12#include <IDISA/idisa_builder.h>
[5057]13
14using namespace pablo;
[5059]15using namespace kernel;
[5100]16using namespace parabix;
[5217]17using namespace IDISA;
[5057]18
[5217]19Var * PabloKernel::addInput(const std::string name, Type * const type) {
[5230]20    Var * param = new (mAllocator) Var(mSymbolTable->make(name, iBuilder), type, mAllocator, true);
[5217]21    mInputs.push_back(param);
[5229]22    if (isa<ArrayType>(type) || isa<StreamType>(type)) {
[5227]23        mStreamSetInputs.emplace_back(type, name);
[5217]24    } else {
25        mScalarInputs.emplace_back(type, name);
26    }
27    assert (mStreamSetInputs.size() + mScalarInputs.size() == mInputs.size());
28    return param;
29}
[5202]30
[5217]31Var * PabloKernel::addOutput(const std::string name, Type * const type) {
[5230]32    Var * result = new (mAllocator) Var(mSymbolTable->make(name, iBuilder), type, mAllocator, false);
[5217]33    mOutputs.push_back(result);
[5229]34    if (isa<ArrayType>(type) || isa<StreamType>(type)) {
[5227]35        mStreamSetOutputs.emplace_back(type, name);
[5217]36    } else {
37        mScalarOutputs.emplace_back(type, name);
[5133]38    }
[5217]39    assert (mStreamSetOutputs.size() + mScalarOutputs.size() == mOutputs.size());
40    return result;
41}
[5057]42
[5217]43Var * PabloKernel::makeVariable(PabloAST * name, Type * const type) {
[5230]44    Var * const var = new (mAllocator) Var(name, type, mAllocator);
[5217]45    mVariables.push_back(var);
46    return var;
47}
[5204]48
[5217]49Zeroes * PabloKernel::getNullValue(Type * type) {
50    if (type == nullptr) {
[5229]51        type = getStreamTy();
[5217]52    }
53    for (PabloAST * constant : mConstants) {
54        if (isa<Zeroes>(constant) && constant->getType() == type) {
55            return cast<Zeroes>(constant);
[5202]56        }
[5057]57    }
[5230]58    Zeroes * value = new (mAllocator) Zeroes(type, mAllocator);
[5217]59    mConstants.push_back(value);
60    return value;
[5057]61}
62
[5217]63Ones * PabloKernel::getAllOnesValue(Type * type) {
64    if (type == nullptr) {
[5229]65        type = getStreamTy();
[5217]66    }
67    for (PabloAST * constant : mConstants) {
68        if (isa<Ones>(constant) && constant->getType() == type) {
69            return cast<Ones>(constant);
70        }
71    }
[5230]72    Ones * value = new (mAllocator) Ones(type, mAllocator);
[5217]73    mConstants.push_back(value);
74    return value;
[5202]75}
76
[5076]77void PabloKernel::prepareKernel() {
[5227]78    mPabloCompiler->initializeKernelData();
[5076]79    KernelBuilder::prepareKernel();
[5062]80}
[5059]81
[5074]82void PabloKernel::generateDoBlockMethod() {
[5202]83    auto savePoint = iBuilder->saveIP();
[5227]84    Module * const m = iBuilder->getModule();
85    Function * const f = m->getFunction(mKernelName + doBlock_suffix);
86    Value * const self = &*(f->arg_begin());
87    mPabloCompiler->compile(self, f);
[5183]88    Value * produced = getProducedItemCount(self);
89    produced = iBuilder->CreateAdd(produced, ConstantInt::get(iBuilder->getSizeTy(), iBuilder->getStride()));
90    setProducedItemCount(self, produced);
91    iBuilder->CreateRetVoid();
[5202]92    #ifndef NDEBUG
[5227]93    llvm::verifyFunction(*f, &errs());
[5202]94    #endif
[5063]95    iBuilder->restoreIP(savePoint);
[5057]96}
97
[5074]98void PabloKernel::generateFinalBlockMethod() {
[5202]99    auto savePoint = iBuilder->saveIP();
[5074]100    Module * m = iBuilder->getModule();
[5062]101    Function * doBlockFunction = m->getFunction(mKernelName + doBlock_suffix);
102    Function * finalBlockFunction = m->getFunction(mKernelName + finalBlock_suffix);
[5057]103    iBuilder->SetInsertPoint(BasicBlock::Create(iBuilder->getContext(), "fb_entry", finalBlockFunction, 0));
104    // Final Block arguments: self, remaining, then the standard DoBlock args.
[5059]105    Function::arg_iterator args = finalBlockFunction->arg_begin();
[5057]106    Value * self = &*(args++);
107    Value * remaining = &*(args++);
108    std::vector<Value *> doBlockArgs = {self};
[5059]109    while (args != finalBlockFunction->arg_end()){
[5057]110        doBlockArgs.push_back(&*args++);
111    }
112    // Standard Pablo convention for final block processing: set a bit marking
[5121]113    // the position just past EOF, as well as a mask marking all positions past EOF.
114    setScalarField(self, "EOFbit", iBuilder->bitblock_set_bit(remaining));
115    setScalarField(self, "EOFmask", iBuilder->bitblock_mask_from(remaining));
[5057]116    iBuilder->CreateCall(doBlockFunction, doBlockArgs);
[5183]117    /* Adjust the produced item count */
118    Value * produced = getProducedItemCount(self);
119    produced = iBuilder->CreateSub(produced, ConstantInt::get(iBuilder->getSizeTy(), iBuilder->getStride()));
120    setProducedItemCount(self, iBuilder->CreateAdd(produced, remaining));
[5057]121    iBuilder->CreateRetVoid();
[5202]122    #ifndef NDEBUG
[5227]123    llvm::verifyFunction(*finalBlockFunction, &errs());
[5202]124    #endif
[5063]125    iBuilder->restoreIP(savePoint);
[5057]126}
[5217]127
[5233]128void PabloKernel::initializeKernelState(Value * self) {
129    iBuilder->CreateStore(Constant::getNullValue(mKernelStateType), self);
130}
131
[5217]132PabloKernel::PabloKernel(IDISA::IDISA_Builder * builder, const std::string & kernelName)
133: KernelBuilder(builder, kernelName, {}, {}, {}, {}, {Binding{builder->getBitBlockType(), "EOFbit"}, Binding{builder->getBitBlockType(), "EOFmask"}})
134, mPabloCompiler(new PabloCompiler(this))
[5230]135, mSymbolTable(new SymbolGenerator(mAllocator))
[5217]136, mEntryBlock(PabloBlock::Create(this))
137{
138
139}
140
141PabloKernel::~PabloKernel() {
142    delete mPabloCompiler;
143    delete mSymbolTable;
144}
145
Note: See TracBrowser for help on using the repository browser.