Changeset 5195


Ignore:
Timestamp:
Oct 16, 2016, 6:37:28 PM (3 years ago)
Author:
cameron
Message:

doSegment with termination signal processing for stdout kernel

File:
1 edited

Legend:

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

    r5192 r5195  
    2121}
    2222
    23 // The doBlock method is deprecated.   But incase it is used, just call doSegment with
     23// The doBlock method is deprecated.   But in case it is used, just call doSegment with
    2424// 1 as the number of blocks to do.
    2525void stdOutKernel::generateDoBlockMethod() {
     
    3535}
    3636           
     37// Rather than using doBlock logic to write one block at a time, this custom
     38// doSegment method, writes the entire segment with a single write call.
    3739void stdOutKernel::generateDoSegmentMethod() {
    3840    IDISA::IDISA_Builder::InsertPoint savePoint = iBuilder->saveIP();
     
    4345   
    4446    iBuilder->SetInsertPoint(BasicBlock::Create(iBuilder->getContext(), "entry", doSegmentFunction, 0));
    45     Constant * stride = ConstantInt::get(iBuilder->getSizeTy(), iBuilder->getStride());
     47    BasicBlock * setTermination = BasicBlock::Create(iBuilder->getContext(), "setTermination", doSegmentFunction, 0);
     48    BasicBlock * stdOutexit = BasicBlock::Create(iBuilder->getContext(), "stdOutexit", doSegmentFunction, 0);
     49    Constant * blockItems = ConstantInt::get(iBuilder->getSizeTy(), iBuilder->getBitBlockWidth());
    4650    Constant * itemBytes = ConstantInt::get(iBuilder->getSizeTy(), mCodeUnitWidth/8);
    4751   
     
    5660    LoadInst * producerPos = iBuilder->CreateAtomicLoadAcquire(mStreamSetInputBuffers[0]->getProducerPosPtr(streamStructPtr));
    5761    //iBuilder->CallPrintInt("producerPos", producerPos);
    58     Value * endSignal = iBuilder->CreateLoad(mStreamSetInputBuffers[0]->hasEndOfInputPtr(streamStructPtr));
    59 
     62    Value * processed = getProcessedItemCount(self);
     63    Value * itemsAvail = iBuilder->CreateSub(producerPos, processed);
     64    Value * itemsMax = iBuilder->CreateMul(blocksToDo, blockItems);
     65    Value * lessThanFullSegment = iBuilder->CreateICmpULT(itemsAvail, itemsMax);
     66    Value * itemsToDo = iBuilder->CreateSelect(lessThanFullSegment, itemsAvail, itemsMax);
     67   
    6068    Value * blockNo = getScalarField(self, blockNoScalar);
    6169    //iBuilder->CallPrintInt("blockNo", blockNo);
    6270    Value * basePtr = getStreamSetBlockPtr(self, "codeUnitBuffer", blockNo);
    6371    //iBuilder->CallPrintInt("basePtr", iBuilder->CreatePtrToInt(basePtr, iBuilder->getInt64Ty()));
     72    Value * byteOffset = iBuilder->CreateMul(iBuilder->CreateURem(processed, blockItems), itemBytes);
     73    Value * bytePtr = iBuilder->CreateGEP(iBuilder->CreateBitCast(basePtr, i8PtrTy), byteOffset);
     74//#undef NDEBUG
     75#ifndef NDEBUG
     76    iBuilder->CallPrintInt(mKernelName + "_segmentNo", segmentNo);
     77    iBuilder->CallPrintInt(mKernelName + "_itemsAvail", itemsAvail);
     78    iBuilder->CallPrintInt(mKernelName + "_itemsToDo", itemsToDo);
     79#endif
     80    iBuilder->CreateCall(writefn, std::vector<Value *>({iBuilder->getInt32(1), bytePtr, iBuilder->CreateMul(itemsToDo, itemBytes)}));
    6481   
    65     Value * processed = getProcessedItemCount(self);
    66     Value * itemsAvail = iBuilder->CreateSub(producerPos, processed);
    67     //iBuilder->CallPrintInt("previously processed", processed);
    68     Value * blocksAvail = iBuilder->CreateUDiv(itemsAvail, stride);
    69     //iBuilder->CallPrintInt("blocksAvail", blocksAvail);
    70    
    71     Value * lessThanFullSegment = iBuilder->CreateICmpULT(blocksAvail, blocksToDo);
    72     Value * inFinalSegment = iBuilder->CreateAnd(endSignal, lessThanFullSegment);
    73     /* Adjust the number of full blocks to do, based on the available data, if necessary. */
    74     blocksToDo = iBuilder->CreateSelect(lessThanFullSegment, blocksAvail, blocksToDo);
    75    
    76     Value * itemsToDo = iBuilder->CreateMul(blocksToDo, stride);
    77     itemsToDo = iBuilder->CreateSelect(inFinalSegment, itemsAvail, itemsToDo);
    78     //iBuilder->CallPrintInt("bytesToDo", bytesToDo);
    79     iBuilder->CreateCall(writefn, std::vector<Value *>({iBuilder->getInt32(1), iBuilder->CreateBitCast(basePtr, i8PtrTy), iBuilder->CreateMul(itemsToDo, itemBytes)}));
    80    
    81     setScalarField(self, blockNoScalar, iBuilder->CreateAdd(blockNo, blocksToDo));
    8282    processed = iBuilder->CreateAdd(processed, itemsToDo);
    8383    setProcessedItemCount(self, processed);
     84    setScalarField(self, blockNoScalar, iBuilder->CreateUDiv(processed, blockItems));
    8485    mStreamSetInputBuffers[0]->setConsumerPos(streamStructPtr, processed);
     86
     87    Value * endSignal = iBuilder->CreateLoad(mStreamSetInputBuffers[0]->hasEndOfInputPtr(streamStructPtr));
     88    Value * inFinalSegment = iBuilder->CreateAnd(endSignal, lessThanFullSegment);
     89   
     90    iBuilder->CreateCondBr(inFinalSegment, setTermination, stdOutexit);
     91    iBuilder->SetInsertPoint(setTermination);
     92#ifndef NDEBUG
     93    iBuilder->CallPrintInt(mKernelName + " termination in segment ", segmentNo);
     94#endif
     95    setTerminationSignal(self);
     96
     97    iBuilder->CreateBr(stdOutexit);
     98    iBuilder->SetInsertPoint(stdOutexit);
    8599    // Must be the last action, for synchronization.
    86100    setLogicalSegmentNo(self, iBuilder->CreateAdd(segmentNo, ConstantInt::get(iBuilder->getSizeTy(), 1)));
    87    
    88101    iBuilder->CreateRetVoid();
    89102    iBuilder->restoreIP(savePoint);
     
    98111   
    99112    iBuilder->SetInsertPoint(BasicBlock::Create(iBuilder->getContext(), "fb_flush", finalBlockFunction, 0));
     113    Constant * blockItems = ConstantInt::get(iBuilder->getSizeTy(), iBuilder->getBitBlockWidth());
     114    Constant * itemBytes = ConstantInt::get(iBuilder->getSizeTy(), mCodeUnitWidth/8);
    100115    Value * self = getParameter(finalBlockFunction, "self");
    101116    Value * streamStructPtr = getStreamSetStructPtr(self, "codeUnitBuffer");
     
    103118    Value * processed = getProcessedItemCount(self);
    104119    Value * itemsAvail = iBuilder->CreateSub(producerPos, processed);
     120    Value * segmentNo = getLogicalSegmentNo(self);
    105121    Value * blockNo = getScalarField(self, blockNoScalar);
    106122    Value * basePtr = getStreamSetBlockPtr(self, "codeUnitBuffer", blockNo);
    107     Value * bytesToDo = iBuilder->CreateMul(itemsAvail, ConstantInt::get(iBuilder->getSizeTy(), mCodeUnitWidth/8));
    108 
    109     iBuilder->CreateCall(writefn, std::vector<Value *>({iBuilder->getInt32(1), iBuilder->CreateBitCast(basePtr, i8PtrTy), bytesToDo}));
    110    
     123    Value * byteOffset = iBuilder->CreateMul(iBuilder->CreateURem(processed, blockItems), itemBytes);
     124    Value * bytePtr = iBuilder->CreateGEP(iBuilder->CreateBitCast(basePtr, i8PtrTy), byteOffset);
     125    iBuilder->CreateCall(writefn, std::vector<Value *>({iBuilder->getInt32(1), bytePtr, iBuilder->CreateMul(itemsAvail, itemBytes)}));
    111126    setProcessedItemCount(self, producerPos);
    112127    mStreamSetInputBuffers[0]->setConsumerPos(streamStructPtr, producerPos);
     128    setTerminationSignal(self);
    113129    iBuilder->CreateRetVoid();
    114130    iBuilder->restoreIP(savePoint);
Note: See TracChangeset for help on using the changeset viewer.