summaryrefslogtreecommitdiff
path: root/TAO/orbsvcs/orbsvcs/RtecScheduler.idl
blob: 998e856cb8e118c9274c070934e968edd72b444e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
// $Id$

#include "CosTimeBase.idl"

module RtecScheduler
{
  // Module TimeBase defines the OMG Time Service.
  typedef TimeBase::TimeT Time; // 100 nanoseconds
  typedef Time Quantum;

  typedef long Period; // 100 nanoseconds

  enum Importance
  // Defines the importance of the operation,
  // which can be used by the Scheduler as a
  // "tie-breaker" when other scheduling
  // parameters are equal.
  {
    VERY_LOW_IMPORTANCE,
    LOW_IMPORTANCE,
    MEDIUM_IMPORTANCE,
    HIGH_IMPORTANCE,
    VERY_HIGH_IMPORTANCE
  };

  typedef long handle_t;
  // RT_Info's are assigned per-application
  // unique identifiers.

  struct Dependency_Info
  {
    long number_of_calls;
    handle_t rt_info;
    // Notice the reference to the RT_Info we
    // depend on.
  };

  typedef sequence<Dependency_Info> Dependency_Set;

  typedef long OS_Priority;
  typedef long Sub_Priority;
  typedef long Preemption_Priority;

  struct RT_Info
    // = TITLE
    //   Describes the QoS for an "RT_Operation".
    //
    // = DESCRIPTION
    // The CPU requirements and QoS for each
    // "entity" implementing an application
    // operation is described by the following
    // information.
  {
    // Application-defined string that uniquely
    // identifies the operation.
    string entry_point;

    // The scheduler-defined unique identifier.
    handle_t handle;

    // Execution times.
    Time worst_case_execution_time;
    Time typical_execution_time;

    // To account for server data caching.
    Time cached_execution_time;

    // For rate-base operations, this expresses
    // the rate.  0 means "completely pasive",
    // i.e., this operation only executes when
    // called.
    Period period;

    // Operation importance, used to "break ties".
    Importance importance;

    // For time-slicing (for BACKGROUND operations only).
    Quantum quantum;

    // The number of internal threads contained by
    // the operation.
    long threads;

    // The following attributes are defined by
    // the Scheduler once the off-line schedule
    // is computed.

    // The operations we depend upon.
    Dependency_Set dependencies;

    // The OS por processing the events generated
    // from this RT_Info.
    OS_Priority priority;

    // For ordering RT_Info's with equal priority.
    Sub_Priority subpriority;

    // The queue number for this RT_Info.
    Preemption_Priority preemption_priority;
  };

  exception DUPLICATE_NAME {};
  // The application is trying to register the same task again.

  exception UNKNOWN_TASK {};
  // The RT_Info handle was not valid.

  exception NOT_SCHEDULED {};
  // The application is trying to obtain scheduling information, but
  // none is available.

  exception UTILIZATION_BOUND_EXCEEDED {};
  exception INSUFFICIENT_THREAD_PRIORITY_LEVELS {};
  exception TASK_COUNT_MISMATCH {};
  // Problems while computing off-line scheduling.

  typedef sequence<RT_Info> RT_Info_Set;

  // TODO: Find a reasonable name for this interface, maybe we should
  // change the name of the module to RtecSchedulerAdmin and name this
  // Scheduler
  interface Scheduler
    // = DESCRIPTION
    //   This class holds all the RT_Info's for a single application.
    //   During the configuration run this will be implemented as a
    //   single remote object, whose services are used by the
    //   suppliers, consumers and the EC.
    //   At run-time each process will hold a copy of the compiled
    //   version of the Scheduler, using the precomputed data to
    //   resolve requests (avoiding any remote calls) and ignoring any
    //   requests for modifying its state.
    //   A Factory class will be used to choose the proper
    //   implementation.
    //
    //   This class must be registered with the naming service using a
    //   well known name ("Scheduler" seems the obvious choice), the
    //   Naming Context will account for different applications and
    //   modes.
    //
    //   Once the scheduling data is computed it can be retrieved
    //   remotely to generate the code for the run-time version.
  {
    handle_t create (in string entry_point) raises (DUPLICATE_NAME);
    // Creates a new RT_Info entry for the function identifier
    // "entry_point", it can be any string, but the fully qualified
    // name function name is suggested.
    // Returns a handle to the RT_Info.

    handle_t lookup (in string entry_point);
    // Lookups a handle for entry_point.
    // TODO: Should we add INVALID_HANDLE or raise an exception?

    RT_Info get (in handle_t handle) raises (UNKNOWN_TASK);
    // Retrieve information about an RT_Info.

    void set (in handle_t handle,
              in Time time,
              in Time typical_time,
              in Time cached_time,
              in Period period,
              in Importance importance,
              in Quantum quantum,
              in long threads)
      raises (UNKNOWN_TASK);
    // Set the attributes of an RT_Info.
    // Notice that some values may not be modified (like priority).

    void add_dependency (in handle_t handle,
                         in handle_t dependency,
                         in long number_of_calls)
      raises (UNKNOWN_TASK);
    // Adds <dependency> to <handle>

    void priority (in handle_t handle,
                       out OS_Priority priority,
                       out Sub_Priority subpriority,
                       out Preemption_Priority p_priority)
      raises (UNKNOWN_TASK, NOT_SCHEDULED);
    void entry_point_priority (in string entry_point,
                               out OS_Priority priority,
                               out Sub_Priority subpriority,
                               out Preemption_Priority p_priority)
      raises (UNKNOWN_TASK, NOT_SCHEDULED);
    // Obtain the run time priorities.
    // TODO: Do we need the two interfaces or is it simply confusing?
    // If we should to keep only the <handle> version: Are the extra
    // round-trips too expensive?
    // If we choose only the <entry_point> version: Are the copies for
    // the string affordable?

    void compute_scheduling (in long minimum_priority,
                             in long maximum_priority,
                             out RT_Info_Set infos)
      raises (UTILIZATION_BOUND_EXCEEDED,
              INSUFFICIENT_THREAD_PRIORITY_LEVELS,
              TASK_COUNT_MISMATCH);
    // Computes the scheduling priorities, returns the RT_Info's with
    // their priorities properly filled.
    // This info can be cached by a Run_Time_Scheduler service or
    // dumped into a C++ file for compilation and even faster (static)
    // lookup.

    // TODO: The dependencies field can be removed from the RT_Info
    // and made part of the secrets of "Application", adding the
    // following to satisfy curious clients:
    //
    // struct Dependency {
    //   long number_of_calls;
    //   handle_t dependency;
    // };
    // typedef sequence<Dependency> Dependency_Set;
    //
    // Dependency_Set dependencies (in handle_t handle)
    //    raises (UNKNOWN_TASK);
    // Returns the list of dependencies
    //
    // long number_of_dependencies (in handle_t handle)
    //    raises (UNKNOWN_TASK);
    // Returns the number of dependencies.

  };
};