<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML Basic 1.1//EN" "http://www.w3.org/TR/xhtml-basic/xhtml-basic11.dtd">
<html>
<head>
<link rel="stylesheet" type="text/css" href="../style/style.css" />
<title>INT n/INTO/INT 3: Call to Interrupt Procedure (x86 Instruction Set Reference)</title>
</head>
<body>
<div class="main_container"><h1>x86 Instruction Set Reference</h1>
<title>INT n/INTO/INT 3: Call to Interrupt Procedure (x86 Instruction Set Reference)</title>
<h1>INT n/INTO/INT 3</h1>
<h2>Call to Interrupt Procedure</h2>
<object>
<table class="box">
<tr>
<th>Opcode</th>
<th>Mnemonic</th>
<th>Description</th>
</tr>
<tr>
<td class="grid"><code>CC</code></td>
<td class="grid"><code>INT 3</code></td>
<td class="grid">Interrupt 3 - trap to debugger.</td>
</tr>
<tr>
<td class="grid"><code>CD ib</code></td>
<td class="grid"><code>INT imm8</code></td>
<td class="grid">Interrupt vector number specified by immediate byte.</td>
</tr>
<tr>
<td class="grid"><code>CE</code></td>
<td class="grid"><code>INTO</code></td>
<td class="grid">Interrupt 4 - if overflow flag is 1.</td>
</tr>
</table>
</object>
<object>
<table class="box">
<tr>
<th>Description</th>
</tr>
<tr>
<td class="instruction_set_reference_box">
<p>The INT n instruction generates a call to the interrupt or exception handler specified with the destination operand (see the section titled "Interrupts and {exceptions}" in Chapter 6 of the IA-32 Intel Architecture Software Developer's Manual, Volume 1). The destination operand specifies an interrupt vector number from 0 to 255, encoded as an 8-bit unsigned intermediate value. Each interrupt vector number provides an index to a gate descriptor in the IDT. The first 32 interrupt vector numbers are reserved by Intel for system use. Some of these interrupts are used for internally generated exceptions.</p>
<p>The INT n instruction is the general mnemonic for executing a software-generated call to an interrupt handler. The INTO instruction is a special mnemonic for calling overflow exception (#OF), interrupt vector number 4. The overflow interrupt checks the OF flag in the EFLAGS register and calls the overflow interrupt handler if the OF flag is set to 1.</p>
<p>The INT 3 instruction generates a special one byte opcode (CC) that is intended for calling the debug exception handler. (This one byte form is valuable because it can be used to replace the first byte of any instruction with a breakpoint, including other one byte instructions, without over-writing other code). To further support its function as a debug breakpoint, the interrupt generated with the CC opcode also differs from the regular software interrupts as follows: - Interrupt redirection does not happen when in VME mode; the interrupt is handled by a protected-mode handler.</p>
<p>The virtual-8086 mode IOPL checks do not occur. The interrupt is taken without faulting at any IOPL level.</p>
<p>Note that the "normal" 2-byte opcode for INT 3 (CD03) does not have these special features.</p>
<p>Intel and Microsoft assemblers will not generate the CD03 opcode from any mnemonic, but this opcode can be created by direct numeric code definition or by self-modifying code.</p>
<p>The action of the INT n instruction (including the INTO and INT 3 instructions) is similar to that of a far call made with the CALL instruction. The primary difference is that with the INT n instruction, the EFLAGS register is pushed onto the stack before the return address. (The return address is a far address consisting of the current values of the CS and EIP registers.) Returns from interrupt procedures are handled with the IRET instruction, which pops the EFLAGS information and return address from the stack.</p>
<p>The interrupt vector number specifies an interrupt descriptor in the interrupt descriptor table (IDT); that is, it provides index into the IDT. The selected interrupt descriptor in turn contains a pointer to an interrupt or exception handler procedure. In protected mode, the IDT contains an array of 8-byte descriptors, each of which is an interrupt gate, trap gate, or task gate. In realaddress mode, the IDT is an array of 4-byte far pointers (2-byte code segment selector and a 2-byte instruction pointer), each of which point directly to a procedure in the selected segment.</p>
<p>(Note that in real-address mode, the IDT is called the interrupt vector table, and its pointers are called interrupt vectors.)</p>
<p>The following decision table indicates which action in the lower portion of the table is taken given the conditions in the upper portion of the table. Each Y in the lower section of the decision table represents a procedure defined in the "Operation" section for this instruction (except #GP).</p>
<div>
<table class="grid">
<caption>Decision Table</caption>
<tr><td>PE</td><td>0</td><td>1</td><td>1</td><td>1</td><td>1</td><td>1</td><td>1</td><td>1</td></tr>
<tr><td>VM</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>0</td><td>1</td><td>1</td></tr>
<tr><td>IOPL</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td><3</td><td>=3</td></tr>
<tr><td>DPL/CPL RELATIONSHIP</td><td>Don't care</td><td>DPL < CPL</td><td>Don't care</td><td>DPL > CPL</td><td>DPL = CPL or C</td><td>DPL < CPL & NC</td><td>Don't care</td><td>Don't care</td></tr>
<tr><td>INTERRUPT TYPE</td><td>Don't care</td><td>S/W</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>Don't care</td><td>Don't care</td></tr>
<tr><td>GATE TYPE</td><td>Don't care</td><td>Don't care</td><td>Task Trap or Interrupt</td><td>Trap or Interrupt</td><td>Trap or Interrupt</td><td>Trap or Interrupt</td><td>Trap or Interrupt</td></tr>
<tr><td>REAL-ADDRESS-MODE</td><td>Action taken</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td></tr>
<tr><td>PROTECTED-MODE</td><td>No action</td><td>Action taken</td><td>Action taken</td><td>Action taken</td><td>Action taken</td><td>Action taken</td><td>Action taken</td><td>Action taken</td></tr>
<tr><td>TRAP-OR-INTERRUPT-GATE</td><td>No action</td><td>No action</td><td>No action</td><td>Action taken</td><td>Action taken</td><td>Action taken</td><td>Action taken</td><td>Action taken</td></tr>
<tr><td>INTER-PRIVILEGE-LEVEL-INTERRUPT</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>Action taken</td><td>No action</td><td>No action</td></tr>
<tr><td>INTRA-PRIVILEGE-LEVEL-INTERRUPT</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>Action taken</td><td>No action</td><td>No action</td><td>No action</td></tr>
<tr><td>INTERRUPT-FROM-VIRTUAL-8086-MODE</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>Action taken</td></tr>
<tr><td>TASK-GATE</td><td>No action</td><td>No action</td><td>Action taken</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td><td>No action</td></tr>
<tr><td>#GP</td><td>No action</td><td>Action taken</td><td>No action</td><td>Action taken</td><td>No action</td><td>No action</td><td>Action taken</td><td>No action</td></tr>
</table>
</div>
<p>When the processor is executing in virtual-8086 mode, the IOPL determines the action of the INT n instruction. If the IOPL is less than 3, the processor generates a general protection exception (#GP); if the IOPL is 3, the processor executes a protected mode interrupt to privilege level 0. The interrupt gate's DPL must be set to 3 and the target CPL of the interrupt handler procedure must be 0 to execute the protected mode interrupt to privilege level 0.</p>
<p>The interrupt descriptor table register (IDTR) specifies the base linear address and limit of the IDT. The initial base address value of the IDTR after the processor is powered up or reset is 0.</p>
</td>
</tr>
</table>
</object>
<object>
<table class="box">
<tr>
<th>Operation</th>
</tr>
<tr>
<td class="instruction_set_reference_box">
<pre><span class="comment">//The following operational description applies not only to the INT n and INTO instructions, but also to external interrupts and exceptions.</span>
<span class="keyword">if</span><span class="operator">(</span>pe <span class="operator">==</span> <span class="number">0</span><span class="operator">)</span> {
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinIDTLimit<span class="operator">(</span>Destination <span class="operator">*</span> <span class="number">4</span> <span class="operator">+</span> <span class="number">3</span><span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">6</span><span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>EFLAGS<span class="operator">[</span><span class="number">0..15</span><span class="operator">]</span><span class="operator">)</span><span class="operator">;</span>
IF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
TF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
AC <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
Push<span class="operator">(</span>CS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>IP<span class="operator">)</span><span class="operator">;</span>
CS <span class="operator">=</span> IDT<span class="operator">(</span>Descriptor<span class="operator">(</span>VectorNumber <span class="operator">*</span> <span class="number">4</span><span class="operator">)</span><span class="operator">,</span> Selector<span class="operator">)</span><span class="operator">;</span>
EIP <span class="operator">=</span> IDT<span class="operator">(</span>Descriptor<span class="operator">(</span>VectorNumber <span class="operator">*</span> <span class="number">4</span><span class="operator">)</span><span class="operator">,</span> Offset<span class="operator">)</span><span class="operator">;</span> <span class="comment">//16 bit offset & 0xFFFF</span>
}
<span class="keyword">else</span> {
<span class="keyword">if</span><span class="operator">(</span>VM <span class="operator">==</span> <span class="number">1</span> <span class="operator">&&</span> IOPL <span class="operator"><</span> <span class="number">3</span> <span class="operator">&&</span> INT<span class="operator">(</span>n<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">else</span> { <span class="comment">//protected mode or virtual-8086 mode interrupt</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinIDTLimits<span class="operator">(</span>Destination <span class="operator">*</span> <span class="number">8</span> <span class="operator">+</span> <span class="number">7</span><span class="operator">)</span> <span class="operator">||</span> <span class="operator">!</span><span class="operator">(</span>GetCurrentIDTDescriptorType<span class="operator">(</span><span class="operator">)</span> <span class="operator">&</span> <span class="operator">(</span>TYPE_INTERRUPT <span class="operator">|</span> TYPE_TRAP <span class="operator">|</span> TYPE_TASK_GATE<span class="operator">)</span><span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>Destination <span class="operator">*</span> <span class="number">8</span> <span class="operator">+</span> <span class="number">2</span> <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//Selected IDT descriptor is not an iterrupt-, trap-, or task-gate type; EXT is bit 0 in error code</span>
<span class="keyword">if</span><span class="operator">(</span>IsSoftwareInterrupt<span class="operator">(</span><span class="operator">)</span> <span class="comment">/*generated by INT n, INT 3, or INTO*/</span> <span class="operator">&&</span> GateDescriptor<span class="operator">.</span>DPL <span class="operator"><</span> CPL<span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>VectorNumber <span class="operator">*</span> <span class="number">8</span> <span class="operator">+</span> <span class="number">2</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//PE = 1, DPL < CPL, software interrupt</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsPresent<span class="operator">(</span>Gate<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>NP<span class="operator">(</span>VectorNumber <span class="operator">*</span> <span class="number">8</span> <span class="operator">+</span> <span class="number">2</span> <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>IsTaskGate<span class="operator">(</span><span class="operator">)</span><span class="operator">)</span> {
<span class="comment">//Task-gate</span>
<span class="comment">//PE = 1, task gate</span>
IDTDescriptor <span class="operator">=</span> ReadSegmentSelector<span class="operator">(</span>TaskGate<span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsGlobal<span class="operator">(</span><span class="operator">)</span> <span class="operator">||</span> <span class="operator">!</span>IsWithinGDTLimits<span class="operator">(</span>Index<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>TSSSelector<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
TSSDescriptor <span class="operator">=</span> AccessTSSDescriptor<span class="operator">(</span>GDT<span class="operator">.</span>TSSDescriptor<span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>TSSIsBusy<span class="operator">(</span>TSSDescriptor<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>TSSSelector<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//TSS descriptor specifies that the TSS is busy (low-order 5 bits set to 00001)</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsPresent<span class="operator">(</span>TSSDescriptor<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>NP<span class="operator">(</span>TSSSelector<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
SwitchTasks<span class="operator">(</span>TSSDescriptor<span class="operator">,</span> WithNesting<span class="operator">)</span><span class="operator">;</span> <span class="comment">//Switch tasks (with nesting) to TSS</span>
<span class="keyword">if</span><span class="operator">(</span>InterruptOccured<span class="operator">(</span><span class="operator">)</span><span class="operator">)</span> { <span class="comment">//interrupt caused by fault with error code</span>
<span class="keyword">if</span><span class="operator">(</span>GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> ErrorCodeSize<span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//stack limit does not allow push of error code</span>
Push<span class="operator">(</span>ErrorCode<span class="operator">)</span><span class="operator">;</span>
}
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinCSLimit<span class="operator">(</span>EIP<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
}
<span class="keyword">else</span> { <span class="comment">//PE = 1, trap/interrupt gate</span>
<span class="comment">//Trap interrupt gate</span>
IDTDescriptor <span class="operator">=</span> ReadSegmentSelector<span class="operator">(</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>CodeSegmentSelector <span class="operator">==</span> <span class="number">0</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span><span class="number">0</span> <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//null selector with EXT flag set</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinDescriptorTableLimits<span class="operator">(</span>SegmentSelector<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>SegmentSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
Descriptor <span class="operator">=</span> ReadDescriptor<span class="operator">(</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//Read trap or interrupt handler descriptor</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IndicatesCodeSegment<span class="operator">(</span>Descriptor<span class="operator">)</span> <span class="operator">||</span> CodeSegmentDescriptor<span class="operator">.</span>DPL <span class="operator">></span> CPL<span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>Selector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsPresent<span class="operator">(</span>GateSegment<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>NP<span class="operator">(</span>Selector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsConforming<span class="operator">(</span>CodeSegment<span class="operator">)</span> <span class="operator">&&</span> DPL <span class="operator"><</span> CPL<span class="operator">)</span> {
<span class="keyword">if</span><span class="operator">(</span>VM <span class="operator">==</span> <span class="number">0</span><span class="operator">)</span> {
<span class="comment">//Inter-Privilege-Level interrupt</span>
<span class="comment">//PE == 1, interrupt or trap gate, nonconforming</span>
<span class="comment">//code segment, DPL < CPL, VM == 0</span>
<span class="comment">//Check segment selector and descriptor for stack of new privilege level in current TSS</span>
<span class="keyword">if</span><span class="operator">(</span>Is32BitTSS<span class="operator">(</span>CurrentTSS<span class="operator">)</span><span class="operator">)</span> {
TSSStackAddress <span class="operator">=</span> NewCodSegment<span class="operator">.</span>DPL <span class="operator">*</span> <span class="number">8</span> <span class="operator">+</span> <span class="number">4</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>TSSStackAddress <span class="operator">+</span> <span class="number">7</span> <span class="operator">></span> TSSLim9t<span class="operator">)</span> Exception<span class="operator">(</span>TS<span class="operator">(</span>CurrentTSSSelector<span class="operator">)</span><span class="operator">;</span>
NewSS <span class="operator">=</span> TSSStackAddress <span class="operator">+</span> <span class="number">4</span><span class="operator">;</span>
NewESP <span class="operator">=</span> StackAddress<span class="operator">;</span>
}
<span class="keyword">else</span> { <span class="comment">//TSS is 16-bit</span>
TSSStackAddress <span class="operator">=</span> NewCodSegment<span class="operator">.</span>DPL <span class="operator">*</span> <span class="number">4</span> <span class="operator">+</span> <span class="number">2</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>TSSStackAddress <span class="operator">+</span> <span class="number">4</span> <span class="operator">></span> TSSLim9t<span class="operator">)</span> Exception<span class="operator">(</span>TS<span class="operator">(</span>CurrentTSSSelector<span class="operator">)</span><span class="operator">;</span>
NewSS <span class="operator">=</span> TSSStackAddress <span class="operator">+</span> <span class="number">2</span><span class="operator">;</span>
NewESP <span class="operator">=</span> StackAddress<span class="operator">;</span>
}
<span class="keyword">if</span><span class="operator">(</span>SegmentSelector <span class="operator">==</span> <span class="number">0</span><span class="operator">)</span> Exception<span class="operator">(</span>TS<span class="operator">(</span>EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinDescriptorTableLimits<span class="operator">(</span>SegmentSelector<span class="operator">.</span>Index<span class="operator">)</span> <span class="operator">||</span> SegmentSelector<span class="operator">.</span>RPL <span class="operator">!=</span> CodeSegment<span class="operator">.</span>DPL<span class="operator">)</span> Exception<span class="operator">(</span>TS<span class="operator">(</span>SSSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
StackSegmentDescriptor <span class="operator">=</span> ReadStackSegmentDescriptor<span class="operator">(</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//Read segment descriptor for stack segment in GDT or LDT</span>
<span class="keyword">if</span><span class="operator">(</span>StackSegment<span class="operator">.</span>DPL <span class="operator">!=</span> CodeSegment<span class="operator">.</span>DPL <span class="operator">||</span> <span class="operator">!</span>IndicatesWritableDataSegment<span class="operator">(</span>StackSegment<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>TS<span class="operator">(</span>SSSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsPresent<span class="operator">(</span>StackSegment<span class="operator">)</span><span class="operator">)</span> Excpetion<span class="operator">(</span><span class="preprocessor">#SS(SSSelector + EXT));</span>
<span class="keyword">if</span><span class="operator">(</span>Is32BitGate<span class="operator">(</span><span class="operator">)</span> <span class="operator">&&</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">24</span> <span class="comment">/*error code pushed*/</span> <span class="operator">||</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">20</span> <span class="comment">/*no error code pushed*/</span><span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">(</span>SegmentSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">else</span> <span class="comment">/*16-bit gate*/</span> <span class="keyword">if</span><span class="operator">(</span>GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">12</span> <span class="comment">/*error code pushed*/</span> <span class="operator">||</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">10</span> <span class="comment">/*no error code pushed*/</span><span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">(</span>SegmentSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinCSLimits<span class="operator">(</span>InstructionPointer<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
SS<span class="operator">:</span>ESP <span class="operator">=</span> TSS<span class="operator">(</span>NewSS<span class="operator">:</span>NewESP<span class="operator">)</span> <span class="comment">//segment descriptor information also loaded</span>
<span class="keyword">if</span><span class="operator">(</span>Is32BitGate<span class="operator">(</span><span class="operator">)</span><span class="operator">)</span> {
Push<span class="operator">(</span>FarPointer<span class="operator">(</span>OldStack<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//push a far pointer to the old stack, old SS and ESP, 3 words padded to 4</span>
Push<span class="operator">(</span>EFLAGS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>FarPointer<span class="operator">(</span>ReturnInstruction<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//old CS and EIP, 3 words padded to 4</span>
Push<span class="operator">(</span>ErrorCode<span class="operator">)</span><span class="operator">;</span> <span class="comment">//if needed, 2 bytes</span>
}
<span class="keyword">else</span> { <span class="comment">//16-bit gate</span>
Push<span class="operator">(</span>FarPointer<span class="operator">(</span>OldStack<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//old SS and SP, 2 words</span>
Push<span class="operator">(</span>EFLAGS<span class="operator">[</span><span class="number">0..15</span><span class="operator">]</span><span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>FarPointer<span class="operator">(</span>ReturnInstruction<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//old CS and IP, 2 words</span>
Push<span class="operator">(</span>ErrorCode<span class="operator">)</span><span class="operator">;</span> <span class="comment">//if needed, 2 bytes</span>
}
CPL <span class="operator">=</span> CodeSegmentDescriptor<span class="operator">.</span>DPL<span class="operator">;</span>
CS<span class="operator">.</span>RPL <span class="operator">=</span> CPL<span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>IsInterruptGate<span class="operator">(</span><span class="operator">)</span><span class="operator">)</span> IF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span> <span class="comment">//interrupt flag set to 0: disabled</span>
TF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
VM <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
RF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
NT <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
}
<span class="keyword">else</span> { <span class="comment">//VM == 1</span>
<span class="keyword">if</span><span class="operator">(</span>CodeSegment<span class="operator">.</span>DPL <span class="operator">!=</span> <span class="number">0</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>NewCodeSegmentSelector<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="comment">//Interrupt from Virtual 8086 mode</span>
<span class="comment">//PE = 1, interrupt or trap gate, DPL<CPL, VM = 1</span>
<span class="comment">//Check segment selector and descriptor for privilege level 0 stack in current TSS</span>
<span class="keyword">if</span><span class="operator">(</span>Is32BitTSS<span class="operator">(</span>CurrentTSS<span class="operator">)</span><span class="operator">)</span> {
TSSStackAddress <span class="operator">=</span> NewCodeSegment<span class="operator">.</span>DPL <span class="operator">*</span> <span class="number">8</span> <span class="operator">+</span> <span class="number">4</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>TSSStackAddress <span class="operator">+</span> <span class="number">7</span> <span class="operator">></span> TSSLimit<span class="operator">)</span> Exception<span class="operator">(</span>TS<span class="operator">(</span>CurrentTSSSelector<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
NewSS <span class="operator">=</span> TSSStackAddress <span class="operator">+</span> <span class="number">4</span><span class="operator">;</span>
NewESP <span class="operator">=</span> StackAddress<span class="operator">;</span>
}
<span class="keyword">else</span> { <span class="comment">//TSS is 16-bit</span>
TSSStackAddress <span class="operator">=</span> NewCodeSegment<span class="operator">.</span>DPL <span class="operator">*</span> <span class="number">4</span> <span class="operator">+</span> <span class="number">2</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>TSSStackAddress <span class="operator">+</span> <span class="number">4</span> <span class="operator">></span> TSSLimit<span class="operator">)</span> Excpetion<span class="operator">(</span><span class="preprocessor">#TS(CurrentTSSSelector));</span>
NewESP <span class="operator">=</span> TSSStackAddress<span class="operator">;</span>
NewSS <span class="operator">=</span> TSSStackAddress <span class="operator">+</span> <span class="number">2</span><span class="operator">;</span>
}
<span class="keyword">if</span><span class="operator">(</span>SegmentSelector <span class="operator">==</span> <span class="number">0</span><span class="operator">)</span> Exception<span class="operator">(</span>TS<span class="operator">(</span>EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinDescriptorTableLimits<span class="operator">(</span>SegmentSelector<span class="operator">.</span>Index<span class="operator">)</span> <span class="operator">||</span> SegmentSelector<span class="operator">.</span>RPL <span class="operator">!=</span> CodeSegment<span class="operator">.</span>DPL<span class="operator">)</span> Exception<span class="operator">(</span>TS<span class="operator">(</span>SSSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsPresent<span class="operator">(</span>StackSegment<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">(</span>SSSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>Is32BitGate<span class="operator">(</span><span class="operator">)</span> <span class="operator">&&</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">40</span> <span class="comment">/*error code pushed*/</span> <span class="operator">||</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">36</span> <span class="comment">/*no error code pushed*/</span><span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">(</span>SegmentSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">else</span> <span class="comment">/*16-bit gate*/</span> <span class="keyword">if</span><span class="operator">(</span>GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">20</span> <span class="comment">/*error code pushed*/</span> <span class="operator">||</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">18</span> <span class="comment">/*no error code pushed*/</span><span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">(</span>SegmentSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinCodeSegmentLimits<span class="operator">(</span>InstructionPointer<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
TemporaryEFLAGS <span class="operator">=</span> EFLAGS<span class="operator">;</span>
VM <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
TF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
RF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
NT <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>IsInterruptGateService<span class="operator">(</span><span class="operator">)</span><span class="operator">)</span> IF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span> <span class="comment">//service through interrupt gate</span>
TemporarySS <span class="operator">=</span> SS<span class="operator">;</span>
TemporaryESP <span class="operator">=</span> ESP<span class="operator">;</span>
SS<span class="operator">:</span>ESP <span class="operator">=</span> TSS<span class="operator">(</span>SS0<span class="operator">:</span>ESP0<span class="operator">)</span><span class="operator">;</span> <span class="comment">//Change to level 0 stack segment</span>
<span class="comment">//Folowing pushes are 16 bits for 16-bit gate and 32 bits for 32-bit gates</span>
<span class="comment">//Segment selector pushes in 32-bit mode are padded to two words</span>
Push<span class="operator">(</span>GS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>FS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>DS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>ES<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>TemporarySS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>TemporaryESP<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>TemporaryEFLAGS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>CS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>EIP<span class="operator">)</span><span class="operator">;</span>
GS <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span> <span class="comment">//segment registers nullified, invalid in protection mode</span>
FS <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
DS <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
ES <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
CS <span class="operator">=</span> Gate<span class="operator">(</span>CS<span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>OperandSize <span class="operator">==</span> <span class="number">32</span><span class="operator">)</span> EIP <span class="operator">=</span> Gate<span class="operator">(</span>InstructionPointer<span class="operator">)</span><span class="operator">;</span>
<span class="keyword">else</span> EIP <span class="operator">=</span> Gate<span class="operator">(</span>InstructionPointer<span class="operator">)</span> <span class="operator">&</span> <span class="number">0xFFFF</span><span class="operator">;</span> <span class="comment">//OperandSize is 16</span>
<span class="comment">//Starts execution of new routine in Protected Mode</span>
}
}
<span class="keyword">else</span> { <span class="comment">//PE = 1, interrupt or trap gate, DPL >= CPL</span>
<span class="keyword">if</span><span class="operator">(</span>VM <span class="operator">==</span> <span class="number">1</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>NewCodeSegmentSelector<span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>IsConforming<span class="operator">(</span>CodeSegment<span class="operator">)</span> <span class="operator">||</span> CodeSegment<span class="operator">.</span>DPL <span class="operator">==</span> CPL<span class="operator">)</span> {
<span class="comment">//Intra-privilege level interrupt</span>
<span class="comment">//PE == 1, DPL == CPL or conforming segment</span>
<span class="keyword">if</span><span class="operator">(</span>Is32BitGate<span class="operator">(</span><span class="operator">)</span> <span class="operator">&&</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">16</span> <span class="comment">/*error code pushed*/</span> <span class="operator">||</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">12</span> <span class="comment">/*no error code pushed*/</span><span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">else</span> <span class="comment">/*16-bit gate*/</span> <span class="keyword">if</span><span class="operator">(</span>GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">8</span> <span class="comment">/*error code pushed*/</span> <span class="operator">||</span> GetStackSpace<span class="operator">(</span><span class="operator">)</span> <span class="operator"><</span> <span class="number">6</span> <span class="comment">/*no error code pushed*/</span><span class="operator">)</span> Exception<span class="operator">(</span>SS<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span><span class="operator">!</span>IsWithinCodeSegmentLimit<span class="operator">(</span>InstructionPointer<span class="operator">)</span><span class="operator">)</span> Exception<span class="operator">(</span>GP<span class="operator">(</span><span class="number">0</span><span class="operator">)</span><span class="operator">)</span><span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>Is32BitGate<span class="operator">(</span><span class="operator">)</span><span class="operator">)</span> {
Push<span class="operator">(</span>EFLAGS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>FarPointer<span class="operator">(</span>ReturnInstruction<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//3 words padded to 4</span>
CS<span class="operator">:</span>EIP <span class="operator">=</span> Gate<span class="operator">(</span>CS<span class="operator">:</span>EIP<span class="operator">)</span><span class="operator">;</span> <span class="comment">//segment descriptor information also loaded</span>
Push<span class="operator">(</span>ErrorCode<span class="operator">)</span><span class="operator">;</span> <span class="comment">//if any</span>
}
<span class="keyword">else</span> { <span class="comment">//16-bit gate</span>
Push<span class="operator">(</span>FLAGS<span class="operator">)</span><span class="operator">;</span>
Push<span class="operator">(</span>FarPointer<span class="operator">(</span>ReturnLocation<span class="operator">)</span><span class="operator">)</span><span class="operator">;</span> <span class="comment">//2 words</span>
CS<span class="operator">:</span>IP <span class="operator">=</span> Gate<span class="operator">(</span>CS<span class="operator">:</span>IP<span class="operator">)</span><span class="operator">;</span> <span class="comment">//segment descriptor information also loaded</span>
Push<span class="operator">(</span>ErrorCode<span class="operator">)</span><span class="operator">;</span> <span class="comment">//if any</span>
}
CS<span class="operator">.</span>RPL <span class="operator">=</span> CPL<span class="operator">;</span>
<span class="keyword">if</span><span class="operator">(</span>IsInterruptGate<span class="operator">(</span><span class="operator">)</span><span class="operator">)</span> IF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span> <span class="comment">//interrupt flag is set to 0: disabled</span>
TF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
NT <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
VM <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
RF <span class="operator">=</span> <span class="number">0</span><span class="operator">;</span>
}
<span class="keyword">else</span> Exception<span class="operator">(</span>GP<span class="operator">(</span>CodeSegmentSelector <span class="operator">+</span> EXT<span class="operator">)</span><span class="operator">;</span>
}
}
}
}
</pre>
</td>
</tr>
</table>
</object>
<object>
<table class="box">
<tr>
<th>Flags affected</th>
</tr>
<tr>
<td class="instruction_set_reference_box">
<p>The EFLAGS register is pushed onto the stack. The IF, TF, NT, AC, RF, and VM flags may be cleared, depending on the mode of operation of the processor when the INT instruction is executed (see the "Operation" section). If the interrupt uses a task gate, any flags may be set or cleared, controlled by the EFLAGS image in the new task's TSS.
</p>
</td>
</tr>
</table>
</object>
<object>
<table class="box">
<tr>
<th>Protected Mode Exceptions</th>
</tr>
<tr>
<td class="instruction_set_reference_box">
<div>
<table class="operations_table">
<tr><td><code>#GP(0)</code></td><td>If the instruction pointer in the IDT or in the interrupt-, trap-, or task gate is beyond the code segment limits.</td></tr>
<tr><td><code>#GP(0)</code></td><td>If the instruction pointer in the IDT or in the interrupt-, trap-, or task gate is beyond the code segment limits.</td></tr>
<tr><td><code>#GP(selector)</code></td><td>If the segment selector in the interrupt-, trap-, or task gate is null. If an interrupt-, trap-, or task gate, code segment, or TSS segment selector index is outside its descriptor table limits. If the interrupt vector number is outside the IDT limits. If an IDT descriptor is not an interrupt-, trap-, or task-descriptor. If an interrupt is generated by the INT n, INT 3, or INTO instruction and the DPL of an interrupt-, trap-, or task-descriptor is less than the CPL. If the segment selector in an interrupt- or trap-gate does not point to a segment descriptor for a code segment. If the segment selector for a TSS has its local/global bit set for local. If a TSS segment descriptor specifies that the TSS is busy or not available.</td></tr>
<tr><td><code>#SS(0)</code></td><td>If pushing the return address, flags, or error code onto the stack exceeds the bounds of the stack segment and no stack switch occurs.</td></tr>
<tr><td><code>#SS(selector)</code></td><td>If the SS register is being loaded and the segment pointed to is marked not present. If pushing the return address, flags, error code, or stack segment pointer exceeds the bounds of the new stack segment when a stack switch occurs.</td></tr>
<tr><td><code>#NP(selector)</code></td><td>If code segment, interrupt-, trap-, or task gate, or TSS is not present.</td></tr>
<tr><td><code>#TS(selector)</code></td><td>If the RPL of the stack segment selector in the TSS is not equal to the DPL of the code segment being accessed by the interrupt or trap gate. If DPL of the stack segment descriptor pointed to by the stack segment selector in the TSS is not equal to the DPL of the code segment descriptor for the interrupt or trap gate. If the stack segment selector in the TSS is null. If the stack segment for the TSS is not a writable data segment. If segment-selector index for stack segment is outside descriptor table limits.</td></tr>
</table>
</div>
</td>
</tr>
</table>
</object>
<object>
<table class="box">
<tr>
<th>Real-Address Mode Exceptions</th>
</tr>
<tr>
<td class="instruction_set_reference_box">
<div>
<table class="operations_table">
<tr><td><code>#GP</code></td><td>If a memory operand effective address is outside the CS, DS, ES, FS, or GS segment limit. If the interrupt vector number is outside the IDT limits.</td></tr>
<tr><td><code>#GP</code></td><td>If a memory operand effective address is outside the CS, DS, ES, FS, or GS segment limit. If the interrupt vector number is outside the IDT limits.</td></tr>
</table>
</div>
</td>
</tr>
</table>
</object>
</div>
</body>
</html>