Система команд x86 |
|
Программирование - Архитектура и система команд микропроцессоров x86 |
CLI
Влияние команды на флаги и форматы команды:
0 |
FA |
CLI |
Сброс флага EFLAGS.IF (внешние маскируемые прерывания запрещены) |
8086 |
cli |
Описание:
Команда CLI очищает флаг EFLAGS.IF. Сброс флага EFLAGS.IF означает, что после команды CLI и до точки повторной установки флага микропроцессор прекращает воспринимать (распознавать) и реагировать на запросы прерывания по входу INTR# (внешние маскируемые прерывания). Никакие другие флаги командой CLI не изменяются.
В реальном режиме команда срабатывает без всяких условий и не может привести к генерации особых ситуаций.
В защищенном режиме флаг EFLAGS.IF сбрасывается, только если текущий уровень привилегий как минимум такой же, как и уровень привилегий ввода/вывода (CPL ≤ EFLAGS.IOPL), в противном случае команда вызывает генерацию ошибки общей защиты (#GP). Такое поведение называется IOPL-чувствительностью и в защищенном режиме оно характерно также для команд STI, IN, OUT, INS/NSB/INSW/INSD, OUTS/OUTSB/OUTSW/OUTSD.
В режиме V86 успешное срабатывание команды CLI (с учетом того что в задачах этого режима всегда CPL = 3) возможно только тогда, когда EFLAFS.IOPL = 3. В противном случае также генерируется ошибка общей защиты (#GP). В этом режиме IOPL-чувствительностью обладают также команды STI, POPF/POPFD, PUSHF/PUSHFD, IRET/IRETD, INT n.
В процессорах, начиная с Pentium, поддерживаются специальные расширенные режимы обработки прерываний (виртуальные прерывания). Это позволяет обеспечить нормальное выполнение старого ПО, использующего команды управления внешними маскируемыми прерываниями (векторы от 32 до 255), в современной мультипроцессорной и мультизадачной программно-аппаратной среде. Указанные режимы управляются флагами CR4.PVI и CR4.VME и включают:
- режим с поддержкой виртуальных флагов прерываний (включается установкой флага CR4.PVI = 1 в защищенном режиме);
- режим EV86 (включается установкой флага CR4.VME = 1 в режиме V86).
В этих режимах флаг виртуального прерывания EFLAGS.VIF выступает виртуальным подобием флага EFLAGS.IF. При условии, что виртуальные прерывания инициализированы (CR4.PVI = 1 в защищенном режиме, CR4.VME = 1 в режиме V86), команда CLI (как и команда STI), выполняемая при текущем уровне привилегий равном 3 (CPL = 3), при соблюдении условия EFLAGS.IOPL < 3 не вызывает генерацию ошибки общей защиты (#GP), а оказывает влияние на флаг EFLAGS.VIF, оставляя флаг EFLAGS.IF неизменным. Аналогичный специальный функционал для режима EV86 имеют также команды PUSHF, POPF, STI, IRET и команда вызова программных прерываний INT n.
Таблица событий 6.24. указывает — какое действие из нижней части таблицы произойдет при условиях, стоящих в верхней части.
Таблица 6.24. Действия команды CLI и условия их выполнения
0 |
1 |
1 |
1 |
1 |
1 |
1 |
1 |
|
x |
0 |
0 |
0 |
0 |
1 |
1 |
x |
|
x |
x |
0 |
1 |
1 |
x |
x |
x |
|
x |
x |
x |
x |
x |
0 |
1 |
x |
|
x |
≤ IOPL |
> IOPL |
3 |
< 3 |
x |
x |
x |
|
x |
≥ CPL |
< CPL |
< 3 |
< CPL |
< 3 |
< 3 |
3 |
|
EFLAGS.IF = 0 |
+ |
+ |
+ |
|||||
EFLAGS.VIF = 0 |
+ |
+ |
||||||
+ |
+ |
+ |
Операция:
IF CR0.PE = 0 (* Выполняется в режиме реальной адресации *)
THEN EFLAGS.IF = 0;
ELSE
IF EFLAGS.VM = 0 (* Выполняется в защищенном режиме *)
THEN
IF EFLAGS.IOPL = 3
THEN EFLAGS.IF = 0;
ELSE
IF CPL ≤ EFLAGS.IOPL
THEN EFLAGS.IF = 0;
ELSE (* CPL > EFLAGS.IOPL *)
IF (CPL = 3 and CR4.PVI = 1)
THEN EFLAGS.VIF = 0;
ELSE #GP(0);
FI;
FI;
FI;
ELSE (* Выполняется в виртуальном-8086 режиме *)
IF EFLAGS.IOPL = 3
THEN EFLAGS.IF = 0;
ELSE
IF CR4.VME = 1
THEN EFLAGS.VIF = 0;
ELSE #GP(0);
FI;
FI;
FI;
FI;
Особые ситуации защищенного режима:
#GP(0), если текущий уровень привилегий по значению больше (имеет меньше привилегий), чем уровень привилегий ввода/вывода – CPL > EFLAGS.IOPL (кроме режима с поддержкой виртуальных прерываний).
Intel386 … :
#UD при использовании префикса LOCK.
Pentium … (в режиме с поддержкой виртуальных прерываний – CR4.PVI = 1):
#GP(0) при активном режиме с поддержкой виртуальных прерываний (CR4.PVI = 1), если текущий уровень привилегий меньше 3 и больше чем уровень привилегий ввода/вывода (EFLAGS.IOPL < CPL < 3).
Особые ситуации режима V86:
#GP(0), если не активирован режим EV86 (CR4.VME = 0), а также уровень привилегий ввода/вывода по значению меньше 3 (EFLAGS.IOPL < 3).
Все права защищены © Алексей Ровдо, 1994-2023. Перепечатка возможна только по согласованию с владельцем авторских прав. admin@club155.ru