【问题标题】:TSS entries for stack switching堆栈切换的 TSS 表项
【发布时间】:2020-07-16 08:00:25
【问题描述】:

我已经读到 TSS 包含有关寄存器等的信息。现在,我正在尝试实现从内核到用户模式的切换。我已阅读 Intel 80386 手册,并正在查看此资源:http://www.brokenthorn.com/Resources/OSDev23.html 以了解一般工作流程。他们这样做:

void install_tss (uint32_t idx, uint16_t kernelSS, uint16_t kernelESP) {

    //! install TSS descriptor
    uint32_t base = (uint32_t) &TSS;
    gdt_set_descriptor (idx, base, base + sizeof (tss_entry),
        I86_GDT_DESC_ACCESS|I86_GDT_DESC_EXEC_CODE|I86_GDT_DESC_DPL|I86_GDT_DESC_MEMORY,
        0);

    //! initialize TSS
    memset ((void*) &TSS, 0, sizeof (tss_entry));

    TSS.ss0 = kernelSS;
    TSS.esp0 = kernelESP;

    TSS.cs=0x0b;
    TSS.ss = 0x13;
    TSS.es = 0x13;
    TSS.ds = 0x13;
    TSS.fs = 0x13;
    TSS.gs = 0x13;

    //! flush tss
    flush_tss (idx * sizeof (gdt_descriptor));
}

我很困惑为什么 RPL = 3

在我的情况下,当我处于用户模式并且我想使用陷阱门进入内核模式时,陷阱门中的 cs 段将具有 RPL 0(16 位段的最后 2 位)和与 cs 段相对应的 GDT 条目也将具有 DPL 0。而且我读过一个跨级权限开关切换堆栈(仅??)查看 TSS。我猜上面这段代码肯定有一个 TSS.ss = 0x10。

注意:我们假设经典的 0x08 = 内核代码,0x10 = 内核数据,...这里是 GDT 结构

【问题讨论】:

    标签: c x86 interrupt osdev


    【解决方案1】:

    TSS 结构有很多用于硬件任务切换的字段(例如TSS.ss,如果发生硬件任务切换,ss 寄存器的内容将被保存/加载),加上一些字段用于将任务切换到更高权限级别(例如(e.g.TSS.ss0` 用于切换到 CPL=0)。

    您正在查看用于硬件任务切换的字段(通常不值得打扰,因为执行软件任务切换会更快);我猜有人在里面塞了一些“硬件任务切换兼容”的值(即使它们没有被使用)以避免未初始化的值。

    相反,您想查看 TSS 的 TSS.esp0TSS.ss0 字段,这是 TSS 中唯一与切换到 CPL=0 相关的 2 个字段(并且可能是您曾经使用过的 TSS)。

    【讨论】:

      猜你喜欢
      • 2018-09-07
      • 1970-01-01
      • 2020-01-06
      • 2015-03-03
      • 1970-01-01
      • 2021-08-31
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多