Skip to content
项目
群组
代码片段
帮助
当前项目
正在载入...
登录 / 注册
切换导航面板
R
RoboPLC
项目
项目
详情
活动
周期分析
仓库
仓库
文件
提交
分支
标签
贡献者
图表
比较
统计图
议题
0
议题
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
CI / CD
CI / CD
流水线
作业
日程
统计图
Wiki
Wiki
代码片段
代码片段
成员
成员
折叠边栏
关闭边栏
活动
图像
聊天
创建新问题
作业
提交
问题看板
Open sidebar
黄新宇
RoboPLC
Commits
95eb55b6
提交
95eb55b6
authored
7月 14, 2024
作者:
Serhij S
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
added missing docs
上级
2bb1cb92
隐藏空白字符变更
内嵌
并排
正在显示
16 个修改的文件
包含
132 行增加
和
4 行删除
+132
-4
mod.rs
src/comm/mod.rs
+19
-2
serial.rs
src/comm/serial.rs
+10
-0
tcp.rs
src/comm/tcp.rs
+2
-0
controller.rs
src/controller.rs
+9
-1
hub.rs
src/hub.rs
+7
-0
hub_async.rs
src/hub_async.rs
+6
-0
eapi.rs
src/io/eapi.rs
+8
-0
mod.rs
src/io/mod.rs
+5
-0
mod.rs
src/io/modbus/mod.rs
+6
-0
regs.rs
src/io/modbus/regs.rs
+7
-0
server.rs
src/io/modbus/server.rs
+6
-0
pipe.rs
src/io/pipe.rs
+10
-0
raw_udp.rs
src/io/raw_udp.rs
+3
-0
lib.rs
src/lib.rs
+8
-1
supervisor.rs
src/supervisor.rs
+4
-0
thread_rt.rs
src/thread_rt.rs
+22
-0
没有找到文件。
src/comm/mod.rs
浏览文件 @
95eb55b6
...
...
@@ -9,8 +9,10 @@ use std::{
use
crate
::
Result
;
pub
mod
serial
;
// Serial communications
pub
mod
tcp
;
// TCP communications
/// Serial communications
pub
mod
serial
;
/// TCP communications
pub
mod
tcp
;
/// A versatile (TCP/serial) client
#[derive(Clone)]
...
...
@@ -83,12 +85,14 @@ impl Write for Client {
}
}
/// A guard for the session lock
pub
struct
SessionGuard
{
client
:
Client
,
session_id
:
usize
,
}
impl
SessionGuard
{
/// Get the session id
pub
fn
session_id
(
&
self
)
->
usize
{
self
.session_id
}
...
...
@@ -100,11 +104,15 @@ impl Drop for SessionGuard {
}
}
/// Communication protocol
pub
enum
Protocol
{
/// TCP
Tcp
,
/// Serial
Serial
,
}
/// Stream trait
pub
trait
Stream
:
Read
+
Write
+
Send
{}
trait
Communicator
{
...
...
@@ -122,12 +130,14 @@ trait Communicator {
fn
unlock_session
(
&
self
);
}
/// A communication reader container (used to pass the reader via policy channels)
#[allow(clippy
::
module_name_repetitions)]
pub
struct
CommReader
{
reader
:
Option
<
Box
<
dyn
Read
+
Send
+
'static
>>
,
}
impl
CommReader
{
/// Take reader from the container
pub
fn
take
(
&
mut
self
)
->
Option
<
Box
<
dyn
Read
+
Send
+
'static
>>
{
self
.reader
.take
()
}
...
...
@@ -137,10 +147,14 @@ impl DataDeliveryPolicy for CommReader {}
const
DEFAULT_TIMEOUT
:
Duration
=
Duration
::
from_secs
(
1
);
/// Timeouts
#[derive(Clone)]
pub
struct
Timeouts
{
/// Connect timeout
pub
connect
:
Duration
,
/// Read timeout
pub
read
:
Duration
,
/// Write timeout
pub
write
:
Duration
,
}
...
...
@@ -151,6 +165,7 @@ impl Default for Timeouts {
}
impl
Timeouts
{
/// Create new timeouts with the default value
pub
fn
new
(
default
:
Duration
)
->
Self
{
Self
{
connect
:
default
,
...
...
@@ -158,6 +173,7 @@ impl Timeouts {
write
:
default
,
}
}
/// Create new timeouts with zero values
pub
fn
none
()
->
Self
{
Self
{
connect
:
Duration
::
from_secs
(
0
),
...
...
@@ -167,6 +183,7 @@ impl Timeouts {
}
}
/// Connection handler object, used to perform initial chat in custom protocols
pub
trait
ConnectionHandler
{
/// called right after the connection is established
fn
on_connect
(
...
...
src/comm/serial.rs
浏览文件 @
95eb55b6
...
...
@@ -24,12 +24,18 @@ pub fn connect(path: &str, timeout: Duration, frame_delay: Duration) -> Result<C
Ok
(
Client
(
Serial
::
create
(
path
,
timeout
,
frame_delay
)
?
))
}
/// Serial port parameters
#[derive(Debug,
Clone,
Eq,
PartialEq)]
pub
struct
Parameters
{
/// Serial port device path
pub
port_dev
:
String
,
/// Baud rate
pub
baud_rate
:
serial
::
BaudRate
,
/// Character size
pub
char_size
:
serial
::
CharSize
,
/// Parity
pub
parity
:
serial
::
Parity
,
/// Stop bits
pub
stop_bits
:
serial
::
StopBits
,
}
...
...
@@ -111,6 +117,7 @@ fn parse_path(path: &str) -> Result<Parameters> {
})
}
/// Open a serial port
pub
fn
open
(
params
:
&
Parameters
,
timeout
:
Duration
)
->
Result
<
SystemPort
>
{
let
mut
port
=
serial
::
open
(
&
params
.port_dev
)
.map_err
(
Error
::
io
)
?
;
port
.reconfigure
(
&
|
settings
|
{
...
...
@@ -128,6 +135,7 @@ pub fn open(params: &Parameters, timeout: Duration) -> Result<SystemPort> {
Ok
(
port
)
}
/// Serial port client
#[allow(clippy
::
module_name_repetitions)]
pub
struct
Serial
{
port
:
Mutex
<
SPort
>
,
...
...
@@ -145,6 +153,7 @@ struct SPort {
last_frame
:
Option
<
Instant
>
,
}
/// Serial port client type
#[allow(clippy
::
module_name_repetitions)]
pub
type
SerialClient
=
Arc
<
Serial
>
;
...
...
@@ -218,6 +227,7 @@ impl Communicator for Serial {
}
impl
Serial
{
/// Create a new serial client
pub
fn
create
(
path
:
&
str
,
timeout
:
Duration
,
frame_delay
:
Duration
)
->
Result
<
Arc
<
Self
>>
{
let
params
=
parse_path
(
path
)
?
;
Ok
(
Self
{
...
...
src/comm/tcp.rs
浏览文件 @
95eb55b6
...
...
@@ -38,6 +38,7 @@ pub fn connect_with_options<A: ToSocketAddrs + fmt::Debug>(
impl
Stream
for
TcpStream
{}
/// A TCP client structure
#[allow(clippy
::
module_name_repetitions)]
pub
struct
Tcp
{
addr
:
SocketAddr
,
...
...
@@ -50,6 +51,7 @@ pub struct Tcp {
connection_handler
:
Option
<
Box
<
dyn
ConnectionHandler
+
Send
+
Sync
>>
,
}
/// A TCP client type
#[allow(clippy
::
module_name_repetitions)]
pub
type
TcpClient
=
Arc
<
Tcp
>
;
...
...
src/controller.rs
浏览文件 @
95eb55b6
...
...
@@ -23,6 +23,7 @@ use signal_hook::{
};
use
tracing
::
error
;
/// Controller prelude
pub
mod
prelude
{
pub
use
super
::{
Context
,
Controller
,
WResult
,
Worker
,
WorkerOptions
};
pub
use
roboplc_derive
::
WorkerOpts
;
...
...
@@ -31,6 +32,7 @@ pub mod prelude {
/// Result type, which must be returned by workers' `run` method
pub
type
WResult
=
std
::
result
::
Result
<
(),
Box
<
dyn
std
::
error
::
Error
+
Send
+
Sync
>>
;
/// Sleep step (used in blocking)
pub
const
SLEEP_STEP
:
Duration
=
Duration
::
from_millis
(
100
);
/// Controller state beacon. Can be cloned and shared with no limitations.
...
...
@@ -40,7 +42,7 @@ pub struct State {
}
impl
State
{
pub
fn
new
()
->
Self
{
fn
new
()
->
Self
{
Self
{
state
:
AtomicI8
::
new
(
ControllerStateKind
::
Starting
as
i8
)
.into
(),
}
...
...
@@ -71,11 +73,17 @@ impl Default for State {
#[allow(clippy
::
module_name_repetitions)]
pub
enum
ControllerStateKind
{
#[default]
/// The controller is starting
Starting
=
0
,
/// The controller is active (accepting tasks)
Active
=
1
,
/// The controller is running (tasks are being executed)
Running
=
2
,
/// The controller is stopping
Stopping
=
-
1
,
/// The controller is stopped
Stopped
=
-
100
,
/// The controller state is unknown
Unknown
=
-
128
,
}
...
...
src/hub.rs
浏览文件 @
95eb55b6
...
...
@@ -10,6 +10,7 @@ use self::prelude::DataChannel;
type
ConditionFunction
<
T
>
=
Box
<
dyn
Fn
(
&
T
)
->
bool
+
Send
+
Sync
>
;
/// The hub prelude
pub
mod
prelude
{
pub
use
super
::
Hub
;
pub
use
crate
::
event_matches
;
...
...
@@ -17,8 +18,10 @@ pub mod prelude {
pub
use
rtsc
::
DataChannel
;
}
/// The default priority for the client channel
pub
const
DEFAULT_PRIORITY
:
usize
=
100
;
/// The default client channel capacity
pub
const
DEFAULT_CHANNEL_CAPACITY
:
usize
=
1024
;
/// Sync data communcation hub to implement in-process pub/sub model for thread workers
...
...
@@ -43,6 +46,7 @@ impl<T: DataDeliveryPolicy + Clone> Default for Hub<T> {
}
impl
<
T
:
DataDeliveryPolicy
+
Clone
>
Hub
<
T
>
{
/// Creates a new hub with default settings
pub
fn
new
()
->
Self
{
Self
::
default
()
}
...
...
@@ -238,6 +242,7 @@ where
}
}
/// A client for the hub
pub
struct
Client
<
T
:
DataDeliveryPolicy
+
Clone
>
{
name
:
Arc
<
str
>
,
hub
:
Hub
<
T
>
,
...
...
@@ -285,6 +290,7 @@ impl<T: DataDeliveryPolicy + Clone> Drop for Client<T> {
}
}
/// Client options
pub
struct
ClientOptions
<
T
:
DataDeliveryPolicy
+
Clone
>
{
name
:
Arc
<
str
>
,
priority
:
usize
,
...
...
@@ -294,6 +300,7 @@ pub struct ClientOptions<T: DataDeliveryPolicy + Clone> {
}
impl
<
T
:
DataDeliveryPolicy
+
Clone
>
ClientOptions
<
T
>
{
/// Creates a new client options object
pub
fn
new
<
F
>
(
name
:
&
str
,
condition
:
F
)
->
Self
where
F
:
Fn
(
&
T
)
->
bool
+
Send
+
Sync
+
'static
,
...
...
src/hub_async.rs
浏览文件 @
95eb55b6
...
...
@@ -8,8 +8,10 @@ use crate::{DataDeliveryPolicy, Error, Result};
type
ConditionFunction
<
T
>
=
Box
<
dyn
Fn
(
&
T
)
->
bool
+
Send
+
Sync
>
;
/// The default priority for the client channel
pub
const
DEFAULT_PRIORITY
:
usize
=
100
;
/// The default client channel capacity
pub
const
DEFAULT_CHANNEL_CAPACITY
:
usize
=
1024
;
/// Async data communcation hub to implement in-process pub/sub model for thread workers
...
...
@@ -34,6 +36,7 @@ impl<T: DataDeliveryPolicy + Clone> Default for Hub<T> {
}
impl
<
T
:
DataDeliveryPolicy
+
Clone
>
Hub
<
T
>
{
/// Creates a new hub instance
pub
fn
new
()
->
Self
{
Self
::
default
()
}
...
...
@@ -191,6 +194,7 @@ where
}
}
/// A client for the hub
pub
struct
Client
<
T
:
DataDeliveryPolicy
+
Clone
>
{
name
:
Arc
<
str
>
,
hub
:
Hub
<
T
>
,
...
...
@@ -232,6 +236,7 @@ impl<T: DataDeliveryPolicy + Clone> Drop for Client<T> {
}
}
/// Client options
pub
struct
ClientOptions
<
T
:
DataDeliveryPolicy
+
Clone
>
{
name
:
Arc
<
str
>
,
priority
:
usize
,
...
...
@@ -241,6 +246,7 @@ pub struct ClientOptions<T: DataDeliveryPolicy + Clone> {
}
impl
<
T
:
DataDeliveryPolicy
+
Clone
>
ClientOptions
<
T
>
{
/// Creates a new client options object
pub
fn
new
<
F
>
(
name
:
&
str
,
condition
:
F
)
->
Self
where
F
:
Fn
(
&
T
)
->
bool
+
Send
+
Sync
+
'static
,
...
...
src/io/eapi.rs
浏览文件 @
95eb55b6
...
...
@@ -103,6 +103,7 @@ where
}
config
}
/// Creates a new EAPI connection configuration with the given path
pub
fn
new
(
path
:
&
str
)
->
Self
{
Self
{
path
:
path
.to_owned
(),
...
...
@@ -140,10 +141,12 @@ where
self
.reconnect_delay
=
reconnect_delay
;
self
}
/// Set action handler for the given OID
pub
fn
action_handler
(
mut
self
,
oid
:
OID
,
handler
:
ActionHandlerFn
<
D
,
V
>
)
->
Self
{
self
.action_handlers
.insert
(
oid
,
handler
);
self
}
/// Set bulk action handler for the given OID mask
pub
fn
bulk_action_handler
(
mut
self
,
mask
:
OIDMask
,
handler
:
ActionHandlerFn
<
D
,
V
>
)
->
Self
{
self
.bulk_action_handlers
.push
((
mask
,
handler
));
self
...
...
@@ -467,6 +470,7 @@ where
warn!
(
client
=
self
.inner.name
,
"disconnected from EAPI bus"
);
Ok
(())
}
/// Pushes a data object to the EVA ICS node core
pub
fn
dobj_push
<
T
>
(
&
self
,
name
:
Arc
<
String
>
,
value
:
T
)
->
Result
<
()
>
where
T
:
for
<
'a
>
BinWrite
<
Args
<
'a
>
=
()
>
,
...
...
@@ -481,12 +485,14 @@ where
})
.map_err
(
Into
::
into
)
}
/// Pushes a data object error to the EVA ICS node core
pub
fn
dobj_error
(
&
self
,
name
:
Arc
<
String
>
)
->
Result
<
()
>
{
self
.inner
.tx
.try_send
(
PushPayload
::
DObjError
(
name
))
.map_err
(
Into
::
into
)
}
/// Pushes a state event to the EVA ICS node core
pub
fn
state_push
<
T
:
Serialize
>
(
&
self
,
oid
:
Arc
<
OID
>
,
value
:
T
)
->
Result
<
()
>
{
self
.inner
.tx
...
...
@@ -496,12 +502,14 @@ where
})
.map_err
(
Into
::
into
)
}
/// Pushes a custom (raw) state event to the EVA ICS node core
pub
fn
raw_state_push
(
&
self
,
oid
:
Arc
<
OID
>
,
event
:
RawStateEventOwned
)
->
Result
<
()
>
{
self
.inner
.tx
.try_send
(
PushPayload
::
State
{
oid
,
event
})
.map_err
(
Into
::
into
)
}
/// Pushes a state error event to the EVA ICS node core
pub
fn
state_error
(
&
self
,
oid
:
Arc
<
OID
>
)
->
Result
<
()
>
{
self
.inner
.tx
...
...
src/io/mod.rs
浏览文件 @
95eb55b6
...
...
@@ -19,17 +19,22 @@ pub mod pipe;
/// Raw UDP communication
pub
mod
raw_udp
;
/// Generic I/O mapping trait
#[allow(clippy
::
module_name_repetitions)]
pub
trait
IoMapping
{
/// Options for the mapping
type
Options
;
/// Read data from the raw buffer
fn
read
<
T
>
(
&
mut
self
)
->
Result
<
T
>
where
T
:
for
<
'a
>
BinRead
<
Args
<
'a
>
=
()
>
;
/// Write data to the raw buffer
fn
write
<
T
>
(
&
mut
self
,
value
:
T
)
->
Result
<
()
>
where
T
:
for
<
'a
>
BinWrite
<
Args
<
'a
>
=
()
>
;
}
/// I/O mapping prelude
pub
mod
prelude
{
pub
use
super
::
IoMapping
as
_
;
pub
use
binrw
::
prelude
::
*
;
...
...
src/io/modbus/mod.rs
浏览文件 @
95eb55b6
...
...
@@ -26,6 +26,7 @@ use super::IoMapping;
mod
regs
;
mod
server
;
/// Modbus prelude
pub
mod
prelude
{
pub
use
super
::{
ModbusMapping
,
ModbusMappingOptions
,
ModbusRegister
,
ModbusRegisterKind
,
ModbusServer
,
...
...
@@ -35,6 +36,7 @@ pub mod prelude {
/// Swaps endianess of floating point numbers in case of non-standard IEEE 754 layout.
pub
trait
SwapModbusEndianess
{
/// Swaps endianess of floating point numbers in case of non-standard IEEE 754 layout.
fn
to_swapped_modbus_endianness
(
&
self
)
->
Self
;
}
...
...
@@ -69,9 +71,11 @@ pub struct ModbusMappingOptions {
}
impl
ModbusMappingOptions
{
/// Creates new options for Modbus value mapping
pub
fn
new
()
->
Self
{
Self
{
bulk_write
:
true
}
}
/// Enables or disables bulk writes
pub
fn
bulk_write
(
mut
self
,
value
:
bool
)
->
Self
{
self
.bulk_write
=
value
;
self
...
...
@@ -99,6 +103,7 @@ pub struct ModbusMapping {
}
impl
ModbusMapping
{
/// Creates new Modbus value mapping
pub
fn
create
<
R
>
(
client
:
&
Client
,
unit_id
:
u8
,
register
:
R
,
count
:
u16
)
->
Result
<
Self
>
where
R
:
TryInto
<
ModbusRegister
>
,
...
...
@@ -117,6 +122,7 @@ impl ModbusMapping {
options
:
<
_
>
::
default
(),
})
}
/// Sets options for Modbus value mapping
pub
fn
with_options
(
mut
self
,
options
:
ModbusMappingOptions
)
->
Self
{
self
.options
=
options
;
self
...
...
src/io/modbus/regs.rs
浏览文件 @
95eb55b6
...
...
@@ -5,20 +5,27 @@ use crate::{Error, Result};
/// A Modbus register kind.
#[derive(Eq,
PartialEq,
Copy,
Clone,
Debug)]
pub
enum
Kind
{
/// Coil register (boolean)
Coil
,
/// Discrete register (boolean)
Discrete
,
/// Input register (16-bit)
Input
,
/// Holding register (16-bit)
Holding
,
}
/// A Modbus register type, contains the kind and the offset.
#[derive(Debug,
Clone,
Copy,
Eq,
PartialEq)]
pub
struct
Register
{
/// The register kind.
pub
kind
:
Kind
,
/// The register offset.
pub
offset
:
u16
,
}
impl
Register
{
/// Creates a new register.
pub
fn
new
(
kind
:
Kind
,
offset
:
u16
)
->
Self
{
Self
{
kind
,
offset
}
}
...
...
src/io/modbus/server.rs
浏览文件 @
95eb55b6
...
...
@@ -88,8 +88,10 @@ fn handle_client<
Ok
(())
}
/// Function to block certain context storage
pub
type
AllowFn
=
fn
(
ModbusRegisterKind
,
std
::
ops
::
Range
<
u16
>
)
->
WritePermission
;
/// Context storage write permission
pub
enum
WritePermission
{
/// Write is allowed.
Allow
,
...
...
@@ -126,6 +128,7 @@ pub struct ModbusServer<const C: usize, const D: usize, const I: usize, const H:
allow_external_write_fn
:
Arc
<
AllowFn
>
,
}
impl
<
const
C
:
usize
,
const
D
:
usize
,
const
I
:
usize
,
const
H
:
usize
>
ModbusServer
<
C
,
D
,
I
,
H
>
{
/// Creates new Modbus server
pub
fn
bind
(
protocol
:
Protocol
,
unit
:
u8
,
...
...
@@ -152,6 +155,7 @@ impl<const C: usize, const D: usize, const I: usize, const H: usize> ModbusServe
pub
fn
set_allow_external_write_fn
(
&
mut
self
,
f
:
AllowFn
)
{
self
.allow_external_write_fn
=
f
.into
();
}
/// Creates a new mapping for the server storage context.
pub
fn
mapping
(
&
self
,
register
:
ModbusRegister
,
count
:
u16
)
->
ModbusServerMapping
<
C
,
D
,
I
,
H
>
{
let
buf_capacity
=
match
register
.kind
{
ModbusRegisterKind
::
Coil
|
ModbusRegisterKind
::
Discrete
=>
usize
::
from
(
count
),
...
...
@@ -164,9 +168,11 @@ impl<const C: usize, const D: usize, const I: usize, const H: usize> ModbusServe
data_buf
:
Vec
::
with_capacity
(
buf_capacity
),
}
}
/// Returns a reference to the internal storage.
pub
fn
storage
(
&
self
)
->
Arc
<
Mutex
<
ModbusStorage
<
C
,
D
,
I
,
H
>>>
{
self
.storage
.clone
()
}
/// Runs the server. This function blocks the current thread.
pub
fn
serve
(
&
mut
self
)
->
Result
<
()
>
{
let
timeout
=
self
.timeout
;
let
unit
=
self
.unit
;
...
...
src/io/pipe.rs
浏览文件 @
95eb55b6
//! Data processing with subprocesses
use
std
::{
collections
::
BTreeMap
,
ffi
::{
OsStr
,
OsString
},
...
...
@@ -17,16 +18,19 @@ use crate::{
DataDeliveryPolicy
,
Result
,
};
/// Pipe reader
pub
struct
Reader
{
rx
:
Receiver
<
String
>
,
}
impl
Reader
{
/// Reads a line from the pipe. Blocks until a line is available.
pub
fn
line
(
&
self
)
->
Result
<
String
>
{
self
.rx
.recv_blocking
()
.map_err
(
Into
::
into
)
}
}
/// Data pipe with a subprocess
pub
struct
Pipe
{
program
:
OsString
,
args
:
Vec
<
OsString
>
,
...
...
@@ -37,6 +41,7 @@ pub struct Pipe {
}
impl
Pipe
{
/// Creates a new pipe with a subprocess
pub
fn
new
<
P
:
AsRef
<
OsStr
>>
(
program
:
P
)
->
(
Self
,
Reader
)
{
let
(
tx
,
rx
)
=
pchannel_async
::
bounded
(
10
);
(
...
...
@@ -51,19 +56,23 @@ impl Pipe {
Reader
{
rx
},
)
}
/// Adds a command line argument
pub
fn
arg
(
&
mut
self
,
arg
:
impl
AsRef
<
OsStr
>
)
->
&
mut
Self
{
self
.args
.push
(
arg
.as_ref
()
.to_owned
());
self
}
/// Adds multiple command line arguments
pub
fn
args
(
&
mut
self
,
args
:
impl
IntoIterator
<
Item
=
impl
AsRef
<
OsStr
>>
)
->
&
mut
Self
{
self
.args
.extend
(
args
.into_iter
()
.map
(|
x
|
x
.as_ref
()
.to_owned
()));
self
}
/// Adds an environment variable
pub
fn
env
(
&
mut
self
,
key
:
impl
Into
<
String
>
,
value
:
impl
Into
<
String
>
)
->
&
mut
Self
{
self
.environment
.insert
(
key
.into
(),
value
.into
());
self
}
/// Adds multiple environment variables
pub
fn
envs
(
&
mut
self
,
envs
:
impl
IntoIterator
<
Item
=
(
impl
Into
<
String
>
,
impl
Into
<
String
>
)
>
,
...
...
@@ -77,6 +86,7 @@ impl Pipe {
self
.input_data
=
Some
(
data
.into
());
self
}
/// Delay before restarting the subprocess after it terminates
pub
fn
restart_delay
(
&
mut
self
,
delay
:
Duration
)
->
&
mut
Self
{
self
.restart_delay
=
delay
;
self
...
...
src/io/raw_udp.rs
浏览文件 @
95eb55b6
...
...
@@ -26,6 +26,7 @@ impl<T> UdpReceiver<T>
where
T
:
for
<
'a
>
BinRead
<
Args
<
'a
>
=
()
>
,
{
/// Binds to the specified address and creates a new receiver
pub
fn
bind
<
A
:
ToSocketAddrs
>
(
addr
:
A
,
buf_size
:
usize
)
->
Result
<
Self
>
{
let
server
=
UdpSocket
::
bind
(
addr
)
?
;
Ok
(
Self
{
...
...
@@ -70,6 +71,7 @@ impl<T> UdpSender<T>
where
T
:
for
<
'a
>
BinWrite
<
Args
<
'a
>
=
()
>
,
{
/// Connects to the specified address and creates a new sender
pub
fn
connect
<
A
:
ToSocketAddrs
>
(
addr
:
A
)
->
Result
<
Self
>
{
let
socket
=
UdpSocket
::
bind
((
"0.0.0.0"
,
0
))
?
;
let
target
=
addr
...
...
@@ -84,6 +86,7 @@ where
})
}
/// Sends a value to the target address
pub
fn
send
(
&
mut
self
,
value
:
T
)
->
Result
<
()
>
{
let
mut
buf
=
Cursor
::
new
(
&
mut
self
.data_buf
);
value
.write_le
(
&
mut
buf
)
?
;
...
...
src/lib.rs
浏览文件 @
95eb55b6
#
!
[
doc
=
include_str!
(
concat!
(
env!
(
"CARGO_MANIFEST_DIR"
),
"/"
,
"README.md"
)
)
]
#
!
[
deny
(
missing_docs
)]
use
core
::{
fmt
,
num
};
use
std
::
io
::
Write
;
use
std
::
panic
::
PanicInfo
;
...
...
@@ -41,6 +42,7 @@ pub mod supervisor;
#[cfg(target_os
=
"linux"
)]
pub
mod
thread_rt
;
/// The crate result type
pub
type
Result
<
T
>
=
std
::
result
::
Result
<
T
,
Error
>
;
/// The crate error type
...
...
@@ -71,7 +73,7 @@ pub enum Error {
/// Standard I/O errors
#[error(
"I/O error: {0}"
)]
IO
(
#
[
from
]
std
::
io
::
Error
),
// Non-standard I/O errors
//
/
Non-standard I/O errors
#[error(
"Communication error: {0}"
)]
Comm
(
String
),
/// 3rd party API errors
...
...
@@ -160,15 +162,19 @@ impl_error!(num::ParseFloatError, InvalidData);
impl_error!
(
binrw
::
Error
,
BinRw
);
impl
Error
{
/// Returns true if the data is skipped
pub
fn
is_data_skipped
(
&
self
)
->
bool
{
matches!
(
self
,
Error
::
ChannelSkipped
)
}
/// Creates new invalid data error
pub
fn
invalid_data
<
S
:
fmt
::
Display
>
(
msg
:
S
)
->
Self
{
Error
::
InvalidData
(
msg
.to_string
())
}
/// Creates new I/O error (for non-standard I/O)
pub
fn
io
<
S
:
fmt
::
Display
>
(
msg
:
S
)
->
Self
{
Error
::
Comm
(
msg
.to_string
())
}
/// Creates new function failed error
pub
fn
failed
<
S
:
fmt
::
Display
>
(
msg
:
S
)
->
Self
{
Error
::
Failed
(
msg
.to_string
())
}
...
...
@@ -266,6 +272,7 @@ pub fn configure_logger(filter: LevelFilter) {
builder
.init
();
}
/// Prelude module
pub
mod
prelude
{
#[cfg(target_os
=
"linux"
)]
pub
use
super
::
suicide
;
...
...
src/supervisor.rs
浏览文件 @
95eb55b6
...
...
@@ -7,6 +7,7 @@ use crate::thread_rt::{Builder, ScopedTask, Task};
use
crate
::
time
::
Interval
;
use
crate
::{
Error
,
Result
};
/// The supervisor prelude
pub
mod
prelude
{
pub
use
super
::
Supervisor
;
pub
use
crate
::
thread_rt
::{
Builder
,
Scheduling
};
...
...
@@ -35,6 +36,7 @@ macro_rules! vacant_entry {
}
impl
<
T
>
Supervisor
<
T
>
{
/// Creates a new supervisor object
pub
fn
new
()
->
Self
{
Self
::
default
()
}
...
...
@@ -101,6 +103,7 @@ impl<T> Supervisor<T> {
}
}
/// A scoped supervisor object
#[allow(clippy
::
module_name_repetitions)]
#[derive(Serialize)]
pub
struct
ScopedSupervisor
<
'a
,
'env
:
'a
,
T
>
{
...
...
@@ -110,6 +113,7 @@ pub struct ScopedSupervisor<'a, 'env: 'a, T> {
}
impl
<
'a
,
'env
,
T
>
ScopedSupervisor
<
'a
,
'env
,
T
>
{
/// Creates a new scoped supervisor object
pub
fn
new
(
scope
:
&
'a
thread
::
Scope
<
'a
,
'env
>
)
->
Self
{
Self
{
tasks
:
<
_
>
::
default
(),
...
...
src/thread_rt.rs
浏览文件 @
95eb55b6
...
...
@@ -85,12 +85,18 @@ pub struct Builder {
#[serde(rename_all
=
"UPPERCASE"
)]
pub
enum
Scheduling
{
#[serde(rename
=
"RR"
)]
/// Round-robin
RoundRobin
,
/// First in, first out
FIFO
,
/// Idle
Idle
,
/// Batch
Batch
,
/// Deadline
DeadLine
,
#[default]
/// Other
Other
,
}
...
...
@@ -134,6 +140,7 @@ impl_builder_from!(&str);
impl_builder_from!
(
String
);
impl
Builder
{
/// Creates a new thread builder
pub
fn
new
()
->
Self
{
Self
::
default
()
}
...
...
@@ -316,9 +323,11 @@ pub struct Task<T> {
}
impl
<
T
>
Task
<
T
>
{
/// Returns the task name
pub
fn
name
(
&
self
)
->
&
str
{
&
self
.name
}
/// Returns the task handle
pub
fn
handle
(
&
self
)
->
&
JoinHandle
<
T
>
{
&
self
.handle
}
...
...
@@ -335,12 +344,15 @@ impl<T> Task<T> {
self
.rt_params
=
rt_params
;
Ok
(())
}
/// Returns true if the task is finished
pub
fn
is_finished
(
&
self
)
->
bool
{
self
.handle
.is_finished
()
}
/// Joins the task
pub
fn
join
(
self
)
->
thread
::
Result
<
T
>
{
self
.handle
.join
()
}
/// Converts the task into a standard [`JoinHandle`]
pub
fn
into_join_handle
(
self
)
->
JoinHandle
<
T
>
{
self
.into
()
}
...
...
@@ -348,6 +360,7 @@ impl<T> Task<T> {
pub
fn
elapsed
(
&
self
)
->
Duration
{
self
.info.started_mt
.elapsed
()
}
/// Returns true if the task is blocking
pub
fn
is_blocking
(
&
self
)
->
bool
{
self
.blocking
}
...
...
@@ -377,9 +390,11 @@ pub struct ScopedTask<'scope, T> {
}
impl
<
'scope
,
T
>
ScopedTask
<
'scope
,
T
>
{
/// Returns the task name
pub
fn
name
(
&
self
)
->
&
str
{
&
self
.name
}
/// Returns the task handle
pub
fn
handle
(
&
self
)
->
&
ScopedJoinHandle
<
T
>
{
&
self
.handle
}
...
...
@@ -396,12 +411,15 @@ impl<'scope, T> ScopedTask<'scope, T> {
self
.rt_params
=
rt_params
;
Ok
(())
}
/// Returns true if the task is finished
pub
fn
is_finished
(
&
self
)
->
bool
{
self
.handle
.is_finished
()
}
/// Joins the task
pub
fn
join
(
self
)
->
thread
::
Result
<
T
>
{
self
.handle
.join
()
}
/// Converts the task into a standard [`ScopedJoinHandle`]
pub
fn
into_join_handle
(
self
)
->
ScopedJoinHandle
<
'scope
,
T
>
{
self
.into
()
}
...
...
@@ -409,6 +427,7 @@ impl<'scope, T> ScopedTask<'scope, T> {
pub
fn
elapsed
(
&
self
)
->
Duration
{
self
.info.started_mt
.elapsed
()
}
/// Returns true if the task is blocking
pub
fn
is_blocking
(
&
self
)
->
bool
{
self
.blocking
}
...
...
@@ -429,6 +448,7 @@ pub struct RTParams {
}
impl
RTParams
{
/// Creates a new real-time parameters object
pub
fn
new
()
->
Self
{
Self
::
default
()
}
...
...
@@ -659,6 +679,7 @@ pub struct SystemConfig {
}
impl
SystemConfig
{
/// Creates a new system config object
pub
fn
new
()
->
Self
{
Self
::
default
()
}
...
...
@@ -681,6 +702,7 @@ impl SystemConfig {
}
}
/// A guard object to restore system parameters when dropped
pub
struct
SystemConfigGuard
{
config
:
SystemConfig
,
}
...
...
编写
预览
Markdown
格式
0%
重试
或
添加新文件
添加附件
取消
您添加了
0
人
到此讨论。请谨慎行事。
请先完成此评论的编辑!
取消
请
注册
或者
登录
后发表评论