1 #![allow(unsafe_code)]
2
3 use bitflags::bitflags;
4 use linux_raw_sys::general::{
5 CLONE_FILES, CLONE_FS, CLONE_NEWCGROUP, CLONE_NEWIPC, CLONE_NEWNET, CLONE_NEWNS, CLONE_NEWPID,
6 CLONE_NEWTIME, CLONE_NEWUSER, CLONE_NEWUTS, CLONE_SYSVSEM,
7 };
8
9 use crate::backend::c::c_int;
10 use crate::backend::thread::syscalls;
11 use crate::fd::BorrowedFd;
12 use crate::io;
13
14 bitflags! {
15 /// Thread name space type.
16 pub struct ThreadNameSpaceType: u32 {
17 /// Time name space.
18 const TIME = CLONE_NEWTIME;
19 /// Mount name space.
20 const MOUNT = CLONE_NEWNS;
21 /// Control group (CGroup) name space.
22 const CONTROL_GROUP = CLONE_NEWCGROUP;
23 /// `Host name` and `NIS domain name` (UTS) name space.
24 const HOST_NAME_AND_NIS_DOMAIN_NAME = CLONE_NEWUTS;
25 /// Inter-process communication (IPC) name space.
26 const INTER_PROCESS_COMMUNICATION = CLONE_NEWIPC;
27 /// User name space.
28 const USER = CLONE_NEWUSER;
29 /// Process ID name space.
30 const PROCESS_ID = CLONE_NEWPID;
31 /// Network name space.
32 const NETWORK = CLONE_NEWNET;
33 }
34 }
35
36 /// Type of name space referred to by a link.
37 #[derive(Copy, Clone, Debug, Eq, PartialEq)]
38 #[repr(u32)]
39 pub enum LinkNameSpaceType {
40 /// Time name space.
41 Time = CLONE_NEWTIME,
42 /// Mount name space.
43 Mount = CLONE_NEWNS,
44 /// Control group (CGroup) name space.
45 ControlGroup = CLONE_NEWCGROUP,
46 /// `Host name` and `NIS domain name` (UTS) name space.
47 HostNameAndNISDomainName = CLONE_NEWUTS,
48 /// Inter-process communication (IPC) name space.
49 InterProcessCommunication = CLONE_NEWIPC,
50 /// User name space.
51 User = CLONE_NEWUSER,
52 /// Process ID name space.
53 ProcessID = CLONE_NEWPID,
54 /// Network name space.
55 Network = CLONE_NEWNET,
56 }
57
58 bitflags! {
59 /// `CLONE_*` for use with [`unshare`].
60 pub struct UnshareFlags: u32 {
61 /// `CLONE_FILES`.
62 const FILES = CLONE_FILES;
63 /// `CLONE_FS`.
64 const FS = CLONE_FS;
65 /// `CLONE_NEWCGROUP`.
66 const NWCGROUP = CLONE_NEWCGROUP;
67 /// `CLONE_NEWIPC`.
68 const NEWIPC = CLONE_NEWIPC;
69 /// `CLONE_NEWNET`.
70 const NEWNET = CLONE_NEWNET;
71 /// `CLONE_NEWNS`.
72 const NEWNS = CLONE_NEWNS;
73 /// `CLONE_NEWPID`.
74 const NEWPID = CLONE_NEWPID;
75 /// `CLONE_NEWTIME`.
76 const NEWTIME = CLONE_NEWTIME;
77 /// `CLONE_NEWUSER`.
78 const NEWUSER = CLONE_NEWUSER;
79 /// `CLONE_SYSVSEM`.
80 const SYSVSEM = CLONE_SYSVSEM;
81 }
82 }
83
84 /// Reassociate the calling thread with the namespace associated with link referred to by `fd`.
85 ///
86 /// `fd` must refer to one of the magic links in a `/proc/[pid]/ns/` directory, or a bind mount
87 /// to such a link.
88 ///
89 /// # References
90 /// - [`setns`]
91 ///
92 /// [`setns`]: https://man7.org/linux/man-pages/man2/setns.2.html
move_into_link_name_space( fd: BorrowedFd, allowed_type: Option<LinkNameSpaceType>, ) -> io::Result<()>93 pub fn move_into_link_name_space(
94 fd: BorrowedFd,
95 allowed_type: Option<LinkNameSpaceType>,
96 ) -> io::Result<()> {
97 let allowed_type = allowed_type.map_or(0, |t| t as c_int);
98 syscalls::setns(fd, allowed_type).map(|_r| ())
99 }
100
101 /// Atomically move the calling thread into one or more of the same namespaces as the thread
102 /// referred to by `fd`.
103 ///
104 /// `fd` must refer to a thread ID. See: `pidfd_open` and `clone`.
105 ///
106 /// # References
107 /// - [`setns`]
108 ///
109 /// [`setns`]: https://man7.org/linux/man-pages/man2/setns.2.html
move_into_thread_name_spaces( fd: BorrowedFd, allowed_types: ThreadNameSpaceType, ) -> io::Result<()>110 pub fn move_into_thread_name_spaces(
111 fd: BorrowedFd,
112 allowed_types: ThreadNameSpaceType,
113 ) -> io::Result<()> {
114 syscalls::setns(fd, allowed_types.bits() as c_int).map(|_r| ())
115 }
116
117 /// `unshare(flags)`—Disassociate parts of the current thread's execution
118 /// context with other threads.
119 ///
120 /// # References
121 /// - [`unshare`]
122 ///
123 /// [`unshare`]: https://man7.org/linux/man-pages/man2/unshare.2.html
unshare(flags: UnshareFlags) -> io::Result<()>124 pub fn unshare(flags: UnshareFlags) -> io::Result<()> {
125 syscalls::unshare(flags)
126 }
127