PROTECTION
7.5.1.4
STACK CHANGES CAUSED
BY
CALL GATES
To maintain system integrity, each privilege level has a separate stack. Furthermore, each task normally
uses separate stacks from other tasks for each privilege level. These stacks assure sufficient stack space
to process calls from less privileged levels. Without them, trusted programs may not work correctly,
especially if the calling program does not provide sufficient space
on
the caller's stack.
When a call gate
is
used to change privilege levels, a
new
stack
is
selected
as
determined by the
new
CPL. The
new
stack pointer value
is
loaded from the Task State Segment (TSS). The privilege level
of the
new
stack data segment must equal the
new
CPL; if it does not, a task stack fault occurs with
the saved machine state pointing at the CALL instruction and the error code identifying the invalid
stack selector.
The
new
stack should contain enough space to hold the old SS:SP, the return address, and all param-
eters and local variables required to process the call. The initial stack pointers for privilege levels
0-2
in the TSS are strictly read only values. They are never changed during the course of execution.
The normal technique for passing parameters to a subroutine
is
to
place them onto the stack. To make
privilege transitions transparent to the called program, a call gate specifies that parameters are to be
copied from the old stack to the
new
stack. The word count field
in
a call gate (see figure 7-10)
specifies
how
many words (up to 31) are
to
be copied from the caller's stack
to
the
new
stack.
If
the
word count
is
zero,
no
parameters are copied.
Before copying the parameters, the
new
stack
is
checked to assure that it
is
large enough to hold the
parameters; if it
is
not, a stack fault occurs with an error code of
O.
After the parameters are copied,
the return link
is
on
the
new
stack (i.e., a pointer to the old stack
is
placed in the
new
stack).
In
particular, the return address
is
pointed at
by
SS:SP. The call and return example of figure 7-12
illustrate the stack contents after a successful inter-level call.
The stack pointer of the caller
is
saved above the caller's return address
as
the first two words pushed
onto the
new
stack. The caller's stack can only be saved for calls to procedures at privilege levels
2,
1,
and
o.
Since level 3 cannot be called by any procedure at any other privilege level, the level 3 stack
will
never contain links to other stacks. '
Procedures requiring more than the
31
words for parameters that may be called from another privilege
level must use the saved SS:SP link to access all parameters beyond the last
word
copied.
The call gate does not check the values
of
the words copied onto the
new
stack. The called procedure
should check each parameter for validity. Section
11.3
discusses
how
the ARPL, VERR, VERW, LSL,
and LAR instructions can be used to check pointer values.
An inter-segment return instruction can also change levels, but only toward programs of equal or lesser
privilege (when code segment DPL
is
numerically greater or equal than the CPL). The RPL of the
selector popped off the stack by the return instruction identifies the privilege level
to
resume execution
of the calling program.
When the RET instruction encounters a saved CS value whose RPL > CPL,
an
inter-level return
occurs. Checks shown
in
table
7-4
are made during such a return.
7-20