While poking around OS X implementation of TrustedBSD to write the sandbox guide I had the idea of trying to abuse it for backdooring purposes. It’s kind of funny that something designed to protect can be so “easily” abused to install backdoors.
This is not rocket science or a big breakthru post – I was just curious about the possibility to abuse the framework. You still need to find a way to install the kernel module!
So without further delay, I present you Rex, The Wonder Dog. It is a very simple policy module for TrustedBSD that gives r00t privileges to a process named “xyz”, if it calls task_for_pid(). For some unknown reason I couldn’t yet do the same with fork() (it was only working for Safari). I was doing this at 3am so I really didn’t bothered too much about it. It is based on SEDarwin sample policies code.
I had some trouble to compile the policy module (duplicate symbols) if I try to use the macro to initialize the module. I strongly suspect this is because I am using XCode’s kernel extension template. This is just a lazy PoC 😉
The code is unstable. Processes start crashing and crash reporter isn’t executing. It could be due to the very lazy way that r00t privileges are changed for the target process (it only starts to happen after backdoor is activated). Kernel land is dangerous territory! It is tested only with Snow Leopard 10.6.8. Might work with Lion without any problems. Load it as a normal kernel module, with kextload.
Dmesg log when module is loaded:
calling mpo_policy_init for rex_the_wonder_dog calling mpo_policy_initbsd for rex_the_wonder_dog Security policy loaded: Rex, the wonder dog! (rex_the_wonder_dog)
Starting the backdoor and getting a r00t shell:
$ ./xyz [info] calling task_for_pid() [info] task for pid returned 0 [info] uid 501 euid 0 [info] setting uid to 0... [info] uid 0 euid 0 [info] executing r00t shell... # id uid=0(root) gid=0(wheel) egid=20(staff) groups=0(wheel),204(_developer),100(_lpoperator),98(_lpadmin),80(admin), 61(localaccounts),29(certusers),20(staff),12(everyone),9(procmod),8(procview),5(operator),4(tty),3(sys),2(kmem),1(daemon), 401(com.apple.access_screensharing),402(com.apple.sharepoint.group.1)
Policy modules open interesting possibilities for implementing other things. Maybe your own binary integrity check module? Or maybe some nice anti-debug for software who must use kernel modules 😉
Sorry for the lazy and unstable code. I’m not that much interested in backdoors, I was just interested in testing the possibility. It’s (just) a clean way to activate a kernel backdoor. If you improve and want to share your code feel free to send it!
Here are the goodies.