流程
用户态 —-> 内核态
I.切换GS段寄存器
通过 `swapgs` 切换 GS 段寄存器,将 GS 寄存器值和一个特定位置的值进行交换,目的是保存 GS 值,同时将该位置的值作为内核执行时的 GS 值使用
II.保存用户态栈帧信息
将当前栈顶(用户空间栈顶)记录在 CPU 独占变量区域里,将 CPU 独占区域里记录的内核栈顶放入 rsp/esp
III.保存用户态寄存器信息
通过 push 保存各寄存器值到栈上,以便后续“着陆”回用户态
IV.通过汇编指令判断是否为32位
V.控制权转交内核,执行系统调用
在这里用到一个全局函数表`sys_call_table`,其中保存着系统调用的函数指针
内核态 —-> 用户态
由内核态重新“着陆”回用户态只需要恢复用户空间信息即可:
- `swapgs`指令恢复用户态GS寄存器
- `sysretq`或者`iretq`恢复到用户空间
方式一
进程权限凭证结构体cred ,它用于 保存每个进程的权限定义如下:
struct cred {
atomic_t usage;
atomic_t subscribers; /* number of processes subscribed */
void *put_addr;
unsigned magic;
kuid_t uid; /* 实际用户id */
kgid_t gid; /* 实际用户组id */
kuid_t suid; /* 保存的用户uid */
kgid_t sgid; /* 保存的用户组gid */
kuid_t euid; /* 真正有效的用户id */
kgid_t egid; /* 真正有效的用户组id */
kuid_t fsuid;
kgid_t fsgid;
unsigned securebits; /* 安全管理标识;用来控制凭证的操作与继承 */
kernel_cap_t cap_inheritable; /* execve时可以继承的权限 */
kernel_cap_t cap_permitted; /* 可以(通过capset)赋予cap_effective的权限 */
kernel_cap_t cap_effective; /* 进程实际使用的权限 */
kernel_cap_t cap_bset; /* capability bounding set */
kernel_cap_t cap_ambient; /* Ambient capability set */
//。。。。。。
};
} __randomize_layout;
真实用户ID(real UID):标识一个进程启动时的用户ID
保存用户ID(saved UID):标识一个进程最初的有效用户ID

最低0.47元/天 解锁文章
4255

被折叠的 条评论
为什么被折叠?



