background image

5-18 Vol. 3A

PROTECTION

privilege levels). These stacks are disposed of when a return is made from the called procedure. The next time the 
procedure is called, a new stack is created using the initial stack pointer. (The TSS does not specify a stack for priv-
ilege level 3 because the processor does not allow a transfer of program control from a procedure running at a CPL 
of 0, 1, or 2 to a procedure running at a CPL of 3, except on a return.)
The operating system is responsible for creating stacks and stack-segment descriptors for all the privilege levels to 
be used and for loading initial pointers for these stacks into the TSS. Each stack must be read/write accessible (as 
specified in the type field of its segment descriptor) and must contain enough space (as specified in the limit field) 
to hold the following items:

The contents of the SS, ESP, CS, and EIP registers for the calling procedure.

The parameters and temporary variables required by the called procedure.

The EFLAGS register and error code, when implicit calls are made to an exception or interrupt handler.

The stack will need to require enough space to contain many frames of these items, because procedures often call 
other procedures, and an operating system may support nesting of multiple interrupts. Each stack should be large 
enough to allow for the worst case nesting scenario at its privilege level.
(If the operating system does not use the processor’s multitasking mechanism, it still must create at least one TSS 
for this stack-related purpose.) 
When a procedure call through a call gate results in a change in privilege level, the processor performs the 
following steps to switch stacks and begin execution of the called procedure at a new privilege level:
1. Uses the DPL of the destination code segment (the new CPL) to select a pointer to the new stack (segment

selector and stack pointer) from the TSS. 

2. Reads the segment selector and stack pointer for the stack to be switched to from the current TSS. Any limit 

violations detected while reading the stack-segment selector, stack pointer, or stack-segment descriptor cause 
an invalid TSS (#TS) exception to be generated.

3. Checks the stack-segment descriptor for the proper privileges and type and generates an invalid TSS (#TS) 

exception if violations are detected.

4. Temporarily saves the current values of the SS and ESP registers.
5. Loads the segment selector and stack pointer for the new stack in the SS and ESP registers.
6. Pushes the temporarily saved values for the SS and ESP registers (for the calling procedure) onto the new stack 

(see Figure 5-13).

7. Copies the number of parameter specified in the parameter count field of the call gate from the calling 

procedure’s stack to the new stack. If the count is 0, no parameters are copied.

8. Pushes the return instruction pointer (the current contents of the CS and EIP registers) onto the new stack.
9. Loads the segment selector for the new code segment and the new instruction pointer from the call gate into 

the CS and EIP registers, respectively, and begins execution of the called procedure.

See the description of the CALL instruction in Chapter 3, Instruction Set Reference, in the IA-32 Intel Architecture 
Software Developer’s Manual, Volume 2
, for a detailed description of the privilege level checks and other protection 
checks that the processor performs on a far call through a call gate.