diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index ee56d145..29972671 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -18,7 +18,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Rust ${{ matrix.rust }} uses: dtolnay/rust-toolchain@master with: @@ -41,7 +41,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Rust uses: dtolnay/rust-toolchain@master with: @@ -65,7 +65,7 @@ jobs: runs-on: ${{ matrix.os }} steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Rust ${{ matrix.rust }} uses: dtolnay/rust-toolchain@master with: @@ -80,7 +80,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Rust ${{ matrix.rust }} uses: dtolnay/rust-toolchain@stable - name: Install doxygen 1.9.5 @@ -125,7 +125,7 @@ jobs: test: false steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Rust uses: dtolnay/rust-toolchain@master with: @@ -137,9 +137,9 @@ jobs: - name: Create FFI modules DIR run: mkdir ffi-modules\${{ matrix.target }} - name: Build FFI - run: cargo build -p dnp3-ffi --release --target ${{ matrix.target }} --message-format json | Out-File -encoding "UTF8" .\ffi-modules\${{ matrix.target }}\build.jni.log + run: cargo build -p dnp3-ffi --release --target ${{ matrix.target }} - name: Build JNI - run: cargo build -p dnp3-ffi-java --release --target ${{ matrix.target }} --message-format json | Out-File -encoding "UTF8" .\ffi-modules\${{ matrix.target }}\build.jni.log + run: cargo build -p dnp3-ffi-java --release --target ${{ matrix.target }} - name: Copy the FFI and JNI libs shell: pwsh run: | @@ -170,7 +170,7 @@ jobs: - x86_64-apple-darwin # 64-bit macOS (10.7+, Lion+) steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Rust uses: dtolnay/rust-toolchain@stable - name: Caching @@ -179,9 +179,9 @@ jobs: - name: Create FFI modules dir run: mkdir -p ffi-modules/${{ matrix.target }} - name: Build FFI - run: cargo build -p dnp3-ffi --release --message-format json > ffi-modules/${{ matrix.target }}/build.ffi.log + run: cargo build -p dnp3-ffi --release - name: Build JNI - run: cargo build -p dnp3-ffi-java --release --message-format json > ffi-modules/${{ matrix.target }}/build.jni.log + run: cargo build -p dnp3-ffi-java --release - name: Copy the FFI and JNI libs run: | cp ./target/release/libdnp3_ffi.dylib ./ffi-modules/${{ matrix.target }} @@ -218,7 +218,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Rust uses: dtolnay/rust-toolchain@stable with: @@ -231,9 +231,9 @@ jobs: - name: Create FFI modules dir run: mkdir -p ffi-modules/${{ matrix.target }} - name: Build FFI - run: cross build -p dnp3-ffi --release --target ${{ matrix.target }} --message-format json > ffi-modules/${{ matrix.target }}/build.ffi.log + run: cross build -p dnp3-ffi --release --target ${{ matrix.target }} - name: Build JNI - run: cross build -p dnp3-ffi-java --release --target ${{ matrix.target }} --message-format json > ffi-modules/${{ matrix.target }}/build.jni.log + run: cross build -p dnp3-ffi-java --release --target ${{ matrix.target }} - name: Copy the FFI and JNI libs run: | cp ./target/${{ matrix.target }}/release/libdnp3_ffi.so ./ffi-modules/${{ matrix.target }} @@ -247,7 +247,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install dependencies working-directory: guide run: yarn install @@ -269,35 +269,38 @@ jobs: steps: - name: Install Rust uses: dtolnay/rust-toolchain@stable + - name: Install Cargo CycloneDx + run: cargo install cargo-cyclonedx + - name: Install custom allow-list tool + run: cargo install --git https://github.com/stepfunc/bom-tools.git - name: Caching if: ${{ !startsWith(github.ref, 'refs/tags/') }} uses: Swatinem/rust-cache@v2 - - name: Checkout BOM tools repo - uses: actions/checkout@v3 - with: - repository: stepfunc/bom-tools - ref: 0.1.0 - path: bom-tools - - name: Install BOM tools - working-directory: bom-tools - run: cargo install --path bom-tools - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Download compiled FFI uses: actions/download-artifact@v3 with: name: ffi-modules path: ffi-modules + - name: Create SBOMs + run: | + for dir in ffi-modules/*; do + target=`basename "${dir}"` + cargo cyclonedx -f json --target $target + mv ./ffi/dnp3-ffi/dnp3-ffi.cdx.json ffi-modules/$target + mv ./ffi/dnp3-ffi-java/dnp3-ffi-java.cdx.json ffi-modules/$target + done - name: Create FFI third-party-licenses.txt - run: bom-tools gen-licenses-dir ./ffi-modules build.ffi.log ./dep_config.json > third-party-licenses.txt + run: allow-list gen-licenses-dir -l ffi-modules -b dnp3-ffi.cdx.json -c dep_config.json > third-party-licenses.txt + - name: Create FFI third-party-licenses-java.txt + run: allow-list gen-licenses-dir -l ffi-modules -b dnp3-ffi-java.cdx.json -c dep_config.json > third-party-licenses-java.txt - name: Package C/C++ bindings run: cargo run --bin dnp3-bindings -- --c --package ./ffi-modules --options ./packaging.json -f third-party-licenses.txt - name: Package .NET bindings run: cargo run --bin dnp3-bindings -- --dotnet --package ./ffi-modules --options ./packaging.json -f third-party-licenses.txt - - name: Create JNI third-party-licenses.txt - run: bom-tools gen-licenses-dir ./ffi-modules build.jni.log ./dep_config.json > third-party-licenses.txt - name: Package Java bindings - run: cargo run --bin dnp3-bindings -- --java --package ./ffi-modules --options ./packaging.json -f third-party-licenses.txt + run: cargo run --bin dnp3-bindings -- --java --package ./ffi-modules --options ./packaging.json -f third-party-licenses-java.txt - name: Upload C/C++ bindings uses: actions/upload-artifact@v3 with: @@ -323,7 +326,7 @@ jobs: runs-on: ubuntu-latest steps: - name: Checkout - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Rust uses: dtolnay/rust-toolchain@stable - name: Caching @@ -337,7 +340,7 @@ jobs: shell: bash run: (cd ffi/bindings/java/dnp3 && sudo mvn install) - name: Checkout dnp4s - uses: actions/checkout@v3 + uses: actions/checkout@v4 with: repository: stepfunc/dnp4s ssh-key: ${{ secrets.DNP4S_SSH_KEY }} @@ -372,7 +375,7 @@ jobs: cd ../conformance-results zip -r ../../release/conformance-results.zip . - name: Checkout stepfunc/docs - uses: actions/checkout@v3 + uses: actions/checkout@v4 with: repository: stepfunc/docs ssh-key: ${{ secrets.SFIO_DOCS_SSH_KEY }} diff --git a/Cargo.lock b/Cargo.lock index 1bd12e67..5550063b 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1204,9 +1204,9 @@ dependencies = [ [[package]] name = "sfio-tracing-ffi" -version = "0.8.0" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "94955ac2db413b6f32297e862581db2c05f6312881939393f4b68f173a8be8b4" +checksum = "e1be29c84c2a7b298e74b8882c3167818f43e8ce1d73840cd35e2c34e791cf5c" dependencies = [ "oo-bindgen", ] diff --git a/dep_config.json b/dep_config.json index 2b780ca2..06c1763a 100644 --- a/dep_config.json +++ b/dep_config.json @@ -632,6 +632,23 @@ } ] }, + "getrandom": { + "id": "getrandom", + "source": "crates.io", + "authors": null, + "licenses": [ + { + "MIT": { + "copyright": { + "Lines": [ + "Copyright (c) 2018-2024 The rust-random Project Developers", + "Copyright (c) 2014 The Rust Project Developers" + ] + } + } + } + ] + }, "hmac": { "id": "hmac", "source": "crates.io", diff --git a/dnp3/src/app/attr.rs b/dnp3/src/app/attr.rs index a358b6bf..17854390 100644 --- a/dnp3/src/app/attr.rs +++ b/dnp3/src/app/attr.rs @@ -1042,7 +1042,7 @@ impl Display for BadAttribute { pub(crate) enum AttrWriteError { /// underlying cursor error - Cursor(WriteError), + Cursor, /// attribute value could not be encoded BadAttribute(BadAttribute), } @@ -1054,8 +1054,8 @@ impl From for AttrWriteError { } impl From for AttrWriteError { - fn from(err: WriteError) -> Self { - AttrWriteError::Cursor(err) + fn from(_: WriteError) -> Self { + AttrWriteError::Cursor } } @@ -1472,7 +1472,7 @@ impl<'a> Attribute<'a> { impl From for TaskError { fn from(value: AttrWriteError) -> Self { match value { - AttrWriteError::Cursor(_) => TaskError::WriteError, + AttrWriteError::Cursor => TaskError::WriteError, AttrWriteError::BadAttribute(x) => TaskError::BadEncoding(BadEncoding::Attribute(x)), } } diff --git a/dnp3/src/app/extensions.rs b/dnp3/src/app/extensions.rs index 9bd7707d..bac26f25 100644 --- a/dnp3/src/app/extensions.rs +++ b/dnp3/src/app/extensions.rs @@ -1,5 +1,4 @@ use crate::app::control::*; -use crate::app::measurement::Flags; use crate::app::measurement::*; use crate::app::{FunctionCode, QualifierCode}; use crate::util::bit::bits::{BIT_6, BIT_7}; diff --git a/dnp3/src/app/parse/traits.rs b/dnp3/src/app/parse/traits.rs index fe4a8654..3930d669 100644 --- a/dnp3/src/app/parse/traits.rs +++ b/dnp3/src/app/parse/traits.rs @@ -20,10 +20,6 @@ pub(crate) trait Index: Copy + Clone + FixedSize + PartialEq + Display { fn next(self) -> Self; fn widen_to_u16(self) -> u16; - fn is_zero(&self) -> bool { - *self == Self::zero() - } - fn one() -> Self { Self::zero().next() } diff --git a/dnp3/src/app/types.rs b/dnp3/src/app/types.rs index 1375544a..d9c6d0a0 100644 --- a/dnp3/src/app/types.rs +++ b/dnp3/src/app/types.rs @@ -1,4 +1,3 @@ -use std::convert::TryFrom; use std::time::{Duration, SystemTime}; use crate::app::measurement::DoubleBit; diff --git a/dnp3/src/lib.rs b/dnp3/src/lib.rs index e533037a..ed7f00a7 100644 --- a/dnp3/src/lib.rs +++ b/dnp3/src/lib.rs @@ -11,7 +11,6 @@ patterns_in_fns_without_body, pub_use_of_private_extern_crate, unknown_crate_types, order_dependent_trait_objects, -illegal_floating_point_literal_pattern, improper_ctypes, late_bound_lifetime_arguments, non_camel_case_types, diff --git a/dnp3/src/link/format.rs b/dnp3/src/link/format.rs index a852e6c2..0207f96a 100644 --- a/dnp3/src/link/format.rs +++ b/dnp3/src/link/format.rs @@ -47,7 +47,7 @@ impl<'a> FrameData<'a> { // this can all be statically verified not to panic since the buffer is a constant length pub(crate) fn format_header_fixed_size( header: Header, - buffer: &mut [u8; super::constant::LINK_HEADER_LENGTH], + buffer: &mut [u8; constant::LINK_HEADER_LENGTH], ) { fn to_le(x: u16) -> (u8, u8) { let low = (x & 0xFF) as u8; diff --git a/dnp3/src/link/parser.rs b/dnp3/src/link/parser.rs index ba503c78..84332323 100644 --- a/dnp3/src/link/parser.rs +++ b/dnp3/src/link/parser.rs @@ -16,14 +16,14 @@ enum ParseState { pub(crate) struct FramePayload { length: usize, - buffer: [u8; super::constant::MAX_FRAME_PAYLOAD_LENGTH], + buffer: [u8; constant::MAX_FRAME_PAYLOAD_LENGTH], } impl FramePayload { pub(crate) fn new() -> Self { Self { length: 0, - buffer: [0; super::constant::MAX_FRAME_PAYLOAD_LENGTH], + buffer: [0; constant::MAX_FRAME_PAYLOAD_LENGTH], } } diff --git a/dnp3/src/master/file.rs b/dnp3/src/master/file.rs index 0470df1e..d1599b03 100644 --- a/dnp3/src/master/file.rs +++ b/dnp3/src/master/file.rs @@ -129,7 +129,7 @@ impl std::fmt::Display for FileError { FileError::NoPermission => f.write_str("no permission"), FileError::BadBlockNum => f.write_str("bad block number"), FileError::AbortByUser => f.write_str("aborted by user"), - FileError::TaskError(t) => std::fmt::Debug::fmt(&t, f), + FileError::TaskError(t) => Debug::fmt(&t, f), FileError::MaxLengthExceeded => f.write_str("exceeded maximum received length"), } } diff --git a/dnp3/src/master/handler.rs b/dnp3/src/master/handler.rs index 9dda0779..5b377c26 100644 --- a/dnp3/src/master/handler.rs +++ b/dnp3/src/master/handler.rs @@ -2,7 +2,6 @@ use std::time::{Duration, SystemTime}; use crate::app::attr::*; use crate::app::measurement::*; -use crate::app::variations::Variation; use crate::app::*; use crate::decode::DecodeLevel; @@ -31,7 +30,7 @@ use crate::util::session::Enabled; /// Handle to a master communication channel. This handle controls /// a task running on the Tokio Runtime. /// -/// It provides a uniform API for all of the various types of communication channels supported +/// It provides a uniform API for all the various types of communication channels supported /// by the library. #[derive(Debug, Clone)] pub struct MasterChannel { @@ -461,10 +460,6 @@ pub trait AssociationInformation: Send + Sync { fn unsolicited_response(&mut self, _is_duplicate: bool, _seq: Sequence) {} } -pub(crate) struct NullAssociationInformation; - -impl AssociationInformation for NullAssociationInformation {} - /// Information about the object header and specific variation #[derive(Copy, Clone, Debug, PartialEq, Eq)] pub struct HeaderInfo { @@ -645,8 +640,3 @@ pub(crate) fn handle_attribute( } } } - -/// read handler that does nothing -#[derive(Copy, Clone)] -pub(crate) struct NullReadHandler; -impl ReadHandler for NullReadHandler {} diff --git a/dnp3/src/master/task.rs b/dnp3/src/master/task.rs index abc30c33..95a6e663 100644 --- a/dnp3/src/master/task.rs +++ b/dnp3/src/master/task.rs @@ -163,7 +163,7 @@ impl MasterSession { return self.handle_fragment_while_idle(io, writer, source, response).await } Some(TransportResponse::LinkLayerMessage(msg)) => self.notify_link_activity(msg.source), - Some(TransportResponse::Error(_, _)) => return Ok(()), // ignore the malformed response + Some(TransportResponse::Error(_)) => return Ok(()), // ignore the malformed response None => return Ok(()), } } @@ -196,7 +196,7 @@ impl MasterSession { return self.handle_fragment_while_idle(io, writer, source, response).await } Some(TransportResponse::LinkLayerMessage(msg)) => self.notify_link_activity(msg.source), - Some(TransportResponse::Error(_, _)) => return Ok(()), // ignore the malformed response + Some(TransportResponse::Error(_)) => return Ok(()), // ignore the malformed response None => return Ok(()), } } @@ -436,7 +436,7 @@ impl MasterSession { } } Some(TransportResponse::LinkLayerMessage(msg)) => self.notify_link_activity(msg.source), - Some(TransportResponse::Error(_, err)) => { + Some(TransportResponse::Error(err)) => { task.on_task_error(self.associations.get_mut(destination).ok(), err.into()); return Err(err.into()); }, @@ -569,7 +569,7 @@ impl MasterSession { } } Some(TransportResponse::LinkLayerMessage(msg)) => self.notify_link_activity(msg.source), - Some(TransportResponse::Error(_, err)) => return Err(err.into()), + Some(TransportResponse::Error(err)) => return Err(err.into()), None => continue } } @@ -735,7 +735,7 @@ impl MasterSession { writer: &mut TransportWriter, ) -> Result<(), LinkError> { let mut cursor = self.tx_buffer.write_cursor(); - crate::app::format::write::confirm_unsolicited(seq, &mut cursor)?; + write::confirm_unsolicited(seq, &mut cursor)?; writer .write(io, self.decode_level, destination.wrap(), cursor.written()) @@ -802,7 +802,7 @@ impl MasterSession { self.notify_link_activity(msg.source); return Ok(()); } - Some(TransportResponse::Error(_, _)) => return Err(TaskError::UnexpectedResponseHeaders), + Some(TransportResponse::Error(_)) => return Err(TaskError::UnexpectedResponseHeaders), None => continue, } } diff --git a/dnp3/src/master/tasks/time.rs b/dnp3/src/master/tasks/time.rs index 84904e56..2e393b25 100644 --- a/dnp3/src/master/tasks/time.rs +++ b/dnp3/src/master/tasks/time.rs @@ -315,9 +315,14 @@ mod tests { use crate::app::Sequence; use crate::app::*; use crate::link::EndpointAddress; - use crate::master::handler::{AssociationHandler, NullReadHandler}; + use crate::master::handler::AssociationHandler; use crate::master::tasks::RequestWriter; - use crate::master::{AssociationConfig, NullAssociationInformation}; + use crate::master::{AssociationConfig, AssociationInformation, ReadHandler}; + + struct NullReadHandler; + impl ReadHandler for NullReadHandler {} + struct NullAssociationInformation; + impl AssociationInformation for NullAssociationInformation {} use scursor::WriteCursor; diff --git a/dnp3/src/outstation/control/control_type.rs b/dnp3/src/outstation/control/control_type.rs index b77306a0..55fb30b0 100644 --- a/dnp3/src/outstation/control/control_type.rs +++ b/dnp3/src/outstation/control/control_type.rs @@ -10,9 +10,6 @@ pub(crate) trait ControlType: Debug { /// make a copy of this control type with a new status code fn with_status(&self, status: CommandStatus) -> Self; - /// get the command status - fn status(&self) -> CommandStatus; - /// select a control on a handler fn select( self, @@ -35,10 +32,6 @@ impl ControlType for Group12Var1 { Self { status, ..*self } } - fn status(&self) -> CommandStatus { - self.status - } - fn select( self, transaction: &mut ControlTransaction, @@ -64,10 +57,6 @@ impl ControlType for Group41Var1 { Self { status, ..*self } } - fn status(&self) -> CommandStatus { - self.status - } - fn select( self, transaction: &mut ControlTransaction, @@ -93,10 +82,6 @@ impl ControlType for Group41Var2 { Self { status, ..*self } } - fn status(&self) -> CommandStatus { - self.status - } - fn select( self, transaction: &mut ControlTransaction, @@ -122,10 +107,6 @@ impl ControlType for Group41Var3 { Self { status, ..*self } } - fn status(&self) -> CommandStatus { - self.status - } - fn select( self, transaction: &mut ControlTransaction, @@ -151,10 +132,6 @@ impl ControlType for Group41Var4 { Self { status, ..*self } } - fn status(&self) -> CommandStatus { - self.status - } - fn select( self, transaction: &mut ControlTransaction, diff --git a/dnp3/src/outstation/database/details/attrs/mod.rs b/dnp3/src/outstation/database/details/attrs/mod.rs index 99f4bb8c..8367a9c8 100644 --- a/dnp3/src/outstation/database/details/attrs/mod.rs +++ b/dnp3/src/outstation/database/details/attrs/mod.rs @@ -146,7 +146,7 @@ impl Selection { let mut writer = HeaderWriter::new(cursor); if let Err(err) = writer.write_attribute(attr) { match err { - AttrWriteError::Cursor(_) => return false, // out of space + AttrWriteError::Cursor => return false, // out of space AttrWriteError::BadAttribute(err) => { tracing::error!("Unable to write attribute: {}", err); } diff --git a/dnp3/src/outstation/database/details/event/buffer.rs b/dnp3/src/outstation/database/details/event/buffer.rs index 1caf546d..5210646b 100644 --- a/dnp3/src/outstation/database/details/event/buffer.rs +++ b/dnp3/src/outstation/database/details/event/buffer.rs @@ -428,11 +428,6 @@ pub(crate) enum InsertError { Overflow { created: u64, discarded: u64 }, } -#[derive(Copy, Clone, Debug, PartialEq)] -pub(crate) struct EventWriteError { - pub(crate) count: usize, -} - impl EventBuffer { pub(crate) fn new(config: EventBufferConfig) -> Self { let max_size = config.max_events(); diff --git a/dnp3/src/outstation/database/details/range/static_db.rs b/dnp3/src/outstation/database/details/range/static_db.rs index 6b803033..23e86c91 100644 --- a/dnp3/src/outstation/database/details/range/static_db.rs +++ b/dnp3/src/outstation/database/details/range/static_db.rs @@ -232,10 +232,10 @@ where range: IndexRange, variation: Option, ) -> Option { - for (_index, point) in self.inner.range_mut(( - std::ops::Bound::Included(&range.start), - std::ops::Bound::Included(&range.stop), - )) { + for (_index, point) in self + .inner + .range_mut((Bound::Included(&range.start), Bound::Included(&range.stop))) + { // for every point in the range, we copy the current value into a distinct 'selected' cell // when writing the response(s) we use the selected value // this allows the outstation to send consistent snapshot of the values when a multi-fragment response is required diff --git a/dnp3/src/outstation/database/mod.rs b/dnp3/src/outstation/database/mod.rs index c19e58ce..913736b2 100644 --- a/dnp3/src/outstation/database/mod.rs +++ b/dnp3/src/outstation/database/mod.rs @@ -356,7 +356,7 @@ impl From for AttrDefError { /// Core database implementation shared between an outstation task and the user facing API. /// This type is always guarded by a `DatabaseHandle` which provides a transactional API. pub struct Database { - pub(crate) inner: crate::outstation::database::details::database::Database, + pub(crate) inner: details::database::Database, } impl Database { @@ -367,11 +367,7 @@ impl Database { config: EventBufferConfig, ) -> Self { Self { - inner: crate::outstation::database::details::database::Database::new( - max_read_selection, - class_zero_config, - config, - ), + inner: details::database::Database::new(max_read_selection, class_zero_config, config), } } diff --git a/dnp3/src/outstation/database/read.rs b/dnp3/src/outstation/database/read.rs index 64a97d20..5569b452 100644 --- a/dnp3/src/outstation/database/read.rs +++ b/dnp3/src/outstation/database/read.rs @@ -20,6 +20,7 @@ pub(crate) enum StaticReadHeader { Counter(Option, Option), FrozenCounter(Option, Option), Analog(Option, Option), + #[allow(dead_code)] // TODO - this can be removed if we support these request FrozenAnalog(Option, Option), AnalogOutputStatus( Option, @@ -42,6 +43,7 @@ pub(crate) enum EventReadHeader { Counter(Option, Option), FrozenCounter(Option, Option), Analog(Option, Option), + #[allow(dead_code)] // TODO - this can be removed if we support these request FrozenAnalog(Option, Option), AnalogOutputStatus(Option, Option), OctetString(Option), diff --git a/dnp3/src/outstation/session.rs b/dnp3/src/outstation/session.rs index a64ac2de..c49a3cd2 100644 --- a/dnp3/src/outstation/session.rs +++ b/dnp3/src/outstation/session.rs @@ -15,7 +15,6 @@ use crate::app::variations::{ Group34Var1, Group34Var2, Group34Var3, Group50Var1, Group50Var3, Group52Var1, Group52Var2, }; use crate::app::*; -use crate::app::{ControlField, Iin, Iin1, Iin2, ResponseFunction, ResponseHeader}; use crate::decode::DecodeLevel; use crate::link::error::LinkError; use crate::link::header::BroadcastConfirmMode; @@ -739,7 +738,7 @@ impl OutstationSession { self.on_link_activity(); (info, request) } - Some(TransportRequest::LinkLayerMessage(_)) => { + Some(TransportRequest::LinkLayerMessage) => { self.on_link_activity(); return Ok(UnsolicitedWaitResult::ReadNext); } @@ -1001,7 +1000,7 @@ impl OutstationSession { } } } - Some(TransportRequest::LinkLayerMessage(_)) => { + Some(TransportRequest::LinkLayerMessage) => { self.on_link_activity(); } Some(TransportRequest::Error(from, err)) => { @@ -2116,7 +2115,7 @@ impl OutstationSession { self.on_link_activity(); (info, request) } - Some(TransportRequest::LinkLayerMessage(_)) => { + Some(TransportRequest::LinkLayerMessage) => { self.on_link_activity(); return ConfirmAction::ContinueWait; } diff --git a/dnp3/src/outstation/traits.rs b/dnp3/src/outstation/traits.rs index e56446ce..7974e282 100644 --- a/dnp3/src/outstation/traits.rs +++ b/dnp3/src/outstation/traits.rs @@ -1,7 +1,4 @@ use crate::app::attr::Attribute; -use crate::app::parse::count::CountSequence; -use crate::app::parse::prefix::Prefix; -use crate::app::parse::traits::{FixedSizeVariation, Index}; use crate::app::variations::Group50Var2; use crate::app::RequestHeader; use crate::app::Sequence; @@ -550,67 +547,3 @@ impl ControlSupport for DefaultControlHandler { self.status } } - -trait HasCommandStatus { - fn status(&self) -> CommandStatus; - fn with_status(&self, status: CommandStatus) -> Self; -} - -trait ControlSupportExt: ControlSupport -where - T: FixedSizeVariation + HasCommandStatus, -{ - fn operate( - &mut self, - seq: CountSequence>, - op_type: OperateType, - database: &mut DatabaseHandle, - mut func: F, - ) where - F: FnMut(T, I), - I: Index, - { - for item in seq.iter() { - let status = { - if item.value.status() == CommandStatus::Success { - ControlSupport::::operate( - self, - item.value, - item.index.widen_to_u16(), - op_type, - database, - ) - } else { - CommandStatus::FormatError - } - }; - func(item.value.with_status(status), item.index) - } - } - - fn select( - &mut self, - seq: CountSequence>, - database: &mut DatabaseHandle, - mut func: F, - ) where - F: FnMut(T, I), - I: Index, - { - for item in seq.iter() { - let status = { - if item.value.status() == CommandStatus::Success { - ControlSupport::::select( - self, - item.value, - item.index.widen_to_u16(), - database, - ) - } else { - CommandStatus::FormatError - } - }; - func(item.value.with_status(status), item.index) - } - } -} diff --git a/dnp3/src/tcp/outstation.rs b/dnp3/src/tcp/outstation.rs index 95f89d61..7c4eb18c 100644 --- a/dnp3/src/tcp/outstation.rs +++ b/dnp3/src/tcp/outstation.rs @@ -3,7 +3,6 @@ use tracing::Instrument; use crate::app::{ConnectStrategy, Listener, Shutdown}; use crate::link::LinkErrorMode; use crate::outstation::task::OutstationTask; -use crate::outstation::OutstationHandle; use crate::outstation::*; use crate::tcp::client::ClientTask; use crate::tcp::server::{NewSession, ServerTask}; diff --git a/dnp3/src/tcp/tls/master.rs b/dnp3/src/tcp/tls/master.rs index e0327297..523e4af3 100644 --- a/dnp3/src/tcp/tls/master.rs +++ b/dnp3/src/tcp/tls/master.rs @@ -1,5 +1,4 @@ use sfio_rustls_config::NameVerifier; -use std::convert::TryFrom; use std::net::{Ipv4Addr, SocketAddr}; use std::path::Path; use std::sync::Arc; diff --git a/dnp3/src/transport/reader.rs b/dnp3/src/transport/reader.rs index 2418bf06..876ac2bc 100644 --- a/dnp3/src/transport/reader.rs +++ b/dnp3/src/transport/reader.rs @@ -121,12 +121,12 @@ impl TransportReader { match data { Ok(ParsedTransportData::Fragment(info, fragment)) => match fragment.to_response() { Ok(response) => Some(TransportResponse::Response(info.source, response)), - Err(err) => Some(TransportResponse::Error(info.source, err.into())), + Err(err) => Some(TransportResponse::Error(err.into())), }, Ok(ParsedTransportData::LinkLayerMessage(msg)) => { Some(TransportResponse::LinkLayerMessage(msg)) } - Err((err, source)) => Some(TransportResponse::Error(source, err.into())), + Err((err, _)) => Some(TransportResponse::Error(err.into())), } } @@ -159,8 +159,8 @@ impl TransportReader { err.into(fragment.control.seq), )), }, - Ok(ParsedTransportData::LinkLayerMessage(msg)) => { - Some(TransportRequest::LinkLayerMessage(msg)) + Ok(ParsedTransportData::LinkLayerMessage(_)) => { + Some(TransportRequest::LinkLayerMessage) } Err((err, source)) => Some(TransportRequest::Error(source, err.into())), } diff --git a/dnp3/src/transport/types.rs b/dnp3/src/transport/types.rs index d110d09d..a8b3ad9a 100644 --- a/dnp3/src/transport/types.rs +++ b/dnp3/src/transport/types.rs @@ -51,7 +51,7 @@ pub(crate) enum LinkLayerMessageType { pub(crate) enum TransportResponse<'a> { Response(EndpointAddress, Response<'a>), LinkLayerMessage(LinkLayerMessage), - Error(EndpointAddress, TransportResponseError), + Error(TransportResponseError), } #[derive(Copy, Clone, Debug, PartialEq)] @@ -74,7 +74,7 @@ impl From for TransportResponseError { pub(crate) enum TransportRequest<'a> { Request(FragmentInfo, Request<'a>), - LinkLayerMessage(LinkLayerMessage), + LinkLayerMessage, Error(EndpointAddress, TransportRequestError), } diff --git a/dnp3/src/util/slice_ext.rs b/dnp3/src/util/slice_ext.rs index 65ffea30..4996ec3b 100644 --- a/dnp3/src/util/slice_ext.rs +++ b/dnp3/src/util/slice_ext.rs @@ -5,15 +5,10 @@ use crate::link::error::LogicError; pub(crate) trait SliceExtNoPanic { fn np_split_at(&self, pos: usize) -> Result<(&[T], &[T]), LogicError>; fn np_split_at_no_error(&self, pos: usize) -> (&[T], &[T]); - fn np_get(&self, range: Range) -> Result<&[T], LogicError>; - fn np_take(&self, count: usize) -> Result<&[T], LogicError> { - self.np_get(0..count) - } } pub(crate) trait MutSliceExtNoPanic { fn np_get_mut(&mut self, range: Range) -> Result<&mut [T], LogicError>; - fn np_skip_mut(&mut self, count: usize) -> Result<&mut [T], LogicError>; } impl SliceExtNoPanic for &[T] { @@ -30,13 +25,6 @@ impl SliceExtNoPanic for &[T] { _ => (self, &[]), } } - - fn np_get(&self, range: Range) -> Result<&[T], LogicError> { - match self.get(range) { - Some(x) => Ok(x), - None => Err(LogicError::BadSize), - } - } } impl MutSliceExtNoPanic for &mut [T] { @@ -46,11 +34,4 @@ impl MutSliceExtNoPanic for &mut [T] { None => Err(LogicError::BadSize), } } - - fn np_skip_mut(&mut self, count: usize) -> Result<&mut [T], LogicError> { - match self.get_mut(count..) { - Some(remainder) => Ok(remainder), - None => Err(LogicError::BadSize), - } - } } diff --git a/ffi/dnp3-ffi/Cargo.toml b/ffi/dnp3-ffi/Cargo.toml index b93bb3f7..aec61423 100644 --- a/ffi/dnp3-ffi/Cargo.toml +++ b/ffi/dnp3-ffi/Cargo.toml @@ -25,5 +25,5 @@ serial = ["dnp3/serial"] [build-dependencies] dnp3-schema = { path = "../dnp3-schema" } oo-bindgen = "0.8" -sfio-tracing-ffi = "0.8" +sfio-tracing-ffi = "0.8.1" sfio-tokio-ffi = "0.8" \ No newline at end of file diff --git a/ffi/dnp3-ffi/src/handler.rs b/ffi/dnp3-ffi/src/handler.rs index 9dc5e48d..8ce360bc 100644 --- a/ffi/dnp3-ffi/src/handler.rs +++ b/ffi/dnp3-ffi/src/handler.rs @@ -2,7 +2,6 @@ use crate::attr::FfiAttrValue; use dnp3::app::attr::*; use dnp3::app::measurement::*; use dnp3::app::*; -use dnp3::app::{ResponseFunction, ResponseHeader}; use dnp3::master::{ AssociationHandler, AssociationInformation, HeaderInfo, ReadHandler, ReadType, TaskError, TaskType, diff --git a/ffi/dnp3-ffi/src/outstation/mod.rs b/ffi/dnp3-ffi/src/outstation/mod.rs index 438cf10a..8f4272b6 100644 --- a/ffi/dnp3-ffi/src/outstation/mod.rs +++ b/ffi/dnp3-ffi/src/outstation/mod.rs @@ -21,6 +21,7 @@ mod struct_constructors; enum OutstationServerState { Configuring(dnp3::tcp::Server), + #[allow(dead_code)] Running(ServerHandle), } @@ -173,8 +174,8 @@ pub unsafe fn outstation_server_bind(server: *mut OutstationServer) -> Result<() if server.is_null() { return Err(ffi::ParamError::NullParameter); } + // TODO - this pattern doesn't look correct let mut server = Box::from_raw(server); - let server_handle = match server.state { OutstationServerState::Configuring(server) => server, OutstationServerState::Running(_) => return Err(ffi::ParamError::ServerAlreadyStarted),