!21 [sync] PR-18: sync patches from upstream

From: @openeuler-sync-bot 
Reviewed-by: @jiayi0118 
Signed-off-by: @jiayi0118
This commit is contained in:
openeuler-ci-bot 2023-06-19 03:04:11 +00:00 committed by Gitee
commit dbab064f79
No known key found for this signature in database
GPG Key ID: 173E9B9CA92EEF8F
23 changed files with 3059 additions and 3 deletions

View File

@ -0,0 +1,22 @@
From 3db42578519edc87886b06428db5c31630957684 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 14 Jun 2023 11:35:13 +0800
Subject: [PATCH] docs: note that we only support no more than 500 units by
default
---
docs/man/all.md | 1 +
1 file changed, 1 insertion(+)
diff --git a/docs/man/all.md b/docs/man/all.md
index 2b3ec2c..337e156 100644
--- a/docs/man/all.md
+++ b/docs/man/all.md
@@ -1,3 +1,4 @@
# Warnings
1. 由于Rust使用String字符串,对于长度无限制, 建议用户在撰写配置文件时控制在合理的长度内.
+2. sysmaster默认支持的unit最大数量为500个超过该值可能会一场退出。用户可以通过修改/etc/sysmaster/system.toml的DbSize配置提高unit上限。修改方法请参考[外置db配置](./sysmaster.conf.md)
--
2.30.2

View File

@ -0,0 +1,106 @@
From 5fbd070f79a0526f647fb5bb734ad9edac9e2fe1 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 11:08:24 +0800
Subject: [PATCH 3/9] feature: add as_any() to SubUnit so we can downcast
SubUnit trait to concrete componnent
---
coms/mount/src/unit.rs | 4 ++++
coms/service/src/unit.rs | 4 ++++
coms/socket/src/unit.rs | 5 +++++
coms/target/src/unit.rs | 4 ++++
core/lib/unit/base.rs | 3 +++
5 files changed, 20 insertions(+)
diff --git a/coms/mount/src/unit.rs b/coms/mount/src/unit.rs
index dfa6087..dc84403 100644
--- a/coms/mount/src/unit.rs
+++ b/coms/mount/src/unit.rs
@@ -64,6 +64,10 @@ impl MountUnit {
}
impl SubUnit for MountUnit {
+ fn as_any(&self) -> &dyn std::any::Any {
+ self
+ }
+
fn load(&self, _paths: Vec<PathBuf>) -> Result<()> {
if let Some(u) = self.comm.owner() {
u.set_ignore_on_isolate(true)
diff --git a/coms/service/src/unit.rs b/coms/service/src/unit.rs
index c91a296..7ea3c44 100644
--- a/coms/service/src/unit.rs
+++ b/coms/service/src/unit.rs
@@ -71,6 +71,10 @@ impl ReStation for ServiceUnit {
}
impl SubUnit for ServiceUnit {
+ fn as_any(&self) -> &dyn std::any::Any {
+ self
+ }
+
fn init(&self) {
todo!()
}
diff --git a/coms/socket/src/unit.rs b/coms/socket/src/unit.rs
index 198fafc..8e33ee8 100644
--- a/coms/socket/src/unit.rs
+++ b/coms/socket/src/unit.rs
@@ -23,6 +23,7 @@ use crate::{
use basic::logger;
use nix::sys::wait::WaitStatus;
use std::{path::PathBuf, rc::Rc};
+use std::any::Any;
use sysmaster::error::*;
use sysmaster::exec::ExecContext;
use sysmaster::rel::{ReStation, Reliability};
@@ -68,6 +69,10 @@ impl ReStation for SocketUnit {
}
impl SubUnit for SocketUnit {
+ fn as_any(&self) -> &dyn Any {
+ self
+ }
+
fn load(&self, paths: Vec<PathBuf>) -> Result<()> {
log::debug!("socket begin to load conf file");
self.config.load(paths, true)?;
diff --git a/coms/target/src/unit.rs b/coms/target/src/unit.rs
index 26b9950..e4caf5d 100644
--- a/coms/target/src/unit.rs
+++ b/coms/target/src/unit.rs
@@ -120,6 +120,10 @@ impl Target {
}
impl SubUnit for Target {
+ fn as_any(&self) -> &dyn std::any::Any {
+ self
+ }
+
fn load(&self, _conf_str: Vec<PathBuf>) -> Result<()> {
//todo add default dependency funnction need add
log::debug!("load for target");
diff --git a/core/lib/unit/base.rs b/core/lib/unit/base.rs
index 0996f5d..d279295 100644
--- a/core/lib/unit/base.rs
+++ b/core/lib/unit/base.rs
@@ -17,6 +17,7 @@ use super::umif::UnitMngUtil;
use crate::error::*;
use nix::sys::wait::WaitStatus;
use nix::{sys::socket::UnixCredentials, unistd::Pid};
+use std::any::Any;
use std::{collections::HashMap, path::PathBuf, rc::Rc};
///The trait Defining Shared Behavior from Base Unit to SUB unit
@@ -72,6 +73,8 @@ pub trait UnitBase {
/// difference sub unit ref by dynamic trait
///
pub trait SubUnit: ReStation + UnitMngUtil {
+ ///
+ fn as_any(&self) -> &dyn Any;
///
fn init(&self) {}
--
2.30.2

View File

@ -0,0 +1,447 @@
From ca86515f0d1cfcaae7d5552ef9f7df89cf6398d9 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Thu, 1 Jun 2023 15:38:02 +0800
Subject: [PATCH] feature: get credential from the connection, and use it to
check if the request is send from root
---
core/bin/manager/commands.rs | 33 ++++++-----
core/bin/unit/entry/config.rs | 6 +-
core/bin/unit/util/unit_file.rs | 35 ++++++++++--
libs/cmdproto/src/error.rs | 3 +
libs/cmdproto/src/proto/execute.rs | 68 ++++++++++++++++++++--
libs/cmdproto/src/proto/frame.rs | 91 +++++++++++++++++++++++++-----
6 files changed, 194 insertions(+), 42 deletions(-)
diff --git a/core/bin/manager/commands.rs b/core/bin/manager/commands.rs
index 1279206..a8320e2 100644
--- a/core/bin/manager/commands.rs
+++ b/core/bin/manager/commands.rs
@@ -73,21 +73,28 @@ where
}
fn dispatch(&self, _e: &Events) -> i32 {
- log::trace!("Dispatching Command!");
-
self.reli.set_last_frame1(ReliLastFrame::CmdOp as u32);
- match self.fd.incoming().next() {
- None => log::info!("None CommandRequest!"),
- Some(stream) => {
- log::trace!("{stream:?}");
- if let Ok(s) = stream {
- let dispatch = ProstServerStream::new(s, self.command_action.clone());
- match dispatch.process() {
- Ok(_) => (),
- Err(e) => log::error!("Commands failed: {:?}", e),
- }
- }
+ let client = match socket::accept(self.socket_fd) {
+ Err(e) => {
+ log::error!("Failed to accept connection: {}, ignoring.", e);
+ return 0;
+ }
+ Ok(v) => v,
+ };
+ let cred = match socket::getsockopt(client, socket::sockopt::PeerCredentials) {
+ Err(e) => {
+ log::error!(
+ "Failed to get the credentials of the connection: {}, refuse any request.",
+ e
+ );
+ None
}
+ Ok(v) => Some(v),
+ };
+ let dispatch = ProstServerStream::new(client, self.command_action.clone(), cred);
+ match dispatch.process() {
+ Ok(_) => (),
+ Err(e) => log::error!("Commands failed: {:?}", e),
}
self.reli.clear_last_frame();
diff --git a/core/bin/unit/entry/config.rs b/core/bin/unit/entry/config.rs
index e629c77..705512d 100644
--- a/core/bin/unit/entry/config.rs
+++ b/core/bin/unit/entry/config.rs
@@ -136,14 +136,12 @@ impl UeConfig {
let unit_conf_frag = files.get_unit_id_fragment_pathbuf(name);
if unit_conf_frag.is_empty() {
- log::error!("config file for {} is not exist", name);
- return Err(format!("config file for {name} is not exist").into());
+ return Err(format!("{name} doesn't have corresponding config file").into());
}
// fragment
for v in unit_conf_frag {
if !v.exists() {
- log::error!("config file is not exist");
- return Err(format!("config file is not exist {name}").into());
+ return Err(format!("Config file {:?} of {name} doesn't exist", v).into());
}
builder = builder.file(&v);
}
diff --git a/core/bin/unit/util/unit_file.rs b/core/bin/unit/util/unit_file.rs
index 31f5838..0871703 100644
--- a/core/bin/unit/util/unit_file.rs
+++ b/core/bin/unit/util/unit_file.rs
@@ -133,12 +133,39 @@ impl UnitFileData {
format!("{v}/{name}")
};
let tmp = Path::new(&path);
- if tmp.exists() && !tmp.is_symlink() {
- let path = format!("{}.toml", tmp.to_string_lossy());
- if let Err(e) = std::fs::copy(tmp, &path) {
+ if !tmp.exists() {
+ continue;
+ }
+ /* Add .toml to the original path name */
+ if !tmp.is_symlink() {
+ let path_toml = format!("{}.toml", tmp.to_string_lossy());
+ let to = Path::new(&path_toml);
+ if let Err(e) = std::fs::copy(tmp, to) {
log::warn!("copy file content to toml file error: {}", e);
}
- let to = Path::new(&path);
+ pathbuf_fragment.push(to.to_path_buf());
+ } else {
+ let real_path = match std::fs::read_link(tmp) {
+ Err(e) => {
+ log::error!("Failed to chase the symlink {:?}: {e}", tmp);
+ continue;
+ }
+ Ok(v) => v,
+ };
+ /* Only support one-level symlink. */
+ if real_path.is_symlink() {
+ continue;
+ }
+ let real_path = tmp.parent().unwrap().join(real_path);
+ let real_path = fs::canonicalize(&real_path).unwrap();
+ let path_toml = format!("{}.toml", real_path.to_string_lossy());
+ let to = Path::new(&path_toml);
+ if let Err(e) = std::fs::copy(&real_path, to) {
+ log::warn!(
+ "copy file content {:?} to toml file {path_toml} error: {e}",
+ real_path
+ );
+ }
pathbuf_fragment.push(to.to_path_buf());
}
}
diff --git a/libs/cmdproto/src/error.rs b/libs/cmdproto/src/error.rs
index 5d64109..618e6ad 100644
--- a/libs/cmdproto/src/error.rs
+++ b/libs/cmdproto/src/error.rs
@@ -33,6 +33,9 @@ pub enum Error {
#[snafu(display("ReadStreamFailed"))]
ReadStream { msg: String },
+ #[snafu(display("SendStreamFailed"))]
+ SendStream { msg: String },
+
#[snafu(display("ManagerStartFailed"))]
ManagerStart { msg: String },
}
diff --git a/libs/cmdproto/src/proto/execute.rs b/libs/cmdproto/src/proto/execute.rs
index f9ca73a..280b878 100644
--- a/libs/cmdproto/src/proto/execute.rs
+++ b/libs/cmdproto/src/proto/execute.rs
@@ -18,7 +18,7 @@ use super::{
use crate::error::*;
use http::StatusCode;
-use nix;
+use nix::{self, sys::socket::UnixCredentials};
use std::{fmt::Display, rc::Rc};
pub(crate) trait Executer {
@@ -27,6 +27,7 @@ pub(crate) trait Executer {
self,
manager: Rc<impl ExecuterAction>,
call_back: Option<fn(&str) -> String>,
+ cred: Option<UnixCredentials>,
) -> CommandResponse;
}
@@ -73,7 +74,11 @@ pub trait ExecuterAction {
}
/// Depending on the type of request
-pub(crate) fn dispatch<T>(cmd: CommandRequest, manager: Rc<T>) -> CommandResponse
+pub(crate) fn dispatch<T>(
+ cmd: CommandRequest,
+ manager: Rc<T>,
+ cred: Option<UnixCredentials>,
+) -> CommandResponse
where
T: ExecuterAction,
{
@@ -89,10 +94,10 @@ where
};
match cmd.request_data {
- Some(RequestData::Ucomm(param)) => param.execute(manager, Some(call_back)),
- Some(RequestData::Mcomm(param)) => param.execute(manager, None),
- Some(RequestData::Syscomm(param)) => param.execute(manager, Some(call_back)),
- Some(RequestData::Ufile(param)) => param.execute(manager, Some(call_back)),
+ Some(RequestData::Ucomm(param)) => param.execute(manager, Some(call_back), cred),
+ Some(RequestData::Mcomm(param)) => param.execute(manager, None, cred),
+ Some(RequestData::Syscomm(param)) => param.execute(manager, Some(call_back), cred),
+ Some(RequestData::Ufile(param)) => param.execute(manager, Some(call_back), cred),
_ => CommandResponse::default(),
}
}
@@ -103,12 +108,45 @@ fn new_line_break(s: &mut String) {
}
}
+fn response_if_credential_dissatisfied(
+ cred: Option<UnixCredentials>,
+ command_is_allowed_for_nonroot: bool,
+) -> Option<CommandResponse> {
+ let sender = match cred {
+ None => {
+ return Some(CommandResponse {
+ status: StatusCode::OK.as_u16() as _,
+ error_code: 1,
+ message: "Failed to execute your command: cannot determine user credentials."
+ .to_string(),
+ })
+ }
+ Some(v) => v.uid(),
+ };
+ if sender != 0 && !command_is_allowed_for_nonroot {
+ return Some(CommandResponse {
+ status: StatusCode::OK.as_u16() as _,
+ error_code: 1,
+ message: "Failed to execute your command: Operation not permitted.".to_string(),
+ });
+ }
+ None
+}
+
impl Executer for UnitComm {
fn execute(
self,
manager: Rc<impl ExecuterAction>,
call_back: Option<fn(&str) -> String>,
+ cred: Option<UnixCredentials>,
) -> CommandResponse {
+ if let Some(v) = response_if_credential_dissatisfied(
+ cred,
+ [unit_comm::Action::Status].contains(&self.action()),
+ ) {
+ return v;
+ }
+
let mut reply = String::new();
let mut units: Vec<String> = Vec::new();
let mut error_code: u32 = 0;
@@ -197,7 +235,15 @@ impl Executer for MngrComm {
self,
manager: Rc<impl ExecuterAction>,
_call_back: Option<fn(&str) -> String>,
+ cred: Option<UnixCredentials>,
) -> CommandResponse {
+ if let Some(v) = response_if_credential_dissatisfied(
+ cred,
+ [mngr_comm::Action::Listunits].contains(&self.action()),
+ ) {
+ return v;
+ }
+
match self.action() {
mngr_comm::Action::Reexec => {
manager.daemon_reexec();
@@ -241,7 +287,12 @@ impl Executer for SysComm {
self,
manager: Rc<impl ExecuterAction>,
_call_back: Option<fn(&str) -> String>,
+ cred: Option<UnixCredentials>,
) -> CommandResponse {
+ if let Some(v) = response_if_credential_dissatisfied(cred, false) {
+ return v;
+ }
+
let ret = if self.force {
let unit_name = self.action().to_string() + ".target";
match manager.start(&unit_name) {
@@ -279,7 +330,12 @@ impl Executer for UnitFile {
self,
manager: Rc<impl ExecuterAction>,
call_back: Option<fn(&str) -> String>,
+ cred: Option<UnixCredentials>,
) -> CommandResponse {
+ if let Some(v) = response_if_credential_dissatisfied(cred, false) {
+ return v;
+ }
+
let mut reply = String::new();
let mut units: Vec<String> = Vec::new();
let mut error_code: u32 = 0;
diff --git a/libs/cmdproto/src/proto/frame.rs b/libs/cmdproto/src/proto/frame.rs
index 9b942a8..6b6912b 100644
--- a/libs/cmdproto/src/proto/frame.rs
+++ b/libs/cmdproto/src/proto/frame.rs
@@ -12,6 +12,7 @@
//! Encapsulate the command request into a frame
use crate::error::*;
+use nix::sys::socket::{self, UnixCredentials};
use prost::bytes::{BufMut, BytesMut};
use prost::Message;
use std::{
@@ -48,8 +49,49 @@ where
impl FrameCoder for CommandRequest {}
impl FrameCoder for CommandResponse {}
+/// Read frame from accept fd.
+pub fn read_frame_from_fd(fd: i32, buf: &mut BytesMut) -> Result<()> {
+ // 1. Got the message length
+ let mut msg_len = [0_u8; USIZE_TO_U8_LENGTH];
+ match socket::recv(fd, &mut msg_len, socket::MsgFlags::empty()) {
+ Ok(len) => {
+ if len != USIZE_TO_U8_LENGTH {
+ return Err(Error::ReadStream {
+ msg: "Invalid message length".to_string(),
+ });
+ }
+ }
+ Err(e) => {
+ return Err(Error::ReadStream { msg: e.to_string() });
+ }
+ }
+ let msg_len = get_msg_len(msg_len);
+
+ // 2. Got the message
+ let mut tmp = vec![0; MAX_FRAME];
+ let mut cur_len: usize = 0;
+ loop {
+ match socket::recv(fd, &mut tmp, socket::MsgFlags::empty()) {
+ Ok(len) => {
+ cur_len += len;
+ buf.put_slice(&tmp[..len]);
+ /* If there is no more message (len < MAX_FRAME), or
+ * we have got enough message (cur_len >= msg_len),
+ * then we finish reading. */
+ if len < MAX_FRAME || cur_len >= msg_len {
+ break;
+ }
+ }
+ Err(e) => {
+ return Err(Error::ReadStream { msg: e.to_string() });
+ }
+ }
+ }
+ Ok(())
+}
+
/// read frame from stream
-pub fn read_frame<S>(stream: &mut S, buf: &mut BytesMut) -> Result<()>
+pub fn read_frame_from_stream<S>(stream: &mut S, buf: &mut BytesMut) -> Result<()>
where
S: Read + Unpin + Send,
{
@@ -66,6 +108,9 @@ where
Ok(len) => {
cur_len += len;
buf.put_slice(&tmp[..len]);
+ /* If there is no more message (len < MAX_FRAME), or
+ * we have got enough message (cur_len >= msg_len),
+ * then we finish reading. */
if len < MAX_FRAME || cur_len >= msg_len {
break;
}
@@ -89,9 +134,10 @@ fn get_msg_len(message: [u8; USIZE_TO_U8_LENGTH]) -> usize {
}
/// Handle read and write of server-side socket
-pub struct ProstServerStream<S, T> {
- inner: S,
+pub struct ProstServerStream<T> {
+ accept_fd: i32,
manager: Rc<T>,
+ cred: Option<UnixCredentials>,
}
/// Handle read and write of client-side socket
@@ -99,23 +145,23 @@ pub struct ProstClientStream<S> {
inner: S,
}
-impl<S, T> ProstServerStream<S, T>
+impl<T> ProstServerStream<T>
where
- S: Read + Write + Unpin + Send,
T: ExecuterAction,
{
/// new ProstServerStream
- pub fn new(stream: S, manager: Rc<T>) -> Self {
+ pub fn new(accept_fd: i32, manager: Rc<T>, cred: Option<UnixCredentials>) -> Self {
Self {
- inner: stream,
+ accept_fd,
manager,
+ cred,
}
}
/// process frame in server-side
pub fn process(mut self) -> Result<()> {
if let Ok(cmd) = self.recv() {
- let res = execute::dispatch(cmd, Rc::clone(&self.manager));
+ let res = execute::dispatch(cmd, Rc::clone(&self.manager), self.cred);
self.send(res)?;
};
Ok(())
@@ -126,16 +172,32 @@ where
msg.encode_frame(&mut buf)?;
let encoded = buf.freeze();
let msg_len = msg_len_vec(encoded.len());
- self.inner.write_all(&msg_len).context(IoSnafu)?;
- self.inner.write_all(&encoded).context(IoSnafu)?;
- self.inner.flush().context(IoSnafu)?;
+ match socket::send(self.accept_fd, &msg_len, socket::MsgFlags::empty()) {
+ Ok(len) => {
+ if len != msg_len.len() {
+ return Err(Error::SendStream {
+ msg: "Invalid message length".to_string(),
+ });
+ }
+ }
+ Err(e) => return Err(Error::SendStream { msg: e.to_string() }),
+ }
+ match socket::send(self.accept_fd, &encoded, socket::MsgFlags::empty()) {
+ Ok(len) => {
+ if len != encoded.len() {
+ return Err(Error::SendStream {
+ msg: "Invalid message length".to_string(),
+ });
+ }
+ }
+ Err(e) => return Err(Error::SendStream { msg: e.to_string() }),
+ }
Ok(())
}
fn recv(&mut self) -> Result<CommandRequest> {
let mut buf = BytesMut::new();
- let stream = &mut self.inner;
- read_frame(stream, &mut buf)?;
+ read_frame_from_fd(self.accept_fd, &mut buf)?;
CommandRequest::decode_frame(&mut buf)
}
}
@@ -169,8 +231,7 @@ where
fn recv(&mut self) -> Result<CommandResponse> {
let mut buf = BytesMut::new();
- let stream = &mut self.inner;
- read_frame(stream, &mut buf)?;
+ read_frame_from_stream(&mut self.inner, &mut buf)?;
CommandResponse::decode_frame(&mut buf)
}
}
--
2.30.2

View File

@ -0,0 +1,91 @@
From 5798474ac1e7e5e41eb525884ecfff7a29f3800a Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 11:13:56 +0800
Subject: [PATCH 5/9] fix: add has_source to events, and use this in
socket.watch_fds() to avoid adding same source to events loop. This PR also
contains some nonfunctional cleanups
---
coms/socket/src/mng.rs | 5 +++--
libs/event/src/events.rs | 16 +++++++++++++++-
libs/event/src/poll/epoll.rs | 7 +++++--
3 files changed, 23 insertions(+), 5 deletions(-)
diff --git a/coms/socket/src/mng.rs b/coms/socket/src/mng.rs
index fe77517..aace9c7 100644
--- a/coms/socket/src/mng.rs
+++ b/coms/socket/src/mng.rs
@@ -576,8 +576,9 @@ impl SocketMng {
continue;
}
let source = Rc::clone(mport);
- events.add_source(source).unwrap();
- let source = Rc::clone(mport);
+ if !events.has_source(source.clone()) {
+ events.add_source(source.clone()).unwrap();
+ }
events.set_enabled(source, EventState::On).unwrap();
}
}
diff --git a/libs/event/src/events.rs b/libs/event/src/events.rs
index fba671f..ed7fa1c 100644
--- a/libs/event/src/events.rs
+++ b/libs/event/src/events.rs
@@ -53,6 +53,11 @@ impl Events {
self.data.borrow_mut().add_source(source)
}
+ /// for all: check if the source exists
+ pub fn has_source(&self, source: Rc<dyn Source>) -> bool {
+ self.data.borrow().has_source(source)
+ }
+
/// for all: delete source
pub fn del_source(&self, source: Rc<dyn Source>) -> Result<i32> {
self.data.borrow_mut().del_source(source)
@@ -233,6 +238,11 @@ impl EventsData {
Ok(0)
}
+ pub(self) fn has_source(&self, source: Rc<dyn Source>) -> bool {
+ let token = source.token();
+ self.sources.contains_key(&token)
+ }
+
pub(self) fn del_source(&mut self, source: Rc<dyn Source>) -> Result<i32> {
self.source_offline(&source)?;
@@ -287,7 +297,11 @@ impl EventsData {
pub(self) fn set_enabled(&mut self, source: Rc<dyn Source>, state: EventState) -> Result<i32> {
let token = source.token();
-
+ if let Some(current_state) = self.state.get(&token) {
+ if current_state == &state {
+ return Ok(0);
+ }
+ }
match state {
EventState::On | EventState::OneShot => {
self.source_online(&source)?;
diff --git a/libs/event/src/poll/epoll.rs b/libs/event/src/poll/epoll.rs
index 61926df..ad236ed 100644
--- a/libs/event/src/poll/epoll.rs
+++ b/libs/event/src/poll/epoll.rs
@@ -77,8 +77,11 @@ impl Epoll {
}
pub(crate) fn register(&mut self, fd: RawFd, event: &mut epoll_event) -> Result<()> {
- self.n_sources.fetch_add(1, Ordering::Relaxed);
- syscall!(epoll_ctl(self.epoll_fd, EPOLL_CTL_ADD, fd, event)).map(|_| ())
+ let res = syscall!(epoll_ctl(self.epoll_fd, EPOLL_CTL_ADD, fd, event)).map(|_| ());
+ if res.is_ok() {
+ self.n_sources.fetch_add(1, Ordering::Relaxed);
+ }
+ res
}
pub(crate) fn reregister(&mut self, fd: RawFd, event: &mut epoll_event) -> Result<()> {
--
2.30.2

View File

@ -0,0 +1,29 @@
From ef57fb8a85d78dfc6e7cbbf2ac6756da93ffd45f Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 11:15:32 +0800
Subject: [PATCH 6/9] fix: change if port.fd() is valid, we should avoid
dealing with invalid port.
---
coms/socket/src/mng.rs | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/coms/socket/src/mng.rs b/coms/socket/src/mng.rs
index aace9c7..82fdcbe 100644
--- a/coms/socket/src/mng.rs
+++ b/coms/socket/src/mng.rs
@@ -593,8 +593,9 @@ impl SocketMng {
fn flush_ports(&self) {
for port in self.ports().iter() {
- port.flush_accept();
-
+ if port.fd() < 0 {
+ continue;
+ }
port.flush_fd();
}
}
--
2.30.2

View File

@ -0,0 +1,165 @@
From 6ac9cdc2b5c38153a5faaf41ce8421b09aaf053e Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 11:20:33 +0800
Subject: [PATCH 8/9] fix: change the socket logic to keep the same as systemd
1. check the events number got from wait_for_events(), quick return when it
is 0. 2. make flush_accept() return the error. 3. close the accepted fd
instead port fd itself.
---
coms/socket/src/mng.rs | 1 +
coms/socket/src/port.rs | 54 ++++++++++++++++++++++++++---------------
core/lib/error.rs | 28 +++++++++++++++++++++
3 files changed, 63 insertions(+), 20 deletions(-)
diff --git a/coms/socket/src/mng.rs b/coms/socket/src/mng.rs
index 0435827..da396de 100644
--- a/coms/socket/src/mng.rs
+++ b/coms/socket/src/mng.rs
@@ -597,6 +597,7 @@ impl SocketMng {
if port.fd() < 0 {
continue;
}
+ let _ = port.flush_accept();
port.flush_fd();
}
}
diff --git a/coms/socket/src/port.rs b/coms/socket/src/port.rs
index 870cb70..0500669 100644
--- a/coms/socket/src/port.rs
+++ b/coms/socket/src/port.rs
@@ -151,29 +151,43 @@ impl SocketPort {
}
}
- pub(super) fn flush_accept(&self) {
+ pub(super) fn flush_accept(&self) -> Result<()> {
if let Ok(true) = socket::getsockopt(self.fd(), sockopt::AcceptConn) {
for _i in 1..1024 {
- while let Err(e) = io_util::wait_for_events(self.fd(), PollFlags::POLLIN, 0) {
- if let basic::Error::Nix {
- source: Errno::EINTR,
- } = e
- {
- continue;
+ let events = match io_util::wait_for_events(self.fd(), PollFlags::POLLIN, 0) {
+ Err(e) => {
+ if let basic::Error::Nix {
+ source: Errno::EINTR,
+ } = e
+ {
+ continue;
+ }
+ return Err(e.into());
}
- return;
+ Ok(v) => v,
+ };
+ if events == 0 {
+ return Ok(());
}
- match socket::accept4(self.fd(), SockFlag::SOCK_NONBLOCK | SockFlag::SOCK_CLOEXEC)
- .map(|_| fd_util::close(self.fd()))
- {
- Ok(_) => {}
- Err(_e) => {
- // todo!(): if e == Errno::EAGAIN { return; }
- return;
+ let cfd = match socket::accept4(
+ self.fd(),
+ SockFlag::SOCK_NONBLOCK | SockFlag::SOCK_CLOEXEC,
+ ) {
+ Err(e) => {
+ if e == Errno::EAGAIN {
+ return Ok(());
+ }
+ if error_is_accept_again(&e) {
+ continue;
+ }
+ return Err(e.into());
}
- }
+ Ok(v) => v,
+ };
+ fd_util::close(cfd);
}
}
+ Ok(())
}
pub(super) fn flush_fd(&self) {
@@ -356,7 +370,7 @@ mod tests {
assert_ne!(port.fd(), SOCKET_INVALID_FD);
assert_eq!(port.family(), AddressFamily::Inet);
- port.flush_accept();
+ assert!(port.flush_accept().is_ok());
port.flush_fd();
port.close(false);
}
@@ -387,7 +401,7 @@ mod tests {
assert_ne!(port.fd(), SOCKET_INVALID_FD);
assert_eq!(port.family(), AddressFamily::Unix);
- port.flush_accept();
+ assert!(port.flush_accept().is_ok());
port.flush_fd();
port.close(false);
}
@@ -424,7 +438,7 @@ mod tests {
assert_ne!(port.fd(), SOCKET_INVALID_FD);
assert_eq!(port.family(), AddressFamily::Netlink);
- port.flush_accept();
+ assert!(port.flush_accept().is_ok());
port.flush_fd();
port.close(false);
}
@@ -519,7 +533,7 @@ mod tests {
}
// Rosource reclaim
- port.flush_accept();
+ assert!(port.flush_accept().is_ok());
port.flush_fd();
port.close(false);
}
diff --git a/core/lib/error.rs b/core/lib/error.rs
index 100eb3c..331f367 100644
--- a/core/lib/error.rs
+++ b/core/lib/error.rs
@@ -289,3 +289,31 @@ impl From<event::Error> for Error {
/// new Result
pub type Result<T, E = Error> = std::result::Result<T, E>;
+
+pub fn error_is_disconnect(e: &Errno) -> bool {
+ [
+ Errno::ECONNABORTED,
+ Errno::ECONNREFUSED,
+ Errno::ECONNRESET,
+ Errno::EHOSTDOWN,
+ Errno::EHOSTUNREACH,
+ Errno::ENETDOWN,
+ Errno::ENETRESET,
+ Errno::ENONET,
+ Errno::ENOPROTOOPT,
+ Errno::ENOTCONN,
+ Errno::EPIPE,
+ Errno::EPROTO,
+ Errno::ESHUTDOWN,
+ Errno::ETIMEDOUT,
+ ]
+ .contains(e)
+}
+
+pub fn error_is_transient(e: &Errno) -> bool {
+ [Errno::EAGAIN, Errno::EINTR].contains(e)
+}
+
+pub fn error_is_accept_again(e: &Errno) -> bool {
+ error_is_disconnect(e) || error_is_transient(e) || e == &Errno::EOPNOTSUPP
+}
--
2.30.2

View File

@ -0,0 +1,193 @@
From 8123dcec5160b0d29e541cec1c9a027a1dd42c48 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 14 Jun 2023 15:52:40 +0800
Subject: [PATCH] fix: check if the given unit name is valid before we prepare
the unit
---
core/bin/unit/base/load.rs | 8 -----
core/bin/unit/manager.rs | 8 ++++-
core/bin/unit/uload.rs | 6 +++-
core/lib/unit/base.rs | 70 ++++++++++++++++++++++++++++++++++++++
core/lib/unit/mod.rs | 3 +-
5 files changed, 84 insertions(+), 11 deletions(-)
diff --git a/core/bin/unit/base/load.rs b/core/bin/unit/base/load.rs
index 2281d06..700237d 100644
--- a/core/bin/unit/base/load.rs
+++ b/core/bin/unit/base/load.rs
@@ -10,14 +10,6 @@
// NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
// See the Mulan PSL v2 for more details.
-#[allow(dead_code)]
-enum UnitNameFlags {
- Plain = 1,
- Instance = 2,
- Template = 4,
- Any = 1 | 2 | 4,
-}
-
#[allow(dead_code)]
enum UnitFileState {
Enabled,
diff --git a/core/bin/unit/manager.rs b/core/bin/unit/manager.rs
index 4b3f4fb..cb5d957 100644
--- a/core/bin/unit/manager.rs
+++ b/core/bin/unit/manager.rs
@@ -50,7 +50,10 @@ use sysmaster::error::*;
use sysmaster::exec::ExecParameters;
use sysmaster::exec::{ExecCommand, ExecContext};
use sysmaster::rel::{ReStation, ReStationKind, ReliLastFrame, Reliability};
-use sysmaster::unit::{UmIf, UnitActiveState, UnitDependencyMask, UnitStatus, UnitType};
+use sysmaster::unit::{
+ unit_name_is_valid, UmIf, UnitActiveState, UnitDependencyMask, UnitNameFlags, UnitStatus,
+ UnitType,
+};
use unit_submanager::UnitSubManagers;
//#[derive(Debug)]
@@ -525,6 +528,9 @@ impl UnitManager {
///
pub fn units_get(&self, name: &str) -> Option<Rc<Unit>> {
+ if !unit_name_is_valid(name, UnitNameFlags::PLAIN | UnitNameFlags::INSTANCE) {
+ return None;
+ }
self.db.units_get(name).map(|uxr| uxr.unit())
}
diff --git a/core/bin/unit/uload.rs b/core/bin/unit/uload.rs
index d972fb4..d6fea43 100644
--- a/core/bin/unit/uload.rs
+++ b/core/bin/unit/uload.rs
@@ -22,7 +22,7 @@ use crate::utils::table::{TableOp, TableSubscribe};
use basic::path_lookup::LookupPaths;
use std::cell::RefCell;
use std::rc::{Rc, Weak};
-use sysmaster::unit::UnitType;
+use sysmaster::unit::{unit_name_is_valid, UnitNameFlags, UnitType};
//#[derive(Debug)]
pub(super) struct UnitLoad {
@@ -100,6 +100,10 @@ impl UnitLoadData {
}
pub(self) fn prepare_unit(&self, name: &str) -> Option<Rc<UnitX>> {
+ if !unit_name_is_valid(name, UnitNameFlags::PLAIN | UnitNameFlags::INSTANCE) {
+ return None;
+ }
+
if let Some(u) = self.db.units_get(name) {
if u.load_state() != UnitLoadState::NotFound {
return Some(Rc::clone(&u));
diff --git a/core/lib/unit/base.rs b/core/lib/unit/base.rs
index f066ed7..555bb69 100644
--- a/core/lib/unit/base.rs
+++ b/core/lib/unit/base.rs
@@ -14,10 +14,14 @@ use super::super::rel::ReStation;
use super::kill::{KillContext, KillOperation};
use super::state::{UnitActiveState, UnitNotifyFlags};
use super::umif::UnitMngUtil;
+use super::UnitType;
use crate::error::*;
+use bitflags::bitflags;
use nix::sys::wait::WaitStatus;
use nix::{sys::socket::UnixCredentials, unistd::Pid};
use std::any::Any;
+use std::num::ParseIntError;
+use std::str::FromStr;
use std::{collections::HashMap, path::PathBuf, rc::Rc};
///The trait Defining Shared Behavior from Base Unit to SUB unit
@@ -206,3 +210,69 @@ macro_rules! declure_unitobj_plugin_with_param {
}
};
}
+
+bitflags! {
+ /// used to when check the given unit name is valid
+ pub struct UnitNameFlags: u8 {
+ /// Allow foo.service
+ const PLAIN = 1 << 0;
+ /// Allow foo@.service
+ const TEMPLATE = 1 << 1;
+ /// Allow foo@123.service
+ const INSTANCE = 1 << 2;
+ /// Any of the above
+ const ANY = Self::PLAIN.bits() | Self::TEMPLATE.bits() | Self::INSTANCE.bits();
+ }
+}
+
+/// The maximum length of a valid unit name
+const UNIT_NAME_MAX: usize = 255;
+
+/// check if the given unit name is valid
+pub fn unit_name_is_valid(name: &str, flag: UnitNameFlags) -> bool {
+ if name.is_empty() {
+ return false;
+ }
+ if name.len() > UNIT_NAME_MAX {
+ return false;
+ }
+ /* Take foo@123.service for example, "foo@123" is its first_name,
+ * "foo" is prefix, "service" is its last_name, suffix, or type. */
+ let (first_name, last_name) = match name.split_once('.') {
+ None => return false,
+ Some(v) => (v.0, v.1),
+ };
+
+ let unit_type = match unit_type_from_string(last_name) {
+ Err(_) => return false,
+ Ok(v) => v,
+ };
+
+ if unit_type == UnitType::UnitTypeInvalid {
+ return false;
+ }
+
+ match first_name.split_once('@') {
+ None => flag.contains(UnitNameFlags::PLAIN),
+ Some(v) => {
+ /* "@" is the first character */
+ if v.0.is_empty() {
+ return false;
+ }
+ /* "@" is the last character */
+ if v.1.is_empty() {
+ return flag.contains(UnitNameFlags::TEMPLATE);
+ }
+ /* there is more than one "@" */
+ if v.1.contains('@') {
+ return false;
+ }
+ flag.contains(UnitNameFlags::INSTANCE)
+ }
+ }
+}
+
+/// convert the type string of one unit to UnitType
+pub fn unit_type_from_string(type_string: &str) -> Result<UnitType, ParseIntError> {
+ UnitType::from_str(type_string)
+}
diff --git a/core/lib/unit/mod.rs b/core/lib/unit/mod.rs
index 7211aec..1eb565c 100644
--- a/core/lib/unit/mod.rs
+++ b/core/lib/unit/mod.rs
@@ -11,11 +11,12 @@
// See the Mulan PSL v2 for more details.
//!
-pub use base::{SubUnit, UnitBase};
+pub use base::{unit_name_is_valid, SubUnit, UnitBase, UnitNameFlags};
pub use deps::{UnitDependencyMask, UnitRelationAtom, UnitRelations, UnitType};
pub use kill::{KillContext, KillMode, KillOperation};
pub use state::{UnitActiveState, UnitNotifyFlags, UnitStatus};
pub use umif::{UmIf, UnitManagerObj, UnitMngUtil};
+
mod base;
mod deps;
mod kill;
--
2.30.2

View File

@ -0,0 +1,28 @@
From e0a828649165701afa9efa039650ddcd4afa4c6e Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 24 May 2023 16:45:10 +0800
Subject: [PATCH] fix: check if the returned state is None
---
libs/event/src/events.rs | 5 ++++-
1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/libs/event/src/events.rs b/libs/event/src/events.rs
index 7b0346d..8b29835 100644
--- a/libs/event/src/events.rs
+++ b/libs/event/src/events.rs
@@ -108,7 +108,10 @@ impl Events {
}
let top = first.unwrap();
- let state = self.data.borrow().source_state(&top).unwrap();
+ let state = match self.data.borrow().source_state(&top) {
+ None => return Ok(0),
+ Some(v) => v,
+ };
match state {
EventState::Off => {
println!("set_enabled Off: {top:?}");
--
2.30.2

View File

@ -0,0 +1,557 @@
From a8ca02c09ebffa5eabbb935be96b3864d8091549 Mon Sep 17 00:00:00 2001
From: chenjiayi <chenjiayi22@huawei.com>
Date: Thu, 18 May 2023 16:45:47 +0800
Subject: [PATCH] fix: compatible with rusc 1.60 lint check
---
core/bin/main.rs | 2 +-
core/bin/unit/execute/spawn.rs | 5 +-
core/bin/unit/uload.rs | 16 +-
core/lib/exec/cmd.rs | 1 -
exts/devmaster/src/lib/builtin/path_id.rs | 6 +-
exts/devmaster/src/lib/rules/rule_execute.rs | 156 ++++++-------------
exts/init/src/runtime/param.rs | 8 +-
exts/init/src/runtime/timer.rs | 1 +
exts/random_seed/src/random_seed.rs | 4 +-
libs/basic/src/user_group_util.rs | 2 +-
libs/event/src/timer.rs | 1 +
libs/macros/src/unit_conf_parse.rs | 13 +-
tests/docker_config_test.rs | 1 +
tests/docker_example.rs | 1 +
tests/docker_perf.rs | 1 +
tests/docker_reliable.rs | 1 +
16 files changed, 81 insertions(+), 138 deletions(-)
diff --git a/core/bin/main.rs b/core/bin/main.rs
index 26638d6..eb06ed6 100644
--- a/core/bin/main.rs
+++ b/core/bin/main.rs
@@ -169,7 +169,7 @@ fn set_child_reaper() {
}
}
-fn do_reexecute(args: &Vec<String>, reload: bool) {
+fn do_reexecute(args: &[String], reload: bool) {
let args_size = args.len().max(MANAGER_ARGS_SIZE_MAX);
let path;
diff --git a/core/bin/unit/execute/spawn.rs b/core/bin/unit/execute/spawn.rs
index cbde2b5..8e55970 100644
--- a/core/bin/unit/execute/spawn.rs
+++ b/core/bin/unit/execute/spawn.rs
@@ -259,8 +259,7 @@ fn build_run_args(
let cmd = std::ffi::CString::new(cmdline.path().clone()).unwrap();
let exec_name = std::ffi::CString::new(cmdline.path().clone()).unwrap();
- let mut args = Vec::new();
- args.push(exec_name);
+ let mut args = vec![exec_name];
let var_regex = Regex::new(r"(\$[A-Z_]+)|(\$\{[A-Z_]+\})").unwrap();
for arg in cmdline.argv() {
@@ -356,7 +355,7 @@ fn close_all_fds(fds: &[i32]) -> bool {
true
}
-fn shift_fds(fds: &mut Vec<i32>) -> bool {
+fn shift_fds(fds: &mut [i32]) -> bool {
let mut start = 0;
loop {
let mut restart = -1;
diff --git a/core/bin/unit/uload.rs b/core/bin/unit/uload.rs
index a7d1bea..d972fb4 100644
--- a/core/bin/unit/uload.rs
+++ b/core/bin/unit/uload.rs
@@ -210,14 +210,14 @@ impl UnitLoadData {
// dependency
for (relation, list) in config.deps.iter() {
for o_name in list {
- let tmp_unit: Rc<UnitX>;
- if let Some(o_unit) = self.push_dep_unit_into_load_queue(o_name) {
- //can not call unit_load directly, will be nested.
- tmp_unit = Rc::clone(&o_unit);
- } else {
- log::error!("create unit obj error in unit manager");
- return;
- }
+ let tmp_unit: Rc<UnitX> =
+ if let Some(o_unit) = self.push_dep_unit_into_load_queue(o_name) {
+ //can not call unit_load directly, will be nested.
+ Rc::clone(&o_unit)
+ } else {
+ log::error!("create unit obj error in unit manager");
+ return;
+ };
if let Err(_e) = self
.db
diff --git a/core/lib/exec/cmd.rs b/core/lib/exec/cmd.rs
index 406ee00..040b7f9 100644
--- a/core/lib/exec/cmd.rs
+++ b/core/lib/exec/cmd.rs
@@ -116,7 +116,6 @@ impl DeserializeWith for ExecCommand {
continue;
}
- #[allow(clippy::trim_split_whitespace)]
let mut command: Vec<String> = Vec::new();
let re = Regex::new(r"'([^']*)'|\S+").unwrap();
for cap in re.captures_iter(cmd) {
diff --git a/exts/devmaster/src/lib/builtin/path_id.rs b/exts/devmaster/src/lib/builtin/path_id.rs
index 6d0de56..2ebaecd 100644
--- a/exts/devmaster/src/lib/builtin/path_id.rs
+++ b/exts/devmaster/src/lib/builtin/path_id.rs
@@ -146,6 +146,7 @@ impl Builtin for PathId {
}
impl PathId {
+ #[allow(clippy::ptr_arg)]
fn compose_path(
&self,
dev: Arc<Mutex<Device>>,
@@ -982,6 +983,7 @@ impl PathId {
) -> Option<Arc<Mutex<Device>>> {
let mut dev = device.clone();
let mut parent = device;
+ #[allow(clippy::while_let_loop)]
loop {
let subsystem = match parent.lock().unwrap().get_subsystem() {
Ok(str) => str,
diff --git a/exts/devmaster/src/lib/rules/rule_execute.rs b/exts/devmaster/src/lib/rules/rule_execute.rs
index 36acc8f..384d490 100644
--- a/exts/devmaster/src/lib/rules/rule_execute.rs
+++ b/exts/devmaster/src/lib/rules/rule_execute.rs
@@ -111,7 +111,7 @@ impl ExecuteUnit {
}
/// apply runtime substitution on all formatters in the string
- pub fn apply_format(&self, src: &String, replace_whitespace: bool) -> Result<String> {
+ pub fn apply_format(&self, src: &str, replace_whitespace: bool) -> Result<String> {
let mut idx: usize = 0;
let mut ret = String::new();
while idx < src.len() {
@@ -370,7 +370,7 @@ impl ExecuteUnit {
}
fn get_subst_type(
- s: &String,
+ s: &str,
idx: &mut usize,
strict: bool,
) -> Result<Option<(FormatSubstitutionType, Option<String>)>> {
@@ -1641,146 +1641,102 @@ mod tests {
let unit = ExecuteUnit::new(device);
// test long substitution formatter
// $kernel
- assert_eq!(
- unit.apply_format(&"$kernel".to_string(), false).unwrap(),
- "lo"
- );
+ assert_eq!(unit.apply_format("$kernel", false).unwrap(), "lo");
// $number
- assert_eq!(
- unit.apply_format(&"$number".to_string(), false).unwrap(),
- ""
- );
+ assert_eq!(unit.apply_format("$number", false).unwrap(), "");
// $devpath
assert_eq!(
- unit.apply_format(&"$devpath".to_string(), false).unwrap(),
+ unit.apply_format("$devpath", false).unwrap(),
"/devices/virtual/net/lo"
);
// $id
- assert_eq!(unit.apply_format(&"$id".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("$id", false).unwrap(), "");
// $driver
- assert_eq!(
- unit.apply_format(&"$driver".to_string(), false).unwrap(),
- ""
- );
+ assert_eq!(unit.apply_format("$driver", false).unwrap(), "");
// $attr{sysattr}
assert_eq!(
- unit.apply_format(&"$attr{address}".to_string(), false)
- .unwrap(),
+ unit.apply_format("$attr{address}", false).unwrap(),
"00:00:00:00:00:00"
);
// $env{key}
assert_eq!(
- unit.apply_format(&"$env{DEVPATH}".to_string(), false)
- .unwrap(),
+ unit.apply_format("$env{DEVPATH}", false).unwrap(),
"/devices/virtual/net/lo"
);
// $major
- assert_eq!(
- unit.apply_format(&"$major".to_string(), false).unwrap(),
- "0"
- );
+ assert_eq!(unit.apply_format("$major", false).unwrap(), "0");
// $minor
- assert_eq!(
- unit.apply_format(&"$minor".to_string(), false).unwrap(),
- "0"
- );
+ assert_eq!(unit.apply_format("$minor", false).unwrap(), "0");
// $result
- assert_eq!(
- unit.apply_format(&"$result".to_string(), false).unwrap(),
- ""
- );
+ assert_eq!(unit.apply_format("$result", false).unwrap(), "");
// $result{index}
- assert_eq!(
- unit.apply_format(&"$result{1}".to_string(), false).unwrap(),
- ""
- );
+ assert_eq!(unit.apply_format("$result{1}", false).unwrap(), "");
// $result{index+}
- assert_eq!(
- unit.apply_format(&"$result{1+}".to_string(), false)
- .unwrap(),
- ""
- );
+ assert_eq!(unit.apply_format("$result{1+}", false).unwrap(), "");
// $parent
- assert_eq!(
- unit.apply_format(&"$parent".to_string(), false).unwrap(),
- ""
- );
+ assert_eq!(unit.apply_format("$parent", false).unwrap(), "");
// $name
- assert_eq!(
- unit.apply_format(&"$name".to_string(), false).unwrap(),
- "lo"
- );
+ assert_eq!(unit.apply_format("$name", false).unwrap(), "lo");
// $links
- assert_eq!(unit.apply_format(&"$links".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("$links", false).unwrap(), "");
// $root
- assert_eq!(
- unit.apply_format(&"$root".to_string(), false).unwrap(),
- "/dev"
- );
+ assert_eq!(unit.apply_format("$root", false).unwrap(), "/dev");
// $sys
- assert_eq!(
- unit.apply_format(&"$sys".to_string(), false).unwrap(),
- "/sys"
- );
+ assert_eq!(unit.apply_format("$sys", false).unwrap(), "/sys");
// $devnode
- assert_eq!(
- unit.apply_format(&"$devnode".to_string(), false).unwrap(),
- ""
- );
+ assert_eq!(unit.apply_format("$devnode", false).unwrap(), "");
// test short substitution formatter
// %k
- assert_eq!(unit.apply_format(&"%k".to_string(), false).unwrap(), "lo");
+ assert_eq!(unit.apply_format("%k", false).unwrap(), "lo");
// %n
- assert_eq!(unit.apply_format(&"%n".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%n", false).unwrap(), "");
// %p
assert_eq!(
- unit.apply_format(&"%p".to_string(), false).unwrap(),
+ unit.apply_format("%p", false).unwrap(),
"/devices/virtual/net/lo"
);
// %b
- assert_eq!(unit.apply_format(&"%b".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%b", false).unwrap(), "");
// %d
- assert_eq!(unit.apply_format(&"%d".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%d", false).unwrap(), "");
// %s{sysattr}
assert_eq!(
- unit.apply_format(&"%s{address}".to_string(), false)
- .unwrap(),
+ unit.apply_format("%s{address}", false).unwrap(),
"00:00:00:00:00:00"
);
// %E{key}
assert_eq!(
- unit.apply_format(&"%E{DEVPATH}".to_string(), false)
- .unwrap(),
+ unit.apply_format("%E{DEVPATH}", false).unwrap(),
"/devices/virtual/net/lo"
);
// %M
- assert_eq!(unit.apply_format(&"%M".to_string(), false).unwrap(), "0");
+ assert_eq!(unit.apply_format("%M", false).unwrap(), "0");
// %m
- assert_eq!(unit.apply_format(&"%m".to_string(), false).unwrap(), "0");
+ assert_eq!(unit.apply_format("%m", false).unwrap(), "0");
// %c
- assert_eq!(unit.apply_format(&"%c".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%c", false).unwrap(), "");
// %c{index}
- assert_eq!(unit.apply_format(&"%c{1}".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%c{1}", false).unwrap(), "");
// %c{index+}
- assert_eq!(unit.apply_format(&"%c{1+}".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%c{1+}", false).unwrap(), "");
// %P
- assert_eq!(unit.apply_format(&"%P".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%P", false).unwrap(), "");
// %D
- assert_eq!(unit.apply_format(&"%D".to_string(), false).unwrap(), "lo");
+ assert_eq!(unit.apply_format("%D", false).unwrap(), "lo");
// %L
- assert_eq!(unit.apply_format(&"%L".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%L", false).unwrap(), "");
// %r
- assert_eq!(unit.apply_format(&"%r".to_string(), false).unwrap(), "/dev");
+ assert_eq!(unit.apply_format("%r", false).unwrap(), "/dev");
// %S
- assert_eq!(unit.apply_format(&"%S".to_string(), false).unwrap(), "/sys");
+ assert_eq!(unit.apply_format("%S", false).unwrap(), "/sys");
// %N
- assert_eq!(unit.apply_format(&"%N".to_string(), false).unwrap(), "");
+ assert_eq!(unit.apply_format("%N", false).unwrap(), "");
// $$
- assert_eq!(unit.apply_format(&"$$".to_string(), false).unwrap(), "$");
+ assert_eq!(unit.apply_format("$$", false).unwrap(), "$");
// %%
- assert_eq!(unit.apply_format(&"%%".to_string(), false).unwrap(), "%");
+ assert_eq!(unit.apply_format("%%", false).unwrap(), "%");
}
#[test]
@@ -1790,30 +1746,12 @@ mod tests {
Device::from_subsystem_sysname("block".to_string(), "sda1".to_string()).unwrap(),
));
let unit = ExecuteUnit::new(device);
- assert_eq!(
- unit.apply_format(&"$number".to_string(), false).unwrap(),
- "1"
- );
- assert_eq!(
- unit.apply_format(&"$major".to_string(), false).unwrap(),
- "8"
- );
- assert_eq!(
- unit.apply_format(&"$minor".to_string(), false).unwrap(),
- "1"
- );
- assert_eq!(
- unit.apply_format(&"$driver".to_string(), false).unwrap(),
- ""
- );
- assert_eq!(unit.apply_format(&"$id".to_string(), false).unwrap(), "");
- assert_eq!(
- unit.apply_format(&"$parent".to_string(), false).unwrap(),
- "sda"
- );
- assert_eq!(
- unit.apply_format(&"$devnode".to_string(), false).unwrap(),
- "/dev/sda1"
- );
+ assert_eq!(unit.apply_format("$number", false).unwrap(), "1");
+ assert_eq!(unit.apply_format("$major", false).unwrap(), "8");
+ assert_eq!(unit.apply_format("$minor", false).unwrap(), "1");
+ assert_eq!(unit.apply_format("$driver", false).unwrap(), "");
+ assert_eq!(unit.apply_format("$id", false).unwrap(), "");
+ assert_eq!(unit.apply_format("$parent", false).unwrap(), "sda");
+ assert_eq!(unit.apply_format("$devnode", false).unwrap(), "/dev/sda1");
}
}
diff --git a/exts/init/src/runtime/param.rs b/exts/init/src/runtime/param.rs
index 7aed5dc..c795a8c 100644
--- a/exts/init/src/runtime/param.rs
+++ b/exts/init/src/runtime/param.rs
@@ -13,7 +13,7 @@ const DEFAULT_TIMECNT: i64 = 5;
const DEFAULT_TIMEWAIT: i64 = 10;
const INIT_PARAM: i32 = 0;
// const SYSMASTER_PARAM: i32 = 1;
-type Callback = fn(arg: &str, key: &String, init_param: &mut InitParam);
+type Callback = fn(arg: &str, key: &str, init_param: &mut InitParam);
struct Dispatch<'a> {
key: &'a str,
@@ -34,7 +34,7 @@ const PARAM_TABLE: &[Dispatch] = &[
},
];
-fn parse_timecnt(arg: &str, key: &String, init_param: &mut InitParam) {
+fn parse_timecnt(arg: &str, key: &str, init_param: &mut InitParam) {
let str1 = &arg[key.len()..];
if let Ok(value) = str1.parse::<i64>() {
if value >= 2 {
@@ -43,7 +43,7 @@ fn parse_timecnt(arg: &str, key: &String, init_param: &mut InitParam) {
}
}
-fn parse_timewait(arg: &str, key: &String, init_param: &mut InitParam) {
+fn parse_timewait(arg: &str, key: &str, init_param: &mut InitParam) {
let str1 = &arg[key.len()..];
if let Ok(value) = str1.parse::<i64>() {
if value >= DEFAULT_TIMEWAIT {
@@ -78,7 +78,7 @@ impl Param {
for table in PARAM_TABLE {
if arg.starts_with(table.key) && table.callback.is_some() {
if INIT_PARAM == table.param_type {
- table.callback.unwrap()(&arg, &table.key.to_string(), &mut self.init_param);
+ table.callback.unwrap()(&arg, table.key, &mut self.init_param);
} else {
self.manager_param.push(arg);
}
diff --git a/exts/init/src/runtime/timer.rs b/exts/init/src/runtime/timer.rs
index c054c6c..f7b5f30 100644
--- a/exts/init/src/runtime/timer.rs
+++ b/exts/init/src/runtime/timer.rs
@@ -55,6 +55,7 @@ impl Timer {
}
}
+ #[allow(clippy::wrong_self_convention)]
pub fn is_time_out(&mut self, event: EpollEvent) -> Result<bool, Errno> {
if self.epoll.is_err(event) {
return Err(Errno::EIO);
diff --git a/exts/random_seed/src/random_seed.rs b/exts/random_seed/src/random_seed.rs
index 2130b2e..f862163 100644
--- a/exts/random_seed/src/random_seed.rs
+++ b/exts/random_seed/src/random_seed.rs
@@ -58,7 +58,7 @@ fn random_pool_size() -> usize {
}
}
-pub fn get_random(data: &mut Vec<u8>, flags: u32) -> Result<usize, ()> {
+pub fn get_random(data: &mut [u8], flags: u32) -> Result<usize, ()> {
let size;
unsafe {
size = libc::getrandom(data.as_mut_ptr() as *mut libc::c_void, data.len(), flags);
@@ -103,7 +103,7 @@ ioctl_write_ptr!(
ENTROPY_SETOPTIONS,
rand_pool_info
);
-fn random_write_entropy(random_fd: &mut File, data: &mut Vec<u8>, credit: bool) -> bool {
+fn random_write_entropy(random_fd: &mut File, data: &mut [u8], credit: bool) -> bool {
assert!(!data.is_empty());
if data.is_empty() {
diff --git a/libs/basic/src/user_group_util.rs b/libs/basic/src/user_group_util.rs
index bd9e4b2..7af8d62 100644
--- a/libs/basic/src/user_group_util.rs
+++ b/libs/basic/src/user_group_util.rs
@@ -117,7 +117,7 @@ pub fn parse_gid(gid_str: &String) -> Result<Group> {
}
/// Parse a string as Username
-pub fn parse_name(name_str: &String) -> Result<User> {
+pub fn parse_name(name_str: &str) -> Result<User> {
if name_str.is_empty() {
return Err(Error::Invalid {
what: "Username is empty".to_string(),
diff --git a/libs/event/src/timer.rs b/libs/event/src/timer.rs
index 31c808c..a94025b 100644
--- a/libs/event/src/timer.rs
+++ b/libs/event/src/timer.rs
@@ -126,6 +126,7 @@ impl Timer {
}
}
+ #[allow(clippy::wrong_self_convention)]
pub fn is_empty(&mut self, et: &EventType) -> bool {
if let Some(inner) = self.timer_set.get_mut(et) {
return inner.data.is_empty();
diff --git a/libs/macros/src/unit_conf_parse.rs b/libs/macros/src/unit_conf_parse.rs
index de9c6f0..ab0c0a2 100644
--- a/libs/macros/src/unit_conf_parse.rs
+++ b/libs/macros/src/unit_conf_parse.rs
@@ -128,13 +128,12 @@ fn gererate_setter_functions(
let mut final_stream = proc_macro2::TokenStream::new();
for (ident, _type) in idents.iter().zip(types.iter()) {
- let token_piece;
let set_field_name = format!("set_{}", ident.as_ref().unwrap());
let get_field_name = format!("get_{}", ident.as_ref().unwrap());
let set_field_ident = syn::Ident::new(&set_field_name, ident.span());
let get_field_ident = syn::Ident::new(&get_field_name, ident.span());
- if let Some(inner_ty) = get_option_inner_type(_type) {
- token_piece = quote! {
+ let token_piece = if let Some(inner_ty) = get_option_inner_type(_type) {
+ quote! {
#vis fn #set_field_ident(&mut self, #ident: #inner_ty) -> &mut Self{
self.#ident = std::option::Option::Some(#ident);
self
@@ -146,9 +145,9 @@ fn gererate_setter_functions(
return std::option::Option::Some(self.#ident.as_ref().unwrap().clone());
}
}
- };
+ }
} else {
- token_piece = quote! {
+ quote! {
#vis fn #set_field_ident(&mut self, #ident: #_type) -> &mut Self{
self.#ident = #ident;
self
@@ -156,8 +155,8 @@ fn gererate_setter_functions(
#vis fn #get_field_ident(&self) -> #_type{
return self.#ident.clone();
}
- };
- }
+ }
+ };
final_stream.extend(token_piece);
}
Ok(final_stream)
diff --git a/tests/docker_config_test.rs b/tests/docker_config_test.rs
index a3969ee..b98c612 100644
--- a/tests/docker_config_test.rs
+++ b/tests/docker_config_test.rs
@@ -10,6 +10,7 @@
// NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
// See the Mulan PSL v2 for more details.
+#[rustfmt::skip]
mod common;
#[test]
diff --git a/tests/docker_example.rs b/tests/docker_example.rs
index a2f2952..97b1127 100644
--- a/tests/docker_example.rs
+++ b/tests/docker_example.rs
@@ -10,6 +10,7 @@
// NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
// See the Mulan PSL v2 for more details.
+#[rustfmt::skip]
mod common;
#[test]
diff --git a/tests/docker_perf.rs b/tests/docker_perf.rs
index 2a45ab0..41021ed 100644
--- a/tests/docker_perf.rs
+++ b/tests/docker_perf.rs
@@ -10,6 +10,7 @@
// NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
// See the Mulan PSL v2 for more details.
+#[rustfmt::skip]
mod common;
#[test]
diff --git a/tests/docker_reliable.rs b/tests/docker_reliable.rs
index 63a2420..8db2c0d 100644
--- a/tests/docker_reliable.rs
+++ b/tests/docker_reliable.rs
@@ -10,6 +10,7 @@
// NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
// See the Mulan PSL v2 for more details.
+#[rustfmt::skip]
mod common;
#[test]
--
2.30.2

View File

@ -416,5 +416,5 @@ index ac39820..d9c5289 100644
type Err = crate::error::Error;
--
2.33.0
2.30.2

View File

@ -0,0 +1,26 @@
From a2563cafd9b64d0703b69bc4dddc653d5c092bf3 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Tue, 13 Jun 2023 20:21:31 +0800
Subject: [PATCH] fix: don't mount all subsystem to every /sys/fs/cgroup
directory
---
core/bin/mount/setup.rs | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/core/bin/mount/setup.rs b/core/bin/mount/setup.rs
index ccc6a25..6a13626 100644
--- a/core/bin/mount/setup.rs
+++ b/core/bin/mount/setup.rs
@@ -428,7 +428,7 @@ pub fn mount_cgroup_controllers() -> Result<()> {
} else {
(controllers[index].to_string(), "".to_string())
};
-
+ m_point.options = Some(target.to_string());
let target_dir = Path::new(CG_BASE_DIR).join(target);
let target = target_dir.to_str().expect("invalid cgroup path");
m_point.set_target(target);
--
2.30.2

View File

@ -0,0 +1,105 @@
From 86f01db06f5c20416a17a88a207ffb012588d0d8 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 11:17:52 +0800
Subject: [PATCH 7/9] fix: enable trigger() for socket, and use this interface
to check service state make socket reenter listening state when it triggered
service enters dead state.
---
coms/socket/src/mng.rs | 3 ++-
coms/socket/src/unit.rs | 16 ++++++++++++++++
core/bin/unit/entry/uentry.rs | 5 +++++
core/bin/unit/entry/unitx.rs | 4 +++-
core/lib/unit/base.rs | 3 +++
5 files changed, 29 insertions(+), 2 deletions(-)
diff --git a/coms/socket/src/mng.rs b/coms/socket/src/mng.rs
index 82fdcbe..0435827 100644
--- a/coms/socket/src/mng.rs
+++ b/coms/socket/src/mng.rs
@@ -341,8 +341,9 @@ impl SocketMng {
self.set_state(SocketState::StartPost);
}
- fn enter_listening(&self) {
+ pub(crate) fn enter_listening(&self) {
log::debug!("enter start listening state");
+ /* Seem logic as systemd's socket has configured FlushPending=yes */
if !self.config.config_data().borrow().Socket.Accept {
self.flush_ports();
}
diff --git a/coms/socket/src/unit.rs b/coms/socket/src/unit.rs
index 8e33ee8..d96c258 100644
--- a/coms/socket/src/unit.rs
+++ b/coms/socket/src/unit.rs
@@ -115,6 +115,22 @@ impl SubUnit for SocketUnit {
Ok(())
}
+ fn trigger(&self, other: &String) {
+ let um = self.comm.um();
+ let service_state = um.get_subunit_state(other);
+ if [
+ "dead".to_string(),
+ "failed".to_string(),
+ "finalsigterm".to_string(),
+ "finalsigkill".to_string(),
+ "autorestart".to_string(),
+ ]
+ .contains(&service_state)
+ {
+ self.mng.enter_listening();
+ }
+ }
+
fn sigchld_events(&self, wait_status: WaitStatus) {
self.mng.sigchld_event(wait_status)
}
diff --git a/core/bin/unit/entry/uentry.rs b/core/bin/unit/entry/uentry.rs
index 307240b..f6b4db4 100644
--- a/core/bin/unit/entry/uentry.rs
+++ b/core/bin/unit/entry/uentry.rs
@@ -545,6 +545,11 @@ impl Unit {
self.config.clone()
}
+ pub(super) fn trigger(&self, other: &Self) {
+ let other_unit_id = other.id();
+ self.sub.trigger(other_unit_id);
+ }
+
pub(super) fn in_load_queue(&self) -> bool {
self.load.in_load_queue()
}
diff --git a/core/bin/unit/entry/unitx.rs b/core/bin/unit/entry/unitx.rs
index d9878f4..92b4ebb 100644
--- a/core/bin/unit/entry/unitx.rs
+++ b/core/bin/unit/entry/unitx.rs
@@ -106,7 +106,9 @@ impl UnitX {
self.0.sigchld_events(wait_status)
}
- pub(crate) fn trigger(&self, _other: &Self) {}
+ pub(crate) fn trigger(&self, other: &Self) {
+ self.0.trigger(other);
+ }
pub(crate) fn in_load_queue(&self) -> bool {
self.0.in_load_queue()
}
diff --git a/core/lib/unit/base.rs b/core/lib/unit/base.rs
index d279295..8d76cab 100644
--- a/core/lib/unit/base.rs
+++ b/core/lib/unit/base.rs
@@ -127,6 +127,9 @@ pub trait SubUnit: ReStation + UnitMngUtil {
Vec::new()
}
+ ///
+ fn trigger(&self, _other: &String) {}
+
///Get the the unit state
///
/// Every sub unit can define self states and map to [`UnitActiveState`]
--
2.30.2

View File

@ -0,0 +1,122 @@
From 4490bcd3d40b15f22446af46500039d2cbd37bf9 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 11:24:36 +0800
Subject: [PATCH 9/9] fix: fix some cargo clippies
---
coms/socket/src/unit.rs | 4 ++--
core/bin/unit/data/table.rs | 3 +--
core/bin/unit/datastore/sets.rs | 2 +-
core/bin/utils/table.rs | 6 +-----
core/lib/error.rs | 3 +++
core/lib/unit/base.rs | 2 +-
6 files changed, 9 insertions(+), 11 deletions(-)
diff --git a/coms/socket/src/unit.rs b/coms/socket/src/unit.rs
index d96c258..9f0f6ce 100644
--- a/coms/socket/src/unit.rs
+++ b/coms/socket/src/unit.rs
@@ -22,8 +22,8 @@ use crate::{
};
use basic::logger;
use nix::sys::wait::WaitStatus;
-use std::{path::PathBuf, rc::Rc};
use std::any::Any;
+use std::{path::PathBuf, rc::Rc};
use sysmaster::error::*;
use sysmaster::exec::ExecContext;
use sysmaster::rel::{ReStation, Reliability};
@@ -115,7 +115,7 @@ impl SubUnit for SocketUnit {
Ok(())
}
- fn trigger(&self, other: &String) {
+ fn trigger(&self, other: &str) {
let um = self.comm.um();
let service_state = um.get_subunit_state(other);
if [
diff --git a/core/bin/unit/data/table.rs b/core/bin/unit/data/table.rs
index 161ac5f..256e8df 100644
--- a/core/bin/unit/data/table.rs
+++ b/core/bin/unit/data/table.rs
@@ -60,8 +60,7 @@ impl DataManager {
ud_config: UnitDepConf,
) -> Option<UnitDepConf> {
{
- let old = self.tables.0.insert(u_name, ud_config);
- old
+ self.tables.0.insert(u_name, ud_config)
}
}
diff --git a/core/bin/unit/datastore/sets.rs b/core/bin/unit/datastore/sets.rs
index 538df8f..9a94a4b 100644
--- a/core/bin/unit/datastore/sets.rs
+++ b/core/bin/unit/datastore/sets.rs
@@ -62,7 +62,7 @@ impl UnitSets {
.borrow()
.get_all()
.iter()
- .map(|ur| Rc::clone(ur))
+ .map(Rc::clone)
.collect::<Vec<_>>()
}
diff --git a/core/bin/utils/table.rs b/core/bin/utils/table.rs
index e1768d2..482d168 100644
--- a/core/bin/utils/table.rs
+++ b/core/bin/utils/table.rs
@@ -82,11 +82,7 @@ where
}
pub fn get_all(&self) -> Vec<V> {
- self.data
- .borrow()
- .values()
- .map(|v| v.clone())
- .collect::<Vec<V>>()
+ self.data.borrow().values().cloned().collect::<Vec<V>>()
}
pub fn subscribe(
diff --git a/core/lib/error.rs b/core/lib/error.rs
index 331f367..72471db 100644
--- a/core/lib/error.rs
+++ b/core/lib/error.rs
@@ -290,6 +290,7 @@ impl From<event::Error> for Error {
/// new Result
pub type Result<T, E = Error> = std::result::Result<T, E>;
+/// check if the error is disconnect
pub fn error_is_disconnect(e: &Errno) -> bool {
[
Errno::ECONNABORTED,
@@ -310,10 +311,12 @@ pub fn error_is_disconnect(e: &Errno) -> bool {
.contains(e)
}
+/// check if the error is transient
pub fn error_is_transient(e: &Errno) -> bool {
[Errno::EAGAIN, Errno::EINTR].contains(e)
}
+/// check if the error is accept or again
pub fn error_is_accept_again(e: &Errno) -> bool {
error_is_disconnect(e) || error_is_transient(e) || e == &Errno::EOPNOTSUPP
}
diff --git a/core/lib/unit/base.rs b/core/lib/unit/base.rs
index 8d76cab..2ec3e73 100644
--- a/core/lib/unit/base.rs
+++ b/core/lib/unit/base.rs
@@ -128,7 +128,7 @@ pub trait SubUnit: ReStation + UnitMngUtil {
}
///
- fn trigger(&self, _other: &String) {}
+ fn trigger(&self, _other: &str) {}
///Get the the unit state
///
--
2.30.2

View File

@ -0,0 +1,28 @@
From 71b0283e4c34078497c4aced37234949d833f45c Mon Sep 17 00:00:00 2001
From: chenjiayi <chenjiayi22@huawei.com>
Date: Wed, 7 Jun 2023 00:40:37 +0800
Subject: [PATCH] fix(fstab): use fixed inotify version 0.10.0 to be compatible
with rustc 1.60
Latest inotify crate 0.10.1 requires rustc 1.63.0. Previously we didn't
state the minimum version number of inotify, which lead to cargo
automatically use the latest version and fails to build.
---
exts/fstab/Cargo.toml | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/exts/fstab/Cargo.toml b/exts/fstab/Cargo.toml
index 3445698..59ba4c4 100644
--- a/exts/fstab/Cargo.toml
+++ b/exts/fstab/Cargo.toml
@@ -6,6 +6,6 @@ edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
-inotify = "0.10"
+inotify = "=0.10.0"
log = "0.4"
nix = "0.24"
--
2.30.2

View File

@ -0,0 +1,399 @@
From b2800ac267a76c19ce3229b031d809c4539ba5e7 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 11:10:42 +0800
Subject: [PATCH 4/9] fix: move RefCell to the inside of Table, no functional
change
---
core/bin/unit/data/dep_conf.rs | 2 +-
core/bin/unit/data/state.rs | 2 +-
core/bin/unit/data/table.rs | 49 +++++++++-------------
core/bin/unit/datastore/sets.rs | 2 +-
core/bin/unit/entry/ratelimit.rs | 2 +-
core/bin/utils/table.rs | 71 +++++++++++++++++---------------
6 files changed, 60 insertions(+), 68 deletions(-)
diff --git a/core/bin/unit/data/dep_conf.rs b/core/bin/unit/data/dep_conf.rs
index 9c203c5..e61ce5b 100644
--- a/core/bin/unit/data/dep_conf.rs
+++ b/core/bin/unit/data/dep_conf.rs
@@ -13,7 +13,7 @@
use std::collections::HashMap;
use sysmaster::unit::UnitRelations;
-#[derive(Default)]
+#[derive(Default, Clone)]
pub struct UnitDepConf {
pub deps: HashMap<UnitRelations, Vec<String>>,
}
diff --git a/core/bin/unit/data/state.rs b/core/bin/unit/data/state.rs
index fcdd51e..68e8607 100644
--- a/core/bin/unit/data/state.rs
+++ b/core/bin/unit/data/state.rs
@@ -12,7 +12,7 @@
use sysmaster::unit::{UnitActiveState, UnitNotifyFlags};
-#[derive(Debug)]
+#[derive(Debug, Clone)]
pub(crate) struct UnitState {
pub(crate) os: UnitActiveState,
pub(crate) ns: UnitActiveState,
diff --git a/core/bin/unit/data/table.rs b/core/bin/unit/data/table.rs
index 480a026..161ac5f 100644
--- a/core/bin/unit/data/table.rs
+++ b/core/bin/unit/data/table.rs
@@ -15,17 +15,16 @@ use super::state::UnitState;
use crate::job::JobResult;
use crate::unit::entry::StartLimitResult;
use crate::utils::table::{Table, TableSubscribe};
-use std::cell::RefCell;
use std::rc::Rc;
use sysmaster::rel::ReStation;
#[allow(clippy::type_complexity)]
pub struct DataManager {
tables: (
- RefCell<Table<String, UnitDepConf>>, // [0]unit-dep-config
- RefCell<Table<String, UnitState>>, // [1]unit-state
- RefCell<Table<String, StartLimitResult>>, // [2]unit-start-limit-hit
- RefCell<Table<String, JobResult>>, // [3] unit-job-timeout
+ Table<String, UnitDepConf>, // [0]unit-dep-config
+ Table<String, UnitState>, // [1]unit-state
+ Table<String, StartLimitResult>, // [2]unit-start-limit-hit
+ Table<String, JobResult>, // [3] unit-job-timeout
),
}
@@ -35,8 +34,8 @@ impl ReStation for DataManager {
// reload
fn entry_clear(&self) {
- self.tables.0.borrow_mut().data_clear();
- self.tables.1.borrow_mut().data_clear();
+ self.tables.0.data_clear();
+ self.tables.1.data_clear();
}
}
@@ -51,12 +50,7 @@ impl Drop for DataManager {
impl DataManager {
pub fn new() -> DataManager {
DataManager {
- tables: (
- RefCell::new(Table::new()),
- RefCell::new(Table::new()),
- RefCell::new(Table::new()),
- RefCell::new(Table::new()),
- ),
+ tables: (Table::new(), Table::new(), Table::new(), Table::new()),
}
}
@@ -66,7 +60,7 @@ impl DataManager {
ud_config: UnitDepConf,
) -> Option<UnitDepConf> {
{
- let old = self.tables.0.borrow_mut().insert(u_name, ud_config);
+ let old = self.tables.0.insert(u_name, ud_config);
old
}
}
@@ -76,8 +70,7 @@ impl DataManager {
name: &str,
subscriber: Rc<dyn TableSubscribe<String, UnitDepConf>>,
) -> Option<Rc<dyn TableSubscribe<String, UnitDepConf>>> {
- let mut table = self.tables.0.borrow_mut();
- table.subscribe(name.to_string(), subscriber)
+ self.tables.0.subscribe(name.to_string(), subscriber)
}
pub(crate) fn insert_unit_state(
@@ -85,8 +78,7 @@ impl DataManager {
u_name: String,
u_state: UnitState,
) -> Option<UnitState> {
- let mut table = self.tables.1.borrow_mut();
- table.insert(u_name, u_state)
+ self.tables.1.insert(u_name, u_state)
}
pub(crate) fn register_unit_state(
@@ -94,8 +86,7 @@ impl DataManager {
name: &str,
subscriber: Rc<dyn TableSubscribe<String, UnitState>>,
) -> Option<Rc<dyn TableSubscribe<String, UnitState>>> {
- let mut table = self.tables.1.borrow_mut();
- table.subscribe(name.to_string(), subscriber)
+ self.tables.1.subscribe(name.to_string(), subscriber)
}
pub(crate) fn insert_start_limit_result(
@@ -103,8 +94,7 @@ impl DataManager {
u_name: String,
start_limit_res: StartLimitResult,
) -> Option<StartLimitResult> {
- let mut table = self.tables.2.borrow_mut();
- table.insert(u_name, start_limit_res)
+ self.tables.2.insert(u_name, start_limit_res)
}
pub(crate) fn register_start_limit_result(
@@ -112,8 +102,7 @@ impl DataManager {
name: &str,
subscriber: Rc<dyn TableSubscribe<String, StartLimitResult>>,
) -> Option<Rc<dyn TableSubscribe<String, StartLimitResult>>> {
- let mut table = self.tables.2.borrow_mut();
- table.subscribe(name.to_string(), subscriber)
+ self.tables.2.subscribe(name.to_string(), subscriber)
}
pub(crate) fn insert_job_result(
@@ -121,8 +110,7 @@ impl DataManager {
u_name: String,
job_result: JobResult,
) -> Option<JobResult> {
- let mut table = self.tables.3.borrow_mut();
- table.insert(u_name, job_result)
+ self.tables.3.insert(u_name, job_result)
}
pub(crate) fn register_job_result(
@@ -130,19 +118,20 @@ impl DataManager {
name: &str,
subscriber: Rc<dyn TableSubscribe<String, JobResult>>,
) -> Option<Rc<dyn TableSubscribe<String, JobResult>>> {
- let mut table = self.tables.3.borrow_mut();
- table.subscribe(name.to_string(), subscriber)
+ self.tables.3.subscribe(name.to_string(), subscriber)
}
// repeating protection
pub(crate) fn clear(&self) {
- self.tables.0.borrow_mut().clear();
- self.tables.1.borrow_mut().clear();
+ self.tables.0.clear();
+ self.tables.1.clear();
}
}
#[cfg(test)]
mod tests {
+ use std::cell::RefCell;
+
use super::*;
use crate::unit::UnitRelations;
use crate::utils::table::TableOp;
diff --git a/core/bin/unit/datastore/sets.rs b/core/bin/unit/datastore/sets.rs
index 677d21b..538df8f 100644
--- a/core/bin/unit/datastore/sets.rs
+++ b/core/bin/unit/datastore/sets.rs
@@ -54,7 +54,7 @@ impl UnitSets {
}
pub(super) fn get(&self, name: &str) -> Option<Rc<UnitX>> {
- self.t.borrow().get(&name.to_string()).cloned()
+ self.t.borrow().get(&name.to_string())
}
pub(super) fn get_all(&self) -> Vec<Rc<UnitX>> {
diff --git a/core/bin/unit/entry/ratelimit.rs b/core/bin/unit/entry/ratelimit.rs
index 2f2a446..2c67232 100644
--- a/core/bin/unit/entry/ratelimit.rs
+++ b/core/bin/unit/entry/ratelimit.rs
@@ -17,7 +17,7 @@ pub(super) struct StartLimit {
start_limit: RefCell<RateLimit>,
}
-#[derive(PartialEq, Eq)]
+#[derive(PartialEq, Eq, Clone)]
pub(crate) enum StartLimitResult {
StartLimitNotHit,
StartLimitHit,
diff --git a/core/bin/utils/table.rs b/core/bin/utils/table.rs
index 90846cc..e1768d2 100644
--- a/core/bin/utils/table.rs
+++ b/core/bin/utils/table.rs
@@ -10,6 +10,7 @@
// NON-INFRINGEMENT, MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
// See the Mulan PSL v2 for more details.
+use std::cell::RefCell;
use std::collections::HashMap;
use std::hash::Hash;
use std::rc::Rc;
@@ -30,47 +31,45 @@ pub trait TableSubscribe<K, V> {
//#[derive(Debug)]
pub struct Table<K, V> {
- data: HashMap<K, V>, // key + value
- subscribers: HashMap<String, Rc<dyn TableSubscribe<K, V>>>, // key: name, value: subscriber
+ data: RefCell<HashMap<K, V>>, // key + value
+ subscribers: RefCell<HashMap<String, Rc<dyn TableSubscribe<K, V>>>>, // key: name, value: subscriber
}
impl<K, V> Table<K, V>
where
K: Eq + Hash + Clone,
+ V: Clone,
{
pub fn new() -> Table<K, V> {
Table {
- data: HashMap::new(),
- subscribers: HashMap::new(),
+ data: RefCell::new(HashMap::new()),
+ subscribers: RefCell::new(HashMap::new()),
}
}
- pub fn data_clear(&mut self) {
+ pub fn data_clear(&self) {
// clear all data without notifying subscribers
- self.data.clear();
+ self.data.borrow_mut().clear();
}
- pub fn clear(&mut self) {
+ pub fn clear(&self) {
// clear all, including data and subscribers
self.data_clear();
- self.subscribers.clear();
+ self.subscribers.borrow_mut().clear();
}
- pub fn insert(&mut self, k: K, v: V) -> Option<V> {
+ pub fn insert(&self, k: K, v: V) -> Option<V> {
let key = k.clone();
- let ret = self.data.insert(k, v);
- let value = self
- .data
- .get(&key)
- .expect("something inserted is not found.");
- let op = TableOp::TableInsert(&key, value);
+ let ret = self.data.borrow_mut().insert(k, v);
+ let value = self.get(&key).expect("something inserted is not found.");
+ let op = TableOp::TableInsert(&key, &value);
self.notify(&op);
ret
}
#[allow(dead_code)]
- pub fn remove(&mut self, k: &K) -> Option<V> {
- let ret = self.data.remove(k);
+ pub fn remove(&self, k: &K) -> Option<V> {
+ let ret = self.data.borrow_mut().remove(k);
if let Some(v) = &ret {
let op = TableOp::TableRemove(k, v);
self.notify(&op);
@@ -78,29 +77,33 @@ where
ret
}
- pub fn get(&self, k: &K) -> Option<&V> {
- self.data.get(k)
+ pub fn get(&self, k: &K) -> Option<V> {
+ self.data.borrow().get(k).cloned()
}
- pub fn get_all(&self) -> Vec<&V> {
- self.data.values().collect::<Vec<_>>()
+ pub fn get_all(&self) -> Vec<V> {
+ self.data
+ .borrow()
+ .values()
+ .map(|v| v.clone())
+ .collect::<Vec<V>>()
}
pub fn subscribe(
- &mut self,
+ &self,
name: String,
subscriber: Rc<dyn TableSubscribe<K, V>>,
) -> Option<Rc<dyn TableSubscribe<K, V>>> {
- self.subscribers.insert(name, subscriber)
+ self.subscribers.borrow_mut().insert(name, subscriber)
}
#[allow(dead_code)]
- pub fn unsubscribe(&mut self, name: &str) -> Option<Rc<dyn TableSubscribe<K, V>>> {
- self.subscribers.remove(name)
+ pub fn unsubscribe(&self, name: &str) -> Option<Rc<dyn TableSubscribe<K, V>>> {
+ self.subscribers.borrow_mut().remove(name)
}
fn notify(&self, op: &TableOp<'_, K, V>) {
- for (_, subscriber) in self.subscribers.iter() {
+ for (_, subscriber) in self.subscribers.borrow().iter() {
if subscriber.filter(op) {
subscriber.notify(op);
}
@@ -115,7 +118,7 @@ mod tests {
#[test]
fn table_insert() {
- let mut table: Table<u32, char> = Table::new();
+ let table: Table<u32, char> = Table::new();
let old = table.insert(1, 'a');
assert_eq!(old, None);
@@ -129,7 +132,7 @@ mod tests {
#[test]
fn table_remove() {
- let mut table: Table<u32, char> = Table::new();
+ let table: Table<u32, char> = Table::new();
let old = table.remove(&1);
assert_eq!(old, None);
@@ -148,25 +151,25 @@ mod tests {
#[test]
fn table_get() {
- let mut table: Table<u32, char> = Table::new();
+ let table: Table<u32, char> = Table::new();
let value = table.get(&1);
assert_eq!(value, None);
table.insert(1, 'a');
let value = table.get(&1);
- assert_eq!(value.cloned(), Some('a'));
+ assert_eq!(value, Some('a'));
let value = table.get(&2);
assert_eq!(value, None);
table.insert(2, 'b');
let value = table.get(&2);
- assert_eq!(value.cloned(), Some('b'));
+ assert_eq!(value, Some('b'));
}
#[test]
fn table_subscribe() {
- let mut table: Table<u32, char> = Table::new();
+ let table: Table<u32, char> = Table::new();
let sub_test1 = Rc::new(TableTest::new());
let sub_test2 = Rc::new(TableTest::new());
@@ -185,7 +188,7 @@ mod tests {
#[test]
fn table_unsubscribe() {
- let mut table: Table<u32, char> = Table::new();
+ let table: Table<u32, char> = Table::new();
let sub_test1 = Rc::new(TableTest::new());
let sub_test2 = Rc::new(TableTest::new());
@@ -209,7 +212,7 @@ mod tests {
#[test]
fn table_notify() {
- let mut table: Table<u32, char> = Table::new();
+ let table: Table<u32, char> = Table::new();
let sub_test1 = Rc::new(TableTest::new());
let sub_test2 = Rc::new(TableTest::new());
--
2.30.2

View File

@ -0,0 +1,52 @@
From 8e872af3529d75a05fad98824786415045c8cf10 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 15:57:55 +0800
Subject: [PATCH] fix: only remove one unit's pid from db PR #568 removes all
unit's pids when one unit enters dead state, which is definitely wrong. We
should only remove one unit's pid from db, and other unit's pids should still
be watched.
---
core/bin/unit/datastore/child.rs | 12 +++++++-----
1 file changed, 7 insertions(+), 5 deletions(-)
diff --git a/core/bin/unit/datastore/child.rs b/core/bin/unit/datastore/child.rs
index 60c73c5..f4460f0 100644
--- a/core/bin/unit/datastore/child.rs
+++ b/core/bin/unit/datastore/child.rs
@@ -59,7 +59,7 @@ impl UnitChild {
}
pub(super) fn add_watch_pid(&self, id: &str, pid: Pid) {
- log::debug!("borrow add watch_pids for pid:{}, id:{}", pid, id);
+ log::debug!("Adding watch_pids {} to {}", pid, id);
let unit = self.units.get(id).unwrap();
self.data.add_watch_pid(unit.clone(), pid);
unit.child_add_pids(pid);
@@ -67,17 +67,19 @@ impl UnitChild {
pub(super) fn unwatch_pid(&self, id: &str, pid: Pid) {
let unit = self.units.get(id).unwrap();
- log::debug!("borrow remove watch_pids for {}", pid);
+ log::debug!("Removing watch_pids {} from {}", pid, id);
self.data.unwatch_pid(unit.clone(), pid);
unit.child_remove_pids(pid);
}
pub(super) fn unwatch_all_pids(&self, id: &str) {
+ log::debug!("Unwatching all watch_pids of {}", id);
let unit = self.units.get(id).unwrap();
- for i in self.data.watch_pids.borrow().keys() {
- unit.child_remove_pids(*i);
+ let delete_pids = unit.get_pids();
+ for pid in delete_pids {
+ unit.child_remove_pids(pid);
+ self.data.unwatch_pid(unit.clone(), pid);
}
- self.data.watch_pids.borrow_mut().clear();
}
pub(super) fn get_unit_by_pid(&self, pid: Pid) -> Option<Rc<UnitX>> {
--
2.30.2

View File

@ -0,0 +1,79 @@
From a9134b19fc0c942f842a7b51a956347951c89f8b Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 14 Jun 2023 17:24:08 +0800
Subject: [PATCH] fix: really use usec
watchdog_usec was actually watchdog_sec formerly
---
coms/service/src/mng.rs | 14 +++++++-------
coms/service/src/spawn.rs | 2 +-
2 files changed, 8 insertions(+), 8 deletions(-)
diff --git a/coms/service/src/mng.rs b/coms/service/src/mng.rs
index 5c71531..bfa2c9f 100644
--- a/coms/service/src/mng.rs
+++ b/coms/service/src/mng.rs
@@ -1233,9 +1233,9 @@ impl ServiceMng {
}
fn restart_watchdog(&self) {
- self.monitor
- .borrow_mut()
- .set_original_watchdog(self.config.config_data().borrow().Service.WatchdogSec);
+ self.monitor.borrow_mut().set_original_watchdog(
+ self.config.config_data().borrow().Service.WatchdogSec * 1000000,
+ );
let watchdog_usec = self.monitor.borrow().watchdog_usec();
if watchdog_usec == 0 || watchdog_usec == u64::MAX {
self.stop_watchdog();
@@ -2455,7 +2455,7 @@ impl Source for ServiceTimer {
struct ServiceMonitorData {
mng: RefCell<Weak<ServiceMng>>,
// owned objects
- time: RefCell<u64>,
+ time: RefCell<u64>, /* usec */
}
// the declaration "pub(self)" is for identification only.
@@ -2511,7 +2511,7 @@ impl Source for ServiceMonitorData {
}
fn time_relative(&self) -> u64 {
- *self.time.borrow() * 1000000
+ *self.time.borrow()
}
fn dispatch(&self, _: &Events) -> i32 {
@@ -2575,7 +2575,7 @@ mod tests {
assert!(rt.armd_watchdog());
assert_eq!(
rt.watchdog().time(),
- config.config_data().borrow().Service.WatchdogSec
+ config.config_data().borrow().Service.WatchdogSec * 1000000
);
}
@@ -2594,7 +2594,7 @@ mod tests {
assert!(rt.armd_watchdog());
assert_eq!(
rt.watchdog().time(),
- config.config_data().borrow().Service.WatchdogSec
+ config.config_data().borrow().Service.WatchdogSec * 1000000
);
messages.remove("WATCHDOG");
diff --git a/coms/service/src/spawn.rs b/coms/service/src/spawn.rs
index 9b895aa..2ff9e92 100644
--- a/coms/service/src/spawn.rs
+++ b/coms/service/src/spawn.rs
@@ -164,6 +164,6 @@ impl ServiceSpawn {
}
fn watchdog_timer(&self) -> u64 {
- self.config.config_data().borrow().Service.WatchdogSec
+ self.config.config_data().borrow().Service.WatchdogSec * 1000000
}
}
--
2.30.2

View File

@ -0,0 +1,78 @@
From c7600975afe9a2b13d33c10cc081e5de4b0d8270 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 10:51:33 +0800
Subject: [PATCH 1/9] fix: remove some debug message, no functional change
---
coms/socket/src/mng.rs | 2 --
core/bin/unit/notify.rs | 2 --
libs/event/tests/inotify.rs | 1 -
libs/event/tests/io.rs | 1 -
libs/event/tests/signal.rs | 1 -
5 files changed, 7 deletions(-)
diff --git a/coms/socket/src/mng.rs b/coms/socket/src/mng.rs
index e7a6a01..33b9812 100644
--- a/coms/socket/src/mng.rs
+++ b/coms/socket/src/mng.rs
@@ -848,8 +848,6 @@ impl Source for SocketMngPort {
}
fn dispatch(&self, _: &Events) -> i32 {
- println!("Dispatching IO!");
-
self.reli().set_last_frame2(
ReliLastFrame::SubManager as u32,
UnitType::UnitSocket as u32,
diff --git a/core/bin/unit/notify.rs b/core/bin/unit/notify.rs
index cb05330..f824725 100644
--- a/core/bin/unit/notify.rs
+++ b/core/bin/unit/notify.rs
@@ -332,8 +332,6 @@ impl Source for Notify {
}
fn dispatch(&self, _e: &Events) -> i32 {
- log::debug!("begin to dispatch notify event");
-
self.reli.set_last_frame1(ReliLastFrame::Notify as u32);
let ret = self.notify_dispatch();
self.reli.clear_last_frame();
diff --git a/libs/event/tests/inotify.rs b/libs/event/tests/inotify.rs
index 5fb3f5f..e9bdf72 100644
--- a/libs/event/tests/inotify.rs
+++ b/libs/event/tests/inotify.rs
@@ -49,7 +49,6 @@ mod test {
}
fn dispatch(&self, e: &Events) -> i32 {
- println!("Dispatching inotify!");
e.set_exit();
0
}
diff --git a/libs/event/tests/io.rs b/libs/event/tests/io.rs
index 292ed16..be79494 100644
--- a/libs/event/tests/io.rs
+++ b/libs/event/tests/io.rs
@@ -54,7 +54,6 @@ mod test {
}
fn dispatch(&self, _: &Events) -> i32 {
- println!("Dispatching IO!");
0
}
diff --git a/libs/event/tests/signal.rs b/libs/event/tests/signal.rs
index 3a54812..961bd5a 100644
--- a/libs/event/tests/signal.rs
+++ b/libs/event/tests/signal.rs
@@ -47,7 +47,6 @@ impl Source for Signals {
}
fn dispatch(&self, e: &Events) -> i32 {
- println!("Dispatching signal!");
match e.read_signals() {
Ok(Some(info)) => {
println!("read signo: {:?}", info.ssi_signo);
--
2.30.2

View File

@ -0,0 +1,145 @@
From c38d3c9dd677b28cbdd638b853475f74c42936bf Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Mon, 22 May 2023 11:56:18 +0800
Subject: [PATCH] fix: unwatch all pids when the service enters dead
---
coms/service/src/mng.rs | 10 ++++++++++
coms/service/src/pid.rs | 6 ++++++
core/bin/unit/datastore/child.rs | 18 ++++++++++++------
core/bin/unit/datastore/mod.rs | 4 ++++
core/bin/unit/manager.rs | 9 +++++++++
core/lib/unit/umif.rs | 3 +++
6 files changed, 44 insertions(+), 6 deletions(-)
diff --git a/coms/service/src/mng.rs b/coms/service/src/mng.rs
index dff610e..d73fa34 100644
--- a/coms/service/src/mng.rs
+++ b/coms/service/src/mng.rs
@@ -845,6 +845,16 @@ impl ServiceMng {
self.set_cmd_type(None);
}
+ if vec![
+ ServiceState::Dead,
+ ServiceState::Failed,
+ ServiceState::AutoRestart,
+ ]
+ .contains(&state)
+ {
+ self.pid.child_unwatch_all_pids();
+ }
+
// todo!()
// trigger the unit the dependency trigger_by
diff --git a/coms/service/src/pid.rs b/coms/service/src/pid.rs
index deba828..a25de50 100644
--- a/coms/service/src/pid.rs
+++ b/coms/service/src/pid.rs
@@ -94,6 +94,12 @@ impl ServicePid {
}
}
+ pub(super) fn child_unwatch_all_pids(&self) {
+ if let Some(u) = self.comm.owner() {
+ self.comm.um().child_unwatch_all_pids(u.id());
+ }
+ }
+
pub(super) fn main(&self) -> Option<Pid> {
self.data.borrow().main()
}
diff --git a/core/bin/unit/datastore/child.rs b/core/bin/unit/datastore/child.rs
index fd8fffa..af63792 100644
--- a/core/bin/unit/datastore/child.rs
+++ b/core/bin/unit/datastore/child.rs
@@ -57,17 +57,23 @@ impl UnitChild {
pub(super) fn add_watch_pid(&self, id: &str, pid: Pid) {
log::debug!("borrow add watch_pids for pid:{}, id:{}", pid, id);
let unit = self.units.get(id).unwrap();
- let u = Rc::clone(&unit);
- self.data.add_watch_pid(unit, pid);
- u.child_add_pids(pid);
+ self.data.add_watch_pid(unit.clone(), pid);
+ unit.child_add_pids(pid);
}
pub(super) fn unwatch_pid(&self, id: &str, pid: Pid) {
let unit = self.units.get(id).unwrap();
- let u = Rc::clone(&unit);
log::debug!("borrow remove watch_pids for {}", pid);
- self.data.unwatch_pid(unit, pid);
- u.child_remove_pids(pid);
+ self.data.unwatch_pid(unit.clone(), pid);
+ unit.child_remove_pids(pid);
+ }
+
+ pub(super) fn unwatch_all_pids(&self, id: &str) {
+ let unit = self.units.get(id).unwrap();
+ for i in self.data.watch_pids.borrow().keys() {
+ unit.child_remove_pids(*i);
+ }
+ self.data.watch_pids.borrow_mut().clear();
}
pub(super) fn get_unit_by_pid(&self, pid: Pid) -> Option<Rc<UnitX>> {
diff --git a/core/bin/unit/datastore/mod.rs b/core/bin/unit/datastore/mod.rs
index d3f8839..1dc09d7 100644
--- a/core/bin/unit/datastore/mod.rs
+++ b/core/bin/unit/datastore/mod.rs
@@ -160,6 +160,10 @@ impl UnitDb {
}
}
+ pub fn child_unwatch_all_pids(&self, id: &str) {
+ self.child.unwatch_all_pids(id);
+ }
+
pub fn get_unit_by_pid(&self, pid: Pid) -> Option<Rc<UnitX>> {
self.child.get_unit_by_pid(pid)
}
diff --git a/core/bin/unit/manager.rs b/core/bin/unit/manager.rs
index 0677c1b..bee3093 100644
--- a/core/bin/unit/manager.rs
+++ b/core/bin/unit/manager.rs
@@ -392,6 +392,10 @@ impl UmIf for UnitManager {
self.child_watch_all_pids(id)
}
+ fn child_unwatch_all_pids(&self, id: &str) {
+ self.child_unwatch_all_pids(id)
+ }
+
fn notify_socket(&self) -> Option<PathBuf> {
self.notify_socket()
}
@@ -480,6 +484,11 @@ impl UnitManager {
self.db.child_watch_all_pids(id)
}
+ /// remove all pids
+ fn child_unwatch_all_pids(&self, id: &str) {
+ self.db.child_unwatch_all_pids(id)
+ }
+
/// delete the pid from the db
fn child_unwatch_pid(&self, id: &str, pid: Pid) {
self.db.child_unwatch_pid(id, pid)
diff --git a/core/lib/unit/umif.rs b/core/lib/unit/umif.rs
index 027c59f..4821ff9 100644
--- a/core/lib/unit/umif.rs
+++ b/core/lib/unit/umif.rs
@@ -134,6 +134,9 @@ pub trait UmIf {
/// add all the pid of unit id, read pids from cgroup path.
fn child_watch_all_pids(&self, _id: &str) {}
+ /// remove all the pid of unit id
+ fn child_unwatch_all_pids(&self, _id: &str) {}
+
///rentry_trigger_merge
fn rentry_trigger_merge(&self, _unit_id: &str, _force: bool) {}
--
2.30.2

View File

@ -0,0 +1,189 @@
From 95210185215c933fa00be50c96505ef390df349c Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Wed, 31 May 2023 10:57:10 +0800
Subject: [PATCH 2/9] refactor: rename UNitNotifyFlags to shorten code a bit
change UNIT_NOTIFY_SUCCESS to EMPTY, the original SUCCESS doesn't make sense
---
coms/mount/src/mng.rs | 2 +-
coms/service/src/mng.rs | 6 +++---
coms/socket/src/mng.rs | 2 +-
coms/target/src/mng.rs | 2 +-
core/bin/job/entry.rs | 2 +-
core/bin/job/manager.rs | 5 ++---
core/bin/unit/data/table.rs | 2 +-
core/bin/unit/entry/uentry.rs | 6 +-----
core/bin/unit/manager.rs | 1 -
core/lib/unit/state.rs | 8 ++++----
10 files changed, 15 insertions(+), 21 deletions(-)
diff --git a/coms/mount/src/mng.rs b/coms/mount/src/mng.rs
index e09d1f7..5383c4d 100644
--- a/coms/mount/src/mng.rs
+++ b/coms/mount/src/mng.rs
@@ -108,7 +108,7 @@ impl MountMng {
u.notify(
old_unit_state,
new_unit_state,
- UnitNotifyFlags::UNIT_NOTIFY_RELOAD_FAILURE,
+ UnitNotifyFlags::RELOAD_FAILURE,
)
}
diff --git a/coms/service/src/mng.rs b/coms/service/src/mng.rs
index 0f5db5f..fa6237a 100644
--- a/coms/service/src/mng.rs
+++ b/coms/service/src/mng.rs
@@ -862,14 +862,14 @@ impl ServiceMng {
let os = service_state_to_unit_state(self.config.service_type(), original_state);
let ns = service_state_to_unit_state(self.config.service_type(), state);
if let Some(u) = self.comm.owner() {
- let mut flags = UnitNotifyFlags::UNIT_NOTIFY_SUCCESS;
+ let mut flags = UnitNotifyFlags::EMPTY;
if self.rd.will_auto_restart() {
- flags |= UnitNotifyFlags::UNIT_NOTIFY_WILL_AUTO_RESTART;
+ flags |= UnitNotifyFlags::WILL_AUTO_RESTART;
}
if self.reload_result() != ServiceResult::Success {
- flags |= UnitNotifyFlags::UNIT_NOTIFY_RELOAD_FAILURE;
+ flags |= UnitNotifyFlags::RELOAD_FAILURE;
}
u.notify(os, ns, flags)
}
diff --git a/coms/socket/src/mng.rs b/coms/socket/src/mng.rs
index 33b9812..fe77517 100644
--- a/coms/socket/src/mng.rs
+++ b/coms/socket/src/mng.rs
@@ -650,7 +650,7 @@ impl SocketMng {
u.notify(
original_state.to_unit_active_state(),
state.to_unit_active_state(),
- UnitNotifyFlags::UNIT_NOTIFY_RELOAD_FAILURE,
+ UnitNotifyFlags::RELOAD_FAILURE,
)
}
}
diff --git a/coms/target/src/mng.rs b/coms/target/src/mng.rs
index 039fa9e..dc52339 100644
--- a/coms/target/src/mng.rs
+++ b/coms/target/src/mng.rs
@@ -112,7 +112,7 @@ impl TargetMng {
unit.notify(
old_unit_state,
new_unit_state,
- UnitNotifyFlags::UNIT_NOTIFY_RELOAD_FAILURE,
+ UnitNotifyFlags::RELOAD_FAILURE,
);
self.db_update();
diff --git a/core/bin/job/entry.rs b/core/bin/job/entry.rs
index 54af665..81f443a 100755
--- a/core/bin/job/entry.rs
+++ b/core/bin/job/entry.rs
@@ -621,7 +621,7 @@ fn job_process_unit_reload(
flags: UnitNotifyFlags,
) -> (Option<JobResult>, bool) {
let mut result = JobResult::Done;
- if flags.intersects(UnitNotifyFlags::UNIT_NOTIFY_RELOAD_FAILURE) {
+ if flags.intersects(UnitNotifyFlags::RELOAD_FAILURE) {
result = JobResult::Failed;
}
match ns {
diff --git a/core/bin/job/manager.rs b/core/bin/job/manager.rs
index e8eee8b..028c4d5 100755
--- a/core/bin/job/manager.rs
+++ b/core/bin/job/manager.rs
@@ -268,7 +268,6 @@ impl Source for JobManagerData {
fn dispatch(&self, _event: &Events) -> i32 {
log::debug!("job manager data dispatch");
-
self.reli.set_last_frame1(ReliLastFrame::JobManager as u32);
self.run(None);
self.reli.clear_last_frame();
@@ -728,7 +727,7 @@ impl JobManagerData {
) {
// OnFailure=
if ns != os
- && !flags.intersects(UnitNotifyFlags::UNIT_NOTIFY_WILL_AUTO_RESTART)
+ && !flags.intersects(UnitNotifyFlags::WILL_AUTO_RESTART)
&& ns == UnitActiveState::UnitFailed
{
let job_mode = unit
@@ -746,7 +745,7 @@ impl JobManagerData {
// OnSuccess=
if ns == UnitActiveState::UnitInActive
- && !flags.intersects(UnitNotifyFlags::UNIT_NOTIFY_WILL_AUTO_RESTART)
+ && !flags.intersects(UnitNotifyFlags::WILL_AUTO_RESTART)
{
match os {
UnitActiveState::UnitFailed
diff --git a/core/bin/unit/data/table.rs b/core/bin/unit/data/table.rs
index cfacf80..480a026 100644
--- a/core/bin/unit/data/table.rs
+++ b/core/bin/unit/data/table.rs
@@ -178,7 +178,7 @@ mod tests {
let dm = DataManager::new();
let os = UnitActiveState::UnitInActive;
let ns = UnitActiveState::UnitActive;
- let flags = UnitNotifyFlags::UNIT_NOTIFY_RELOAD_FAILURE;
+ let flags = UnitNotifyFlags::RELOAD_FAILURE;
let us_sub = Rc::new(UnitStatesTest::new(ns));
let old = dm.insert_unit_state(String::from("test"), UnitState::new(os, ns, flags));
diff --git a/core/bin/unit/entry/uentry.rs b/core/bin/unit/entry/uentry.rs
index a22ad10..307240b 100644
--- a/core/bin/unit/entry/uentry.rs
+++ b/core/bin/unit/entry/uentry.rs
@@ -694,11 +694,7 @@ impl Unit {
Ok(_) => Ok(()),
Err(e) => match e {
Error::UnitActionEOpNotSupp => {
- self.notify(
- active_state,
- active_state,
- UnitNotifyFlags::UNIT_NOTIFY_SUCCESS,
- );
+ self.notify(active_state, active_state, UnitNotifyFlags::EMPTY);
Ok(())
}
_ => Err(e),
diff --git a/core/bin/unit/manager.rs b/core/bin/unit/manager.rs
index 6e83240..d5c3e10 100644
--- a/core/bin/unit/manager.rs
+++ b/core/bin/unit/manager.rs
@@ -1051,7 +1051,6 @@ impl UnitManager {
if let Err(_e) = self.jm.try_finish(&unitx, state.os, state.ns, state.flags) {
// debug
}
-
let atom = UnitRelationAtom::UnitAtomTriggeredBy;
for other in self.db.dep_gets_atom(&unitx, atom) {
other.trigger(&unitx);
diff --git a/core/lib/unit/state.rs b/core/lib/unit/state.rs
index d5e204a..1ae747b 100644
--- a/core/lib/unit/state.rs
+++ b/core/lib/unit/state.rs
@@ -102,12 +102,12 @@ impl std::fmt::Display for UnitActiveState {
bitflags! {
/// notify unit state to manager
pub struct UnitNotifyFlags: u8 {
- /// the default flags propagate to jobs, it meas nothing.
- const UNIT_NOTIFY_SUCCESS = 0;
+ /// the default flags propagate to jobs, it means nothing.
+ const EMPTY = 0;
/// notify that the unit running reload failure
- const UNIT_NOTIFY_RELOAD_FAILURE = 1 << 0;
+ const RELOAD_FAILURE = 1 << 0;
/// notify that the unit is in auto restart state
- const UNIT_NOTIFY_WILL_AUTO_RESTART = 1 << 1;
+ const WILL_AUTO_RESTART = 1 << 1;
}
}
--
2.30.2

View File

@ -0,0 +1,141 @@
From 95ccf8bc7738d23844411a3770d95dd702cdabb1 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Thu, 1 Jun 2023 15:37:11 +0800
Subject: [PATCH] refactor: use UnixStream instead TcpListener to get the
message from sctl
---
core/bin/manager/commands.rs | 37 ++++++++++++++++++++++++++----------
exts/sctl/Cargo.toml | 1 +
exts/sctl/src/main.rs | 15 ++++-----------
libs/constants/src/lib.rs | 3 +++
4 files changed, 35 insertions(+), 21 deletions(-)
diff --git a/core/bin/manager/commands.rs b/core/bin/manager/commands.rs
index d6ef907..1279206 100644
--- a/core/bin/manager/commands.rs
+++ b/core/bin/manager/commands.rs
@@ -13,32 +13,49 @@
use cmdproto::proto::execute::ExecuterAction;
use cmdproto::proto::ProstServerStream;
use event::{EventType, Events, Source};
-use std::net::{SocketAddr, TcpListener};
+use nix::sys::{socket, stat};
use std::os::unix::io::RawFd;
+use std::path::Path;
use std::{os::unix::prelude::AsRawFd, rc::Rc};
use sysmaster::rel::{ReliLastFrame, Reliability};
+use constants::SCTL_SOCKET;
+
pub(super) struct Commands<T> {
// associated objects
reli: Rc<Reliability>,
command_action: Rc<T>,
// owned objects
- fd: TcpListener,
+ socket_fd: i32,
}
impl<T> Commands<T> {
pub(super) fn new(relir: &Rc<Reliability>, comm_action: T) -> Self {
- let addrs = [
- SocketAddr::from(([127, 0, 0, 1], 9526)),
- SocketAddr::from(([127, 0, 0, 1], 9527)),
- ];
- let fd = TcpListener::bind(&addrs[..]).unwrap();
- fd.set_nonblocking(true).expect("set non-blocking");
+ let sctl_socket_path = Path::new(SCTL_SOCKET);
+ /* remove the old socket if it exists */
+ if sctl_socket_path.exists() && !sctl_socket_path.is_symlink() {
+ let _ = std::fs::remove_file(sctl_socket_path);
+ }
+ let sctl_socket_addr = socket::UnixAddr::new(Path::new(SCTL_SOCKET)).unwrap();
+ let socket_fd = socket::socket(
+ socket::AddressFamily::Unix,
+ socket::SockType::Stream,
+ socket::SockFlag::empty(),
+ None,
+ )
+ .unwrap();
+ /* create the socket with mode 666 */
+ let old_mask = stat::umask(stat::Mode::from_bits_truncate(!0o666));
+ let _ = socket::bind(socket_fd, &sctl_socket_addr);
+ /* restore our umask */
+ let _ = stat::umask(old_mask);
+ /* Allow at most 10 incomming connections can queue */
+ let _ = socket::listen(socket_fd, 10);
Commands {
reli: Rc::clone(relir),
command_action: Rc::new(comm_action),
- fd,
+ socket_fd,
}
}
}
@@ -83,7 +100,7 @@ where
}
fn fd(&self) -> RawFd {
- self.fd.as_raw_fd()
+ self.socket_fd.as_raw_fd()
}
fn priority(&self) -> i8 {
diff --git a/exts/sctl/Cargo.toml b/exts/sctl/Cargo.toml
index 775bc85..b0c0bfc 100644
--- a/exts/sctl/Cargo.toml
+++ b/exts/sctl/Cargo.toml
@@ -10,3 +10,4 @@ clap = { version = "3.1.8", features = ["derive"] }
cmdproto = { path = "../../libs/cmdproto" }
basic = { path = "../../libs/basic" }
nix = "0.24"
+constants = { version = "0.1.0", path = "../../libs/constants" }
diff --git a/exts/sctl/src/main.rs b/exts/sctl/src/main.rs
index ef360c7..c6d9281 100644
--- a/exts/sctl/src/main.rs
+++ b/exts/sctl/src/main.rs
@@ -17,11 +17,9 @@ use cmdproto::proto::{
abi::{sys_comm, unit_comm, CommandRequest},
mngr_comm, unit_file, ProstClientStream,
};
-use std::io::Write;
-use std::{
- net::{SocketAddr, TcpStream},
- process::exit,
-};
+use constants::SCTL_SOCKET;
+use std::process::exit;
+use std::{io::Write, os::unix::net::UnixStream};
/// parse program arguments
#[derive(Parser, Debug)]
@@ -195,12 +193,7 @@ fn main() {
Some(v) => v,
};
- let addrs = [
- SocketAddr::from(([127, 0, 0, 1], 9526)),
- SocketAddr::from(([127, 0, 0, 1], 9527)),
- ];
-
- let stream = match TcpStream::connect(&addrs[..]) {
+ let stream = match UnixStream::connect(SCTL_SOCKET) {
Err(e) => {
eprintln!("Failed to connect to sysmaster: {}", e);
exit(e.raw_os_error().unwrap() as i32);
diff --git a/libs/constants/src/lib.rs b/libs/constants/src/lib.rs
index bd3fba2..7c918aa 100644
--- a/libs/constants/src/lib.rs
+++ b/libs/constants/src/lib.rs
@@ -25,3 +25,6 @@ pub const SIG_SWITCH_ROOT_OFFSET: i32 = 10;
pub const INIT_SOCKET: &str = "/run/sysmaster/init";
/// sysmaster send this to init to keep alive
pub const ALIVE: &str = "ALIVE01234567890";
+
+/// Socket used to transfer message between sysmaster and sctl
+pub const SCTL_SOCKET: &str = "/run/sysmaster/sctl";
--
2.30.2

View File

@ -0,0 +1,25 @@
From e5368bb7b9c2681f802993f0225e832d5e647b70 Mon Sep 17 00:00:00 2001
From: licunlong <licunlong1@huawei.com>
Date: Fri, 2 Jun 2023 14:11:24 +0800
Subject: [PATCH] typo: fix some typoes, no functional change
---
core/bin/manager/commands.rs | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/core/bin/manager/commands.rs b/core/bin/manager/commands.rs
index a8320e2..5eeb927 100644
--- a/core/bin/manager/commands.rs
+++ b/core/bin/manager/commands.rs
@@ -50,7 +50,7 @@ impl<T> Commands<T> {
let _ = socket::bind(socket_fd, &sctl_socket_addr);
/* restore our umask */
let _ = stat::umask(old_mask);
- /* Allow at most 10 incomming connections can queue */
+ /* Allow at most 10 incoming connections can queue */
let _ = socket::listen(socket_fd, 10);
Commands {
reli: Rc::clone(relir),
--
2.30.2

View File

@ -11,14 +11,40 @@
Name: sysmaster
Version: 0.2.3
Release: 2
Release: 3
Summary: redesign and reimplement process1.
License: Mulan PSL v2
URL: https://gitee.com/openeuler/sysmaster
Source0: %{name}-%{version}.tar.gz
Patch0001: backport-fix-compatible-with-rustc-1.60.patch
Patch6000: backport-fix-check-if-the-returned-state-is-None.patch
Patch6001: backport-fix-unwatch-all-pids-when-the-service-enters-dead.patch
Patch6002: backport-fix-only-remove-one-unit-s-pid-from-db-PR-568-remove.patch
# Patch6003-Patch6011: https://gitee.com/openeuler/sysmaster/pulls/585
Patch6003: backport-fix-remove-some-debug-message-no-functional-change.patch
Patch6004: backport-refactor-rename-UNitNotifyFlags-to-shorten-code-a-bi.patch
Patch6005: backport-feature-add-as_any-to-SubUnit-so-we-can-downcast-Sub.patch
Patch6006: backport-fix-move-RefCell-to-the-inside-of-Table-no-functiona.patch
Patch6007: backport-fix-add-has_source-to-events-and-use-this-in-socket..patch
Patch6008: backport-fix-change-if-port.fd-is-valid-we-should-avoid-deali.patch
Patch6009: backport-fix-enable-trigger-for-socket-and-use-this-interface.patch
Patch6010: backport-fix-change-the-socket-logic-to-keep-the-same-as-syst.patch
Patch6011: backport-fix-fix-some-cargo-clippies.patch
Patch6012: backport-fix-compatible-with-rustc-1.60.patch
Patch6013: backport-fix-compatible-with-rusc-1.60-lint-check.patch
#Patch6014-Patch6016: https://gitee.com/openeuler/sysmaster/pulls/598
Patch6014: backport-refactor-use-UnixStream-instead-TcpListener-to-get-t.patch
Patch6015: backport-feature-get-credential-from-the-connection-and-use-i.patch
Patch6016: backport-typo-fix-some-typoes-no-functional-change.patch
Patch6017: backport-fix-fstab-use-fixed-inotify-version-0.10.0-to-be-com.patch
Patch6018: backport-fix-don-t-mount-all-subsystem-to-every-sys-fs-cgroup.patch
Patch6019: backport-fix-check-if-the-given-unit-name-is-valid-before-we-.patch
Patch6020: backport-fix-really-use-usec.patch
Patch6021: backport-docs-note-that-we-only-support-no-more-than-500-unit.patch
ExclusiveArch: x86_64 aarch64
@ -73,6 +99,9 @@ install -Dm0640 -t %{sysmaster_install_target}/plugin %{conf_install_source}/plu
/usr/lib/sysmaster/*
%changelog
* Fri Jun 16 2023 licunlong<licunlong1@huawei.com> - 0.2.3-3
- sync patches from upstream
* Tue May 30 2023 shenyangyang<shenyangyang4@huawei.com> - 0.2.3-2
- Support compatible compile with rust 1.60