Resources

People often ask me "How did you learn how to hack?" The answer: by reading. This page is a collection of the blog posts and other articles that I have accumulated over the years of my journey. Enjoy!

Who Contains the Containers? - 452

James Forshaw - Project Zero (P0)Posted 4 Years Ago
  • Windows 10 added support for application containerization. It is quite similar to how containerization is done on Linux but wild different. While Docker on Windows works quite well, the implementation details for containers are abstracted away and not well-documented (besides onMSDN. This article is an overview of Windows containerization primitives and four bugs found along the way.
  • The goal of containers is to hide the real OS from the application. On Windows, the Server Silo is allows the redirection of resources such as the object manager, registry and networking. This is a special type of Job object.
  • There are two types of containers on Windows: Windows Server Containers and Hyper-V Isolated Containers. The difference is that the Hyper-V version runs in a lightweight VM under the hypervisor. The current specs say that only the Hyper-V container type has security promises, even though they are both containers.
  • The author wanted to crate their own container and understand what was going on. Luckily, Microsoft has a simple Go client and Windows Docker images are existing as well. After setting up a nice testing environment, it was time to find some vulns!
  • As the ContainerUser, the author wanted to see the permissions of this user. Although the groups did not seem interesting, the user had the SeImpersonatePrivilege! This permission allows this user to become any other user, including admin. This is a good (even bad?) start to the research.
  • The second bug was a registry key issue. By using relative opens for registries, it was ignoring the registry overlays. So, a non-administrative user could access user keys on the host if the user can pass the access key check.
  • Another issue was found with the registry keys and symbolic links. When accessing a symbolic link in a hive (grouping of registry keys), a kernel component should reject using the symbolic link or verify the ownership of the location. However, the function PsIsCurrentThreadInServerSilo will essentially always return TRUE. This appears to be something done in the testing phase that was never fixed.
  • Using the above bug, an attacker can use a kernel component to write to an arbitrary registry key. This could be used to escalate permissions within the container to cause major damage.
  • The final bug results from a discrepancy between application and server silos. With Linux, the syscall chroot can change the root directory for a user. In Windows land, a similar concept can be used to isolate an object manager namespace for users.
  • When attempting to find the right silo for the container, it does NOT validate which type of silo it is. Because an application silo can be created by any user, this is really bad. In order to perform this attack, simple create an application silo and assign this silo to a process. Now, the silo manager will use this malicious silo as if it was on the host machine.
  • Because the namespace has been put onto the actual root location, data can be accessed on the host through the object manager. Damn, such a simple mistake led to such a horrible outcome!
  • Putting all of these bugs together, it is possible to write content to the root of the hosts system drive. In particular, James uses the impersonation bug with the namespace bug to write to the host OS.