It has two modes of operation; one in which it uses ptrace with PTRACE_SYSEMU, which was implemented so that User Mode Linux could intercept all syscalls. This works in all environments, whether or not hardware virtualization is available (included VMs which don't enable nested virtualization).
The other is that it can use KVM, without any hardware emulation, to utilize hardware virtualization support and do it more efficiently.
Neither way relies purely on user-space; they both use kernel features that are designed specifically for allowing one user-space process to virtualize another.
You can follow that link to see how it does it.
It has two modes of operation; one in which it uses ptrace with PTRACE_SYSEMU, which was implemented so that User Mode Linux could intercept all syscalls. This works in all environments, whether or not hardware virtualization is available (included VMs which don't enable nested virtualization).
The other is that it can use KVM, without any hardware emulation, to utilize hardware virtualization support and do it more efficiently.
Neither way relies purely on user-space; they both use kernel features that are designed specifically for allowing one user-space process to virtualize another.