explicate the JobPlanningSequence definition
..causing the compiler to instantiate the involved templates, i.e. get the complete pipeline definition through the compiler
This commit is contained in:
parent
b52a1a8366
commit
062e1bbdc1
4 changed files with 45 additions and 15 deletions
|
|
@ -175,9 +175,11 @@ namespace lib {
|
|||
typedef typename SRC::reference reference;
|
||||
typedef typename SRC::pointer pointer;
|
||||
|
||||
/** Metafunction: the resulting type when binding a functor of type FUN */
|
||||
/** Metafunction: the resulting type when binding ("flat mapping")
|
||||
* a functor of type FUN. Basically the result of binding a function
|
||||
* is again an IterExplorer (with an "expanded" state core type) */
|
||||
template<class FUN>
|
||||
struct Binding
|
||||
struct FlatMapped
|
||||
{
|
||||
typedef IterExplorer<_COM_<IterExplorer,FUN>, _COM_> Type;
|
||||
};
|
||||
|
|
@ -210,11 +212,11 @@ namespace lib {
|
|||
* of the result iterator.
|
||||
*/
|
||||
template<class FUN>
|
||||
IterExplorer<_COM_<IterExplorer,FUN>, _COM_>
|
||||
typename FlatMapped<FUN>::Type
|
||||
operator >>= (FUN explorer)
|
||||
{
|
||||
typedef _COM_<IterExplorer,FUN> Combinator; // instantiation of the combinator strategy
|
||||
typedef IterExplorer<Combinator, _COM_> ResultsIter; // result IterExplorer using that instance as state core
|
||||
typedef typename FlatMapped<FUN>::Type ResultsIter; // result IterExplorer using that instance as state core
|
||||
|
||||
return ResultsIter (
|
||||
Combinator (explorer // build a new iteration state core
|
||||
|
|
|
|||
|
|
@ -230,6 +230,13 @@ namespace meta{
|
|||
typedef typename FunctionSignature<function<SIG> >::Ret Ret;
|
||||
typedef typename FunctionSignature<function<SIG> >::Args Args;
|
||||
};
|
||||
/** Specialisation when using a function reference */
|
||||
template<typename SIG>
|
||||
struct _Fun<SIG&>
|
||||
{
|
||||
typedef typename FunctionSignature<function<SIG> >::Ret Ret;
|
||||
typedef typename FunctionSignature<function<SIG> >::Args Args;
|
||||
};
|
||||
/** Specialisation for passing a functor */
|
||||
template<typename SIG>
|
||||
struct _Fun<function<SIG> >
|
||||
|
|
|
|||
|
|
@ -28,6 +28,7 @@
|
|||
//#include "proc/state.hpp"
|
||||
#include "proc/engine/job.hpp"
|
||||
#include "proc/engine/job-ticket.hpp"
|
||||
#include "proc/engine/time-anchor.hpp"
|
||||
//#include "proc/engine/frame-coord.hpp"
|
||||
//#include "lib/time/timevalue.hpp"
|
||||
//#include "lib/time/timequant.hpp"
|
||||
|
|
@ -190,7 +191,7 @@ namespace engine {
|
|||
return this->wrapping(*prerequisites);
|
||||
// explanation: PlanningState represents a sequence of successive planning points.
|
||||
// actually this is implemented by switching an embedded JobPlanning element
|
||||
// through a sequence of states. Thus the initial state of the investigation
|
||||
// through a sequence of states. Thus the initial state of an investigation
|
||||
// (which is a JobPlanning) can stand-in for the sequence of prerequisites
|
||||
}
|
||||
|
||||
|
|
@ -210,10 +211,10 @@ namespace engine {
|
|||
|
||||
|
||||
inline PlanningState
|
||||
expandPrerequisites (PlanningState const& calculationStep)
|
||||
expandPrerequisites (JobPlanning const& calculationStep)
|
||||
{
|
||||
PlanningState newSubEvaluation(
|
||||
calculationStep->discoverPrerequisites());
|
||||
calculationStep.discoverPrerequisites());
|
||||
return newSubEvaluation;
|
||||
}
|
||||
|
||||
|
|
@ -233,11 +234,18 @@ namespace engine {
|
|||
*/
|
||||
class PlanningStepGenerator
|
||||
{
|
||||
engine::TimeAnchor anchor_;
|
||||
|
||||
public:
|
||||
typedef JobPlanning value_type;
|
||||
typedef JobPlanning& reference;
|
||||
typedef JobPlanning * pointer;
|
||||
|
||||
// PlanningStepGenerator() { }
|
||||
|
||||
PlanningStepGenerator(engine::TimeAnchor startPoint)
|
||||
: anchor_(startPoint)
|
||||
{ }
|
||||
|
||||
/* === Iteration control API for IterStateWrapper== */
|
||||
|
||||
|
|
@ -261,8 +269,14 @@ namespace engine {
|
|||
};
|
||||
|
||||
|
||||
#if false /////////////////////////////////////////////////////////////////////////////////////////////////////////////UNIMPLEMENTED :: TICKET #827
|
||||
#endif /////////////////////////////////////////////////////////////////////////////////////////////////////////////UNIMPLEMENTED :: TICKET #827
|
||||
|
||||
|
||||
typedef PlanningState (*SIG_expandPrerequisites) (JobPlanning const&);
|
||||
|
||||
typedef lib::IterExplorer<PlanningStepGenerator
|
||||
,lib::iter_explorer::RecursiveSelfIntegration> JobPlanningChunkStartPoint;
|
||||
|
||||
typedef JobPlanningChunkStartPoint::FlatMapped<SIG_expandPrerequisites>::Type ExpandedPlanningSequence;
|
||||
|
||||
|
||||
|
||||
|
|
@ -270,11 +284,18 @@ namespace engine {
|
|||
* @todo 6/12 WIP-WIP-WIP how to prepare jobs for scheduling
|
||||
*/
|
||||
class JobPlanningSequence
|
||||
: public lib::IterExplorer<PlanningStepGenerator
|
||||
,lib::iter_explorer::RecursiveSelfIntegration>
|
||||
: public ExpandedPlanningSequence
|
||||
{
|
||||
|
||||
public:
|
||||
// JobPlanningSequence() { }
|
||||
|
||||
JobPlanningSequence(engine::TimeAnchor startPoint)
|
||||
: ExpandedPlanningSequence(
|
||||
JobPlanningChunkStartPoint(
|
||||
PlanningStepGenerator(startPoint))
|
||||
>>= expandPrerequisites)
|
||||
{ }
|
||||
|
||||
};
|
||||
|
||||
|
|
|
|||
|
|
@ -2797,15 +2797,15 @@ From experiences with other middle scale projects, I prefer having the test code
|
|||
[img[Example: Interfaces/Namespaces of the ~Session-Subsystems|uml/fig130053.png]]
|
||||
</pre>
|
||||
</div>
|
||||
<div title="JobTicket" modifier="Ichthyostega" modified="201204290241" created="201202120018" tags="spec Rendering draft" changecount="12">
|
||||
<pre>The actual media data is rendered by [[individually scheduled render jobs|RenderJob]]. When preparing such jobs, in order to [[dispatch|FrameDispatcher]] the individual frames calculations required to make a given [[stream of calculations|CalcStream]] happen, a ''node planning phase'' is performed. The goal is to find out
|
||||
<div title="JobTicket" modifier="Ichthyostega" modified="201208311625" created="201202120018" tags="spec Rendering draft" changecount="14">
|
||||
<pre>The actual media data is rendered by [[individually scheduled render jobs|RenderJob]]. All these calculations together implement a [[stream of calculations|CalcStream]], as demanded and directed by the PlayProcess. During the preparation of playback, a ''node planning phase'' is performed, to arrange for [[dispatching|FrameDispatcher]] the individual calculations per frame. The goal of these //preparations//&nbsp; is to find out
|
||||
* what channel(s) to pull
|
||||
* what prerequisites to prepare
|
||||
* what parameters to provide
|
||||
The result of this planning phase is the {{{JobTicket}}}, a complete ''execution plan''.
|
||||
This planning is uniform for each segment and treated for all channels together, resulting in a nested tree structure of sub job tickets, allocated and stored alongside with the processing nodes and wiring descriptors to form the segment's data and descriptor network. Job tickets are //higher order functions:// entering a concrete frame number and channel into a given job ticket will produce an actual job descriptor, which in itself is again a function, to be invoked through the scheduler when it's time to trigger the actual calculations.
|
||||
This planning is uniform for each [[segment|Segmentation]] and treated for all channels together, resulting in a nested tree structure of sub job tickets, allocated and stored alongside with the processing nodes and wiring descriptors to form the segment's data and descriptor network. Job tickets are //higher order functions:// entering a concrete frame number and channel into a given job ticket will produce an actual job descriptor, which in itself is again a function, to be invoked through the scheduler when it's time to trigger the actual calculations.
|
||||
|
||||
!Structure of the render Jobs created
|
||||
!Structure of the Render Jobs created
|
||||
To be more precise: in the general case, invoking the ~JobTicket with a given frame number will produce //multiple jobs// -- typically each frame rendering will require at least one further source media frame; and because Lumiera render jobs will //never block waiting on IO,// this source media access will be packaged as a separate [[resource retrieving job|ResourceJob]], to be treated specifically by the scheduler.
|
||||
|
||||
To support the generation of multiple dependent jobs, a ~JobTicket might refer to further ~JobTickets corresponding to the prerequisites. These prerequisite ~JobTickets are the result of a classical recursive descent call into the top level ProcNode, to perform the planning step. There is always an 1:1 relation between actual jobs generated and the corresponding tickets. More precisely, for each possible job to generate there is a suitable ''job closure'', representing exactly the context information necessary to get that job started. To stress that point: a ProcNode might be configured such as to perform a series of recursive invocations of other prerequisite nodes right away (especially when those recursive invocations correspond just to further CPU bound calculations) -- yet still there is only //one//&nbsp; ~JobTicket, because there will be only one Job to invoke the whole sequence. On the other hand, when there is a prerequisite requiring an operation to be scheduled separately, a corresponding separate {{{JobClosure}}} will be referred.
|
||||
|
|
|
|||
Loading…
Reference in a new issue