使用气泡包装为NetBSD添加沙盒
Using bubblewrap to add sandboxing to NetBSD

原始链接: https://blog.netbsd.org/tnf/entry/gsoc2025_bubblewrap_sandboxing

## NetBSD 沙盒化与 Linux 命名空间:GSoC 2025 总结 该 Google 暑期实习项目旨在为 NetBSD 引入一种新的沙盒机制,灵感来自 Linux 命名空间。目前,NetBSD 除了有限的 `chroot` 之外,缺乏强大的沙盒化功能。该项目专注于实现两种关键的命名空间类型:UTS(主机名/域名)和挂载命名空间。 该实现利用 NetBSD 的 `kauth` 子系统进行凭证和生命周期管理,模仿 Linux 的方法,为每种命名空间类型使用单独的“secmodels”。 UTS 命名空间的成功实现允许应用程序修改它们感知的hostname,而不会影响系统。 挂载命名空间虽然更复杂且仍在进行中,但旨在隔离文件系统挂载,使应用程序能够以独立的文件系统层次结构视图运行。 代码可在 GitHub 上找到(maksymlanko/netbsd-src gsoc-bubblewrap 分支),包括一个基础的命名空间框架、一个带有测试的完整实现的 UTS 命名空间,以及正在进行的挂载命名空间工作。 虽然完整的挂载命名空间实现需要进一步努力,但该项目证明了将 Linux 风格的命名空间引入 NetBSD 的可行性,可能使本机应用程序和通过 `compat_linux` 与 Linux 二进制文件的兼容性都受益。 未来的工作可以探索 PID 和用户命名空间以增强隔离性。

使用气泡膜为NetBSD添加沙盒 (netbsd.org) 17点,由jaypatelani 2小时前发布 | 隐藏 | 过去 | 收藏 | 2评论 lovegrenoble 5分钟前 | 下一个 [–] 气泡破裂 )) https://brainteaser.top/bubblespop.html 回复 jmclnx 26分钟前 | 上一个 [–] 很高兴在这里看到NetBSD帖子,这个不错的操作系统几乎没有受到关注。回复 考虑申请YC冬季2026批次!申请截止至11月10日 指南 | 常见问题 | 列表 | API | 安全 | 法律 | 申请YC | 联系 搜索:
相关文章

原文

November 08, 2025 posted by Leonardo Taccari

This report was written by Vasyl Lanko as part of Google Summer of Code 2025.

As of the time of writing, there is no real sandboxing technique available to NetBSD. There is chroot, which can be considered a weak sandbox because it modifies the root directory of the process, effectively restricting the process' view of the file system, but it doesn't isolate anything else, so all networking, IPC, and mounts inside this restricted file system are the same as of the system, and are accessible.

There has already been some research on implementing kernel-level isolation in NetBSD with tools like gaols, mult and netbsd-sandbox, but they haven't been merged to NetBSD. Other operating systems have their own ways to isolate programs, FreeBSD has jails, and Linux has namespaces.

The goal of this project is to bring a new way of sandboxing to NetBSD. More specifically, we want to implement a mechanism like Linux namespaces. These namespaces allow the isolation of parts of the system from a namespace, or, as the user sees it, from an application.

NetBSD has compat_linux to run Linux binaries on NetBSD systems, and the implementation of namespaces can also be utilized to emulate namespace-related functionality of Linux binaries.

A simple example to visualize our intended result is to consider an application running under an isolated UTS namespace that modifies the hostname. From the system's view, the hostname remains the same old hostname, but from the application's view it sees the modified hostname.

Linux has 8 namespace types, in this project we will focus on only 2 of them:

  • UTS namespace, it is the simplest so we can focus on building the general namespace infrastructure with little namespace-specific details
  • mount namespace, it is a prerequisite to most other namespace types because UNIX follows the philosophy of "everything is a file", so we need a separate mount namespace to have different configuration files on the same location as the system.

Linux creates namespaces via the unshare or clone system calls, and it will also be our way of calling the namespace creation logic.

We setup the base for implementing Linux namespaces in the NetBSD kernel using kauth, the subsystem managing all authorization requests inside the kernel. It associates credentials with objects, and because the namespace lifecycle management is related to the credential lifecycle it handles all the credential inheritance and reference counting for us. (Thanks kauth devs!)

We separate the implementation of each namespace in a different secmodel, resulting in a similar framework to Linux which allows the isolation of a single namespace type. Our implementation also allows users to pick whether they want to have namespace support, and of what kind, via compilation flags, just like in Linux.

UTS namespace

UTS stands for UNIX Timesharing System, because it allows multiple users to share a single computer system. Isolating the utsname can be useful to give users the illusion that they have control over the system's hostname, and also, for example, to give different hostnames to virtual servers.

The UTS namespace stores the namespace's hostname, domain name, and their lengths. To isolate the utsname we need to first create a copy of the current UTS information, plus we need a variable containing the number of credentials referencing this namespace, or, in simpler terms, the reference count of this namespace.

This namespace specific information needs to be saved somewhere, and for that we use the credential's private_data field, so we can use a UTS_key to save and retrieve UTS related information from the secmodel. The key specifies the type of information we want to retrieve from the private_data, hence using a UTS_key for the UTS namespace. The key for each namespace is a fixed value (we don't create a new key for every credential), but the retrieved value for that key from different credentials may be different.

We had to modify kernel code that was directly accessing the hostname and domainname variables, to instead call get_uts(), which retrieves the UTS struct for the namespace of the calling process. We didn't modify occurrences in kernel drivers because drivers are not part of any namespace, so they should still access the system's resources directly.

MNT namespace

The MNT namespace isolates mounts across namespaces. It is used to have different versions of mounted filesystems across namespaces, meaning a user inside a mount namespace can mount and unmount whatever they want without affecting or even breaking the system.

The mount namespace structure in Linux is fairly complicated. To have something similar in NetBSD we need to be able to control the mounts accessed by each namespace, and for that we need to control what is each namespace's mountlist, this is also enough for unmounting file systems, because in practice we can just hide them.

For the mount_namespace, mountlist structure and the number of credentials using the mount namespace are stored in the credential's private data with the MNT_key. Similarly to the UTS namespace, we had to modify kernel code to not directly access the mountlist, but instead go through a wrapper called get_mountlist() which returns the correct mountlist for the namespace the calling process resides in.

Implementation for the mount namespace is immensely more complex than for the UTS namespace, it involves having a good understanding of both Linux and NetBSD behaviour, and I would frequently find myself wondering how to implement something after reading the Linux man pages, which would lead to me looking for it in the Linux source code, understanding it, then going back to NetBSD source code, trying to implement it, and seeing it's too different to implement in the same way.

You can find all code written during this project in GitHub at maksymlanko/netbsd-src gsoc-bubblewrap branch. Because I intend to continue this work outside of GSoC, I want to reinforce that this was the last commit still during GSoC on gsoc-bubblewrap branch and this was the last one for the mnt_ns still WIP branch.

The link includes implementation of general namespace code via secmodels, implementation of the UTS namespace and related ATF-tests, and the work-in-progress implementation of mount namespaces.

The mount namespace functionality is not finished as it would require much more work than the time available for this project. To complete it, it would be required invasive and non-trivial changes to the original source code, and, of course, more time.

As previously mentioned, Linux has 8 namespace types, it is important to see which of the missing namespaces are considered useful and feasible to implement.

I believe that after mount namespaces it would be interesting to implement PID namespaces as this in combination with mount namespaces would permit process isolation from this sandbox. Afterwards, implementing user namespaces would allow users to get capabilities similar to root in the namespace, giving them sudo permissions while still restricting system-wide actions like shutting down the machine.

A lower hanging fruit is to implement the namespace management functionality, which in Linux is lsns to list existing namespaces, and setns to move the current process to an already existing namespace.

  • Semantics. Did you know the unmount system call with MNT_FORCE flag in Linux (usually) returns EBUSY, and in NetBSD it forces the unmounting? One of them makes it easier to implement mount namespaces.
  • The behaviour of namespaces is not fully specified in the man pages. If something is not clear from the man pages you need to read the source code.
  • Unexpected need to learn a lot of VFS concepts and their differences in NetBSD and Linux.
  • There was a much bigger research component than I anticipated.

In the end, Linux and NetBSD are different operating systems, implemented in different ways. Linux is complex and it is not trivial to port namespaces to NetBSD.

The project is called "Using bubblewrap to add sandboxing to NetBSD" and was initially projected to emulate the unshare system call into compat_linux, but, seeing that having namespaces could be useful for NetBSD, and that it would be easy to add to compat_linux afterwards, we decided to instead implement namespaces directly in the NetBSD kernel. Implementing other system calls necessary to make the bwrap linux binary work correctly also wouldn't be as satisfying as implementing namespaces directly into NetBSD, so this was why the project was initially called "Using bubblewrap to add sandboxing to NetBSD" but nowadays it would be more accurate to call it "Sandboxing in NetBSD with Linux-like namespaces".

I am very grateful to Google for Google Summer of Code, because without it I wouldn't have learned so much this summer, wouldn't have met with smart and interesting people, and for sure wouldn't have tried to contribute to a project like NetBSD, even if I always wanted to write operating systems code... But, the biggest thing I will take with me from this project is the confidence to be able to contribute to NetBSD and other open source projects.

I would also like to thank the members of the NetBSD organization for helping me throughout this project, and more specifically:

  • Taylor R. Campbell, Harold Gutch and Nia Alarie from IRC, for helping me fix a nasty LD_LIBRARY_PATH bug I had on my system which wouldn't let me finish compiling NetBSD, and general GSoC recomendations.
  • Emmanuel Dreyfus from tech-kern, with whom I discussed ideas for projects and proposal suggestions, and in the end inspired the namespaces project.
  • Christoph Badura and Leonardo Taccari who volunteered to be my mentors. They took time to research and answer my questions, anticipated possible problems in my approaches, and always pointed me in the right direction, daily, during all of GSoC's period. This project is from the 3 of us.
[0 comments]

 

联系我们 contact @ memedata.com