Commit graph

24 commits

Author SHA1 Message Date
1601838037 BufferProvider: reduce synchronisation effort
The recursive synchronisation up the parent-chain can in most cases be skipped,
by relying on the fact that inconsistent data is never stored in the BufferMetadata
table. If thus an entry is locally present and matches the entry from the
other side, then it can be concluded that its parent must also be already in sync.
2026-04-19 15:14:31 +02:00
c05a73d68a BufferProvider: draft mechanism for buffer metadata synchronisation
Since the intention is to run several thread-local instances of `BufferMetadata`
in a concurrent setup, we need a way to publish and exchange chains of
registered type-keys and metadata entries.

The first step is to develop a mechanic for data exchange,
and to define the rules when such synchronisation is (not) allowed.
2026-04-19 01:21:24 +02:00
8d563d1ea9 BufferProvider: lift the family-ID to the BufferStage level
During the last days, I started with analysis to find a way
to operate the `BufferProvider`, as implemented thus far,
within a massively concurrent environment.

Since I intend to create thread-local caches,
the initialisation of the `BufferMetadata` store must be static.

It turns out that the root-ID, which acts like a mandator ID,
is only used at a single code path, when creating or accessing
an abstract type-Key. It is thus easy to extract and relocate
this distinguishing ID into the actual `BufferStage` implementation.
2026-04-17 19:08:46 +02:00
4dc6885665 BufferProvider: complete the clean-up effort
Looking through all my work notes, it seems that all the
problematic aspects are now solved in a satisfactory way.
 * it is clear how to dependency-inject a `BufferProvider`
 * the internals of the `BufferProvider` front-End have been restructured
 * there are now two ''pillars'' of the implementation: `BufferStage` and `BufferStore`
 * both can be subclassed independently
 * `BufferProviderSetup` exposes a proxying-mechanism (used for `DiagnosticBufferProvider`)
 * the `BufferMetadata` have been reviewed and some minor details were rectified
 * after a re-Design of `OutputSlot`, `BuffHandle` can now be used as unified front-End
 * both `DiagnosticBufferProvider` and `DiagnosticOutputSlot` have been rewritten
 * they are now independent, self-contained specialisations, layered on top

Overall, what might seem like a detour, was an important step towards
well-balanced structures and a better understanding of the Render Engine.
2026-04-14 01:22:55 +02:00
9b6933b572 OutputSlot: consider how to integrate the proxy provider
...which still looks like a nasty task
 * the good part is, we have a working `BufferProxyAdaptor` now
 * yet this setup does not seem to fit into the `OutputSlot::AllocState`

As an aside, several test definitions need to be relocated to the Vault,
since the whole compound around `BufferProvider` migrated down
2026-03-17 00:48:08 +01:00
ea0ae5f78e BufferProvider: propagate the actual buffer-size info
This is a nasty new requirement, discovered as an aside while looking
into ways to resolve the ''crucial mismatch'' between the `OutputSlot`
and `BufferProvider`, using the proxy-implementation of `BufferProvider`
(thereby expanding on the recent draft with the `BufferProxyAdaptor`)

The point is, if the BufferMetadata will be used beyond the internal coordination
within BufferProvider, then it will be used as part of actual buffer storage.
And this implies that the actual size of the allocation may differ (be greater)
than the nominally required size (since we'll very likely employ some kind
of memory tiling, for reasons of performance).

This leads again to an analysis of `BufferMetadata` usage,
with the conclusion to add the actual storage size directly into the API,
but treat it as an ''extra'' and not integrated into the ''buffer type''

Phew ... quite complex alltogether
2026-03-16 23:45:24 +01:00
94320d2d23 BufferProvider: remove the lock-onlyNew feature
This might have seemed like a good idea, adding an additional ''consistency check''...
However — we ''do have'' a generic check, insofar `BufferMetadata` is a **state engine**.

As long as we're able to prevent, reliably, that the same buffer address
ends up being classified as a different buffer type, this should be enough
to prevent double-use of any buffer (letting aside that `BufferProvider` is
backed by an implementing memory allocator, which in itself should prevent
any double-use.

Removing this feature resolves some ambiguity in the overall design,
and allows to turn `BufferMetadata::lock(type, address)` into a private
implementation function.

In the old code, there were some external access paths directly entering
into that implementation function, which caused a lot of confusion (at least for me...)
2026-03-16 20:37:24 +01:00
7463228d38 BufferProvider: reorganise internal BufferStore API
This refacotring prepares for the planned changes in `OutputSlot`
 * introduce a new compound parameter (tuple) BufferAlloc
 * wire this through all calls involved with storage handling

__Background__:
 * `BufferMetadata` deemed important for the implementation of buffer storage
 * ''new requirement detected'': must be able to handle an actual storage block
   that is ''larger'' than the requested buffer size (⟼ tiling)
 * need compact and uniform info, also for the `BufferProxyAdaptor` callbacks
2026-03-16 00:41:16 +01:00
259d0a5728 BufferProvider: now able to relocate OutputSlot into Vault Layer
The old implementation of `DiagnosticOutputSlot` is now disabled
and will be re-written from scratch, and no longer tangled to `BufferProvider`

 - `OutputManager` remains in Steam-Layer for now
 - the `Timings` and `OutputSlot` are now a self-contained
2026-03-10 23:12:30 +01:00
7dee16ba90 BufferProvider: relocate into Vault Layer
building upon all the preparations done during the last days,
the compound of code connected to the `BufferProvide` can now
be migrated down into the vault:
 - `BuffHandle`
 - `BufferProvider`
 - `BufferMetadata`
 - `BufferProviderSetup`
 - the simple standard implementations
 - `DiagnosticBufferProvider`
 - all directly related unit tests
2026-03-08 00:53:41 +01:00
9c74466778 Tests: build an link a test-support library
This is something I wanted to clean-up since a very long time indeed,
but always postponed it, since it requires a lot of nasty clean-up and disentangling....

Several parts had been stashed away into `src/lib/test`, which are not really related:
 * the testrunner and testsuite builder
 * generic helper utilities
 * specialised test-support facilities, e.g. the EventLog

This changeset introduces a new top-level test folder and a namespace `::test`
Code from this folder is linked into a shared library `libtestsupport.so`,
which resides in the linkage hierarchy between »Vessel« and »Vault«,
yet is no longer part of the Lumiera application and only linked into the test-suite.
2026-03-06 23:16:32 +01:00
806db414dd Copyright: clarify and simplify the file headers
* Lumiera source code always was copyrighted by individual contributors
 * there is no entity "Lumiera.org" which holds any copyrights
 * Lumiera source code is provided under the GPL Version 2+

== Explanations ==
Lumiera as a whole is distributed under Copyleft, GNU General Public License Version 2 or above.
For this to become legally effective, the ''File COPYING in the root directory is sufficient.''

The licensing header in each file is not strictly necessary, yet considered good practice;
attaching a licence notice increases the likeliness that this information is retained
in case someone extracts individual code files. However, it is not by the presence of some
text, that legally binding licensing terms become effective; rather the fact matters that a
given piece of code was provably copyrighted and published under a license. Even reformatting
the code, renaming some variables or deleting parts of the code will not alter this legal
situation, but rather creates a derivative work, which is likewise covered by the GPL!

The most relevant information in the file header is the notice regarding the
time of the first individual copyright claim. By virtue of this initial copyright,
the first author is entitled to choose the terms of licensing. All further
modifications are permitted and covered by the License. The specific wording
or format of the copyright header is not legally relevant, as long as the
intention to publish under the GPL remains clear. The extended wording was
based on a recommendation by the FSF. It can be shortened, because the full terms
of the license are provided alongside the distribution, in the file COPYING.
2024-11-17 23:42:55 +01:00
a20e233ca0 Library: now using controlled seed and replaced rand (closes #1378)
After augmenting our `lib/random.hpp` abstraction framework to add the necessary flexibility,
a common seeding scheme was ''built into the Test-Runner.''
 * all tests relying on some kind of randomness should invoke `seedRand()`
 * this draws a seed from the `entropyGen` — which is also documented in the log
 * individual tests can now be launched with `--seed` to force a dedicated seed
 * moreover, tests should build a coherent structure of linked generators,
   especially when running concurrently. The existing tests were adapted accordingly

All usages of `rand()` in the code base were investigated and replaced
by suitable calls to our abstraction framework; the code base is thus
isolated from the actual implementation, simplifying further adaptation.
2024-11-17 19:45:41 +01:00
0b9e184fa3 Library: replace usages of rand() in the whole code base
* most usages are drop-in replacements
 * occasionally the other convenience functions can be used
 * verify call-paths from core code to identify usages
 * ensure reseeding for all tests involving some kind of randomness...

__Note__: some tests were not yet converted,
since their usage of randomness is actually not thread-safe.
This problem existed previously, since also `rand()` is not thread safe,
albeit in most cases it is possible to ignore this problem, as
''garbled internal state'' is also somehow „random“
2024-11-13 04:23:46 +01:00
5055ba7144 Block-Flow: rationalise iterator usage
...with the preceding IterableDecorator refactoring,
the navigation and access to the storage extents can now be
organised into a clear progression

Allocator::iterator -> EpochIter -> Epoch&

Convenience management and support functions can then be
pushed down into Epoch, while iteration control can be done
high-level in BlockFlow, based on the helpers in Epoch
2023-07-13 18:35:10 +02:00
946f7c17f7 Block-Flow: implement opening a new Epoch
..this is the most simple case, where no Epochs are opened yet
..add diagnostics to inspect alloc count and deadlines
..add accessors for the first/last underlying Extent
2023-07-13 04:41:58 +02:00
18904e5b58 Block-Flow: completed implementation of low-level cyclic extent storage
..verified boundary cases for expansion while retaining addresses
of currently active extents...
2023-07-12 21:55:50 +02:00
824a626c2e Block-Flow: investigate proper working of on-demand allocation
Library: add "obvious" utility to the IterExplorer, allowing to
         materialise all contents of the Pipeline into a container

...use this to take a snapshot of all currently active Extent addresses
2023-07-12 19:19:41 +02:00
f5813a1f29 Block-Flow: veryfy proper handling of extent reuse
- use a checksum to prove that ctor / dtor of "content" is not invoked
- let the usage of active extents "wrap around" so that the mem block is re-used
- verify that the same data is still there
2023-07-12 04:53:30 +02:00
6409e0eb36 Block-Flow: implement iteration and expansion of ExtentFamily
The low-level allocator is basically implemented now,
but we still need to check thoroughly that the tricky
wrap-around and expansion logic behaves sane...
(see #1311)
2023-07-11 03:52:24 +02:00
3401f18c2c Block-Flow: consider usage in ActivityTerm and rectify iteration
Iteration should just yield an Reference to an Extent,
thereby hiding all details of the actual raw storage (char[]).
This can be achieved by usind a wrapper type around a pointer
into the managing vector; from this pointer we may convert
into a vector::iterator with the trick described here

https://stackoverflow.com/a/37101607/444796


Furthermore, continued planning of the Activity-Language,
basically clarified the complete usage scenario for now;
seems all implementable right away without further difficulties
2023-07-11 01:08:26 +02:00
c1b16349f2 Block-Flow: define next steps for implementation of low-level allocator 2023-07-09 04:03:02 +02:00
022d40a8cf Block-Flow: initial draft of ExtentFamily storage
using a simple yet performant data structure.
Not clear yet if this approach is sustainable

- assuming that no value initialisation happens for POD payload
- performance trade-off growth when in wrapped-state vs using a list
2023-07-04 04:42:53 +02:00
23a6fbdf4f Scheduler: investigate modes of operation
- analysis of Activity usage
- derive possible memory management schemes
- research regarding asynchronous IO
- decision regarding the memory management scheme
2023-07-03 18:40:37 +02:00