Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit 3287694

Browse filesBrowse files
authored
Merge pull request #69 from tcytan/cni-dev
update youki
2 parents b0a9565 + 517b3bb commit 3287694
Copy full SHA for 3287694

File tree

14 files changed

+5113
-4836
lines changed
Filter options

14 files changed

+5113
-4836
lines changed

‎project/libcgroups/Cargo.toml

Copy file name to clipboardExpand all lines: project/libcgroups/Cargo.toml
+4-4Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -22,19 +22,19 @@ cgroupsv2_devices = ["rbpf", "libbpf-sys", "errno", "libc", "nix/dir"]
2222
[dependencies]
2323
nix = { version = "0.29.0", features = ["signal", "user", "fs"] }
2424
procfs = "0.17.0"
25-
oci-spec = { version = "~0.7.1", features = ["runtime"] }
25+
oci-spec = { version = "~0.8.1", features = ["runtime"] }
2626
fixedbitset = "0.5.7"
2727
serde = { version = "1.0", features = ["derive"] }
2828
rbpf = { version = "0.3.0", optional = true }
2929
libbpf-sys = { version = "1.5.0", optional = true }
30-
errno = { version = "0.3.10", optional = true }
31-
libc = { version = "0.2.171", optional = true }
30+
errno = { version = "0.3.11", optional = true }
31+
libc = { version = "0.2.172", optional = true }
3232
thiserror = "2.0.12"
3333
tracing = { version = "0.1.41", features = ["attributes"] }
3434

3535
[dev-dependencies]
3636
anyhow = "1.0"
37-
oci-spec = { version = "~0.7.1", features = ["proptests", "runtime"] }
37+
oci-spec = { version = "~0.8.1", features = ["proptests", "runtime"] }
3838
quickcheck = "1"
3939
mockall = { version = "0.13.1", features = [] }
4040
clap = "4.1.6"

‎project/libcgroups/src/v1/devices.rs

Copy file name to clipboardExpand all lines: project/libcgroups/src/v1/devices.rs
+1-2Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -158,7 +158,7 @@ mod tests {
158158
fn property_test_apply_multiple_devices(devices: Vec<LinuxDeviceCgroup>) -> bool {
159159
let tmp = tempfile::tempdir().unwrap();
160160
devices.iter()
161-
.map(|device| {
161+
.all(|device| {
162162
set_fixture(tmp.path(), "devices.allow", "").expect("create allowed devices list");
163163
set_fixture(tmp.path(), "devices.deny", "").expect("create denied devices list");
164164
Devices::apply_device(device, tmp.path()).expect("Apply default device");
@@ -172,7 +172,6 @@ mod tests {
172172
denied_content == device.to_string()
173173
}
174174
})
175-
.all(|is_ok| is_ok)
176175
}
177176
}
178177
}

‎project/libcontainer/Cargo.toml

Copy file name to clipboardExpand all lines: project/libcontainer/Cargo.toml
+6-6Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ chrono = { version = "0.4", default-features = false, features = [
2626
"serde",
2727
] }
2828
fastrand = "^2.3.0"
29-
libc = "0.2.171"
29+
libc = "0.2.172"
3030
nix = { version = "0.29.0", features = [
3131
"socket",
3232
"sched",
@@ -37,8 +37,8 @@ nix = { version = "0.29.0", features = [
3737
"term",
3838
"hostname",
3939
] }
40-
oci-spec = { version = "0.7.1", features = ["runtime"] }
41-
once_cell = "1.21.2"
40+
oci-spec = { version = "0.8.1", features = ["runtime"] }
41+
once_cell = "1.21.3"
4242
procfs = "0.17.0"
4343
prctl = "1.0.0"
4444
libcgroups = { path = "../libcgroups", default-features = false, version = "0.5.3" } # MARK: Version
@@ -50,13 +50,13 @@ regex = { version = "1.10.6", default-features = false, features = ["std", "unic
5050
thiserror = "2.0.12"
5151
tracing = { version = "0.1.41", features = ["attributes"] }
5252
safe-path = "0.1.0"
53-
nc = "0.9.5"
53+
nc = "0.9.6"
5454

5555
[dev-dependencies]
56-
oci-spec = { version = "~0.7.1", features = ["proptests", "runtime"] }
56+
oci-spec = { version = "~0.8.1", features = ["proptests", "runtime"] }
5757
quickcheck = "1"
5858
serial_test = "3.1.1"
5959
tempfile = "3"
6060
anyhow = "1.0"
61-
rand = "0.9.0"
61+
rand = "0.9.1"
6262
scopeguard = "1"

‎project/libcontainer/src/config.rs

Copy file name to clipboardExpand all lines: project/libcontainer/src/config.rs
+2-2Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -46,8 +46,8 @@ pub struct YoukiConfig {
4646
pub cgroup_path: PathBuf,
4747
}
4848

49-
impl<'a> YoukiConfig {
50-
pub fn from_spec(spec: &'a Spec, container_id: &str) -> Result<Self> {
49+
impl YoukiConfig {
50+
pub fn from_spec(spec: &Spec, container_id: &str) -> Result<Self> {
5151
Ok(YoukiConfig {
5252
hooks: spec.hooks().clone(),
5353
cgroup_path: utils::get_cgroup_path(

‎project/libcontainer/src/container/tenant_builder.rs

Copy file name to clipboardExpand all lines: project/libcontainer/src/container/tenant_builder.rs
+82-4Lines changed: 82 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ use nix::unistd::{pipe2, read, Pid};
1414
use oci_spec::runtime::{
1515
Capabilities as SpecCapabilities, Capability as SpecCapability, LinuxBuilder,
1616
LinuxCapabilities, LinuxCapabilitiesBuilder, LinuxNamespace, LinuxNamespaceBuilder,
17-
LinuxNamespaceType, LinuxSchedulerPolicy, Process, ProcessBuilder, Spec,
17+
LinuxNamespaceType, LinuxSchedulerPolicy, Process, ProcessBuilder, Spec, UserBuilder,
1818
};
1919
use procfs::process::Namespace;
2020

@@ -32,6 +32,26 @@ const NAMESPACE_TYPES: &[&str] = &["ipc", "uts", "net", "pid", "mnt", "cgroup"];
3232
const TENANT_NOTIFY: &str = "tenant-notify-";
3333
const TENANT_TTY: &str = "tenant-tty-";
3434

35+
fn get_path_from_spec(spec: &Spec) -> Option<String> {
36+
let process = match spec.process() {
37+
Some(p) => p,
38+
None => return None,
39+
};
40+
let env = match process.env() {
41+
Some(e) => e,
42+
None => return None,
43+
};
44+
// as per runtime spec, env vars should follow https://pubs.opengroup.org/onlinepubs/9699919799/basedefs/V1_chap08.html#tag_08_01
45+
// and that specifies having multiple env with same name is undefined behaviour
46+
// so we take the last occurrence of PATH as that is somewhat intuitional of last
47+
// specified value overriding
48+
env.iter()
49+
.find(|e| e.starts_with("PATH"))
50+
.iter()
51+
.last()
52+
.map(|s| s.to_string())
53+
}
54+
3555
/// Builder that can be used to configure the properties of a process
3656
/// that will join an existing container sandbox
3757
pub struct TenantContainerBuilder {
@@ -44,6 +64,9 @@ pub struct TenantContainerBuilder {
4464
process: Option<PathBuf>,
4565
detached: bool,
4666
as_sibling: bool,
67+
additional_gids: Vec<u32>,
68+
user: Option<u32>,
69+
group: Option<u32>,
4770
}
4871

4972
/// This is a helper function to get capabilities for tenant container, based on
@@ -136,6 +159,9 @@ impl TenantContainerBuilder {
136159
process: None,
137160
detached: false,
138161
as_sibling: false,
162+
additional_gids: vec![],
163+
user: None,
164+
group: None,
139165
}
140166
}
141167

@@ -184,6 +210,21 @@ impl TenantContainerBuilder {
184210
self
185211
}
186212

213+
pub fn with_additional_gids(mut self, gids: Vec<u32>) -> Self {
214+
self.additional_gids = gids;
215+
self
216+
}
217+
218+
pub fn with_user(mut self, user: Option<u32>) -> Self {
219+
self.user = user;
220+
self
221+
}
222+
223+
pub fn with_group(mut self, group: Option<u32>) -> Self {
224+
self.group = group;
225+
self
226+
}
227+
187228
/// Joins an existing container
188229
pub fn build(self) -> Result<Pid, LibcontainerError> {
189230
let container_dir = self.lookup_container_dir()?;
@@ -398,9 +439,10 @@ impl TenantContainerBuilder {
398439
let process = if let Some(process) = &self.process {
399440
self.get_process(process)?
400441
} else {
442+
let original_path_env = get_path_from_spec(spec);
401443
let mut process_builder = ProcessBuilder::default()
402444
.args(self.get_args()?)
403-
.env(self.get_environment());
445+
.env(self.get_environment(original_path_env));
404446
if let Some(cwd) = self.get_working_dir()? {
405447
process_builder = process_builder.cwd(cwd);
406448
}
@@ -412,6 +454,22 @@ impl TenantContainerBuilder {
412454
let capabilities = get_capabilities(&self.capabilities, spec)?;
413455
process_builder = process_builder.capabilities(capabilities);
414456

457+
let mut user_builder = UserBuilder::default();
458+
459+
if !self.additional_gids.is_empty() {
460+
user_builder = user_builder.additional_gids(self.additional_gids.clone());
461+
}
462+
463+
if let Some(uid) = self.user {
464+
user_builder = user_builder.uid(uid);
465+
}
466+
467+
if let Some(gid) = self.group {
468+
user_builder = user_builder.gid(gid);
469+
}
470+
471+
process_builder = process_builder.user(user_builder.build()?);
472+
415473
process_builder.build()?
416474
};
417475

@@ -471,8 +529,28 @@ impl TenantContainerBuilder {
471529
Ok(self.args.clone())
472530
}
473531

474-
fn get_environment(&self) -> Vec<String> {
475-
self.env.iter().map(|(k, v)| format!("{k}={v}")).collect()
532+
fn get_environment(&self, path: Option<String>) -> Vec<String> {
533+
let mut env_exists = false;
534+
let mut env: Vec<String> = self
535+
.env
536+
.iter()
537+
.map(|(k, v)| {
538+
if k == "PATH" {
539+
env_exists = true;
540+
}
541+
format!("{k}={v}")
542+
})
543+
.collect();
544+
// It is not possible in normal flow that path is None. The original container
545+
// creation would have failed if path was absent. However we use Option
546+
// just as a caution, and if neither exec cmd not original spec has PATH,
547+
// the container creation will fail later which is ok
548+
if let Some(p) = path {
549+
if !env_exists {
550+
env.push(p);
551+
}
552+
}
553+
env
476554
}
477555

478556
fn get_no_new_privileges(&self) -> Option<bool> {

‎project/libcontainer/src/process/channel.rs

Copy file name to clipboardExpand all lines: project/libcontainer/src/process/channel.rs
+10-10Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -28,16 +28,16 @@ pub enum ChannelError {
2828
OtherError(String),
2929
}
3030

31-
/// Channel Design
32-
///
33-
/// Each of the main, intermediate, and init process will have a uni-directional
34-
/// channel, a sender and a receiver. Each process will hold the receiver and
35-
/// listen message on it. Each sender is shared between each process to send
36-
/// message to the corresponding receiver. For example, main_sender and
37-
/// main_receiver is used for the main process. The main process will use
38-
/// receiver to receive all message sent to the main process. The other
39-
/// processes will share the main_sender and use it to send message to the main
40-
/// process.
31+
// Channel Design
32+
//
33+
// Each of the main, intermediate, and init process will have a uni-directional
34+
// channel, a sender and a receiver. Each process will hold the receiver and
35+
// listen message on it. Each sender is shared between each process to send
36+
// message to the corresponding receiver. For example, main_sender and
37+
// main_receiver is used for the main process. The main process will use
38+
// receiver to receive all message sent to the main process. The other
39+
// processes will share the main_sender and use it to send message to the main
40+
// process.
4141

4242
pub fn main_channel() -> Result<(MainSender, MainReceiver), ChannelError> {
4343
let (sender, receiver) = channel::<Message>()?;

‎project/libcontainer/src/process/container_init_process.rs

Copy file name to clipboardExpand all lines: project/libcontainer/src/process/container_init_process.rs
+35-38Lines changed: 35 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -613,12 +613,12 @@ pub fn container_init_process(
613613
tracing::error!(?err, "failed to reset effective capabilities");
614614
InitProcessError::SyscallOther(err)
615615
})?;
616-
// if let Some(caps) = proc.capabilities() {
617-
// capabilities::drop_privileges(caps, syscall.as_ref()).map_err(|err| {
618-
// tracing::error!(?err, "failed to drop capabilities");
619-
// InitProcessError::SyscallOther(err)
620-
// })?;
621-
// }
616+
if let Some(caps) = proc.capabilities() {
617+
capabilities::drop_privileges(caps, syscall.as_ref()).map_err(|err| {
618+
tracing::error!(?err, "failed to drop capabilities");
619+
InitProcessError::SyscallOther(err)
620+
})?;
621+
}
622622

623623
// Change directory to process.cwd if process.cwd is not empty
624624
if do_chdir {
@@ -795,41 +795,38 @@ fn set_supplementary_gids(
795795

796796
/// set_io_priority set io priority
797797
fn set_io_priority(syscall: &dyn Syscall, io_priority_op: &Option<LinuxIOPriority>) -> Result<()> {
798-
match io_priority_op {
799-
Some(io_priority) => {
800-
let io_prio_class_mapping: HashMap<_, _> = [
801-
(IOPriorityClass::IoprioClassRt, 1i64),
802-
(IOPriorityClass::IoprioClassBe, 2i64),
803-
(IOPriorityClass::IoprioClassIdle, 3i64),
804-
]
805-
.iter()
806-
.filter_map(|(class, num)| match serde_json::to_string(&class) {
807-
Ok(class_str) => Some((class_str, *num)),
808-
Err(err) => {
809-
tracing::error!(?err, "failed to parse io priority class");
810-
None
811-
}
812-
})
813-
.collect();
798+
if let Some(io_priority) = io_priority_op {
799+
let io_prio_class_mapping: HashMap<_, _> = [
800+
(IOPriorityClass::IoprioClassRt, 1i64),
801+
(IOPriorityClass::IoprioClassBe, 2i64),
802+
(IOPriorityClass::IoprioClassIdle, 3i64),
803+
]
804+
.iter()
805+
.filter_map(|(class, num)| match serde_json::to_string(&class) {
806+
Ok(class_str) => Some((class_str, *num)),
807+
Err(err) => {
808+
tracing::error!(?err, "failed to parse io priority class");
809+
None
810+
}
811+
})
812+
.collect();
814813

815-
let iop_class = serde_json::to_string(&io_priority.class())
816-
.map_err(|err| InitProcessError::IoPriorityClass(err.to_string()))?;
817-
818-
match io_prio_class_mapping.get(&iop_class) {
819-
Some(value) => {
820-
syscall
821-
.set_io_priority(*value, io_priority.priority())
822-
.map_err(|err| {
823-
tracing::error!(?err, ?io_priority, "failed to set io_priority");
824-
InitProcessError::SyscallOther(err)
825-
})?;
826-
}
827-
None => {
828-
return Err(InitProcessError::IoPriorityClass(iop_class));
829-
}
814+
let iop_class = serde_json::to_string(&io_priority.class())
815+
.map_err(|err| InitProcessError::IoPriorityClass(err.to_string()))?;
816+
817+
match io_prio_class_mapping.get(&iop_class) {
818+
Some(value) => {
819+
syscall
820+
.set_io_priority(*value, io_priority.priority())
821+
.map_err(|err| {
822+
tracing::error!(?err, ?io_priority, "failed to set io_priority");
823+
InitProcessError::SyscallOther(err)
824+
})?;
825+
}
826+
None => {
827+
return Err(InitProcessError::IoPriorityClass(iop_class));
830828
}
831829
}
832-
None => {}
833830
}
834831
Ok(())
835832
}

‎project/libipam/src/main.rs

Copy file name to clipboardExpand all lines: project/libipam/src/main.rs
+1-2Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ fn main() {
3838
);
3939

4040
let rt = tokio::runtime::Builder::new_current_thread()
41-
.enable_all() // 开启 IO、定时器等必要功能
41+
.enable_all()
4242
.build()
4343
.unwrap();
4444

@@ -133,7 +133,6 @@ async fn cmd_del(inputs: Inputs) -> Result<IpamSuccessReply, CniError> {
133133
}
134134

135135
if !errors.is_empty() {
136-
// 合并所有错误信息,用分号分隔
137136
let combined_error = errors.join("; ");
138137
return Err(CniError::Generic(combined_error));
139138
}

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.