Ignore:
Timestamp:
Nov 6, 2016, 8:37:11 PM (3 years ago)
Author:
nmedfort
Message:

Initial work on adding types to PabloAST and mutable Var objects.

File:
1 edited

Legend:

Unmodified
Added
Removed
  • icGREP/icgrep-devel/icgrep/kernels/kernel.cpp

    r5194 r5202  
    1818KernelBuilder::KernelBuilder(IDISA::IDISA_Builder * builder,
    1919                                 std::string kernelName,
    20                                  std::vector<StreamSetBinding> stream_inputs,
    21                                  std::vector<StreamSetBinding> stream_outputs,
    22                                  std::vector<ScalarBinding> scalar_parameters,
    23                                  std::vector<ScalarBinding> scalar_outputs,
    24                                  std::vector<ScalarBinding> internal_scalars) :
     20                                 std::vector<Binding> stream_inputs,
     21                                 std::vector<Binding> stream_outputs,
     22                                 std::vector<Binding> scalar_parameters,
     23                                 std::vector<Binding> scalar_outputs,
     24                                 std::vector<Binding> internal_scalars) :
    2525    KernelInterface(builder, kernelName, stream_inputs, stream_outputs, scalar_parameters, scalar_outputs, internal_scalars) {}
    2626
    27 void KernelBuilder::addScalar(Type * t, std::string scalarName) {
     27void KernelBuilder::addScalar(Type * t, std::string name) {
    2828    if (LLVM_UNLIKELY(mKernelStateType != nullptr)) {
    29         llvm::report_fatal_error("Illegal addition of kernel field after kernel state finalized: " + scalarName);
     29        llvm::report_fatal_error("Illegal addition of kernel field after kernel state finalized: " + name);
    3030    }
    3131    unsigned index = mKernelFields.size();
    3232    mKernelFields.push_back(t);
    33     mInternalStateNameMap.emplace(scalarName, index);
     33    mInternalStateNameMap.emplace(name, index);
    3434}
    3535
     
    3737    unsigned blockSize = iBuilder->getBitBlockWidth();
    3838    if (mStreamSetInputs.size() != mStreamSetInputBuffers.size()) {
    39         llvm::report_fatal_error("Kernel preparation: Incorrect number of input buffers");
     39        std::string tmp;
     40        raw_string_ostream out(tmp);
     41        out << "kernel contains " << mStreamSetInputBuffers.size() << " input buffers for "
     42            << mStreamSetInputs.size() << " input stream sets.";
     43        llvm::report_fatal_error(out.str());
    4044    }
    4145    if (mStreamSetOutputs.size() != mStreamSetOutputBuffers.size()) {
    42         llvm::report_fatal_error("Kernel preparation: Incorrect number of output buffers");
     46        std::string tmp;
     47        raw_string_ostream out(tmp);
     48        out << "kernel contains " << mStreamSetOutputBuffers.size() << " output buffers for "
     49            << mStreamSetOutputs.size() << " output stream sets.";
     50        llvm::report_fatal_error(out.str());
    4351    }
    4452    addScalar(iBuilder->getSizeTy(), blockNoScalar);
     
    4957    int streamSetNo = 0;
    5058    for (unsigned i = 0; i < mStreamSetInputs.size(); i++) {
    51         if (!(mStreamSetInputBuffers[i]->getBufferStreamSetType() == mStreamSetInputs[i].ssType)) {
    52              llvm::report_fatal_error("Kernel preparation: Incorrect input buffer type");
     59        if ((mStreamSetInputBuffers[i]->getBufferSize() > 0) && (mStreamSetInputBuffers[i]->getBufferSize() < codegen::SegmentSize + (blockSize + mLookAheadPositions - 1)/blockSize)) {
     60             llvm::report_fatal_error("Kernel preparation: Buffer size too small " + mStreamSetInputs[i].name);
    5361        }
    54         if ((mStreamSetInputBuffers[i]->getBufferSize() > 0) && (mStreamSetInputBuffers[i]->getBufferSize() < codegen::SegmentSize + (blockSize + mLookAheadPositions - 1)/blockSize)) {
    55              errs() << " buffer size = " << mStreamSetInputBuffers[i]->getBufferSize() << "\n";
    56              llvm::report_fatal_error("Kernel preparation: Buffer size too small " + mStreamSetInputs[i].ssName);
    57         }
    58         mScalarInputs.push_back(ScalarBinding{mStreamSetInputBuffers[i]->getStreamSetStructPointerType(), mStreamSetInputs[i].ssName + structPtrSuffix});
    59         mStreamSetNameMap.emplace(mStreamSetInputs[i].ssName, streamSetNo);
     62        mScalarInputs.push_back(Binding{mStreamSetInputBuffers[i]->getStreamSetStructPointerType(), mStreamSetInputs[i].name + structPtrSuffix});
     63        mStreamSetNameMap.emplace(mStreamSetInputs[i].name, streamSetNo);
    6064        streamSetNo++;
    6165    }
    6266    for (unsigned i = 0; i < mStreamSetOutputs.size(); i++) {
    63         if (!(mStreamSetOutputBuffers[i]->getBufferStreamSetType() == mStreamSetOutputs[i].ssType)) {
    64              llvm::report_fatal_error("Kernel preparation: Incorrect output buffer type " + mStreamSetOutputs[i].ssName);
    65         }
    66         mScalarInputs.push_back(ScalarBinding{mStreamSetOutputBuffers[i]->getStreamSetStructPointerType(), mStreamSetOutputs[i].ssName + structPtrSuffix});
    67         mStreamSetNameMap.emplace(mStreamSetOutputs[i].ssName, streamSetNo);
     67        mScalarInputs.push_back(Binding{mStreamSetOutputBuffers[i]->getStreamSetStructPointerType(), mStreamSetOutputs[i].name + structPtrSuffix});
     68        mStreamSetNameMap.emplace(mStreamSetOutputs[i].name, streamSetNo);
    6869        streamSetNo++;
    6970    }
    7071    for (auto binding : mScalarInputs) {
    71         addScalar(binding.scalarType, binding.scalarName);
     72        addScalar(binding.type, binding.name);
    7273    }
    7374    for (auto binding : mScalarOutputs) {
    74         addScalar(binding.scalarType, binding.scalarName);
     75        addScalar(binding.type, binding.name);
    7576    }
    7677    for (auto binding : mInternalScalars) {
    77         addScalar(binding.scalarType, binding.scalarName);
     78        addScalar(binding.type, binding.name);
    7879    }
    7980    mKernelStateType = StructType::create(iBuilder->getContext(), mKernelFields, mKernelName);
     
    8283std::unique_ptr<Module> KernelBuilder::createKernelModule(std::vector<StreamSetBuffer *> input_buffers, std::vector<StreamSetBuffer *> output_buffers) {
    8384    Module * saveModule = iBuilder->getModule();
    84     IDISA::IDISA_Builder::InsertPoint savePoint = iBuilder->saveIP();
     85    auto savePoint = iBuilder->saveIP();
    8586    std::unique_ptr<Module> theModule = make_unique<Module>(mKernelName + "_" + iBuilder->getBitBlockTypeName(), iBuilder->getContext());
    8687    Module * m = theModule.get();
     
    9394
    9495void KernelBuilder::generateKernel(std::vector<StreamSetBuffer *> input_buffers, std::vector<StreamSetBuffer*> output_buffers) {
    95     IDISA::IDISA_Builder::InsertPoint savePoint = iBuilder->saveIP();
     96    auto savePoint = iBuilder->saveIP();
    9697    Module * m = iBuilder->getModule();
    9798    mStreamSetInputBuffers = input_buffers;
     
    105106    // Implement the accumulator get functions
    106107    for (auto binding : mScalarOutputs) {
    107         auto fnName = mKernelName + accumulator_infix + binding.scalarName;
     108        auto fnName = mKernelName + accumulator_infix + binding.name;
    108109        Function * accumFn = m->getFunction(fnName);
    109         iBuilder->SetInsertPoint(BasicBlock::Create(iBuilder->getContext(), "get_" + binding.scalarName, accumFn, 0));
     110        iBuilder->SetInsertPoint(BasicBlock::Create(iBuilder->getContext(), "get_" + binding.name, accumFn, 0));
    110111        Value * self = &*(accumFn->arg_begin());
    111         Value * ptr = iBuilder->CreateGEP(self, {iBuilder->getInt32(0), getScalarIndex(binding.scalarName)});
     112        Value * ptr = iBuilder->CreateGEP(self, {iBuilder->getInt32(0), getScalarIndex(binding.name)});
    112113        Value * retVal = iBuilder->CreateLoad(ptr);
    113114        iBuilder->CreateRet(retVal);
     
    122123    for (auto binding : mScalarInputs) {
    123124        Value * parm = &*(args++);
    124         Value * ptr = iBuilder->CreateGEP(self, {iBuilder->getInt32(0), getScalarIndex(binding.scalarName)});
     125        Value * ptr = iBuilder->CreateGEP(self, {iBuilder->getInt32(0), getScalarIndex(binding.name)});
    125126        iBuilder->CreateStore(parm, ptr);
    126127    }
     
    131132//  The default finalBlock method simply dispatches to the doBlock routine.
    132133void KernelBuilder::generateFinalBlockMethod() {
    133     IDISA::IDISA_Builder::InsertPoint savePoint = iBuilder->saveIP();
     134    auto savePoint = iBuilder->saveIP();
    134135    Module * m = iBuilder->getModule();
    135136    Function * doBlockFunction = m->getFunction(mKernelName + doBlock_suffix);
     
    159160//  each block of the given number of blocksToDo, and then updates counts.
    160161void KernelBuilder::generateDoSegmentMethod() {
    161     IDISA::IDISA_Builder::InsertPoint savePoint = iBuilder->saveIP();
     162    auto savePoint = iBuilder->saveIP();
    162163    Module * m = iBuilder->getModule();
    163164    Function * doSegmentFunction = m->getFunction(mKernelName + doSegment_suffix);
     
    184185    std::vector<Value *> endSignalPtrs;
    185186    for (unsigned i = 0; i < mStreamSetInputs.size(); i++) {
    186         Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetInputs[i].ssName);
     187        Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetInputs[i].name);
    187188        inbufProducerPtrs.push_back(mStreamSetInputBuffers[i]->getProducerPosPtr(ssStructPtr));
    188189        endSignalPtrs.push_back(mStreamSetInputBuffers[i]->hasEndOfInputPtr(ssStructPtr));
     
    202203    Value * processed = getProcessedItemCount(self);
    203204    Value * itemsAvail = iBuilder->CreateSub(availablePos, processed);
    204 #ifndef NDEBUG
    205     iBuilder->CallPrintInt(mKernelName + "_itemsAvail", itemsAvail);
    206 #endif
     205//#ifndef NDEBUG
     206//    iBuilder->CallPrintInt(mKernelName + "_itemsAvail", itemsAvail);
     207//#endif
    207208    Value * stridesToDo = iBuilder->CreateUDiv(blocksToDo, strideBlocks);
    208209    Value * stridesAvail = iBuilder->CreateUDiv(itemsAvail, stride);
     
    260261   
    261262    for (unsigned i = 0; i < mStreamSetOutputs.size(); i++) {
    262         Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].ssName);
     263        Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].name);
    263264        mStreamSetOutputBuffers[i]->setEndOfInput(ssStructPtr);
    264265    }
     
    268269    iBuilder->SetInsertPoint(segmentDone);
    269270    Value * produced = getProducedItemCount(self);
    270 #ifndef NDEBUG
    271     iBuilder->CallPrintInt(mKernelName + "_produced", produced);
    272 #endif
     271//#ifndef NDEBUG
     272//    iBuilder->CallPrintInt(mKernelName + "_produced", produced);
     273//#endif
    273274    for (unsigned i = 0; i < mStreamSetOutputs.size(); i++) {
    274         Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].ssName);
     275        Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].name);
    275276        Value * producerPosPtr = mStreamSetOutputBuffers[i]->getProducerPosPtr(ssStructPtr);
    276277        iBuilder->CreateAtomicStoreRelease(produced, producerPosPtr);
     
    290291    const auto f = mInternalStateNameMap.find(fieldName);
    291292    if (LLVM_UNLIKELY(f == mInternalStateNameMap.end())) {
    292         llvm::report_fatal_error("Kernel does not contain internal state: " + fieldName);
     293        throw std::runtime_error("Kernel does not contain internal state: " + fieldName);
    293294    }
    294295    return iBuilder->getInt32(f->second);
    295296}
    296297
    297 
     298Value * KernelBuilder::getScalarFieldPtr(Value * self, std::string fieldName) {
     299    return iBuilder->CreateGEP(self, {iBuilder->getInt32(0), getScalarIndex(fieldName)});
     300}
    298301
    299302Value * KernelBuilder::getScalarField(Value * self, std::string fieldName) {
    300     Value * ptr = iBuilder->CreateGEP(self, {iBuilder->getInt32(0), getScalarIndex(fieldName)});
    301     return iBuilder->CreateLoad(ptr);
     303    return iBuilder->CreateLoad(getScalarFieldPtr(self, fieldName));
    302304}
    303305
    304306void KernelBuilder::setScalarField(Value * self, std::string fieldName, Value * newFieldVal) {
    305     Value * ptr = iBuilder->CreateGEP(self, {iBuilder->getInt32(0), getScalarIndex(fieldName)});
    306     iBuilder->CreateStore(newFieldVal, ptr);
     307    iBuilder->CreateStore(newFieldVal, getScalarFieldPtr(self, fieldName));
    307308}
    308309
     
    325326}
    326327
    327 
    328328void KernelBuilder::setLogicalSegmentNo(Value * self, Value * newCount) {
    329329    Value * ptr = iBuilder->CreateGEP(self, {iBuilder->getInt32(0), getScalarIndex(logicalSegmentNoScalar)});
     
    368368}
    369369
    370 unsigned KernelBuilder::getStreamSetIndex(std::string ssName) {
    371     const auto f = mStreamSetNameMap.find(ssName);
     370unsigned KernelBuilder::getStreamSetIndex(std::string name) {
     371    const auto f = mStreamSetNameMap.find(name);
    372372    if (LLVM_UNLIKELY(f == mStreamSetNameMap.end())) {
    373         llvm::report_fatal_error("Kernel does not contain stream set: " + ssName);
     373        llvm::report_fatal_error("Kernel does not contain stream set: " + name);
    374374    }
    375375    return f->second;
    376376}
    377377
    378 size_t KernelBuilder::getStreamSetBufferSize(Value * self, std::string ssName) {
    379     unsigned ssIndex = getStreamSetIndex(ssName);
    380     if (ssIndex < mStreamSetInputs.size()) {
    381         return mStreamSetInputBuffers[ssIndex]->getBufferSize();
    382     }
    383     else {
    384         return mStreamSetOutputBuffers[ssIndex - mStreamSetInputs.size()]->getBufferSize();
    385     }
    386 }
    387 
    388 Value * KernelBuilder::getStreamSetStructPtr(Value * self, std::string ssName) {
    389     return getScalarField(self, ssName + structPtrSuffix);
    390 }
    391 
    392 Value * KernelBuilder::getStreamSetBlockPtr(Value * self, std::string ssName, Value * blockNo) {
    393     Value * ssStructPtr = getStreamSetStructPtr(self, ssName);
    394     unsigned ssIndex = getStreamSetIndex(ssName);
    395     if (ssIndex < mStreamSetInputs.size()) {
    396         return mStreamSetInputBuffers[ssIndex]->getStreamSetBlockPointer(ssStructPtr, blockNo);
    397     }
    398     else {
    399         return mStreamSetOutputBuffers[ssIndex - mStreamSetInputs.size()]->getStreamSetBlockPointer(ssStructPtr, blockNo);
    400     }
     378size_t KernelBuilder::getStreamSetBufferSize(Value * self, std::string name) {
     379    const unsigned index = getStreamSetIndex(name);
     380    StreamSetBuffer * buf = nullptr;
     381    if (index < mStreamSetInputs.size()) {
     382        buf = mStreamSetInputBuffers[index];
     383    } else {
     384        buf = mStreamSetOutputBuffers[index - mStreamSetInputs.size()];
     385    }
     386    return buf->getBufferSize();
     387}
     388
     389Value * KernelBuilder::getStreamSetStructPtr(Value * self, std::string name) {
     390    return getScalarField(self, name + structPtrSuffix);
     391}
     392
     393Value * KernelBuilder::getStreamSetBlockPtr(Value * self, std::string name, Value * blockNo) {
     394    Value * const structPtr = getStreamSetStructPtr(self, name);
     395    const unsigned index = getStreamSetIndex(name);
     396    StreamSetBuffer * buf = nullptr;
     397    if (index < mStreamSetInputs.size()) {
     398        buf = mStreamSetInputBuffers[index];
     399    } else {
     400        buf = mStreamSetOutputBuffers[index - mStreamSetInputs.size()];
     401    }   
     402    return buf->getStreamSetBlockPointer(structPtr, blockNo);
    401403}
    402404
     
    408410        init_args.push_back(a);
    409411    }
    410     for (auto b : mStreamSetInputBuffers) { 
     412    for (auto b : mStreamSetInputBuffers) {
    411413        init_args.push_back(b->getStreamSetStructPtr());
    412414    }
    413     for (auto b : mStreamSetOutputBuffers) { 
     415    for (auto b : mStreamSetOutputBuffers) {
    414416        init_args.push_back(b->getStreamSetStructPtr());
    415417    }
     
    448450
    449451    for (unsigned i = 0; i < mStreamSetInputs.size(); i++) {
    450         Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetInputs[i].ssName);
     452        Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetInputs[i].name);
    451453        inbufProducerPtrs.push_back(mStreamSetInputBuffers[i]->getProducerPosPtr(ssStructPtr));
    452454        inbufConsumerPtrs.push_back(mStreamSetInputBuffers[i]->getConsumerPosPtr(ssStructPtr));
     
    454456    }
    455457    for (unsigned i = 0; i < mStreamSetOutputs.size(); i++) {
    456         Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].ssName);
     458        Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].name);
    457459        outbufProducerPtrs.push_back(mStreamSetOutputBuffers[i]->getProducerPosPtr(ssStructPtr));
    458460        outbufConsumerPtrs.push_back(mStreamSetOutputBuffers[i]->getConsumerPosPtr(ssStructPtr));
     
    540542        iBuilder->SetInsertPoint(earlyEndBlock);
    541543        for (unsigned i = 0; i < mStreamSetOutputs.size(); i++) {
    542             Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].ssName);
     544            Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].name);
    543545            mStreamSetOutputBuffers[i]->setEndOfInput(ssStructPtr);
    544546        }       
     
    575577
    576578    for (unsigned i = 0; i < mStreamSetOutputs.size(); i++) {
    577         Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].ssName);
     579        Value * ssStructPtr = getStreamSetStructPtr(self, mStreamSetOutputs[i].name);
    578580        mStreamSetOutputBuffers[i]->setEndOfInput(ssStructPtr);
    579581    }
Note: See TracChangeset for help on using the changeset viewer.