BufferProvider: rearrange types to prepare for a BufferStage interface
...still in pursuit of the plan to split the implementation of the `BufferProvider` in a ''state tracking'' part and a ''storage managment'' part...
This commit is contained in:
parent
9b66818bda
commit
5518030a7d
8 changed files with 89 additions and 29 deletions
|
|
@ -80,8 +80,6 @@ namespace engine {
|
|||
class Store
|
||||
: public BufferStore
|
||||
{
|
||||
protected:
|
||||
using Buff = BufferProvider::Buff;
|
||||
};
|
||||
|
||||
|
||||
|
|
|
|||
|
|
@ -147,9 +147,8 @@ namespace engine {
|
|||
void
|
||||
BufferProvider::emitBuffer (BuffHandle const& handle)
|
||||
{
|
||||
metadata::Entry& metaEntry = bufferStage_->get (handle.entryID());
|
||||
size_t buffSiz = metaEntry.storageSize();
|
||||
bufferStore_->mark_emitted (buffSiz, metaEntry.parentKey(), metaEntry.localTag());
|
||||
metadata::Entry& metaEntry = bufferStage_->get (handle);
|
||||
bufferStore_->mark_emitted (metaEntry.storageSize(), metaEntry.parentKey(), metaEntry.localTag());
|
||||
metaEntry.mark(EMITTED);
|
||||
}
|
||||
|
||||
|
|
@ -165,7 +164,7 @@ namespace engine {
|
|||
void
|
||||
BufferProvider::releaseBuffer (BuffHandle const& handle)
|
||||
try {
|
||||
metadata::Entry& metaEntry = bufferStage_->get (handle.entryID());
|
||||
metadata::Entry& metaEntry = bufferStage_->get (handle);
|
||||
size_t buffSiz = metaEntry.storageSize();
|
||||
metaEntry.mark(FREE); // might invoke embedded dtor function
|
||||
bufferStore_->detachBuffer (buffSiz, metaEntry.parentKey()
|
||||
|
|
@ -183,13 +182,13 @@ namespace engine {
|
|||
* @note EX_FREE
|
||||
*/
|
||||
void
|
||||
BufferProvider::emergencyCleanup (BuffHandle const& target, bool invokeDtor)
|
||||
BufferProvider::emergencyCleanup (BuffHandle const& handle, bool invokeDtor)
|
||||
try {
|
||||
metadata::Entry& metaEntry = bufferStage_->get (target.entryID());
|
||||
metadata::Entry& metaEntry = bufferStage_->get (handle);
|
||||
size_t buffSiz = metaEntry.storageSize();
|
||||
metaEntry.invalidate (invokeDtor);
|
||||
bufferStore_->detachBuffer (buffSiz, metaEntry.parentKey()
|
||||
,std::make_tuple (target.rawStorage(), metaEntry.localTag()));
|
||||
,std::make_tuple (handle.rawStorage(), metaEntry.localTag()));
|
||||
bufferStage_->release (metaEntry);
|
||||
}
|
||||
ERROR_LOG_AND_IGNORE (engine, "cleanup of buffer metadata while handling an error")
|
||||
|
|
@ -217,7 +216,7 @@ namespace engine {
|
|||
|
||||
|
||||
size_t
|
||||
BuffDescr::determineBufferSize() const
|
||||
BuffDescr::buffSize() const
|
||||
{
|
||||
ENSURE (provider_);
|
||||
return provider_->getBufferSize (*this);
|
||||
|
|
|
|||
|
|
@ -121,8 +121,10 @@ namespace engine {
|
|||
using std::unique_ptr;
|
||||
using std::forward;
|
||||
|
||||
|
||||
class BufferMetadata;
|
||||
namespace metadata {
|
||||
class Key;
|
||||
}
|
||||
|
||||
|
||||
LUMIERA_ERROR_DECLARE (BUFFER_MANAGEMENT); ///< Problem providing working buffers
|
||||
|
|
@ -177,15 +179,14 @@ namespace engine {
|
|||
size_t getBufferSize (HashVal typeID) const;
|
||||
|
||||
protected:
|
||||
/// placeholder marker type for an actual data buffer
|
||||
using Buff = StreamType::ImplFacade::DataBuffer;
|
||||
|
||||
bool was_created_by_this_provider (BuffDescr const&) const;
|
||||
|
||||
|
||||
class BufferStage
|
||||
: public BufferMetadata /////////////////////////////////////////////////////////////////////TICKET #1410 : mix-in exiting old implementation -- for sake of refactoring only!
|
||||
{
|
||||
protected:
|
||||
using Key = metadata::Key;
|
||||
public:
|
||||
virtual ~BufferStage() { } ///< this is an interface
|
||||
|
||||
|
|
@ -196,6 +197,7 @@ namespace engine {
|
|||
: util::NonCopyable
|
||||
{
|
||||
protected:
|
||||
using Buff = StreamType::ImplFacade::DataBuffer; ///< marker type for an actual data buffer
|
||||
using Slot = std::tuple<Buff*,LocalTag>;
|
||||
public:
|
||||
virtual ~BufferStore() { } ///< this is an interface
|
||||
|
|
|
|||
|
|
@ -92,7 +92,7 @@ namespace engine {
|
|||
// using standard copy operations
|
||||
|
||||
bool verifyValidity() const;
|
||||
size_t determineBufferSize() const;
|
||||
size_t buffSize() const;
|
||||
|
||||
operator HashVal() const { return subClassification_; }
|
||||
|
||||
|
|
@ -117,13 +117,11 @@ namespace engine {
|
|||
|
||||
|
||||
public:
|
||||
using PBuff = Buff*;
|
||||
|
||||
/** @internal a buffer handle may be obtained by "locking"
|
||||
* a buffer from the corresponding BufferProvider */
|
||||
BuffHandle(BuffDescr const& typeInfo, void* storage = 0)
|
||||
: descriptor_(typeInfo)
|
||||
, pBuffer_(static_cast<PBuff>(storage))
|
||||
, pBuffer_(static_cast<Buff*>(storage))
|
||||
{ }
|
||||
|
||||
// using standard copy operations
|
||||
|
|
@ -157,16 +155,10 @@ namespace engine {
|
|||
and descriptor_.verifyValidity();
|
||||
}
|
||||
|
||||
HashVal
|
||||
entryID() const ///////////////////////TICKET 1410 : why can't we just expose operator HashVal() ??
|
||||
{
|
||||
return HashVal(descriptor_);
|
||||
}
|
||||
|
||||
size_t
|
||||
size() const
|
||||
{
|
||||
return descriptor_.determineBufferSize();
|
||||
return descriptor_.buffSize();
|
||||
}
|
||||
|
||||
private:
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@
|
|||
*/
|
||||
|
||||
/** @file heap-mem-provider.hpp
|
||||
** Dummy implementation engine::BufferProvider storage, for sake of conceptual
|
||||
** Dummy engine::BufferProvider storage implementation, for sake of conceptual
|
||||
** demonstration and unit testing. This BufferProvider implementation is notably straight forward,
|
||||
** if not outright silly: it happily claims more and more heap blocks and never releases any memory
|
||||
** dynamically. This both demonstrates the simplest possible implementation of storage handling, and
|
||||
|
|
|
|||
|
|
@ -31,6 +31,7 @@
|
|||
#include "lib/error.hpp"
|
||||
#include "steam/engine/buffer-provider-setup.hpp"
|
||||
#include "steam/engine/heap-mem-buffer-store.hpp"
|
||||
#include "steam/engine/simple-buffer-state-registry.hpp"
|
||||
|
||||
#include <memory>
|
||||
|
||||
|
|
@ -58,7 +59,7 @@ namespace engine {
|
|||
: BufferProviderSetup{*this}
|
||||
{ }
|
||||
|
||||
auto buildStage() { return std::make_unique<Stage> ("Naive_HeapAllocated"); }
|
||||
auto buildStage() { return std::make_unique<SimpleBufferStateRegistry> ("Naive_HeapAllocated"); }
|
||||
auto buildStore() { return std::make_unique<HeapMemBufferStore>(); } /////////////////////////////////TICKET #1410 : turn into a subclass of BufferSetup::Store and push down implementation
|
||||
};
|
||||
|
||||
|
|
|
|||
67
src/steam/engine/simple-buffer-state-registry.hpp
Normal file
67
src/steam/engine/simple-buffer-state-registry.hpp
Normal file
|
|
@ -0,0 +1,67 @@
|
|||
/*
|
||||
SIMPLE-BUFFER-STATE-REGISTRY.hpp - naively tracking buffer states in a central hash table
|
||||
|
||||
Copyright (C)
|
||||
2026 Hermann Vosseler <Ichthyostega@web.de>
|
||||
|
||||
**Lumiera** is free software; you can redistribute it and/or modify it
|
||||
under the terms of the GNU General Public License as published by the
|
||||
Free Software Foundation; either version 2 of the License, or (at your
|
||||
option) any later version. See the file COPYING for further details.
|
||||
|
||||
*/
|
||||
|
||||
/** @file simple-buffer-state-registry.hpp
|
||||
** Demo implementation of engine::BufferProvider state coordination, suitable for unit tests.
|
||||
** Based on a shared metadata table, accessed directly, disregarding concurrency.
|
||||
**
|
||||
** @see buffer-provider.hpp
|
||||
** @see buffer-provider-protocol-test.cpp
|
||||
** @see naive-buffer-setup.hpp
|
||||
*/
|
||||
|
||||
#ifndef STEAM_ENGINE_SIMPLE_BUFFER_STATE_REGISTRY_H
|
||||
#define STEAM_ENGINE_SIMPLE_BUFFER_STATE_REGISTRY_H
|
||||
|
||||
|
||||
#include "lib/error.hpp"
|
||||
//#include "lib/hash-value.h"
|
||||
#include "steam/engine/buffer-provider-setup.hpp"
|
||||
#include "steam/engine/buffer-metadata.hpp"
|
||||
|
||||
#include <memory>
|
||||
|
||||
|
||||
namespace steam {
|
||||
namespace engine {
|
||||
|
||||
namespace error = lumiera::error;
|
||||
|
||||
// using std::unique_ptr;
|
||||
// using lib::HashVal;
|
||||
|
||||
|
||||
/**
|
||||
* Simple Buffer type and state tracking registry, for test and demonstration.
|
||||
* Relies on a central hashtable, without considering any concurrency concerns.
|
||||
*/
|
||||
class SimpleBufferStateRegistry
|
||||
: public BufferProviderSetup::Stage
|
||||
{
|
||||
///////////////////////////////////////////////////////////////////////////////////////////////////////TICKET 1410 : rather hold BufferMetatdata object here
|
||||
public:
|
||||
/* === BufferStage interface === */
|
||||
|
||||
|
||||
public:
|
||||
SimpleBufferStateRegistry (Literal implementationID)
|
||||
: BufferProviderSetup::Stage{implementationID} //////////////////////////////////////////////////TICKET 1410 : rather init BufferMetatdata
|
||||
{ }
|
||||
|
||||
private:
|
||||
};
|
||||
|
||||
|
||||
|
||||
}} // namespace steam::engine
|
||||
#endif /*STEAM_ENGINE_SIMPLE_BUFFER_STATE_REGISTRY_H*/
|
||||
|
|
@ -50,6 +50,7 @@ namespace play {
|
|||
|
||||
//using std::string;
|
||||
using lib::Symbol;
|
||||
using lib::HashVal;
|
||||
using util::unConst;
|
||||
using util::contains;
|
||||
using lib::time::FrameRate;
|
||||
|
|
@ -106,7 +107,7 @@ namespace play {
|
|||
trackFrame (FrameID frameNr, BuffHandle const& newBuffer)
|
||||
{
|
||||
TRACE (test, "Con=%p : track buffer %zu for frame-#%lu"
|
||||
, this, newBuffer.entryID(), frameNr);
|
||||
, this, HashVal(newBuffer), frameNr);
|
||||
REQUIRE (!contains (frameTrackingIndex_,frameNr),
|
||||
"attempt to lock already used frame %lu", frameNr);
|
||||
|
||||
|
|
@ -154,7 +155,7 @@ namespace play {
|
|||
transfer (BuffHandle const& filledBuffer)
|
||||
{
|
||||
TRACE (test, "Con=%p : transfer buffer %zu"
|
||||
, this, filledBuffer.entryID());
|
||||
, this, HashVal(filledBuffer));
|
||||
REQUIRE (!closed_);
|
||||
|
||||
pushout (filledBuffer);
|
||||
|
|
|
|||
Loading…
Reference in a new issue