June 03, 2004: DWCS has been suspended while a new virtual
deadline scheduler, that supercedes DWCS, is being developed.
Time-permitting, DWCS patch files for recent Linux kernels will be
added.
New links will be added to a page on "Virtual Deadline
Scheduling" that orders tasks (e.g., packets or threads) according to a
function of current window-constraints and proportional fairness
requirements. In the meantime, please check the paper list below.
June 11, 2002: After a long period of
inactivity, the Linux DWCS work is being resumed (albeit in limited
capacity).
Certain boundary conditions can force the
scheduler to perform sub-optimally for processes with fixed-sized
timeslices. From a theoretical standpoint, optimality is guaranteed
only for canonical service
constraints on processes. User-controllable support for conversion
of service constraints to their canonical form will be incorporated
into any future releases of the scheduler, one of which is hopefully a
Linux-based packet scheduler.
July 28, 2000: DWCS version 1.2 released.
Major bug fixes and improvements include:
/proc/dwcs enhancements. The
/proc/dwcs code has been rewritten using the VFS functionality,
by supplying functions to handle open(), close(), permissions(), and
most importantly, a new version of read(). The advantage of this
approach is that now we're not restricted to only passing back at most
one memory page of statistical information to the user. Instead, as
much information as necessary can
be passed back to the user.
0/0 window-constraints now work,
thereby enabling the scheduler to run as a pure EDF scheduler. In
previous versions, this would cause a divide-by-zero error.
Added `jiffies_last' to prevent DWCS
updating service constraints multiple times in one jiffy. This was
happening if schedule() was invoked more than once in one jiffy.
Fixed bug in that if DWCS_WORK_CONS
is set FALSE, a process cannot be scheduled multiple times in the same
request period.
November 1, 1999: DWCS version 1.1
released. New features include:
SMP-compliant.
Potential floating-point problems now
fixed. DWCS is now implemented as a pure integer-based algorithm.
Cleaner integration of the DWCS source
code with the rest of the linux source tree.
Simpler installation procedure. A
configuration entry has been added to the "Kernel Hacking" menu to
enable/disable the building of the DWCS scheduler module. Enabling the
compilation of the
DWCS scheduler allows an entry in the /proc filesystem to be
configured,
showing the current state of DWCS scheduled processes.
August 19, 1999: DWCS version 1.0
released for Linux 2.2.7.
Acknowledgements
Thanks to Ivan Ganev for help on versions
1.1 and 1.2. Thanks also to Christian Poellabauer for past
discussions on the algorithm itself.
What is DWCS?
Background. DWCS stands for Dynamic
Window-Constrained Scheduling. Originally, DWCS was designed to be a
network packet scheduler, that limited the number of late or lost
packets
over finite numbers of consecutive packets in loss-tolerant and/or
delay-constrained , heterogeneous traffic streams. For example, virtual
environments, tele-medicine, and real-time multimedia applications
(including video-on-demand
and streamed audio) can tolerate a certain fraction of late
or lost information, without any noticeable degradation in the quality
of playback at the receiver. However, it is important that such
applications do not suffer losses at certain points in time, even
though they
can tolerate a certain fraction of information being lost. For most
loss-tolerant applications, there is usually a restriction on the
number of consecutive packet losses that are acceptable. For
example, losing a series of consecutive packets from an audio stream
might result in the loss of a complete section of audio, rather than
merely a reduction in the signal-to-noise ratio. A
suitable performance measure in this case is a windowed
loss-rate , i.e. loss-rate constrained over a finite range, or
window, of consecutive packets. More precisely, an application might
tolerate x packet losses for every y arrivals at the various service points
across a network. Any service
discipline attempting to meet these requirements must ensure that the
number
of violations to the loss-tolerance specification is minimized (if not
zero)
across the whole stream. As a packet scheduler, DWCS attempts to meet
windowed
loss-rates for multiple packet streams, each with their own performance
objectives.
More recently, we have applied DWCS to scheduling processes (and
threads) for execution on available CPUs of a host machine. In its
current incarnation as a CPU scheduler, DWCS can guarantee that no more
than x deadlines are missed every y deadlines, for a given process (or thread).
Real-Time CPU Scheduling. Many
scheduling policies have been used for real-time scheduling,
including cyclic executives, static priority algorithms (such as
Rate-Monotonic Scheduling), and dynamic algorithms, such as Earliest
Deadline First (EDF). Static priority algorithms all consider that one
process (or thread) is more important to service than another
process, based solely on each process's time-invariant priority.
However, such algorithms do not take into account the importance of
servicing a process can vary with time. Moreover, real-time
systems require processes to complete their service by specific
deadlines, in
order to meet necessary timeliness constraints. Consequently, Earliest
Deadline First scheduling (EDF) considers that each process's
importance (or priority) increases as the urgency of completing that
process's service increases. That is, it is more important to
service a process closer to its deadline than another process further
from its deadline. Although EDF considers a process's importance varies
with time, it does not consider that at any point in time, the
individual importance of two or more processes with the same deadline
may be different. That is, if two processes have the same
deadline, one process may require precedence over another, as
in static priority schemes. Furthermore, EDF assumes that the urgency
of
servicing each process increases at the same rate for all processes.
This is not true in all systems. Hence, there is a need for an
algorithm to combine both static priority and earliest deadline first
properties. DWCS is one such
algorithm that combines both these properties. In fact, DWCS can
perform static
priority, earliest deadline first, and real-time proportional (or
"fair")
scheduling.
Real-Time Scheduling with DWCS
Background. The original DWCS packet scheduler required two
service constraints to be specified for each packet stream. These were
a maximum inter-packet gap (from which a per-packet deadline could be
derived) and a loss-tolerance. For CPU scheduling, these terms were not
so meaningful, so we changed the inter-packet gap to be a request period and the loss-tolerance to be a window-constraint.
For CPU scheduling, a process has attributes in terms of a request period and a window-constraint
. A request period defines an interval (window of time) over
which a process must receive some share of the CPU. The end of one
request period and the start of the next, for any given process,
denotes a deadline. Hence, DWCS derives deadlines for each
process, such that a process's current deadline is at the end of
its current request period. The window-constraint is actually a
fraction, x/y , and states that a process
can miss being serviced at most x
request periods out of every y request
periods. That is, a process can miss x deadlines for every fixed window
of y deadlines that are derived from its request period and current
time. Observe that a process does NOT have to be a periodic
process to use DWCS. For periodic processes, a request period can
identify a window of time over which one instance of a process must
executes to completion, before the next request for the same process
requires servicing. For aperiodic processes (for example, processes
that only execute once) , a request period identifies a window of time
in which part of a process must
execute. That is, for an aperiodic process,
P, the current request period identifies the interval of time in
which one timeslice (or service quantum)
of P must execute, otherwise the
current timeslice of P will miss its deadline. Consequently, the window-constraint of P
specifies that up to x timeslices of P can be serviced late (outside their request
periods) for each consecutive y
timeslices. Clearly, a process, P , has a number of timeslices, dependent upon
its overall service time. With DWCS, the size of each timeslice
can be specified as
some multiple of the system clock. For Intel platforms, the minimum
timeslice for a process is 10mS , with larger timeslices being some multiple of 10mS,
but this will change if we use the UTIME
package from Kansas University. Moreover, each timeslice
for a process (be it the time to service a full instance of a process,
or simply part of
that process) can be preemptible in a given request period.
Example. A process requires 50mS of service every request
period of 100mS, tolerating 2 out of 10 missed service intervals. If
timeslice preemption is enabled, that 50mS can be divided into
10mS units of CPU time, as long as a total of 50mS of CPU time is
granted to this process every 100mS (with the exception of two
intervals of 100mS in which the process can miss being serviced
altogether). This process is said to have a window-constraint of 2/10,
which implies that over every window of 10*100mS, the process can
tolerate not being serviced for 50mS in two of its 100mS request
periods. The minimum utilization for this process is:
U_min = (1 - x / y) * C / T, where C = 50mS of service time, T = 100mS
for the request period, and x / y = 2/10 for the window-constraint.
That is, U_min = 0.4 (or 40%)
For servicing at the granularity of the smallest (10mS) timeslice,
we can consider the service constraints are:
C' = C / 5 = K (i.e., 10mS), T' = T / 5, and x' / y' = x / y.
DWCS is a relatively simple algorithm. It compares pairs of processes
(or, equivalently, threads, or network-bound packets) and selects the
highest priority process for service based on the following table of
precedence rules:
Pairwise Ordering Amongst
Processes
Earliest deadline first
(EDF)
Equal deadlines, order lowest window-constraint first
Equal deadlines and zero window-constraints, order
highest window-denominator first
Equal deadlines and equal non-zero window-constraints,
order lowest window-numerator first
All other cases: first-come-first-serve
Observe that the above table of precedence rules is not always optimal.
That is, there are cases when the minimum required utilization of a set
of processes to meet all window-constraints is less than 100% (meaning
resources are available) but some processes will violate their
window-constraints when serviced according to the above precedence
rules. To deal with this case, each process' service constraints must
be converted to their canonical form which yield equivalent
minimum utilization demands, albeit over finer-grained windows of time.
In most cases, this is actually preferable.
Canonical Service
Constraints
To guarantee a feasible schedule, whereby all process'
window-constraints are met as long as the total minimum utilization is
less than 100%, original service constraints must be converted to their
canonical form. This is because sub-optimal process schedules may
result using a pairwise ordering method that considers deadlines before
window-constraints (or vice versa).
For any process, Pi, with service constraints, (Ci, Ti
, xi / yi), representing service time, request period and
window-constraints, respectively, we can perform an O(1) conversion to
the canonical service constraints, (Ci', Ti', xi' /
yi') as follows:
Ci' = Ci
Ti' = K
xi' = yi * (qi - 1) + xi
yi' = qi * yi
Assuming Ti = qi * K, Ci <= K for some constant K
and positive integer, qi. This assumption is based on the
notion that the system performs scheduling at the granularity of
fixed-sized
time-slots, that are K time units in length. In effect, this
limits
a timeslice to a maximum of K time units also.
Observe that 1 <= i <= n, if there are n
processes, P1...Pn. Moreover, if:
sum (for all i) (1 - xi / yi) * Ci / Ti <= 1.0 then the
minimum total utilization of the canonical constraints is no more than:
sum (for all i) (1 - xi' / yi') * K / Ti' <= 1.0=
U_min_total
The canonical service constraints ensure that no process violates its
original window-constraints of xi / yi if U_min_total <=
1.0
.
In this sense, DWCS is now optimal.
Dynamic Service Constraint Adjustment
For each process serviced for at least one timeslice before its
deadline (i.e. a process that is serviced in its current request
period), the window-constraint x/y is
adjusted dynamically as follows, to, in effect, reduce the urgency of
servicing the same process again when another more "critical" process
requires service:
Let x be a process's original window-numerator, while y is its original window
denominator. These are the values first set for a DWCS process.
Let x' and y'
denote the current window numerator and current window denominator as the process is
executed. Then, if a process is serviced before its deadline:
(A)
if (y' > x') then y' = y' - 1; else if (y' == x') and (x' > 0) then x' = x' - 1; y' =
y' - 1; if (x' == y' == 0) or (the process is tagged with a violation.
i.e. DWCS_VIOLATION is set) then
x' = x; y' = y;
if (the process is tagged with a violation) then
reset DWCS_VIOLATION flag;
For any process not serviced by its deadline (i.e. its next timeslice
has not been serviced in its latest request period) then:
(B)
if (x' > 0) then
x' = x' - 1; y' = y' -1; if (x' == y' == 0) then
x' = x; y' = y;
else if (x' == 0) and (y > 0) then
y' = y' + 1; Tag process with a violation by setting its DWCS_VIOLATION flag;
The pseudo-code for DWCS is as follows.
It's actually more complicated than this but this will give you a basic
understanding of what is happening to your processes:
Let Pi = ith process
di = deadline of Pi
Ti = request period of Pi
Wi' = current window-constraint of Pi
while (TRUE) {
for (each process whose ready time <= current time)
find process, Pi, with the highest priority,
according to the rules in the Table above;
service next timeslice of Pi (which may mean servicing
all of Pi); adjust Wi' according to the rules in (A), above; di = di + Ti; for (each process, Pj, missing its deadline) {
while (deadline missed) {
adjust Wj' according to the rules
in (B), above; dj = dj + Tj;
}
}
}
Observe that a process with an original window-constraint
of 0/0 actually forces the scheduler to treat it as a
deadline-constrained process, whose deadline is calculated from the
current time and the request period.
Observe also (from the table), that deadlines are used as
the primary means of deciding whether to service one process or
another, every time the scheduler runs. In practice, you might think
very few deadlines are actually equal, so why do we need all these
extra
decision rules? Well, in practice, it is unlikely that you would want
to context switch from one process to another too frequently, because
(a)
the advantages of caching recently used instructions and data in the
processor's
cache are defeated, and (b) the context-switching overhead is too
great.
Therefore, most processes will probably want to run for longer
(non-preemptive)
periods of time. If this is the case, it makes sense to round a
process's
deadline to the nearest possible preemption point that is
actually
less than or equal to the real deadline. In doing this, chances are
that
more deadlines will be equal as the size of a non-preemptive timeslice
is increased.
The process can still be set to execute in entirety, or in part,
depending on the size of a process's timeslice. (See sched_setscheduler , below, for details on how
to adjust the size of a process's timeslice. This actually involves
setting the service_time field of struct sched_param ).
Below is a simple example of DWCS scheduling three
processes, P1, P2, and P3, each with a timeslice of 1 time unit
(which may well
be 10mS or 10 seconds in reality). Each process has a request period of
1 time unit and the original window-constraints are 1/2, 3/4, and 6/8.
Since each process has a request period of 1 time unit, each process
has
a new deadline every time unit also. In this example, let P1 comprise
of
8 timeslices, while P2 and P3 each comprise of 4 timeslices. Below the
time axis is a list of current window-constraints and deadlines for
each
process. Deadlines are shown in brackets. Over the full 16 time units,
P1
receives 8 time units of service, while P2 and P3 both receive 4 time
units of service. Moreover, P1 is serviced once every 2 time
units,
while P2 and P3 are serviced once every 4 time units. Therefore, P1 has
not missed more than one deadline every two deadlines, and P2 and P3
have
not missed more than 3 deadlines every window of 4 deadlines. In fact,
P3 has weaker window-constraints, in that it requires that no more than
6 deadlines are missed every 8 consecutive deadlines (or, equivalently,
8 consecutive request periods). As it turns out, over the
smallest
possible window of time (4 time units), P1 receives twice has much
service
as P2 and P3. Hence, real-time proportional (or "fair") service is
granted
to all processes in proportion to their original window-constraints and
request periods.
DWCS Scheduling Modes and Features
Running DWCS in EDF mode: Ensure all process's have
0/0 window-constraints and request periods that are not -1.
Running DWCS in static priority mode: Ensure all
processes have request periods of -1 and then the value of the
window-constraint specifies its priority. The process with the lowest
window-constraint,
x/y, has the highest priority.
DWCS can run in mixed mode (with a combination of static
priority and deadline-constrained processes), but beware that
non-time-constrained (static priority) processes will not run if a
time-constrained process is runnable. That is, a non-time-constrained
process is any process whose request period is -1.
By default, all system processes (e.g. telnetd, klogd, and
related processes, such as an X-server) all run in
non-time-constrained, static priority mode. However, these
processes can be switched into time-constrained mode using dwcs_setscheduler (see below), so that they
receive real-time service. NOTE: Due to the non-real-time nature of the
standard Linux kernel, the real-time guarantees provided by DWCS will
only be "soft" real-time guarantees. This is due to factors other than
the scheduling policy. Work is underway to see how well a Linux-based
system, employing DWCS, can meet real-time service constraints.
Observe that, in Solaris, which has fixed priority classes, for
system, real-time and timesharing processes (actually threads), the
Solaris system processes can be prevented from receiving any service,
if a real-time process is always runnable and never blocks on some wait
condition. However, DWCS can provide proportional share, real-time
service
to processes, so that each process is guaranteed some fraction of CPU
time
over finite intervals of time. The actual amount of service to
each
process is in direct proportion to each process's window-constraints
and
request period.
We have actually proven (theoretically) that if each process, Pi, requires a fixed quantum of service,
Qi
, (i.e. a fixed timeslice) in each request period, Ti , then if the sum of the
worst-case minimum service demands from each process is less than
100% , each process is guaranteed to be serviced (1-Wi)Q*10mS
every window
of Ti*10mS , where
Wi is the window-constraint of Pi. That is, each process has a
worst-case minimum demand for service of
(1-Wi)Q*10mS/Ti*10mS . If the sum of
all processes' worst-case minimum demands for service is 1.0, the CPU
will be 100% utilized (i.e. it will never be idle). However, DWCS
guarantees
that no process will violate its original window-constraint by ensuring
each process's minimum demand for service every window, Ti*10mS . NOTE: These
times assume the scheduler is not invoked by some means other than by a
timer interrupt ,
and ignores interrupt and dispatch latencies. Saying this, we now want
to
prove possible service guarantees offered by DWCS for processes having
variable-length
service-times (i.e. variable-length timeslices) in every request period.
Where can I get DWCS?
linux_2.2.7_dwcs_v1.2.tar.gz
.This is the latest version for Linux 2.2.7, Intel
machines, and should work on both SMP and non-SMP configured machines.
linux_2.2.13_dwcs_v1.2.tar.gz
.This is the latest version for Linux 2.2.13, Intel
machines, and should work on both SMP and non-SMP configured machines.
Linux 2.2.13 is the final 2.2.x kernel to be patched. Patches for
recent Linux kernels may be available upon request.
The following gzip'd tarfiles are now obsolete and are only here
for completeness. Unless you are really curious, you should use the
latest versions above.
linux_2.2.7_dwcs_v1.0.tar.gz
. This version is for Linux 2.2.7, Intel machines. This version
does not work on SMP machines. You should disable SMP support to
be sure that this code works correctly.
linux_2.2.7_dwcs_v1.1.tar.gz
. This version is for Linux 2.2.7, Intel machines, and should
work on both SMP and non-SMP configured machines.
linux_2.2.13_dwcs_v1.1.tar.gz
. This version is for Linux 2.2.13, Intel machines, and should
work on both SMP and non-SMP configured machines.
Installation Notes
1. Download a copy of the tar file
and unpack its contents by typing:
gzip -dc linux_2.2.*_dwcs_v1.*.tar.gz | tar xvf
- (where * is replaced with the
appropriate version number)
2. Read the INSTALL file in the newly-created
dwcs directory.
Using DWCS
DWCS is a kernel loadable module. As root, you must type modprobe dwcs (or depmod
-a; modprobe dwcs or , if all else fails, insmod
dwcs ) to load the DWCS extensions into a running Linux
kernel.
To enable DWCS once the dwcs module
has been loaded, type load_scheduler.
To disable DWCS after it is the active scheduler in the Linux
kernel, type unload_scheduler.
At any point in time, it is safe to remove the DWCS
kernel loadable module by typing rmmod dwcs
. Removing the module will return the system to using the default Linux
(timesharing) scheduler.
If you type cat /proc/dwcs when the dwcs module is loaded, you can
see a snapshot of the DWCS scheduling parameters for processes
currently on the scheduler's runqueue. If there's not much there,
that's because most processes are blocked. Check 'top' to verify the
number of processes actually using
the CPU at the current time.
You can now use the sched_setscheduler
call within your programs to set the service constraints on real-time
DWCS processes. An example of how to adjust the service constraints of
a DWCS process, using sched_setscheduler, is as follows:
/* DWCS_WORK_CONS is set when a process supports
work-conservation. */ #define
DWCS_WORK_CONS
0x00000002
/* DWCS_NON_PREEMPTIVE is set when a
process must execute with non-preemptive timeslices. */ #define DWCS_NON_PREEMPTIVE 0x00000004
int main (int argc, char *argv[]) {
struct sched_param sp; int pid;
pid
= getpid();
/* sp.period is
multiplied by 10mS to get the actual scheduling period. */ sp.period = 5;
/* sp.own is the original
window numerator. This is the value x in
the window-constraint x/y . */ sp.own = 1;
/* sp.owd is the original
window denominator. This is the value y
in the window-constraint x/y . */ sp.owd = 100;
/* sp.flags : Can logical OR
the flags DWCS_WORK_CONS and DWCS_NON_PREEMPTIVE. If
DWCS_WORK_CONS is set, then potentially multiple timeslices of
a given process can execute in a single request period. This will only
happen if all other deadline-constrained processes have been serviced
in their current request period. If
DWCS_NON_PREEMPTIVE is set, then a timeslice must execute
without preemption in
each request period. NOTE: A non-preemptive timeslice will currently
execute
at least 10mS. */ sp.flags = 0;
/* sp.service_time is currently a number that is multiplied by 10mS to
determine the maximum amount of service time each timeslice of a
process should receive in one request period. This can be sufficiently
large to cover the time to service the whole process, in the case of a
periodic process, for example, or can be the time to service part
of a process in one request period. If
DWCS_NON_PREEMPTIVE is not set, then this
service time can be preempted every time the
scheduler executes, to allow other processes' timeslices to execute.
However,
DWCS will still attempt to service a process for sp.service_time*10mS
every sp.period*10mS, except where the process's window-constraints allow
timeslices to skip being serviced in corresponding request periods. */ sp.service_time = 2;
if ((ret = sched_setscheduler (pid, SCHED_DWCS, &sp))
< 0)
The modifications to struct
sched_param can be found in schedbits.h
and sched.h,
included with the downloadable tarfile. Depending on your Linux
distribution, either schedbits.h or
sched.h will replace your existing /usr/include/schedbits.h or
/usr/include/bits/sched.h file. A similar file in the linux source
tree, linux/sched.h , is also modified to include the DWCS scheduling
parameters.
A command-line executable, dwcs_setscheduler
, allows the service constraints of running processes to be altered
from a shell. It is essentially a small program that utilizes
sched_setscheduler, just as in the above example. dwcs_setscheduler takes 4 mandatory arguments
and 2 optional arguments, as follows:
pid - this is the ID of the process whose service constraints
are to be altered.
period - the request period (specified as some number which is
multiplied by 10mS).
own - the original window numerator, which is the value x
in the window-constraint, x/y.
owd - the original window denominator, which is the value
y in the window-constraint, x/y.
The following arguments are optional:
-s <service_time> -
this is the amount of service for a process's timeslice per request
period. It is a number which is multiplied by 10mS to get the actual
service
time. The default service time for one timeslice is 10mS, so the service_time field of struct
sched_param defaults to 1.
-f <flags> - this value sets the flags field of struct
sched_param . The default value is 0. Each new value of flags
can be set by OR-ing the new value with the old value. Currently, only DWCS_WORK_CONS and DWCS_NON_PREEMPTIVE
are acceptible flags. These can be entered on the command line,
separated by a comma, if both flags are to be set. See the example
above for a description of the meaning of these flags.
To Do
Add DWCS packet scheduling to Linux.
Add an on-line admission control (or scheduling analysis)
module to work with DWCS packet and CPU scheduling.
Add UTIME (Kansas
University) microsecond timer support, for fine-grained
timeslices.
This work is part of the Dionisys QoS Adaptive System work at
Georgia Tech. We hope to port the Dionisys QoS Infrastructure to
Linux and, hopefully, embed some of its components into the kernel, to
ultimately implement a distributed, real-time adaptive system
that
adapts communication and computation resources, in terms of CPU and
network
(primarily bandwidth) resources. Dionisys is being prototyped on
Solaris
and Linux in user-space, along with the original DWCS packet scheduler,
which was first implemented in shared memory.
Add real-time events (RTE) to Linux to allow DWCS CPU and
packet service managers to communicate, thereby supporting true
hierarchical scheduling between the host computer and the network.
Selected Papers
Yuting Zhang, Richard West and Xin Qi, "A Virtual Deadline Scheduler for
Window-Constrained
Service Guarantees", in Proceedings of the 25th IEEE
Real-Time Systems Symposium (RTSS), December 2004
Yuting Zhang and Richard West, "End-to-end Window-Constrained
Scheduling for Real-Time Communication", in
Proceedings of
the 10th International Conference on Real-Time and Embedded Computing
Systems and Applications (RTCSA'04), August 2004
Yuting Zhang, Richard West and Xin Qi, "A Virtual Deadline Scheduler for
Window-Constrained
Service Guarantees", Technical Report, 2004-013, Boston
University,
March 2004
Richard West, Yuting Zhang, Karsten Schwan and Christian
Poellabauer, "Dynamic
Window-Constrained Scheduling of Real-Time Streams in Media Servers",
IEEE Transactions
on Computers, Volume 53, Number 6, pp. 744-759, June 2004
Richard West, Ivan Ganev and Karsten Schwan, "Window-Constrained
Process Scheduling for Linux Systems", in Proceedings of the 3rd
Real-Time Linux Workshop, Milan, Italy, November 2001
Richard West and Christian Poellabauer, "Analysis of a
Window-Constrained Scheduler for Real-Time and Best-Effort Packet
Streams" , in Proceedings of the 21st IEEE Real-Time Systems
Symposium (RTSS), 2000
Richard West, Karsten Schwan and Christian Poellabauer,
"Scalable Scheduling Support for Loss and Delay Constrained Media
Streams", in Proceedings of the
5th IEEE Real-Time Technology and Applications Symposium (RTAS), 1999
Richard West and Karsten Schwan, "Dynamic
Window-Constrained Scheduling for Multimedia Applications" , in
Proceedings of the IEEE International Conference on Multimedia
Computing and Systems (ICMCS), 1999
A Virtual Deadline
Scheduler for
Window-Constrained
Service Guarantees, in Proceedings of the 25th IEEE
Real-Time Systems Symposium (RTSS), December 2004
End-to-end
Window-Constrained
Scheduling for Real-Time Communication, in
Proceedings of
the 10th International Conference on Real-Time and Embedded Computing
Systems and Applications (RTCSA'04), August 2004