Scheduler: solve problem with transport from entrance-queue
The test case "scheduleRenderJob()" -- while deliberately operated quite artificially with a disabled WorkForce (so the test can check the contents in the queue and then progress manually -- led to discovery of an open gap in the logic: in the (rare) case that a new task is added ''from the outside'' without acquiring the Grooming-Token, then the new task could sit in the entrace queue, in worst case for 50ms, until the next Scheduler-»Tick« routinely sweeps this queue. Under normal conditions however, each dispatch of another activity will also sweep the entrance queue, yet if there happens to be no other task right now, a new task could be stuck. Thinking through this problem also helped to amend some aspects of Grooming-Token handling and clarified the role of the API-functions.
This commit is contained in:
parent
7a22e7f987
commit
5c6354882d
6 changed files with 121 additions and 64 deletions
|
|
@ -97,6 +97,9 @@ namespace gear {
|
|||
namespace { // Configuration / Scheduling limit
|
||||
|
||||
Offset FUTURE_PLANNING_LIMIT{FSecs{20}}; ///< limit timespan of deadline into the future (~360 MiB max)
|
||||
|
||||
/** convenient short-notation, also used by SchedulerService */
|
||||
auto inline thisThread() { return std::this_thread::get_id(); }
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -115,8 +118,6 @@ namespace gear {
|
|||
using ThreadID = std::thread::id;
|
||||
atomic<ThreadID> groomingToken_{};
|
||||
|
||||
auto thisThread() { return std::this_thread::get_id(); }
|
||||
|
||||
|
||||
public:
|
||||
SchedulerCommutator() = default;
|
||||
|
|
@ -195,6 +196,16 @@ namespace gear {
|
|||
}
|
||||
|
||||
|
||||
/** tend to the input queue if possible */
|
||||
void
|
||||
maybeFeed (SchedulerInvocation& layer1)
|
||||
{
|
||||
if (layer1.hasPendingInput()
|
||||
and (holdsGroomingToken(thisThread())
|
||||
or acquireGoomingToken()))
|
||||
layer1.feedPrioritisation();
|
||||
}
|
||||
|
||||
/**
|
||||
* Look into the queues and possibly retrieve work due by now.
|
||||
* @note transparently discards any outdated entries,
|
||||
|
|
|
|||
|
|
@ -305,6 +305,12 @@ namespace gear {
|
|||
and isActivated (priority_.top().manifestation));
|
||||
}
|
||||
|
||||
bool
|
||||
hasPendingInput() const
|
||||
{
|
||||
return not instruct_.empty();
|
||||
}
|
||||
|
||||
bool
|
||||
empty() const
|
||||
{
|
||||
|
|
|
|||
|
|
@ -306,8 +306,6 @@ namespace gear {
|
|||
}
|
||||
|
||||
|
||||
void postChain (ActivationEvent); //////////////////////////////////////OOO could be private?
|
||||
|
||||
|
||||
/**
|
||||
* The worker-Functor: called by the active Workers from the
|
||||
|
|
@ -317,6 +315,7 @@ namespace gear {
|
|||
|
||||
|
||||
private:
|
||||
void postChain (ActivationEvent);
|
||||
void handleDutyCycle (Time now);
|
||||
void handleWorkerTermination (bool isFailure);
|
||||
void maybeScaleWorkForce();
|
||||
|
|
@ -366,6 +365,13 @@ namespace gear {
|
|||
return setup;
|
||||
}
|
||||
|
||||
void
|
||||
ensureDroppedGroomingToken()
|
||||
{
|
||||
if (layer2_.holdsGroomingToken (thisThread()))
|
||||
layer2_.dropGroomingToken();
|
||||
}
|
||||
|
||||
/** access high-resolution-clock, rounded to µ-Ticks */
|
||||
Time
|
||||
getSchedTime()
|
||||
|
|
@ -466,6 +472,7 @@ namespace gear {
|
|||
scheduler_.engineObserver_.dispatchEvent(qualifier, WorkTiming::stop(now));
|
||||
}
|
||||
|
||||
/** λ-tick : scheduler management duty cycle */
|
||||
activity::Proc
|
||||
tick (Time now)
|
||||
{
|
||||
|
|
@ -511,6 +518,7 @@ namespace gear {
|
|||
, death_
|
||||
, manID_
|
||||
, isCompulsory_});
|
||||
theScheduler_.ensureDroppedGroomingToken();
|
||||
return move(*this);
|
||||
}
|
||||
|
||||
|
|
@ -551,10 +559,10 @@ namespace gear {
|
|||
inline activity::Proc
|
||||
Scheduler::getWork()
|
||||
{
|
||||
auto self = std::this_thread::get_id();
|
||||
try {
|
||||
auto res = WorkerInstruction{}
|
||||
.performStep([&]{
|
||||
layer2_.maybeFeed(layer1_);
|
||||
Time now = getSchedTime();
|
||||
Time head = layer1_.headTime();
|
||||
return scatteredDelay(now,
|
||||
|
|
@ -567,6 +575,7 @@ namespace gear {
|
|||
return layer2_.postDispatch (toDispatch, ctx, layer1_);
|
||||
})
|
||||
.performStep([&]{
|
||||
layer2_.maybeFeed(layer1_);
|
||||
Time now = getSchedTime();
|
||||
Time head = layer1_.headTime();
|
||||
return scatteredDelay(now,
|
||||
|
|
@ -574,15 +583,13 @@ namespace gear {
|
|||
});
|
||||
|
||||
// ensure lock clean-up
|
||||
if (res != activity::PASS
|
||||
and layer2_.holdsGroomingToken(self))
|
||||
layer2_.dropGroomingToken();
|
||||
if (res != activity::PASS)
|
||||
ensureDroppedGroomingToken();
|
||||
return res;
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
if (layer2_.holdsGroomingToken (self))
|
||||
layer2_.dropGroomingToken();
|
||||
ensureDroppedGroomingToken();
|
||||
throw;
|
||||
}
|
||||
}
|
||||
|
|
@ -606,19 +613,16 @@ namespace gear {
|
|||
{
|
||||
auto doTargetedSleep = [&]
|
||||
{ // ensure not to block the Scheduler after management work
|
||||
auto self = std::this_thread::get_id();
|
||||
if (layer2_.holdsGroomingToken (self))
|
||||
layer2_.dropGroomingToken();
|
||||
// relocate this thread(capacity) to a time where its more useful
|
||||
ensureDroppedGroomingToken();
|
||||
// relocate this thread(capacity) to a time where its more useful
|
||||
Offset targetedDelay = loadControl_.scatteredDelayTime (now, capacity);
|
||||
std::this_thread::sleep_for (std::chrono::microseconds (_raw(targetedDelay)));
|
||||
};
|
||||
auto doTendNextHead = [&]
|
||||
{
|
||||
Time head = layer1_.headTime();
|
||||
auto self = std::this_thread::get_id();
|
||||
if (not loadControl_.tendedNext(head)
|
||||
and (layer2_.holdsGroomingToken(self)
|
||||
and (layer2_.holdsGroomingToken(thisThread())
|
||||
or layer2_.acquireGoomingToken()))
|
||||
loadControl_.tendNext(head);
|
||||
};
|
||||
|
|
|
|||
|
|
@ -236,7 +236,7 @@ namespace gear {
|
|||
void
|
||||
incScale()
|
||||
{
|
||||
if (size() > setup_.COMPUTATION_CAPACITY)
|
||||
if (size() >= setup_.COMPUTATION_CAPACITY)
|
||||
return;
|
||||
else
|
||||
workers_.emplace_back (setup_);
|
||||
|
|
|
|||
|
|
@ -31,6 +31,7 @@
|
|||
#include "lib/time/timevalue.hpp"
|
||||
#include "lib/format-cout.hpp"
|
||||
#include "lib/format-string.hpp"
|
||||
#include "lib/test/transiently.hpp"
|
||||
#include "lib/test/microbenchmark.hpp"
|
||||
#include "lib/test/diagnostic-output.hpp"///////////////TODO
|
||||
#include "lib/util.hpp"
|
||||
|
|
@ -466,6 +467,9 @@ namespace test {
|
|||
BlockFlowAlloc bFlow;
|
||||
EngineObserver watch;
|
||||
Scheduler scheduler{bFlow, watch};
|
||||
|
||||
// prevent scale-up of the Scheuler's WorkForce
|
||||
TRANSIENTLY(work::Config::COMPUTATION_CAPACITY) = 0;
|
||||
|
||||
Time nominal{7,7};
|
||||
Time start{0,1};
|
||||
|
|
@ -481,8 +485,8 @@ namespace test {
|
|||
SHOW_EXPR(offset())
|
||||
auto buidl=
|
||||
scheduler.defineSchedule(testJob)
|
||||
.startOffset(200us)
|
||||
.lifeWindow (1ms);
|
||||
.startOffset(400us)
|
||||
.lifeWindow (2ms);
|
||||
SHOW_EXPR(offset())
|
||||
buidl .post();
|
||||
|
||||
|
|
@ -493,7 +497,6 @@ SHOW_EXPR(offset())
|
|||
sleep_for(400us);
|
||||
// CHECK (detector.ensureNoInvocation("testJob"));
|
||||
SHOW_EXPR(offset())
|
||||
scheduler.layer1_.feedPrioritisation();
|
||||
auto res= scheduler.getWork();
|
||||
SHOW_EXPR(offset())
|
||||
SHOW_EXPR(res)
|
||||
|
|
|
|||
|
|
@ -82730,6 +82730,39 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
</node>
|
||||
</node>
|
||||
</node>
|
||||
<node COLOR="#338800" CREATED="1699472012351" FOLDED="true" ID="ID_1226214188" MODIFIED="1699472610417" TEXT="Bedienen der Eingangs-Queue stets sicherstellen">
|
||||
<linktarget COLOR="#4bd448" DESTINATION="ID_1226214188" ENDARROW="Default" ENDINCLINATION="-543;31;" ID="Arrow_ID_1563551910" SOURCE="ID_1620543415" STARTARROW="None" STARTINCLINATION="-231;0;"/>
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node BACKGROUND_COLOR="#c8c0b6" COLOR="#420d67" CREATED="1699472120064" ID="ID_1534221280" MODIFIED="1699472153348" TEXT="nebbich...">
|
||||
<font ITALIC="true" NAME="SansSerif" SIZE="12"/>
|
||||
<icon BUILTIN="smily_bad"/>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1699472162491" ID="ID_903900691" MODIFIED="1699472589008" TEXT="...sonst würden neue Events schlimmstenfalls bis zum nächsten Tick hängenbleiben können...">
|
||||
<richcontent TYPE="NOTE"><html>
|
||||
<head/>
|
||||
<body>
|
||||
<p>
|
||||
<u>Erläuterung</u>:
|
||||
</p>
|
||||
<p>
|
||||
Die gesamte Entscheidungs-Logik baut auf dem Head der Priority-Queue auf. Sofern man aber das GroomingToken nicht erlangen kann (oder will), gehen neue ActivationEvent erst einmal in die Lock-free Instruct-queue. Sie werden von dort <i>nebenbei mit weiterbefördert,</i> und zwar immer dann, wenn jemand grade das Grooming-Token hat und sich an den Queues zu schaffen macht. Leider ist dieser Umstand nur garantiert der Fall im Scheduler-»Tick« — wenngleich auch im regulären Betrieb fast immer irgendwo was „unterwegs“ sein sollte, und deshalb auch das <i>nebenbei Auskehren, </i>praktisch immer funktioniert. Aufgefallen war mir das Problem nur in einem künstlichen Test-Setup SchedulerService_test::scheduleRenderJob(), wo ich die Worker bewußt außer Gefecht gesetzt habe. Aber es gibt eben durchaus mögliche Umstände, wo das auch passieren könnte:
|
||||
</p>
|
||||
<ul>
|
||||
<li>
|
||||
wenn jemand ganz von Außen etwas einstellt
|
||||
</li>
|
||||
<li>
|
||||
wenn grade ein anderer Worker mit Management-Aufgaben beschäftigt ist, aber am <i>Auskehren der Eingangsqueue</i> bereits vorbei ist.
|
||||
</li>
|
||||
</ul>
|
||||
<p>
|
||||
Grade in letzterem Fall könnte es passieren, daß das dummer Weise die letzte Aktion ist, und dann eine lange Pause kommt, bis zum nächsten Tick. Man könnte zwar so etwas leicht beim Einplanen neuer Jobs kompensieren, aber das ist genau die Art von heimtückischer Verkoppelung, die ich um jeden Preis zu verhindern suche.
|
||||
</p>
|
||||
</body>
|
||||
</html></richcontent>
|
||||
<icon BUILTIN="messagebox_warning"/>
|
||||
</node>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#eef0c5" COLOR="#990000" CREATED="1698004014170" ID="ID_359097355" MODIFIED="1699235836029" TEXT="Test">
|
||||
<icon BUILTIN="pencil"/>
|
||||
<node COLOR="#435e98" CREATED="1698203252783" ID="ID_161810851" MODIFIED="1698240150155" TEXT="was kann man hier sinnvoll testen?">
|
||||
|
|
@ -83016,8 +83049,8 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
</node>
|
||||
<node CREATED="1699068495938" ID="ID_1790197795" MODIFIED="1699068527242" TEXT="das ist ein internes API — aber die zentrale Achse"/>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#fafe99" COLOR="#fa002a" CREATED="1699313803867" HGAP="-20" ID="ID_1032033223" MODIFIED="1699328444728" TEXT="Logik-Fehler: neu geplanter Job steckt fest" VSHIFT="18">
|
||||
<linktarget COLOR="#f91d6b" DESTINATION="ID_1032033223" ENDARROW="Default" ENDINCLINATION="-973;63;" ID="Arrow_ID_46385590" SOURCE="ID_550874585" STARTARROW="None" STARTINCLINATION="630;-68;"/>
|
||||
<node COLOR="#435e98" CREATED="1699313803867" HGAP="-20" ID="ID_1032033223" MODIFIED="1699472735854" TEXT="Logik-Fehler: neu geplanter Job steckt fest" VSHIFT="18">
|
||||
<linktarget COLOR="#1d60f9" DESTINATION="ID_1032033223" ENDARROW="Default" ENDINCLINATION="-973;63;" ID="Arrow_ID_46385590" SOURCE="ID_550874585" STARTARROW="None" STARTINCLINATION="630;-68;"/>
|
||||
<icon BUILTIN="broken-line"/>
|
||||
<node CREATED="1699314171601" ID="ID_911884909" MODIFIED="1699314174654" TEXT="Szenario">
|
||||
<node CREATED="1699314175722" ID="ID_760916314" MODIFIED="1699314218863" TEXT="Render-Job per high-level API eingestellt">
|
||||
|
|
@ -83028,10 +83061,11 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<icon BUILTIN="forward"/>
|
||||
</node>
|
||||
</node>
|
||||
<node CREATED="1699314283068" ID="ID_1215190474" MODIFIED="1699314330289" TEXT="Problem-Situation">
|
||||
<node CREATED="1699314283068" ID="ID_1215190474" MODIFIED="1699472726565" TEXT="Problem-Situation">
|
||||
<icon BUILTIN="info"/>
|
||||
<node CREATED="1699314331405" ID="ID_601536457" MODIFIED="1699314347447" TEXT="das neue ActivationEvent sitzt noch in der Eingangs-Queue"/>
|
||||
<node CREATED="1699314348751" ID="ID_786038008" MODIFIED="1699314417293" TEXT="⟹ die pre-Dispatch-Kapazitätssteuerung ⟼ idle-WAIT"/>
|
||||
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1699314450362" ID="ID_1548210369" MODIFIED="1699314482186" TEXT="Problem: solange niemand das Grooming-Token hat, passiert kein feedPrioritisation()">
|
||||
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1699314450362" ID="ID_1548210369" MODIFIED="1699472717737" TEXT="Problem: solange niemand das Grooming-Token hat, passiert kein feedPrioritisation()">
|
||||
<icon BUILTIN="clanbomber"/>
|
||||
<node CREATED="1699314936837" ID="ID_1589318425" MODIFIED="1699315051503" TEXT="die pre-Dispatch-Kapazitätssteuerung will das (bisher) nicht machen">
|
||||
<richcontent TYPE="NOTE"><html>
|
||||
|
|
@ -83053,7 +83087,7 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<node CREATED="1699315202665" ID="ID_1173720570" MODIFIED="1699315242168" TEXT="außerdem würde jeder aktive Dispatch das auslösen"/>
|
||||
</node>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1699314501904" ID="ID_39607284" MODIFIED="1699315340563" TEXT="das ist eine Lücke im Konzept auf Ebene der Komponenten-Integration">
|
||||
<node COLOR="#435e98" CREATED="1699314501904" ID="ID_39607284" MODIFIED="1699472722313" TEXT="das ist eine Lücke im Konzept auf Ebene der Komponenten-Integration">
|
||||
<icon BUILTIN="yes"/>
|
||||
<node CREATED="1699315440090" ID="ID_1962711320" MODIFIED="1699315495053" TEXT="gemäß geplantem Nutzen nicht wirklich relevant">
|
||||
<linktarget COLOR="#2b2ab6" DESTINATION="ID_1962711320" ENDARROW="Default" ENDINCLINATION="32;-22;" ID="Arrow_ID_747379729" SOURCE="ID_1445276544" STARTARROW="None" STARTINCLINATION="-224;9;"/>
|
||||
|
|
@ -83075,12 +83109,13 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<arrowlink COLOR="#373a76" DESTINATION="ID_1435123962" ENDARROW="Default" ENDINCLINATION="304;54;" ID="Arrow_ID_928822414" STARTARROW="None" STARTINCLINATION="-255;13;"/>
|
||||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
<node CREATED="1699401804396" ID="ID_1620543415" MODIFIED="1699402101803" TEXT="tendiere dazu, dieses Problem „unter den Teppich zu kehren“">
|
||||
<node COLOR="#338800" CREATED="1699401804396" ID="ID_1620543415" MODIFIED="1699472703173" TEXT="möglichst unauffällig gefixt">
|
||||
<richcontent TYPE="NOTE"><html>
|
||||
<head>
|
||||
|
||||
</head>
|
||||
<head/>
|
||||
<body>
|
||||
<p>
|
||||
Ich finde dieses Problem ziemlich ärgerlich, und würde es am liebsten „unter den Teppich kehren“
|
||||
</p>
|
||||
<p>
|
||||
Warum?
|
||||
</p>
|
||||
|
|
@ -83099,14 +83134,24 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
</li>
|
||||
</ul>
|
||||
<p>
|
||||
Und — <i>last but not least </i>— die Lösung ist hässlich und redundant: man müßte das in die work-Function ganz am Anfang reinhängen. Oder zumindest in die Kapazitäts-Behandlung (im 1. und 3.Block)
|
||||
Und — <i>last but not least </i>— die Lösung ist hässlich und redundant; effektiv müßte der Check in jedem Aufruf der Work-Function laufen, und würde auch das Grooming-Token benötigen....
|
||||
</p>
|
||||
<p>
|
||||
|
||||
</p>
|
||||
<p>
|
||||
Aber letztlich: <font color="#8315ca">↯</font> <b><font color="#c30665">Augen zu und durch </font></b><font color="#8315ca">↯ </font>! So eine Falle darf nicht in der Logik bleiben. Der Scheduler ist so komplex, daß ich jetzt Wochen gebraucht habe, um alle Zusammenhänge herzustellen, und der Code ist extra mit vielen Abstraktionen so geschrieben, daß man immer alles im Detail verstehen muß. Eine solche Lücke würde das untergraben. Daher baue ich jetzt den Fix unauffälig in die Kapazitäts-Behandlung mit ein. Und zwar sowohl <b>pre-Dispatch</b>, alsoauch <b>post-Dispatch</b> — denn auch bei letzterem hätten wir noch die gleiche Lücke (wenn jemand pre-Dispatch das Grooming-Token nicht erlangen kann)
|
||||
</p>
|
||||
</body>
|
||||
</html>
|
||||
</richcontent>
|
||||
</html></richcontent>
|
||||
<arrowlink COLOR="#4bd448" DESTINATION="ID_1226214188" ENDARROW="Default" ENDINCLINATION="-543;31;" ID="Arrow_ID_1563551910" STARTARROW="None" STARTINCLINATION="-231;0;"/>
|
||||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
</node>
|
||||
</node>
|
||||
<node COLOR="#338800" CREATED="1699472727759" ID="ID_675352193" MODIFIED="1699472733833" TEXT="Problem gefixt, Test läuft...">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
</node>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#d2beaf" COLOR="#5c4d6e" CREATED="1697763699242" ID="ID_272943268" MODIFIED="1699414198627" TEXT="EngineObserver-Schnittstelle">
|
||||
|
|
@ -92516,8 +92561,8 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<arrowlink COLOR="#f4336b" DESTINATION="ID_1142273023" ENDARROW="Default" ENDINCLINATION="-737;663;" ID="Arrow_ID_891496003" STARTARROW="None" STARTINCLINATION="1218;-76;"/>
|
||||
<icon BUILTIN="button_ok"/>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#fdfdcf" COLOR="#ff0000" CREATED="1699243361425" ID="ID_565283839" MODIFIED="1699328504602" TEXT="ruft die work-Function direkt auf">
|
||||
<icon BUILTIN="flag-pink"/>
|
||||
<node COLOR="#338800" CREATED="1699243361425" ID="ID_565283839" MODIFIED="1699472780291" TEXT="ruft die work-Function direkt auf">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node CREATED="1699328505477" ID="ID_1796712383" MODIFIED="1699328750570" TEXT="keine WorkForce">
|
||||
<icon BUILTIN="yes"/>
|
||||
</node>
|
||||
|
|
@ -92534,7 +92579,7 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<node CREATED="1699328525667" ID="ID_956033802" MODIFIED="1699328535177" TEXT="WorkForce skaliert automatisch">
|
||||
<icon BUILTIN="messagebox_warning"/>
|
||||
</node>
|
||||
<node CREATED="1699328910407" ID="ID_337063855" MODIFIED="1699328936432" TEXT="Ausweg: WorkForce-Stärke manipulieren">
|
||||
<node COLOR="#435e98" CREATED="1699328910407" FOLDED="true" ID="ID_337063855" MODIFIED="1699472777212" TEXT="Ausweg: WorkForce-Stärke manipulieren">
|
||||
<icon BUILTIN="idea"/>
|
||||
<node CREATED="1699328956633" ID="ID_1757255005" MODIFIED="1699368367892" TEXT="das wäre dann ein WorkForce-Betriebsparameter">
|
||||
<arrowlink COLOR="#786a97" DESTINATION="ID_1177531499" ENDARROW="Default" ENDINCLINATION="-920;53;" ID="Arrow_ID_1670167461" STARTARROW="None" STARTINCLINATION="61;-138;"/>
|
||||
|
|
@ -92545,12 +92590,15 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
</node>
|
||||
</node>
|
||||
</node>
|
||||
<node BACKGROUND_COLOR="#fafe99" COLOR="#fa002a" CREATED="1699243391733" ID="ID_1214068544" MODIFIED="1699310666524" TEXT="verifiziert Aufruf per Log">
|
||||
<icon BUILTIN="broken-line"/>
|
||||
<node BACKGROUND_COLOR="#fafe99" COLOR="#fa002a" CREATED="1699313612489" ID="ID_550874585" MODIFIED="1699328444728" TEXT="Fehler in der Schedule/Dispatch-Logik">
|
||||
<arrowlink COLOR="#f91d6b" DESTINATION="ID_1032033223" ENDARROW="Default" ENDINCLINATION="-973;63;" ID="Arrow_ID_46385590" STARTARROW="None" STARTINCLINATION="630;-68;"/>
|
||||
<node COLOR="#338800" CREATED="1699243391733" ID="ID_1214068544" MODIFIED="1699472763073" TEXT="verifiziert Aufruf per Log">
|
||||
<icon BUILTIN="button_ok"/>
|
||||
<node BACKGROUND_COLOR="#e0ceaa" COLOR="#690f14" CREATED="1699313612489" ID="ID_550874585" MODIFIED="1699472757847" TEXT="Fehler in der Schedule/Dispatch-Logik">
|
||||
<arrowlink COLOR="#1d60f9" DESTINATION="ID_1032033223" ENDARROW="Default" ENDINCLINATION="-973;63;" ID="Arrow_ID_46385590" STARTARROW="None" STARTINCLINATION="630;-68;"/>
|
||||
<icon BUILTIN="broken-line"/>
|
||||
</node>
|
||||
<node COLOR="#435e98" CREATED="1699472790287" ID="ID_825157701" MODIFIED="1699472819342" TEXT="Anpassung: ohne WorkForce und Layer2.maybeFeed()">
|
||||
<icon BUILTIN="idea"/>
|
||||
</node>
|
||||
</node>
|
||||
</node>
|
||||
</node>
|
||||
|
|
@ -94922,16 +94970,13 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<node CREATED="1699403217120" ID="ID_120723001" MODIFIED="1699403224072" TEXT="eine Eingangs-Dispatch-Queue"/>
|
||||
<node CREATED="1699403254867" ID="ID_1562054545" MODIFIED="1699403320882" TEXT="Einspeisen von Nachrichten sehr effizient">
|
||||
<richcontent TYPE="NOTE"><html>
|
||||
<head>
|
||||
|
||||
</head>
|
||||
<head/>
|
||||
<body>
|
||||
<p>
|
||||
Aufruf  aus der Berechnung heraus möglich, d.h. darf höchstens ein paar µs kosten
|
||||
</p>
|
||||
</body>
|
||||
</html>
|
||||
</richcontent>
|
||||
</html></richcontent>
|
||||
</node>
|
||||
<node CREATED="1699403383634" ID="ID_72666374" MODIFIED="1699403396396" TEXT="Addresse ist codiert in einen size_t - Hash">
|
||||
<node CREATED="1699404688180" ID="ID_1754251698" MODIFIED="1699404705526" TEXT="sie repräsentiert einen symbolischen, hierarchischen Endpunkt"/>
|
||||
|
|
@ -94944,16 +94989,13 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
</node>
|
||||
<node CREATED="1699405149557" ID="ID_1423036678" MODIFIED="1699405164251">
|
||||
<richcontent TYPE="NODE"><html>
|
||||
<head>
|
||||
|
||||
</head>
|
||||
<head/>
|
||||
<body>
|
||||
<p>
|
||||
Empfang/Zustellung laufen <b>single-Threaded</b>
|
||||
</p>
|
||||
</body>
|
||||
</html>
|
||||
</richcontent>
|
||||
</html></richcontent>
|
||||
<node CREATED="1699405165067" ID="ID_229778014" MODIFIED="1699405192201" TEXT="könnte implementiert sein als ein separater Event-Thread"/>
|
||||
<node CREATED="1699405193033" ID="ID_1200939317" MODIFIED="1699405209359" TEXT="Alternativ: läuft unter GroomingToken im Scheduler-»Tick«"/>
|
||||
</node>
|
||||
|
|
@ -94969,16 +95011,13 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
</node>
|
||||
<node CREATED="1699405707070" ID="ID_1718899201" MODIFIED="1699405742710">
|
||||
<richcontent TYPE="NODE"><html>
|
||||
<head>
|
||||
|
||||
</head>
|
||||
<head/>
|
||||
<body>
|
||||
<p>
|
||||
<u>Leitbild</u>: <font face="Monospaced">TimingObservable</font>
|
||||
</p>
|
||||
</body>
|
||||
</html>
|
||||
</richcontent>
|
||||
</html></richcontent>
|
||||
<icon BUILTIN="info"/>
|
||||
</node>
|
||||
</node>
|
||||
|
|
@ -94990,16 +95029,13 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<icon BUILTIN="button_ok"/>
|
||||
<node COLOR="#435e98" CREATED="1699413973971" ID="ID_1307699016" MODIFIED="1699414043369">
|
||||
<richcontent TYPE="NODE"><html>
|
||||
<head>
|
||||
|
||||
</head>
|
||||
<head/>
|
||||
<body>
|
||||
<p>
|
||||
<b>EngineEvent</b>-Basisstruktur
|
||||
</p>
|
||||
</body>
|
||||
</html>
|
||||
</richcontent>
|
||||
</html></richcontent>
|
||||
<icon BUILTIN="info"/>
|
||||
<node CREATED="1699414045739" ID="ID_3506591" MODIFIED="1699414061765" TEXT="Symbol + binäre opaque Payload"/>
|
||||
<node CREATED="1699414063936" ID="ID_1879697605" MODIFIED="1699414079359" TEXT="für Payload einen Union-cast-Mechanismus vorsehen"/>
|
||||
|
|
@ -95009,16 +95045,13 @@ Date:   Thu Apr 20 18:53:17 2023 +0200<br/>
|
|||
<node CREATED="1699414118433" ID="ID_639697248" MODIFIED="1699414141250" TEXT="T ist ein Tupel / Record mit den zu publizierenden Daten"/>
|
||||
<node CREATED="1699414142638" ID="ID_529883499" MODIFIED="1699414172640">
|
||||
<richcontent TYPE="NODE"><html>
|
||||
<head>
|
||||
|
||||
</head>
|
||||
<head/>
|
||||
<body>
|
||||
<p>
|
||||
<u>Größenbeschränkung</u>: <b>4 »Slots«</b>
|
||||
</p>
|
||||
</body>
|
||||
</html>
|
||||
</richcontent>
|
||||
</html></richcontent>
|
||||
<icon BUILTIN="yes"/>
|
||||
</node>
|
||||
</node>
|
||||
|
|
|
|||
Loading…
Reference in a new issue