SENDUIPI

发送用户间处理器中断

stableVMJITAOTinstruction

编码

操作码指令Op/En64 位兼容/传统说明
F3 0F C7 /6SENDUIPI regA有效无效发送处理器用户中断 。

操作数编码

每个模式对应上表 Op/En 列的一个取值,说明各操作数按书写顺序分别编码在指令的哪个字段,以及指令对它是读、是写还是两者兼有。

A

  1. modrm.reg lecturaModRM 字节的 reg 字段(第 5-3 位)

实测开销

正在从 arch-data 加载实测数据...

说明

SENDUIPI指令发送用户间处理器中断(IPI),以其注册号操作数表示. (操作数总是有64位;操作数-大小的覆盖,如前缀66被忽略).

SENDUIPI使用一个名为用户中断目标表(UITT)的数据结构. 本表位于线性地址UITTADDR(位于IA32 UINTR TT MSR);包含UITTSZ+116字节条目,其中UITTSZ=IA32 UINT MISC[31:0]. SENDUIPI使用由指令的寄存器操作数索引的UITT条目(UITTE). 每个 UITTE 格式如下:

字节对齐,所以每个UITTE的位数69:64必须是0.

每个UPID都有以下格式(未引用的字段和比特保留):

更多用户在 PIR 中中断.

在此描述符中发送用户中断时,不应发送通知。

(包括SENDUIPI).

位元47:40是8位APIC ID;在x2APIC模式中,整个字段构成32位APIC ID.

如果对应位数为 1,则用户中断请求向量 。

虽然SENDUIPI可以在任何特权级别执行,但所有指令的内存访问(一个UITTE和一个UPID)都是以监督特权执行的.

SENDUIPI发送用户中断,在UPIDADDR引用的UPID中发布用户中断矢量V,然后作为普通的IPI发送该UPID中指定中断的任何通知.

行动

    IF reg > UITTSZ;
          THEN #GP(0);

    FI;
    read tempUITTE from 16 bytes at UITTADDR+ (reg << 4);
    IF tempUITTE.V = 0 or tempUITTE sets any reserved bit

          THEN #GP(0);
    FI;


read tempUPID from 16 bytes at tempUITTE.UPIDADDR;// under lock
IF tempUPID sets any reserved bits or bits that must be zero

      THEN #GP(0); // release lock
FI;
tempUPID.PIR[tempUITTE.UV] := 1;
IF tempUPID.SN = tempUPID.ON = 0

      THEN
            tempUPID.ON := 1;
            sendNotify := 1;

      ELSE sendNotify := 0;
FI;
write tempUPID to 16 bytes at tempUITTE.UPIDADDR;// release lock
IF sendNotify = 1

      THEN
            IF local APIC is in x2APIC mode
                  THEN send ordinary IPI with vector tempUPID.NV
                        to 32-bit physical APIC ID tempUPID.NDST;
                  ELSE send ordinary IPI with vector tempUPID.NV
                        to 8-bit physical APIC ID tempUPID.NDST[15:8];
            FI;

FI;

受影响的旗帜

None.

异常

保护模式
#UDSENDUIPI指令在保护模式中不被识别.
实地址模式
#UDSENDUIPI指令在实地址模式中不被识别.
虚拟 8086 模式
#UDSENDUIPI指令在虚拟 8086 模式中不被识别.
兼容模式
#UDSENDUIPI指令在兼容模式中不被识别.
64 位模式
#UD如果使用 LOCK 前缀。如果在飞地内执行。如果 CR4.UINTR = 0。如果 IA32 UINTR TT[0] = 0。如果 CPUID.07H.00H: EDX.UINTR[5] = 0。
#PF如果发生 页面错误 。
#GP如果寄存器的值 操作数 超过 UITTSZ 。 如果选中的 UITTE 无效或设置了任何保留位。 如果选中的 UPID 设置了任何保留位。 如果试图使用一个线性地址访问内存, 而该地址相对于当前呼呼模式来说不是空洞的 。

来源