📄 serialasync.cpp
字号:
// -*- C++ -*-
// ACL:license
// This software and ancillary information (herein called "SOFTWARE")
// called Tulip is made available under the terms described
// here. The SOFTWARE has been approved for release with associated
// LA-CC Number LA-CC-98-35.
//
// Unless otherwise indicated, this SOFTWARE has been authored by an
// employee or employees of the University of California, operator of the
// Los Alamos National Laboratory under Contract No. W-7405-ENG-36 with
// the U.S. Department of Energy. The U.S. Government has rights to use,
// reproduce, and distribute this SOFTWARE, and to allow others to do so.
// The public may copy, distribute, prepare derivative works and publicly
// display this SOFTWARE without charge, provided that this Notice and
// any statement of authorship are reproduced on all copies. Neither the
// Government nor the University makes any warranty, express or implied,
// or assumes any liability or responsibility for the use of this
// SOFTWARE.
//
// If SOFTWARE is modified to produce derivative works, such modified
// SOFTWARE should be clearly marked, so as not to confuse it with the
// version available from LANL
// ACL:license
//-----------------------------------------------------------------------------
// This program was prepared by the Regents of the University of California
// at Los Alamos National Laboratory (the University) under Contract No.
// W-7405-ENG-36 with the U.S. Department of Energy (DOE). The University has
// certain rights in the program pursuant to the contract and the program
// should not be copied or distributed outside your organization. All rights
// in the program are reserved by the DOE and the University. Neither the U.S.
// Government nor the University makes any warranty, express or implied, or
// assumes any liability or responsibility for the use of this software
//-----------------------------------------------------------------------------
// Class:
// IterateScheduler<SerialAsync>
// Iterate<SerialAsync>
// DataObject<SerialAsync>
//-----------------------------------------------------------------------------
#include "IterateSchedulers/SerialAsync.h"
namespace Smarts {
SystemContext systemContext;
//-----------------------------------------------------------------------------
//
// void IterateScheduler<SerialAsync>::blockingEvaluate
// Evaluate all the iterates in the queue.
//
//-----------------------------------------------------------------------------
void
IterateScheduler<SerialAsync>::blockingEvaluate()
{
// Loop as long as there is anything in the queue.
while (!queue_m.empty())
{
// Get the top iterate.
Iterate<SerialAsync>* p = queue_m.front();
// Delete it from the queue.
queue_m.pop_front();
// Run the iterate.
p->run();
// Delete the iterate. This could put more iterates in the queue.
delete p;
}
}
//-----------------------------------------------------------------------------
//
// void DataObject::releaseIterates(SerialAsync::Action)
// When the last released iterate dies, we need to
// look at the beginning of the queue and tell more iterates
// that they can access this data.
//
//-----------------------------------------------------------------------------
void
DataObject<SerialAsync>::releaseIterates()
{
// Get rid of the reservations that have finished.
queue_m.erase( queue_m.begin() , released_m );
// Next we'll see if we can release some new ones.
// Get the begin and end iterators.
released_m = queue_m.begin();
Iterator_t end = queue_m.end();
// If there are any in the queue, we'll release something.
if ( released_m != end )
{
// Release the first one whatever it is.
released_m->iterate().notify();
++notifications_m;
// Record what action that one will take.
SerialAsync::Action act = released_m->act();
// Look at the next iterate.
++released_m;
// If the first one was a read, release more.
if ( act == SerialAsync::Read )
// As long as we aren't at the end and we have more reads...
while ((released_m != end) &&
(released_m->act()==SerialAsync::Read))
{
// Release it...
released_m->iterate().notify();
++notifications_m;
// And go on to the next.
++released_m;
}
}
}
//
// void DataObject::request(Iterate&, action, generation)
// An iterate makes a reservation with this DataObject for a given action
// in a given generation.
// The request may be granted immediately.
//
void
DataObject<SerialAsync>::request(Iterate<SerialAsync>& it,
SerialAsync::Action act,
int /* generation */ )
{
// The request can be granted immediately if:
// The queue is currently empty, or
// The request is a read and everything in the queue is a read.
bool allReleased = (queue_m.end() == released_m);
bool releasable = queue_m.empty() ||
((act == SerialAsync::Read) &&
(queue_m.begin()->act() == SerialAsync::Read) &&
allReleased);
// Push the request on the stack.
queue_m.push_back( Request(it, act) );
// If it's releasable, release it and record the release.
if (releasable)
{
it.notify();
++notifications_m;
}
// Otherwise, if this is the first nonreleasable iterate,
// make released_m point to the last element of the queue.
else if (allReleased)
{
--released_m;
}
}
// End of Smarts namespace.
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -