I'm doing a research about virtual machines and the rings they are running in. From documentation, this is sometimes hard to find. So I would like to run the VM's and then have a look at the processes and see in which ring they are running.

According to the blog-post of Gustavo Duarte the CPL-Register is set by the processor according to the ring of the process. In here @Stephen Kitt mentioned that there are possibilities. The solution in using gdb returns as mentioned as the register value Ring3. I've tried it with the process like ModemManager or iwlwifi which I suppose is running in Ring0, but they all returned Ring3 as their cs register content.

The suggested way is to use ftrace. But this program is seriously complex and I could not find a tutorial. Does somebody know the magic lines to just get the CS of a process?

Is there any other way retrieve the value from the CS register?


On x86, there’s no real need for another way to figure out which ring a process is running in, because the CS register fully determines the active ring. Since you’re running VMs, depending on which hypervisor you have, it might be possible to use debugging features there to see the current value of the virtual CS inside a VM, from outside.

The big issue with retrieving the value of CS inside a running system is that the value of CS will be entirely determined by the nature of the probe you use to retrieve the value. If you use a user-space probe, you’ll always see a value corresponding to user-space; if you use a kernel-level probe (kprobe or ftrace), you’ll always see a value corresponding to kernel-space.

In any case, on Linux on bare metal the situation is quite straightforward: user code runs in ring 3, the kernel runs in ring 0, and that’s it. This has nothing to do with user-level privileges: processes running as root are still mostly user-level code, so they’ll be running in ring 3 most of the time. The only time a user process runs in ring 0 is when it calls a system call, and you can’t interrupt that using gdb to see the active ring as ring 0.

On Xen with para-virtualised VMs, the situation is slightly different; the hypervisor runs in ring 0, user-space runs in ring 3, and the kernel runs in ring 1 (on 32-bit x86) or ring 3 (on 64-bit x86).

  • I was searching for an other (simpler) way to get the value from the CS register. For Xen in PV-Mode the rule of thumb it not true, because it runs in Ring1 and uses Hypercalls to Ring0 to invoke privileged calls. page 8 to demonstrate it I was looking for an way to show it. – Cutton Eye Apr 11 '18 at 13:52
  • thank YOU for this quick answer! I'm going to go deeper in this matter, can you give me a hint where to start the research? And may I ask where you got this information from about this platform depended rings in Xen PV? – Cutton Eye Apr 11 '18 at 14:08
  • I find QEMU and Bochs quite useful to explore the inner workings of an operating environment, because they have external debuggers which allow the system state to be inspected regardless of what it’s doing. You could start there... Regarding Xen, I know how it operates from reading its source code ;-). – Stephen Kitt Apr 11 '18 at 14:28
  • 1
    From a purely documentation side, I don’t know how much you know — but read up on protection models, the details of x86 protected mode (which is quite complex), etc. – Stephen Kitt Apr 11 '18 at 14:28

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.