📄 s06_03.htm
字号:
<P><H3>6.3.4.2 Returning from a Procedure</H3>The "near" forms of the <A HREF="RET.htm">RET</A> instruction transfer control within the currentcode segment and therefore are subject only to limit checking. The offset ofthe instruction following the corresponding <A HREF="CALL.htm">CALL</A>, is popped from the stack.The processor ensures that this offset does not exceed the limit of thecurrent executable segment.<P>The "far" form of the <A HREF="RET.htm">RET</A> instruction pops the return pointer that waspushed onto the stack by a prior far <A HREF="CALL.htm">CALL</A> instruction. Under normalconditions, the return pointer is valid, because of its relation to theprior <A HREF="CALL.htm">CALL</A> or <A HREF="INT.htm">INT</A>. Nevertheless, the processor performs privilege checkingbecause of the possibility that the current procedure altered the pointer orfailed to properly maintain the stack. The RPL of the CS selector poppedoff the stack by the return instruction identifies the privilege level ofthe calling procedure.<P>An intersegment return instruction can change privilege levels, but onlytoward procedures of lesser privilege. When the <A HREF="RET.htm">RET</A> instruction encounters asaved CS value whose RPL is numerically greater than the CPL, an interlevelreturn occurs. Such a return follows these steps:<OL><LI> The checks shown in Table 6-3 are made, and CS:EIP and SS:ESP areloaded with their former values that were saved on the stack.<LI> The old SS:ESP (from the top of the current stack) value is adjustedby the number of bytes indicated in the <A HREF="RET.htm">RET</A> instruction. The resultingESP value is not compared to the limit of the stack segment. If ESP isbeyond the limit, that fact is not recognized until the next stackoperation. (The SS:ESP value of the returning procedure is notpreserved; normally, this value is the same as that contained in theTSS.)<LI> The contents of the DS, ES, FS, and GS segment registers are checked.If any of these registers refer to segments whose DPL is greater thanthe new CPL (excluding conforming code segments), the segment registeris loaded with the null selector (INDEX = 0, TI = 0). The <A HREF="RET.htm">RET</A>instruction itself does not signal exceptions in these cases;however, any subsequent memory reference that attempts to use asegment register that contains the null selector will cause a generalprotection exception. This prevents less privileged code fromaccessing more privileged segments using selectors left in thesegment registers by the more privileged procedure.</OL><H2>6.3.5 Some Instructions are Reserved for Operating System</H2>Instructions that have the power to affect the protection mechanism or toinfluence general system performance can only be executed by trustedprocedures. The 80386 has two classes of such instructions:<OL><LI> Privileged instructions -- those used for system control.<LI> Sensitive instructions -- those used for I/O and I/O relatedactivities.</OL><PRE>Table 6-3. Interlevel Return ChecksSF = Stack FaultGP = General Protection ExceptionNP = Segment-Not-Present ExceptionType of Check Exception Error CodeESP is within current SS segment SF 0ESP + 7 is within current SS segment SF 0RPL of return CS is greater than CPL GP Return CSReturn CS selector is not null GP Return CSReturn CS segment is within descriptor table limit GP Return CSReturn CS descriptor is a code segment GP Return CSReturn CS segment is present NP Return CSDPL of return nonconforming code segment = RPL of return CS, or DPL of return conforming code segment <= RPL of return CS GP Return CSESP + N + 15 is within SS segmentN Immediate Operand of RET N Instruction SF Return SSSS selector at ESP + N + 12 is not null GP Return SSSS selector at ESP + N + 12 is within descriptor table limit GP Return SSSS descriptor is writable data segment GP Return SSSS segment is present SF Return SSSaved SS segment DPL = RPL of saved CS GP Return SSSaved SS selector RPL = Saved SS segment DPL GP Return SS</PRE><H3>6.3.5.1 Privileged Instructions</H3>The instructions that affect system data structures can only be executedwhen CPL is zero. If the CPU encounters one of these instructions when CPLis greater than zero, it signals a general protection exception. Theseinstructions include:<UL><LI><A HREF="CLTS.htm">CLTS -- Clear Task-Switched Flag</A><LI><A HREF="HLT.htm">HLT -- Halt Processor</A><LI><A HREF="LGDT.htm">LGDT -- Load GDL Register</A><LI><A HREF="LGDT.htm">LIDT -- Load IDT Register</A><LI><A HREF="LLDT.htm">LLDT -- Load LDT Register</A><LI><A HREF="LMSW.htm">LMSW -- Load Machine Status Word</A><LI><A HREF="LTR.htm">LTR -- Load Task Register</A><LI><A HREF="MOVRS.htm">MOV to/from CRn -- Move to Control Register n</A><LI><A HREF="MOVRS.htm">MOV to /from DRn -- Move to Debug Register n</A><LI><A HREF="MOVRS.htm">MOV to/from TRn -- Move to Test Register n</A></UL><H3>6.3.5.2 Sensitive Instructions</H3>Instructions that deal with I/O need to be restricted but also need to beexecuted by procedures executing at privilege levels other than zero. Themechanisms for restriction of I/O operations are covered in detail in<A HREF="c08.htm">Chapter 8</A>, "Input/Output".<H2>6.3.6 Instructions for Pointer Validation</H2>Pointer validation is an important part of locating programming errors.Pointer validation is necessary for maintaining isolation between theprivilege levels. Pointer validation consists of the following steps:<OL><LI> Check if the supplier of the pointer is entitled to access thesegment.<LI> Check if the segment type is appropriate to its intended use.<LI> Check if the pointer violates the segment limit.</OL>Although the 80386 processor automatically performs checks 2 and 3 duringinstruction execution, software must assist in performing the first check.The unprivileged instruction <A HREF="ARPL.htm">ARPL</A> is provided for this purpose. Software canalso explicitly perform steps 2 and 3 to check for potential violations(rather than waiting for an exception). The unprivileged instructions <A HREF="LAR.htm">LAR</A>,<A HREF="LSL.htm">LSL</A>, <A HREF="VERR.htm">VERR</A>, and <A HREF="VERR.htm">VERW</A> are provided for this purpose.<P><A HREF="LAR.htm">LAR</A> (Load Access Rights) is used to verify that a pointer refers to asegment of the proper privilege level and type. <A HREF="LAR.htm">LAR</A> has one operandselector for a descriptor whose access rights are to be examined. Thedescriptor must be visible at the privilege level which is the maximum ofthe CPL and the selector's RPL. If the descriptor is visible, <A HREF="LAR.htm">LAR</A> obtains amasked form of the second doubleword of the descriptor, masks this valuewith 00FxFF00H, stores the result into the specified 32-bit destinationregister, and sets the zero flag. (The x indicates that the correspondingfour bits of the stored value are undefined.) Once loaded, the access-rightsbits can be tested. All valid descriptor types can be tested by the <A HREF="LAR.htm">LAR</A>instruction. If the RPL or CPL is greater than DPL, or if the selector isoutside the table limit, no access-rights value is returned, and the zeroflag is cleared. Conforming code segments may be accessed from any privilegelevel.<P><A HREF="LSL.htm">LSL</A> (Load Segment Limit) allows software to test the limit of a descriptor.If the descriptor denoted by the given selector (in memory or a register) isvisible at the CPL, <A HREF="LSL.htm">LSL</A> loads the specified 32-bit register with a 32-bit,byte granular, unscrambled limit that is calculated from fragmented limitfields and the G-bit of that descriptor. This can only be done for segments(data, code, task state, and local descriptor tables); gate descriptors areinaccessible. (Table 6-4 lists in detail which types are valid and whichare not.) Interpreting the limit is a function of the segment type. Forexample, downward expandable data segments treat the limit differently thancode segments do. For both <A HREF="LAR.htm">LAR</A> and <A HREF="LSL.htm">LSL</A>, the zero flag (ZF) is set if theloading was performed; otherwise, the ZF is cleared.<PRE>Table 6-4. Valid Descriptor Types for LSLType Descriptor Type Valid?Code0 (invalid) NO1 Available 286 TSS YES2 LDT YES3 Busy 286 TSS YES4 286 Call Gate NO5 Task Gate NO6 286 Trap Gate NO7 286 Interrupt Gate NO8 (invalid) NO9 Available 386 TSS YESA (invalid) NOB Busy 386 TSS YESC 386 Call Gate NOD (invalid) NOE 386 Trap Gate NOF 386 Interrupt Gate NO</PRE><H3>6.3.6.1 Descriptor Validation</H3>The 80386 has two instructions, <A HREF="VERR.htm">VERR</A> and <A HREF="VERR.htm">VERW</A>, which determine whether aselector points to a segment that can be read or written at the currentprivilege level. Neither instruction causes a protection fault if the resultis negative.<P><A HREF="VERR.htm">VERR</A> (Verify for Reading) verifies a segment for reading and loads ZF with1 if that segment is readable from the current privilege level. <A HREF="VERR.htm">VERR</A> checksthat:<UL><LI> The selector points to a descriptor within the bounds of the GDT orLDT.<LI> It denotes a code or data segment descriptor.<LI> The segment is readable and of appropriate privilege level.</UL>The privilege check for data segments and nonconforming code segments isthat the DPL must be numerically greater than or equal to both the CPL andthe selector's RPL. Conforming segments are not checked for privilege level.<P><A HREF="VERR.htm">VERW</A> (Verify for Writing) provides the same capability as <A HREF="VERR.htm">VERR</A> forverifying writability. Like the <A HREF="VERR.htm">VERR</A> instruction, <A HREF="VERR.htm">VERW</A> loads ZF if theresult of the writability check is positive. The instruction checks that thedescriptor is within bounds, is a segment descriptor, is writable, and thatits DPL is numerically greater or equal to both the CPL and the selector'sRPL. Code segments are never writable, conforming or not.<H3>6.3.6.2 Pointer Integrity and RPL</H3>The Requestor's Privilege Level (RPL) feature can prevent inappropriate useof pointers that could corrupt the operation of more privileged code or datafrom a less privileged level.<P>A common example is a file system procedure, FREAD (file_id, n_bytes,buffer_ptr). This hypothetical procedure reads data from a file into abuffer, overwriting whatever is there. Normally, FREAD would be available atthe user level, supplying only pointers to the file system procedures anddata located and operating at a privileged level. Normally, such a procedureprevents user-level procedures from directly changing the file tables.However, in the absence of a standard protocol for checking pointervalidity, a user-level procedure could supply a pointer into the file tablesin place of its buffer pointer, causing the FREAD procedure to corrupt themunwittingly.<P>Use of RPL can avoid such problems. The RPL field allows a privilegeattribute to be assigned to a selector. This privilege attribute wouldnormally indicate the privilege level of the code which generated theselector. The 80386 processor automatically checks the RPL of any selectorloaded into a segment register to determine whether the RPL allows access.<P>To take advantage of the processor's checking of RPL, the called procedureneed only ensure that all selectors passed to it have an RPL at least ashigh (numerically) as the original caller's CPL. This action guarantees thatselectors are not more trusted than their supplier. If one of the selectorsis used to access a segment that the caller would not be able to accessdirectly, i.e., the RPL is numerically greater than the DPL, then aprotection fault will result when that selector is loaded into a segmentregister.<P><A HREF="ARPL.htm">ARPL</A> (Adjust Requestor's Privilege Level) adjusts the RPL field of aselector to become the larger of its original value and the value of the RPLfield in a specified register. The latter is normally loaded from the imageof the caller's CS register which is on the stack. If the adjustment changesthe selector's RPL, ZF (the zero flag) is set; otherwise, ZF is cleared.<P><HR><P><B>up:</B> <A HREF="c06.htm">Chapter 6 -- Protection</A><BR><B>prev:</B> <A HREF="s06_02.htm">6.2 Overview of 80386 Protection Mechanisms</A><BR><B>next:</B> <A HREF="s06_04.htm">6.4 Page-Level Protection</A></BODY>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -