Ignore:
Timestamp:
Aug 20, 2017, 10:19:39 PM (21 months ago)
Author:
cameron
Message:

Automatic expansion of dynamic buffers in pipeline

File:
1 edited

Legend:

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

    r5609 r5615  
    147147    for (unsigned i = 0; i < mStreamSetInputs.size(); i++) {
    148148        if ((mStreamSetInputBuffers[i]->getBufferBlocks() != 0) && (mStreamSetInputBuffers[i]->getBufferBlocks() < requiredBlocks)) {
    149             report_fatal_error(getName() + ": " + mStreamSetInputs[i].name + " requires buffer size " + std::to_string(requiredBlocks));
     149            //report_fatal_error(getName() + ": " + mStreamSetInputs[i].name + " requires buffer size " + std::to_string(requiredBlocks));
    150150        }
    151151        mScalarInputs.emplace_back(mStreamSetInputBuffers[i]->getStreamSetHandle()->getType(), mStreamSetInputs[i].name + BUFFER_PTR_SUFFIX);
     
    12221222   
    12231223}
    1224    
    1225 }
     1224 
     1225   
     1226void applyOutputBufferExpansions(const std::unique_ptr<KernelBuilder> & kb,
     1227                                 std::vector<Value *> inputAvailable,
     1228                                 Value * doFinal) {
     1229    auto kernel = kb->getKernel();
     1230    const unsigned inputSetCount = inputAvailable.size();
     1231    if (inputSetCount == 0) return;  //  Cannot calculate buffer items expected from input.
     1232    auto & outputs = kernel->getStreamSetOutputBuffers();
     1233    const unsigned outputSetCount = outputs.size();
     1234
     1235    Constant * blockSize = kb->getSize(kb->getBitBlockWidth());
     1236    Value * newlyAvailInputItems[inputSetCount];
     1237    Value * requiredOutputBufferSpace[outputSetCount];
     1238    for (unsigned i = 0; i < inputSetCount; i++) {
     1239        Value * processed = kb->getProcessedItemCount(kernel->getStreamInput(i).name);
     1240        newlyAvailInputItems[i] = kb->CreateSub(inputAvailable[i], processed);
     1241    }
     1242    //kb->GetInsertBlock()->dump();
     1243    for (unsigned i = 0; i < outputSetCount; i++) {
     1244        requiredOutputBufferSpace[i] = nullptr;
     1245        auto & rate = kernel->getStreamOutput(i).rate;
     1246        if (rate.isUnknownRate()) continue;  // No calculations possible.
     1247        Kernel::Port port; unsigned ssIdx;
     1248        std::tie(port, ssIdx) = kernel->getStreamPort(rate.referenceStreamSet());
     1249        if (port == Kernel::Port::Output) {
     1250            requiredOutputBufferSpace[i] = rate.CreateRatioCalculation(kb.get(), requiredOutputBufferSpace[ssIdx], doFinal);
     1251        }
     1252        else {
     1253            requiredOutputBufferSpace[i] = rate.CreateRatioCalculation(kb.get(), newlyAvailInputItems[ssIdx], doFinal);
     1254        }
     1255        if (auto db = dyn_cast<DynamicBuffer>(outputs[i])) {
     1256            Value * handle = db->getStreamSetHandle();
     1257            // This buffer can be expanded.
     1258            Value * producedBlock = kb->CreateUDivCeil(kb->getProducedItemCount(kernel->getStreamOutput(i).name), blockSize);
     1259            Value * consumedBlock = kb->CreateUDiv(kb->getConsumedItemCount(kernel->getStreamOutput(i).name), blockSize);
     1260            Value * blocksInUse = kb->CreateSub(producedBlock, consumedBlock);
     1261            Value * blocksRequired = kb->CreateAdd(blocksInUse, kb->CreateUDivCeil(requiredOutputBufferSpace[i], blockSize));
     1262            Value * spaceRequired = kb->CreateMul(blocksRequired, blockSize);
     1263            Value * expansionNeeded = kb->CreateICmpUGT(spaceRequired, db->getBufferedSize(kb.get(), handle));
     1264            BasicBlock * doExpand = kb->CreateBasicBlock("doExpand");
     1265            BasicBlock * bufferReady = kb->CreateBasicBlock("bufferReady");
     1266            kb->CreateCondBr(expansionNeeded, doExpand, bufferReady);
     1267            kb->SetInsertPoint(doExpand);
     1268            db->doubleCapacity(kb.get(), handle);
     1269            // Ensure that capacity is sufficient by successive doubling, if necessary.
     1270            expansionNeeded = kb->CreateICmpUGT(spaceRequired, db->getBufferedSize(kb.get(), handle));
     1271            kb->CreateCondBr(expansionNeeded, doExpand, bufferReady);
     1272            kb->SetInsertPoint(bufferReady);
     1273        }
     1274    }
     1275
     1276}
     1277
     1278}
Note: See TracChangeset for help on using the changeset viewer.