在本地描述符表(LDT)中添加一个调用门描述符以进行权限提升

时间:2015-09-18 09:32:26

标签: kernel privileges descriptor

我可以使用系统调用modify_ldt在LDT中添加新条目(调用门描述符)吗?

  • 如果是,这是否意味着我可以用描述符
    设置这个描述符 特权级别(DPL)3和代码段等于KERNEL_CS (这是CPL0的内核代码描述符)指向的 进程的地址空间低于TASK_SIZE,从而允许用户模式 任务在CPL0直接调用自己的代码。
  • 如果不是,为什么不呢?

我是这个领域的初学者。非常感谢您的耐心和努力。

1 个答案:

答案 0 :(得分:0)

  

我可以使用系统调用modify_ldt在LDT中添加新条目(调用门描述符)吗?

不,您无法使用此系统调用添加呼叫门,因为它是系统描述符。查看what information can be provided到系统调用...

struct user_desc {
  unsigned int  entry_number;
  unsigned long base_addr;
  unsigned int  limit;
  unsigned int  seg_32bit:1;
  unsigned int  contents:2; // HERE
  unsigned int  read_exec_only:1;
  unsigned int  limit_in_pages:1;
  unsigned int  seg_not_present:1;
  unsigned int  useable:1;
};

...我们看到我们只能在contents字段中提供两位来描述我们想要的描述符类型。通过Linux内核中的系统调用函数跟踪该数据并不是那么直接,但我很确定这些数据最终到达fill_ldt,其中包含以下行:

// ...
desc->type = (info->read_exec_only ^ 1) << 1;
desc->type |= info->contents << 2;
desc->s = 1;
// ...

member fields types以及描述符权限级别(DPL)和当前标志形式byte 5 of the descriptor的字段。成员s最终位于第4位(嗯,&#34; S&#34;位),它定义描述符是系统描述符(S=0)还是(代码/数据)段(S=1)。由于上面的代码对值1进行了硬编码,因此总是得到(代码/数据)段,而不是系统描述符。所以没有电话门。

  

[..]用于权限提升

因此这里的答案是否定的。否则,这将是Linux内核设计中的一个巨大的安全漏洞。我有点意外的是,处理器实际上允许LDT中的呼叫门,从而给操作系统带来了检测(或完全禁止)滥用该功能的负担。