need to re-work all of this..
Some checks failed
Rust/sat-rs/pipeline/pr-main There was a failure building this commit
Some checks failed
Rust/sat-rs/pipeline/pr-main There was a failure building this commit
This commit is contained in:
@ -105,7 +105,6 @@ pub mod std_mod {
|
||||
self, FailParams, FailParamsWithStep, TcStateStarted, VerificationReportingProvider,
|
||||
},
|
||||
ActiveRequestMapProvider, DefaultActiveRequestMap, EcssTmSenderCore, EcssTmtcError,
|
||||
GenericRoutingError, PusServiceReplyHandler, PusTargetedRequestHandler,
|
||||
ReplyHandlerHook,
|
||||
},
|
||||
};
|
||||
@ -115,27 +114,9 @@ pub mod std_mod {
|
||||
|
||||
use super::*;
|
||||
|
||||
pub type PusService8ActionRequestHandler<
|
||||
TcReceiver,
|
||||
TmSender,
|
||||
TcInMemConverter,
|
||||
VerificationReporter,
|
||||
RequestConverter,
|
||||
RequestRouter,
|
||||
RoutingError = GenericRoutingError,
|
||||
> = PusTargetedRequestHandler<
|
||||
TcReceiver,
|
||||
TmSender,
|
||||
TcInMemConverter,
|
||||
VerificationReporter,
|
||||
RequestConverter,
|
||||
RequestRouter,
|
||||
ActionRequest,
|
||||
RoutingError,
|
||||
>;
|
||||
|
||||
pub type DefaultActiveActionRequestMap = DefaultActiveRequestMap<ActiveActionRequest>;
|
||||
|
||||
/*
|
||||
/// Type definition for a PUS 8 action service reply handler which constrains the
|
||||
/// [PusServiceReplyHandler] active request and reply generics to the [ActiveActionRequest] and
|
||||
/// [ActionReplyPusWithIds] type.
|
||||
@ -299,6 +280,7 @@ pub mod std_mod {
|
||||
)
|
||||
}
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
@ -311,11 +293,12 @@ mod tests {
|
||||
|
||||
use spacepackets::{
|
||||
ecss::{
|
||||
tc::{PusTcCreator, PusTcReader, PusTcSecondaryHeader},
|
||||
tc::{PusTcCreator, PusTcReader},
|
||||
tm::PusTmReader,
|
||||
PusPacket,
|
||||
},
|
||||
CcsdsPacket, SequenceFlags, SpHeader,
|
||||
time::{cds, TimeWriter},
|
||||
CcsdsPacket,
|
||||
};
|
||||
|
||||
use crate::{
|
||||
@ -324,7 +307,7 @@ mod tests {
|
||||
pus::{
|
||||
tests::{
|
||||
PusServiceHandlerWithVecCommon, PusTestHarness, SimplePusPacketHandler,
|
||||
TestConverter, TestRouter, APP_DATA_TOO_SHORT, TEST_APID,
|
||||
TestConverter, TestRouter, APP_DATA_TOO_SHORT,
|
||||
},
|
||||
verification::{
|
||||
self,
|
||||
@ -332,9 +315,9 @@ mod tests {
|
||||
FailParams, TcStateAccepted, TcStateNone, TcStateStarted,
|
||||
VerificationReportingProvider,
|
||||
},
|
||||
EcssTcInVecConverter, EcssTmtcError, GenericRoutingError, MpscTcReceiver,
|
||||
PusPacketHandlerResult, PusPacketHandlingError, PusRequestRouter,
|
||||
PusTcToRequestConverter, ReplyHandlerHook, TmAsVecSenderWithMpsc,
|
||||
EcssTcInMemConverter, EcssTcInVecConverter, EcssTmtcError, GenericRoutingError,
|
||||
MpscTcReceiver, PusPacketHandlerResult, PusPacketHandlingError, PusRequestRouter,
|
||||
PusServiceHelper, PusTcToRequestConverter, ReplyHandlerHook, TmAsVecSenderWithMpsc,
|
||||
},
|
||||
};
|
||||
|
||||
@ -416,29 +399,32 @@ mod tests {
|
||||
}
|
||||
}
|
||||
|
||||
struct Pus8RequestTestbenchWithVec {
|
||||
common: PusServiceHandlerWithVecCommon<TestVerificationReporter>,
|
||||
handler: PusService8ActionRequestHandler<
|
||||
pub struct PusDynRequestHandler<const SERVICE: u8, Request> {
|
||||
srv_helper: PusServiceHelper<
|
||||
MpscTcReceiver,
|
||||
TmAsVecSenderWithMpsc,
|
||||
EcssTcInVecConverter,
|
||||
TestVerificationReporter,
|
||||
TestConverter<8>,
|
||||
TestRouter<ActionRequest>,
|
||||
>,
|
||||
request_converter: TestConverter<SERVICE>,
|
||||
request_router: TestRouter<Request>,
|
||||
}
|
||||
|
||||
struct Pus8RequestTestbenchWithVec {
|
||||
common: PusServiceHandlerWithVecCommon<TestVerificationReporter>,
|
||||
handler: PusDynRequestHandler<8, ActionRequest>,
|
||||
}
|
||||
|
||||
impl Pus8RequestTestbenchWithVec {
|
||||
pub fn new() -> Self {
|
||||
let (common, srv_handler) =
|
||||
PusServiceHandlerWithVecCommon::new_with_test_verif_sender();
|
||||
let (common, srv_helper) = PusServiceHandlerWithVecCommon::new_with_test_verif_sender();
|
||||
Self {
|
||||
common,
|
||||
handler: PusService8ActionRequestHandler::new(
|
||||
srv_handler,
|
||||
TestConverter::default(),
|
||||
TestRouter::default(),
|
||||
),
|
||||
handler: PusDynRequestHandler {
|
||||
srv_helper,
|
||||
request_converter: TestConverter::default(),
|
||||
request_router: TestRouter::default(),
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
@ -474,10 +460,43 @@ mod tests {
|
||||
}
|
||||
}
|
||||
impl SimplePusPacketHandler for Pus8RequestTestbenchWithVec {
|
||||
delegate! {
|
||||
to self.handler {
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError>;
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
let possible_packet = self.handler.srv_helper.retrieve_and_accept_next_packet()?;
|
||||
if possible_packet.is_none() {
|
||||
return Ok(PusPacketHandlerResult::Empty);
|
||||
}
|
||||
let ecss_tc_and_token = possible_packet.unwrap();
|
||||
let tc = self
|
||||
.handler
|
||||
.srv_helper
|
||||
.tc_in_mem_converter
|
||||
.convert_ecss_tc_in_memory_to_reader(&ecss_tc_and_token.tc_in_memory)?;
|
||||
let time_stamp = cds::TimeProvider::from_now_with_u16_days()
|
||||
.expect("timestamp generation failed")
|
||||
.to_vec()
|
||||
.unwrap();
|
||||
let (target_id, action_request) = self.handler.request_converter.convert(
|
||||
ecss_tc_and_token.token,
|
||||
&tc,
|
||||
&time_stamp,
|
||||
&self.handler.srv_helper.common.verification_handler,
|
||||
)?;
|
||||
if let Err(e) = self.handler.request_router.route(
|
||||
target_id,
|
||||
action_request,
|
||||
ecss_tc_and_token.token,
|
||||
) {
|
||||
self.handler.request_router.handle_error(
|
||||
target_id,
|
||||
ecss_tc_and_token.token,
|
||||
&tc,
|
||||
e.clone(),
|
||||
&time_stamp,
|
||||
&self.handler.srv_helper.common.verification_handler,
|
||||
);
|
||||
return Err(e.into());
|
||||
}
|
||||
Ok(PusPacketHandlerResult::RequestHandled)
|
||||
}
|
||||
}
|
||||
|
||||
@ -667,68 +686,6 @@ mod tests {
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn basic_test() {
|
||||
let mut action_handler = Pus8RequestTestbenchWithVec::new();
|
||||
let mut sp_header = SpHeader::tc(TEST_APID, SequenceFlags::Unsegmented, 0, 0).unwrap();
|
||||
let sec_header = PusTcSecondaryHeader::new_simple(8, 1);
|
||||
let action_id: u32 = 1;
|
||||
let action_id_raw = action_id.to_be_bytes();
|
||||
let tc = PusTcCreator::new(&mut sp_header, sec_header, action_id_raw.as_ref(), true);
|
||||
action_handler.send_tc(&tc);
|
||||
let result = action_handler.handle_one_tc();
|
||||
assert!(result.is_ok());
|
||||
action_handler.check_next_conversion(&tc);
|
||||
let (target_id, action_req) = action_handler.retrieve_next_request();
|
||||
assert_eq!(target_id, TEST_APID.into());
|
||||
assert_eq!(action_req.action_id, 1);
|
||||
if let ActionRequestVariant::VecData(data) = action_req.variant {
|
||||
assert_eq!(data, &[]);
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_routing_error() {
|
||||
let mut action_handler = Pus8RequestTestbenchWithVec::new();
|
||||
let mut sp_header = SpHeader::tc(TEST_APID, SequenceFlags::Unsegmented, 0, 0).unwrap();
|
||||
let sec_header = PusTcSecondaryHeader::new_simple(8, 1);
|
||||
let action_id: u32 = 1;
|
||||
let action_id_raw = action_id.to_be_bytes();
|
||||
let tc = PusTcCreator::new(&mut sp_header, sec_header, action_id_raw.as_ref(), true);
|
||||
let error = GenericRoutingError::UnknownTargetId(25);
|
||||
action_handler
|
||||
.handler
|
||||
.request_router
|
||||
.inject_routing_error(error);
|
||||
action_handler.send_tc(&tc);
|
||||
let result = action_handler.handle_one_tc();
|
||||
assert!(result.is_err());
|
||||
let check_error = |routing_error: GenericRoutingError| {
|
||||
if let GenericRoutingError::UnknownTargetId(id) = routing_error {
|
||||
assert_eq!(id, 25);
|
||||
} else {
|
||||
panic!("unexpected error type");
|
||||
}
|
||||
};
|
||||
if let PusPacketHandlingError::RequestRoutingError(routing_error) = result.unwrap_err() {
|
||||
check_error(routing_error);
|
||||
} else {
|
||||
panic!("unexpected error type");
|
||||
}
|
||||
|
||||
action_handler.check_next_conversion(&tc);
|
||||
let (target_id, action_req) = action_handler.retrieve_next_request();
|
||||
assert_eq!(target_id, TEST_APID.into());
|
||||
assert_eq!(action_req.action_id, 1);
|
||||
if let ActionRequestVariant::VecData(data) = action_req.variant {
|
||||
assert_eq!(data, &[]);
|
||||
}
|
||||
|
||||
let (target_id, found_error) = action_handler.retrieve_next_routing_error();
|
||||
assert_eq!(target_id, TEST_APID.into());
|
||||
check_error(found_error);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_reply_handler_completion_success() {
|
||||
let mut reply_testbench = Pus8ReplyTestbench::new(true);
|
||||
|
@ -7,10 +7,7 @@ use spacepackets::ecss::PusPacket;
|
||||
use std::sync::mpsc::Sender;
|
||||
|
||||
use super::verification::VerificationReportingProvider;
|
||||
use super::{
|
||||
get_current_cds_short_timestamp, EcssTcInMemConverter, EcssTcReceiverCore, EcssTmSenderCore,
|
||||
PusServiceHelper,
|
||||
};
|
||||
use super::{EcssTcInMemConverter, EcssTcReceiverCore, EcssTmSenderCore, PusServiceHelper};
|
||||
|
||||
pub struct PusService5EventHandler<
|
||||
TcReceiver: EcssTcReceiverCore,
|
||||
@ -45,7 +42,10 @@ impl<
|
||||
}
|
||||
}
|
||||
|
||||
pub fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
pub fn handle_one_tc(
|
||||
&mut self,
|
||||
time_stamp: &[u8],
|
||||
) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
let possible_packet = self.service_helper.retrieve_and_accept_next_packet()?;
|
||||
if possible_packet.is_none() {
|
||||
return Ok(PusPacketHandlerResult::Empty);
|
||||
@ -63,7 +63,7 @@ impl<
|
||||
ecss_tc_and_token.token,
|
||||
));
|
||||
}
|
||||
let handle_enable_disable_request = |enable: bool, stamp: [u8; 7]| {
|
||||
let handle_enable_disable_request = |enable: bool| {
|
||||
if tc.user_data().len() < 4 {
|
||||
return Err(PusPacketHandlingError::NotEnoughAppData {
|
||||
expected: 4,
|
||||
@ -76,7 +76,7 @@ impl<
|
||||
.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.start_success(ecss_tc_and_token.token, &stamp)
|
||||
.start_success(ecss_tc_and_token.token, time_stamp)
|
||||
.map_err(|_| PartialPusHandlingError::Verification);
|
||||
let partial_error = start_token.clone().err();
|
||||
let mut token: TcStateToken = ecss_tc_and_token.token.into();
|
||||
@ -106,8 +106,6 @@ impl<
|
||||
}
|
||||
Ok(PusPacketHandlerResult::RequestHandled)
|
||||
};
|
||||
let mut partial_error = None;
|
||||
let time_stamp = get_current_cds_short_timestamp(&mut partial_error);
|
||||
match srv.unwrap() {
|
||||
Subservice::TmInfoReport
|
||||
| Subservice::TmLowSeverityReport
|
||||
@ -116,10 +114,10 @@ impl<
|
||||
return Err(PusPacketHandlingError::InvalidSubservice(tc.subservice()))
|
||||
}
|
||||
Subservice::TcEnableEventGeneration => {
|
||||
handle_enable_disable_request(true, time_stamp)?;
|
||||
handle_enable_disable_request(true)?;
|
||||
}
|
||||
Subservice::TcDisableEventGeneration => {
|
||||
handle_enable_disable_request(false, time_stamp)?;
|
||||
handle_enable_disable_request(false)?;
|
||||
}
|
||||
Subservice::TcReportDisabledList | Subservice::TmDisabledEventsReport => {
|
||||
return Ok(PusPacketHandlerResult::SubserviceNotImplemented(
|
||||
@ -137,6 +135,7 @@ impl<
|
||||
mod tests {
|
||||
use delegate::delegate;
|
||||
use spacepackets::ecss::event::Subservice;
|
||||
use spacepackets::time::{cds, TimeWriter};
|
||||
use spacepackets::util::UnsignedEnum;
|
||||
use spacepackets::{
|
||||
ecss::{
|
||||
@ -200,10 +199,9 @@ mod tests {
|
||||
}
|
||||
|
||||
impl SimplePusPacketHandler for Pus5HandlerWithStoreTester {
|
||||
delegate! {
|
||||
to self.handler {
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError>;
|
||||
}
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
let time_stamp = cds::TimeProvider::new_with_u16_days(0, 0).to_vec().unwrap();
|
||||
self.handler.handle_one_tc(&time_stamp)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,280 +0,0 @@
|
||||
pub use spacepackets::ecss::hk::*;
|
||||
|
||||
#[cfg(feature = "std")]
|
||||
#[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
|
||||
pub use std_mod::*;
|
||||
|
||||
#[cfg(feature = "alloc")]
|
||||
#[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
|
||||
#[allow(unused_imports)]
|
||||
pub use alloc_mod::*;
|
||||
|
||||
use crate::{hk::HkRequest, TargetId};
|
||||
|
||||
use super::verification::{TcStateAccepted, VerificationToken};
|
||||
|
||||
/// This trait is an abstraction for the routing of PUS service 3 housekeeping requests to a
|
||||
/// dedicated recipient using the generic [TargetId].
|
||||
pub trait PusHkRequestRouter {
|
||||
type Error;
|
||||
fn route(
|
||||
&self,
|
||||
target_id: TargetId,
|
||||
hk_request: HkRequest,
|
||||
token: VerificationToken<TcStateAccepted>,
|
||||
) -> Result<(), Self::Error>;
|
||||
}
|
||||
|
||||
#[cfg(feature = "alloc")]
|
||||
#[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
|
||||
pub mod alloc_mod {}
|
||||
|
||||
#[cfg(feature = "std")]
|
||||
#[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
|
||||
pub mod std_mod {
|
||||
use crate::pus::{GenericRoutingError, PusTargetedRequestHandler};
|
||||
|
||||
use super::*;
|
||||
|
||||
pub type PusService3HkRequestHandler<
|
||||
TcReceiver,
|
||||
TmSender,
|
||||
TcInMemConverter,
|
||||
VerificationReporter,
|
||||
RequestConverter,
|
||||
RequestRouter,
|
||||
RoutingError = GenericRoutingError,
|
||||
> = PusTargetedRequestHandler<
|
||||
TcReceiver,
|
||||
TmSender,
|
||||
TcInMemConverter,
|
||||
VerificationReporter,
|
||||
RequestConverter,
|
||||
RequestRouter,
|
||||
HkRequest,
|
||||
RoutingError,
|
||||
>;
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use delegate::delegate;
|
||||
use spacepackets::ecss::hk::Subservice;
|
||||
|
||||
use spacepackets::{
|
||||
ecss::{
|
||||
tc::{PusTcCreator, PusTcReader, PusTcSecondaryHeader},
|
||||
tm::PusTmReader,
|
||||
PusPacket,
|
||||
},
|
||||
CcsdsPacket, SequenceFlags, SpHeader,
|
||||
};
|
||||
|
||||
use crate::pus::{MpscTcReceiver, PusTcToRequestConverter, TmAsVecSenderWithMpsc};
|
||||
use crate::{
|
||||
hk::HkRequest,
|
||||
pus::{
|
||||
tests::{
|
||||
PusServiceHandlerWithVecCommon, PusTestHarness, SimplePusPacketHandler,
|
||||
TestConverter, TestRouter, APP_DATA_TOO_SHORT, TEST_APID,
|
||||
},
|
||||
verification::{
|
||||
tests::TestVerificationReporter, FailParams, RequestId, TcStateAccepted,
|
||||
VerificationReportingProvider, VerificationToken,
|
||||
},
|
||||
EcssTcInVecConverter, GenericRoutingError, PusPacketHandlerResult,
|
||||
PusPacketHandlingError,
|
||||
},
|
||||
TargetId,
|
||||
};
|
||||
|
||||
use super::{PusHkRequestRouter, PusService3HkRequestHandler};
|
||||
|
||||
impl PusHkRequestRouter for TestRouter<HkRequest> {
|
||||
type Error = GenericRoutingError;
|
||||
|
||||
fn route(
|
||||
&self,
|
||||
target_id: TargetId,
|
||||
hk_request: HkRequest,
|
||||
_token: VerificationToken<TcStateAccepted>,
|
||||
) -> Result<(), Self::Error> {
|
||||
self.routing_requests
|
||||
.borrow_mut()
|
||||
.push_back((target_id, hk_request));
|
||||
self.check_for_injected_error()
|
||||
}
|
||||
}
|
||||
|
||||
impl PusTcToRequestConverter<HkRequest> for TestConverter<3> {
|
||||
type Error = PusPacketHandlingError;
|
||||
fn convert(
|
||||
&mut self,
|
||||
token: VerificationToken<TcStateAccepted>,
|
||||
tc: &PusTcReader,
|
||||
time_stamp: &[u8],
|
||||
verif_reporter: &impl VerificationReportingProvider,
|
||||
) -> Result<(TargetId, HkRequest), Self::Error> {
|
||||
self.conversion_request.push_back(tc.raw_data().to_vec());
|
||||
self.check_service(tc)?;
|
||||
let target_id = tc.apid();
|
||||
if tc.user_data().len() < 4 {
|
||||
verif_reporter
|
||||
.start_failure(
|
||||
token,
|
||||
FailParams::new(
|
||||
time_stamp,
|
||||
&APP_DATA_TOO_SHORT,
|
||||
(tc.user_data().len() as u32).to_be_bytes().as_ref(),
|
||||
),
|
||||
)
|
||||
.expect("start success failure");
|
||||
return Err(PusPacketHandlingError::NotEnoughAppData {
|
||||
expected: 4,
|
||||
found: tc.user_data().len(),
|
||||
});
|
||||
}
|
||||
if tc.subservice() == Subservice::TcGenerateOneShotHk as u8 {
|
||||
verif_reporter
|
||||
.start_success(token, time_stamp)
|
||||
.expect("start success failure");
|
||||
return Ok((
|
||||
target_id.into(),
|
||||
HkRequest::OneShot(u32::from_be_bytes(
|
||||
tc.user_data()[0..4].try_into().unwrap(),
|
||||
)),
|
||||
));
|
||||
}
|
||||
Err(PusPacketHandlingError::InvalidAppData(
|
||||
"unexpected app data".into(),
|
||||
))
|
||||
}
|
||||
}
|
||||
|
||||
struct Pus3HandlerWithVecTester {
|
||||
common: PusServiceHandlerWithVecCommon<TestVerificationReporter>,
|
||||
handler: PusService3HkRequestHandler<
|
||||
MpscTcReceiver,
|
||||
TmAsVecSenderWithMpsc,
|
||||
EcssTcInVecConverter,
|
||||
TestVerificationReporter,
|
||||
TestConverter<3>,
|
||||
TestRouter<HkRequest>,
|
||||
>,
|
||||
}
|
||||
|
||||
impl Pus3HandlerWithVecTester {
|
||||
pub fn new() -> Self {
|
||||
let (common, srv_handler) =
|
||||
PusServiceHandlerWithVecCommon::new_with_test_verif_sender();
|
||||
Self {
|
||||
common,
|
||||
handler: PusService3HkRequestHandler::new(
|
||||
srv_handler,
|
||||
TestConverter::default(),
|
||||
TestRouter::default(),
|
||||
),
|
||||
}
|
||||
}
|
||||
|
||||
delegate! {
|
||||
to self.handler.request_converter {
|
||||
pub fn check_next_conversion(&mut self, tc: &PusTcCreator);
|
||||
}
|
||||
}
|
||||
delegate! {
|
||||
to self.handler.request_router {
|
||||
pub fn retrieve_next_request(&mut self) -> (TargetId, HkRequest);
|
||||
}
|
||||
}
|
||||
delegate! {
|
||||
to self.handler.request_router {
|
||||
pub fn retrieve_next_routing_error(&mut self) -> (TargetId, GenericRoutingError);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl PusTestHarness for Pus3HandlerWithVecTester {
|
||||
delegate! {
|
||||
to self.common {
|
||||
fn send_tc(&mut self, tc: &PusTcCreator) -> VerificationToken<TcStateAccepted>;
|
||||
fn read_next_tm(&mut self) -> PusTmReader<'_>;
|
||||
fn check_no_tm_available(&self) -> bool;
|
||||
fn check_next_verification_tm(
|
||||
&self,
|
||||
subservice: u8,
|
||||
expected_request_id: RequestId,
|
||||
);
|
||||
}
|
||||
}
|
||||
}
|
||||
impl SimplePusPacketHandler for Pus3HandlerWithVecTester {
|
||||
delegate! {
|
||||
to self.handler {
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError>;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn basic_test() {
|
||||
let mut hk_handler = Pus3HandlerWithVecTester::new();
|
||||
let mut sp_header = SpHeader::tc(TEST_APID, SequenceFlags::Unsegmented, 0, 0).unwrap();
|
||||
let sec_header = PusTcSecondaryHeader::new_simple(3, Subservice::TcGenerateOneShotHk as u8);
|
||||
let unique_id: u32 = 1;
|
||||
let unique_id_raw = unique_id.to_be_bytes();
|
||||
let tc = PusTcCreator::new(&mut sp_header, sec_header, unique_id_raw.as_ref(), true);
|
||||
hk_handler.send_tc(&tc);
|
||||
let result = hk_handler.handle_one_tc();
|
||||
assert!(result.is_ok());
|
||||
hk_handler.check_next_conversion(&tc);
|
||||
let (target_id, hk_request) = hk_handler.retrieve_next_request();
|
||||
assert_eq!(target_id, TEST_APID.into());
|
||||
if let HkRequest::OneShot(id) = hk_request {
|
||||
assert_eq!(id, unique_id);
|
||||
} else {
|
||||
panic!("unexpected request");
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn test_routing_error() {
|
||||
let mut hk_handler = Pus3HandlerWithVecTester::new();
|
||||
let mut sp_header = SpHeader::tc(TEST_APID, SequenceFlags::Unsegmented, 0, 0).unwrap();
|
||||
let sec_header = PusTcSecondaryHeader::new_simple(3, Subservice::TcGenerateOneShotHk as u8);
|
||||
let unique_id: u32 = 1;
|
||||
let unique_id_raw = unique_id.to_be_bytes();
|
||||
let tc = PusTcCreator::new(&mut sp_header, sec_header, unique_id_raw.as_ref(), true);
|
||||
let error = GenericRoutingError::UnknownTargetId(25);
|
||||
hk_handler
|
||||
.handler
|
||||
.request_router
|
||||
.inject_routing_error(error);
|
||||
hk_handler.send_tc(&tc);
|
||||
let result = hk_handler.handle_one_tc();
|
||||
assert!(result.is_err());
|
||||
let check_error = |routing_error: GenericRoutingError| {
|
||||
if let GenericRoutingError::UnknownTargetId(id) = routing_error {
|
||||
assert_eq!(id, 25);
|
||||
} else {
|
||||
panic!("unexpected error type");
|
||||
}
|
||||
};
|
||||
if let PusPacketHandlingError::RequestRoutingError(routing_error) = result.unwrap_err() {
|
||||
check_error(routing_error);
|
||||
} else {
|
||||
panic!("unexpected error type");
|
||||
}
|
||||
|
||||
hk_handler.check_next_conversion(&tc);
|
||||
let (target_id, hk_req) = hk_handler.retrieve_next_request();
|
||||
assert_eq!(target_id, TEST_APID.into());
|
||||
if let HkRequest::OneShot(unique_id) = hk_req {
|
||||
assert_eq!(unique_id, 1);
|
||||
}
|
||||
|
||||
let (target_id, found_error) = hk_handler.retrieve_next_routing_error();
|
||||
assert_eq!(target_id, TEST_APID.into());
|
||||
check_error(found_error);
|
||||
}
|
||||
}
|
@ -29,7 +29,6 @@ pub mod event;
|
||||
pub mod event_man;
|
||||
#[cfg(feature = "std")]
|
||||
pub mod event_srv;
|
||||
pub mod hk;
|
||||
pub mod mode;
|
||||
pub mod scheduler;
|
||||
#[cfg(feature = "std")]
|
||||
@ -44,7 +43,7 @@ pub use alloc_mod::*;
|
||||
#[cfg(feature = "std")]
|
||||
pub use std_mod::*;
|
||||
|
||||
use self::verification::{FailParams, TcStateStarted, VerificationReportingProvider};
|
||||
use self::verification::{TcStateStarted, VerificationReportingProvider};
|
||||
|
||||
#[derive(Debug, PartialEq, Eq, Clone)]
|
||||
pub enum PusTmWrapper<'tm> {
|
||||
@ -298,14 +297,14 @@ pub trait ActiveRequestProvider {
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||
pub struct ActiveRequest {
|
||||
pub struct ActivePusRequest {
|
||||
target_id: TargetId,
|
||||
token: VerificationToken<TcStateStarted>,
|
||||
start_time: UnixTimestamp,
|
||||
timeout: Duration,
|
||||
}
|
||||
|
||||
impl ActiveRequestProvider for ActiveRequest {
|
||||
impl ActiveRequestProvider for ActivePusRequest {
|
||||
fn target_id(&self) -> TargetId {
|
||||
self.target_id
|
||||
}
|
||||
@ -323,30 +322,18 @@ impl ActiveRequestProvider for ActiveRequest {
|
||||
}
|
||||
}
|
||||
|
||||
/// Generic user hook method.
|
||||
///
|
||||
/// This hook method currently serves the following tasks:
|
||||
///
|
||||
/// 1. Pass specific information to the reply handlers which can not be kept inside the
|
||||
/// framework. This includes information like the error codes used for packet verification.
|
||||
/// 2. It exposes callback methods which can be useful to perform custom user operations like
|
||||
/// logging.
|
||||
pub trait ReplyHandlerHook<ActiveRequestType, ReplyType> {
|
||||
fn handle_unexpected_reply(&mut self, reply: &GenericMessage<ReplyType>);
|
||||
fn timeout_callback(&self, active_request: &ActiveRequestType);
|
||||
fn timeout_error_code(&self) -> ResultU16;
|
||||
}
|
||||
|
||||
/// This trait is an abstraction for the routing of PUS request to a dedicated
|
||||
/// recipient using the generic [TargetId].
|
||||
pub trait PusRequestRouter<Request> {
|
||||
type Error;
|
||||
|
||||
fn route(
|
||||
&self,
|
||||
target_id: TargetId,
|
||||
hk_request: Request,
|
||||
token: VerificationToken<TcStateAccepted>,
|
||||
) -> Result<(), Self::Error>;
|
||||
|
||||
fn handle_error(
|
||||
&self,
|
||||
target_id: TargetId,
|
||||
@ -358,6 +345,23 @@ pub trait PusRequestRouter<Request> {
|
||||
);
|
||||
}
|
||||
|
||||
pub trait PusReplyHandler<ActiveRequestInfo: ActiveRequestProvider, ReplyType> {
|
||||
type Error;
|
||||
|
||||
fn handle_reply(
|
||||
&mut self,
|
||||
reply: &GenericMessage<ReplyType>,
|
||||
verification_handler: &impl VerificationReportingProvider,
|
||||
tm_sender: &impl EcssTmSenderCore,
|
||||
) -> Result<bool, Self::Error>;
|
||||
|
||||
fn handle_unexpected_reply(
|
||||
&mut self,
|
||||
reply: &GenericMessage<ReplyType>,
|
||||
tm_sender: &impl EcssTmSenderCore,
|
||||
);
|
||||
}
|
||||
|
||||
#[cfg(feature = "alloc")]
|
||||
pub mod alloc_mod {
|
||||
use hashbrown::HashMap;
|
||||
@ -463,7 +467,7 @@ pub mod alloc_mod {
|
||||
///
|
||||
/// A [VerificationReportingProvider] instance is passed to the user to also allow handling
|
||||
/// of the verification process as part of the PUS standard requirements.
|
||||
pub trait PusTcToRequestConverter<Request> {
|
||||
pub trait PusTcToRequestConverter<ActiveRequestInfo, Request> {
|
||||
type Error;
|
||||
fn convert(
|
||||
&mut self,
|
||||
@ -471,7 +475,7 @@ pub mod alloc_mod {
|
||||
tc: &PusTcReader,
|
||||
time_stamp: &[u8],
|
||||
verif_reporter: &impl VerificationReportingProvider,
|
||||
) -> Result<(TargetId, Request), Self::Error>;
|
||||
) -> Result<(ActiveRequestInfo, Request), Self::Error>;
|
||||
}
|
||||
|
||||
#[derive(Clone, Debug)]
|
||||
@ -513,7 +517,9 @@ pub mod alloc_mod {
|
||||
}
|
||||
}
|
||||
|
||||
/// Generic reply handler structure which can be used to handle replies for a specific PUS service.
|
||||
/*
|
||||
/// Generic reply handler structure which can be used to handle replies for a specific PUS
|
||||
/// service.
|
||||
///
|
||||
/// This is done by keeping track of active requests using an internal map structure. An API
|
||||
/// to register new active requests is exposed as well.
|
||||
@ -524,42 +530,35 @@ pub mod alloc_mod {
|
||||
/// PUS reply handlers. Concrete PUS handlers should constrain the [ActiveRequestProvider] and
|
||||
/// the `ReplyType` generics to specific types tailored towards PUS services in addition to
|
||||
/// providing an API which can process received replies and convert them into verification
|
||||
/// completions or other operation like user hook calls. The framework also provides some concrete
|
||||
/// PUS handlers for common PUS services like the mode, action and housekeeping service.
|
||||
/// completions or other operation like user hook calls. The framework also provides some
|
||||
/// concrete PUS handlers for common PUS services like the mode, action and housekeeping
|
||||
/// service.
|
||||
///
|
||||
/// This object does not automatically update its internal time information used to check for
|
||||
/// timeouts. The user should call the [Self::update_time] and [Self::update_time_from_now] methods
|
||||
/// to do this.
|
||||
/// timeouts. The user should call the [Self::update_time] and [Self::update_time_from_now]
|
||||
/// methods to do this.
|
||||
pub struct PusServiceReplyHandler<
|
||||
VerificationReporter: VerificationReportingProvider,
|
||||
ActiveRequestMap: ActiveRequestMapProvider<ActiveRequestType>,
|
||||
UserHook: ReplyHandlerHook<ActiveRequestType, ReplyType>,
|
||||
TmSender: EcssTmSenderCore,
|
||||
ReplyHook: ReplyHandlerHook<ActiveRequestType, ReplyType>,
|
||||
ActiveRequestType: ActiveRequestProvider,
|
||||
ReplyType,
|
||||
> {
|
||||
pub active_request_map: ActiveRequestMap,
|
||||
pub verification_reporter: VerificationReporter,
|
||||
pub tm_buf: alloc::vec::Vec<u8>,
|
||||
pub current_time: UnixTimestamp,
|
||||
pub user_hook: UserHook,
|
||||
pub tm_sender: TmSender,
|
||||
pub user_hook: ReplyHook,
|
||||
phantom: PhantomData<(ActiveRequestType, ReplyType)>,
|
||||
}
|
||||
|
||||
impl<
|
||||
VerificationReporter: VerificationReportingProvider,
|
||||
ActiveRequestMap: ActiveRequestMapProvider<ActiveRequestType>,
|
||||
UserHook: ReplyHandlerHook<ActiveRequestType, ReplyType>,
|
||||
TmSender: EcssTmSenderCore,
|
||||
ReplyHook: ReplyHandlerHook<ActiveRequestType, ReplyType>,
|
||||
ActiveRequestType: ActiveRequestProvider,
|
||||
ReplyType,
|
||||
>
|
||||
PusServiceReplyHandler<
|
||||
VerificationReporter,
|
||||
ActiveRequestMap,
|
||||
UserHook,
|
||||
TmSender,
|
||||
ReplyHook,
|
||||
ActiveRequestType,
|
||||
ReplyType,
|
||||
>
|
||||
@ -567,15 +566,12 @@ pub mod alloc_mod {
|
||||
#[cfg(feature = "std")]
|
||||
#[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
|
||||
pub fn new_from_now(
|
||||
verification_reporter: VerificationReporter,
|
||||
active_request_map: ActiveRequestMap,
|
||||
fail_data_buf_size: usize,
|
||||
user_hook: UserHook,
|
||||
tm_sender: TmSender,
|
||||
user_hook: ReplyHook,
|
||||
) -> Result<Self, std::time::SystemTimeError> {
|
||||
let current_time = UnixTimestamp::from_now()?;
|
||||
Ok(Self::new(
|
||||
verification_reporter,
|
||||
active_request_map,
|
||||
fail_data_buf_size,
|
||||
user_hook,
|
||||
@ -585,16 +581,14 @@ pub mod alloc_mod {
|
||||
}
|
||||
|
||||
pub fn new(
|
||||
verification_reporter: VerificationReporter,
|
||||
active_request_map: ActiveRequestMap,
|
||||
fail_data_buf_size: usize,
|
||||
user_hook: UserHook,
|
||||
user_hook: ReplyHook,
|
||||
tm_sender: TmSender,
|
||||
init_time: UnixTimestamp,
|
||||
) -> Self {
|
||||
Self {
|
||||
active_request_map,
|
||||
verification_reporter,
|
||||
tm_buf: alloc::vec![0; fail_data_buf_size],
|
||||
current_time: init_time,
|
||||
user_hook,
|
||||
@ -668,6 +662,7 @@ pub mod alloc_mod {
|
||||
self.current_time = time;
|
||||
}
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
||||
#[cfg(feature = "std")]
|
||||
@ -684,13 +679,10 @@ pub mod std_mod {
|
||||
use crate::tmtc::tm_helper::SharedTmPool;
|
||||
use crate::{ChannelId, TargetId};
|
||||
use alloc::vec::Vec;
|
||||
use core::marker::PhantomData;
|
||||
use spacepackets::ecss::tc::PusTcReader;
|
||||
use spacepackets::ecss::tm::PusTmCreator;
|
||||
use spacepackets::ecss::{PusError, WritablePusPacket};
|
||||
use spacepackets::time::cds::TimeProvider;
|
||||
use spacepackets::time::StdTimestampError;
|
||||
use spacepackets::time::TimeWriter;
|
||||
use std::string::String;
|
||||
use std::sync::mpsc;
|
||||
use std::sync::mpsc::TryRecvError;
|
||||
@ -700,7 +692,7 @@ pub mod std_mod {
|
||||
pub use cb_mod::*;
|
||||
|
||||
use super::verification::VerificationReportingProvider;
|
||||
use super::{AcceptedEcssTcAndToken, PusRequestRouter, PusTcToRequestConverter, TcInMemory};
|
||||
use super::{AcceptedEcssTcAndToken, TcInMemory};
|
||||
|
||||
impl From<mpsc::SendError<StoreAddr>> for EcssTmtcError {
|
||||
fn from(_: mpsc::SendError<StoreAddr>) -> Self {
|
||||
@ -974,17 +966,18 @@ pub mod std_mod {
|
||||
}
|
||||
}
|
||||
|
||||
/// This is a high-level handler for the PUS service 8 action service.
|
||||
/// This is a high-level handler for the generic PUS services which need to convert PUS
|
||||
/// commands into a request/reply pattern.
|
||||
///
|
||||
/// It performs the following handling steps:
|
||||
///
|
||||
/// 1. Retrieve the next TC packet from the [PusServiceHelper]. The [EcssTcInMemConverter]
|
||||
/// allows to configure the used telecommand memory backend.
|
||||
/// 2. Convert the TC to a targeted action request using the provided
|
||||
/// [PusActionToRequestConverter]. The generic error type is constrained to the
|
||||
/// [PusTcToRequestConverter]. The generic error type is constrained to the
|
||||
/// [PusPacketHandlingError] for the concrete implementation which offers a packet handler.
|
||||
/// 3. Route the action request using the provided [PusActionRequestRouter].
|
||||
/// 4. Handle all routing errors using the provided [PusRoutingErrorHandler].
|
||||
/// 3. Route the action request using the provided [PusRequestRouter].
|
||||
/*
|
||||
pub struct PusTargetedRequestHandler<
|
||||
TcReceiver: EcssTcReceiverCore,
|
||||
TmSender: EcssTmSenderCore,
|
||||
@ -999,10 +992,12 @@ pub mod std_mod {
|
||||
PusServiceHelper<TcReceiver, TmSender, TcInMemConverter, VerificationReporter>,
|
||||
pub request_converter: RequestConverter,
|
||||
pub request_router: RequestRouter,
|
||||
// pub routing_error_handler: RoutingErrorHandler,
|
||||
phantom: PhantomData<Request>,
|
||||
}
|
||||
|
||||
// pub trait PusReplyHandlerProvider {
|
||||
// fn add_routed_request(&mut self, request_id: RequestId, active_request: ActiveRequest);
|
||||
// }
|
||||
impl<
|
||||
TcReceiver: EcssTcReceiverCore,
|
||||
TmSender: EcssTmSenderCore,
|
||||
@ -1010,7 +1005,6 @@ pub mod std_mod {
|
||||
VerificationReporter: VerificationReportingProvider,
|
||||
RequestConverter: PusTcToRequestConverter<Request, Error = PusPacketHandlingError>,
|
||||
RequestRouter: PusRequestRouter<Request, Error = RoutingError>,
|
||||
// RoutingErrorHandler: PusRoutingErrorHandler<Error = RoutingError>,
|
||||
Request,
|
||||
RoutingError: Clone,
|
||||
>
|
||||
@ -1021,7 +1015,6 @@ pub mod std_mod {
|
||||
VerificationReporter,
|
||||
RequestConverter,
|
||||
RequestRouter,
|
||||
// RoutingErrorHandler,
|
||||
Request,
|
||||
RoutingError,
|
||||
>
|
||||
@ -1042,7 +1035,6 @@ pub mod std_mod {
|
||||
service_helper,
|
||||
request_converter,
|
||||
request_router,
|
||||
// routing_error_handler,
|
||||
phantom: PhantomData,
|
||||
}
|
||||
}
|
||||
@ -1083,7 +1075,7 @@ pub mod std_mod {
|
||||
Ok(PusPacketHandlerResult::RequestHandled)
|
||||
}
|
||||
}
|
||||
|
||||
*/
|
||||
// TODO: All these types could probably be no_std if we implemented error handling ourselves..
|
||||
// but thiserror is really nice, so keep it like this for simplicity for now. Maybe thiserror
|
||||
// will be no_std soon, see https://github.com/rust-lang/rust/issues/103765 .
|
||||
@ -1272,26 +1264,6 @@ pub mod std_mod {
|
||||
pub tm_apid: u16,
|
||||
pub verification_handler: VerificationReporter,
|
||||
}
|
||||
#[cfg(feature = "std")]
|
||||
pub fn get_current_cds_short_timestamp(
|
||||
partial_error: &mut Option<PartialPusHandlingError>,
|
||||
) -> [u8; 7] {
|
||||
let mut time_stamp: [u8; 7] = [0; 7];
|
||||
let time_provider =
|
||||
TimeProvider::from_now_with_u16_days().map_err(PartialPusHandlingError::Time);
|
||||
if let Ok(time_provider) = time_provider {
|
||||
// Can't fail, we have a buffer with the exact required size.
|
||||
time_provider.write_to_bytes(&mut time_stamp).unwrap();
|
||||
} else {
|
||||
*partial_error = Some(time_provider.unwrap_err());
|
||||
}
|
||||
time_stamp
|
||||
}
|
||||
#[cfg(feature = "std")]
|
||||
pub fn get_current_timestamp_ignore_error() -> [u8; 7] {
|
||||
let mut dummy = None;
|
||||
get_current_cds_short_timestamp(&mut dummy)
|
||||
}
|
||||
|
||||
/// This is a high-level PUS packet handler helper.
|
||||
///
|
||||
|
@ -43,45 +43,25 @@ pub mod std_mod {
|
||||
};
|
||||
|
||||
use crate::{
|
||||
mode::{GenericModeReply, ModeRequest},
|
||||
mode::GenericModeReply,
|
||||
pus::{
|
||||
mode::Subservice,
|
||||
verification::{
|
||||
self, FailParams, TcStateStarted, VerificationReportingProvider, VerificationToken,
|
||||
},
|
||||
ActiveRequest, ActiveRequestMapProvider, EcssTmSenderCore, EcssTmtcError,
|
||||
GenericRoutingError, PusServiceReplyHandler, PusTargetedRequestHandler, PusTmWrapper,
|
||||
ReplyHandlerHook,
|
||||
ActivePusRequest, ActiveRequestMapProvider, EcssTmSenderCore, EcssTmtcError,
|
||||
PusServiceReplyHandler, PusTmWrapper, ReplyHandlerHook,
|
||||
},
|
||||
TargetId,
|
||||
};
|
||||
|
||||
pub trait ModeReplyHook: ReplyHandlerHook<ActiveRequest, ModeReply> {
|
||||
pub trait ModeReplyHook: ReplyHandlerHook<ActivePusRequest, ModeReply> {
|
||||
fn wrong_mode_result_code(&self) -> ResultU16;
|
||||
fn can_not_reach_mode_result_code(&self) -> ResultU16;
|
||||
}
|
||||
|
||||
use super::{ModeReply, MODE_SERVICE_ID};
|
||||
|
||||
pub type PusModeServiceRequestHandler<
|
||||
TcReceiver,
|
||||
TmSender,
|
||||
TcInMemConverter,
|
||||
VerificationReporter,
|
||||
RequestConverter,
|
||||
RequestRouter,
|
||||
RoutingError = GenericRoutingError,
|
||||
> = PusTargetedRequestHandler<
|
||||
TcReceiver,
|
||||
TmSender,
|
||||
TcInMemConverter,
|
||||
VerificationReporter,
|
||||
RequestConverter,
|
||||
RequestRouter,
|
||||
ModeRequest,
|
||||
RoutingError,
|
||||
>;
|
||||
|
||||
/// Type definition for a PUS mode servicd reply handler which constrains the
|
||||
/// [PusServiceReplyHandler] active request and reply generics to the [ActiveActionRequest] and
|
||||
/// [ActionReplyPusWithIds] type.
|
||||
@ -95,13 +75,13 @@ pub mod std_mod {
|
||||
ActiveRequestMap,
|
||||
UserHook,
|
||||
TmSender,
|
||||
ActiveRequest,
|
||||
ActivePusRequest,
|
||||
ModeReply,
|
||||
>;
|
||||
|
||||
impl<
|
||||
VerificationReporter: VerificationReportingProvider,
|
||||
ActiveRequestMap: ActiveRequestMapProvider<ActiveRequest>,
|
||||
ActiveRequestMap: ActiveRequestMapProvider<ActivePusRequest>,
|
||||
UserHook: ModeReplyHook,
|
||||
TmSender: EcssTmSenderCore,
|
||||
> PusModeServiceReplyHandler<VerificationReporter, ActiveRequestMap, UserHook, TmSender>
|
||||
@ -116,7 +96,7 @@ pub mod std_mod {
|
||||
) {
|
||||
self.active_request_map.insert(
|
||||
&request_id.into(),
|
||||
ActiveRequest {
|
||||
ActivePusRequest {
|
||||
target_id,
|
||||
token,
|
||||
start_time: self.current_time,
|
||||
|
@ -5,10 +5,9 @@ use super::verification::{
|
||||
VerificationReporterWithVecMpscSender, VerificationReportingProvider,
|
||||
};
|
||||
use super::{
|
||||
get_current_cds_short_timestamp, EcssTcInMemConverter, EcssTcInSharedStoreConverter,
|
||||
EcssTcInVecConverter, EcssTcReceiverCore, EcssTmSenderCore, MpscTcReceiver, PusServiceHelper,
|
||||
TmAsVecSenderWithBoundedMpsc, TmAsVecSenderWithMpsc, TmInSharedPoolSenderWithBoundedMpsc,
|
||||
TmInSharedPoolSenderWithMpsc,
|
||||
EcssTcInMemConverter, EcssTcInSharedStoreConverter, EcssTcInVecConverter, EcssTcReceiverCore,
|
||||
EcssTmSenderCore, MpscTcReceiver, PusServiceHelper, TmAsVecSenderWithBoundedMpsc,
|
||||
TmAsVecSenderWithMpsc, TmInSharedPoolSenderWithBoundedMpsc, TmInSharedPoolSenderWithMpsc,
|
||||
};
|
||||
use crate::pool::PoolProvider;
|
||||
use crate::pus::{PusPacketHandlerResult, PusPacketHandlingError};
|
||||
@ -76,6 +75,7 @@ impl<
|
||||
|
||||
pub fn handle_one_tc(
|
||||
&mut self,
|
||||
time_stamp: &[u8],
|
||||
sched_tc_pool: &mut (impl PoolProvider + ?Sized),
|
||||
) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
let possible_packet = self.service_helper.retrieve_and_accept_next_packet()?;
|
||||
@ -95,15 +95,14 @@ impl<
|
||||
ecss_tc_and_token.token,
|
||||
));
|
||||
}
|
||||
let mut partial_error = None;
|
||||
let time_stamp = get_current_cds_short_timestamp(&mut partial_error);
|
||||
let partial_error = None;
|
||||
match standard_subservice.unwrap() {
|
||||
scheduling::Subservice::TcEnableScheduling => {
|
||||
let start_token = self
|
||||
.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.start_success(ecss_tc_and_token.token, &time_stamp)
|
||||
.start_success(ecss_tc_and_token.token, time_stamp)
|
||||
.expect("Error sending start success");
|
||||
|
||||
self.scheduler.enable();
|
||||
@ -111,7 +110,7 @@ impl<
|
||||
self.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.completion_success(start_token, &time_stamp)
|
||||
.completion_success(start_token, time_stamp)
|
||||
.expect("Error sending completion success");
|
||||
} else {
|
||||
return Err(PusPacketHandlingError::Other(
|
||||
@ -124,7 +123,7 @@ impl<
|
||||
.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.start_success(ecss_tc_and_token.token, &time_stamp)
|
||||
.start_success(ecss_tc_and_token.token, time_stamp)
|
||||
.expect("Error sending start success");
|
||||
|
||||
self.scheduler.disable();
|
||||
@ -132,7 +131,7 @@ impl<
|
||||
self.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.completion_success(start_token, &time_stamp)
|
||||
.completion_success(start_token, time_stamp)
|
||||
.expect("Error sending completion success");
|
||||
} else {
|
||||
return Err(PusPacketHandlingError::Other(
|
||||
@ -145,7 +144,7 @@ impl<
|
||||
.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.start_success(ecss_tc_and_token.token, &time_stamp)
|
||||
.start_success(ecss_tc_and_token.token, time_stamp)
|
||||
.expect("Error sending start success");
|
||||
|
||||
self.scheduler
|
||||
@ -155,7 +154,7 @@ impl<
|
||||
self.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.completion_success(start_token, &time_stamp)
|
||||
.completion_success(start_token, time_stamp)
|
||||
.expect("Error sending completion success");
|
||||
}
|
||||
scheduling::Subservice::TcInsertActivity => {
|
||||
@ -163,7 +162,7 @@ impl<
|
||||
.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.start_success(ecss_tc_and_token.token, &time_stamp)
|
||||
.start_success(ecss_tc_and_token.token, time_stamp)
|
||||
.expect("error sending start success");
|
||||
|
||||
// let mut pool = self.sched_tc_pool.write().expect("locking pool failed");
|
||||
@ -174,7 +173,7 @@ impl<
|
||||
self.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.completion_success(start_token, &time_stamp)
|
||||
.completion_success(start_token, time_stamp)
|
||||
.expect("sending completion success failed");
|
||||
}
|
||||
_ => {
|
||||
@ -241,7 +240,10 @@ mod tests {
|
||||
verification::{RequestId, TcStateAccepted, VerificationToken},
|
||||
EcssTcInSharedStoreConverter,
|
||||
};
|
||||
use crate::pus::{MpscTcReceiver, TmInSharedPoolSenderWithBoundedMpsc};
|
||||
use crate::pus::{
|
||||
MpscTcReceiver, PusPacketHandlerResult, PusPacketHandlingError,
|
||||
TmInSharedPoolSenderWithBoundedMpsc,
|
||||
};
|
||||
use alloc::collections::VecDeque;
|
||||
use delegate::delegate;
|
||||
use spacepackets::ecss::scheduling::Subservice;
|
||||
@ -280,6 +282,12 @@ mod tests {
|
||||
sched_tc_pool,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
let time_stamp = cds::TimeProvider::new_with_u16_days(0, 0).to_vec().unwrap();
|
||||
self.handler
|
||||
.handle_one_tc(&time_stamp, &mut self.sched_tc_pool)
|
||||
}
|
||||
}
|
||||
|
||||
impl PusTestHarness for Pus11HandlerWithStoreTester {
|
||||
@ -347,9 +355,10 @@ mod tests {
|
||||
let token = test_harness.send_tc(&enable_scheduling);
|
||||
|
||||
let request_id = token.req_id();
|
||||
let time_stamp = cds::TimeProvider::new_with_u16_days(0, 0).to_vec().unwrap();
|
||||
test_harness
|
||||
.handler
|
||||
.handle_one_tc(&mut test_harness.sched_tc_pool)
|
||||
.handle_one_tc(&time_stamp, &mut test_harness.sched_tc_pool)
|
||||
.unwrap();
|
||||
test_harness.check_next_verification_tm(1, request_id);
|
||||
test_harness.check_next_verification_tm(3, request_id);
|
||||
@ -407,10 +416,7 @@ mod tests {
|
||||
let token = test_harness.send_tc(&enable_scheduling);
|
||||
|
||||
let request_id = token.req_id();
|
||||
test_harness
|
||||
.handler
|
||||
.handle_one_tc(&mut test_harness.sched_tc_pool)
|
||||
.unwrap();
|
||||
test_harness.handle_one_tc().unwrap();
|
||||
test_harness.check_next_verification_tm(1, request_id);
|
||||
test_harness.check_next_verification_tm(3, request_id);
|
||||
test_harness.check_next_verification_tm(7, request_id);
|
||||
|
@ -11,10 +11,9 @@ use super::verification::{
|
||||
VerificationReporterWithVecMpscSender, VerificationReportingProvider,
|
||||
};
|
||||
use super::{
|
||||
get_current_cds_short_timestamp, EcssTcInMemConverter, EcssTcInSharedStoreConverter,
|
||||
EcssTcInVecConverter, EcssTcReceiverCore, EcssTmSenderCore, MpscTcReceiver, PusServiceHelper,
|
||||
TmAsVecSenderWithBoundedMpsc, TmAsVecSenderWithMpsc, TmInSharedPoolSenderWithBoundedMpsc,
|
||||
TmInSharedPoolSenderWithMpsc,
|
||||
EcssTcInMemConverter, EcssTcInSharedStoreConverter, EcssTcInVecConverter, EcssTcReceiverCore,
|
||||
EcssTmSenderCore, MpscTcReceiver, PusServiceHelper, TmAsVecSenderWithBoundedMpsc,
|
||||
TmAsVecSenderWithMpsc, TmInSharedPoolSenderWithBoundedMpsc, TmInSharedPoolSenderWithMpsc,
|
||||
};
|
||||
|
||||
/// This is a helper class for [std] environments to handle generic PUS 17 (test service) packets.
|
||||
@ -47,7 +46,10 @@ impl<
|
||||
Self { service_helper }
|
||||
}
|
||||
|
||||
pub fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
pub fn handle_one_tc(
|
||||
&mut self,
|
||||
time_stamp: &[u8],
|
||||
) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
let possible_packet = self.service_helper.retrieve_and_accept_next_packet()?;
|
||||
if possible_packet.is_none() {
|
||||
return Ok(PusPacketHandlerResult::Empty);
|
||||
@ -62,12 +64,11 @@ impl<
|
||||
}
|
||||
if tc.subservice() == 1 {
|
||||
let mut partial_error = None;
|
||||
let time_stamp = get_current_cds_short_timestamp(&mut partial_error);
|
||||
let result = self
|
||||
.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.start_success(ecss_tc_and_token.token, &time_stamp)
|
||||
.start_success(ecss_tc_and_token.token, time_stamp)
|
||||
.map_err(|_| PartialPusHandlingError::Verification);
|
||||
let start_token = if let Ok(result) = result {
|
||||
Some(result)
|
||||
@ -78,7 +79,7 @@ impl<
|
||||
// Sequence count will be handled centrally in TM funnel.
|
||||
let mut reply_header =
|
||||
SpHeader::tm_unseg(self.service_helper.common.tm_apid, 0, 0).unwrap();
|
||||
let tc_header = PusTmSecondaryHeader::new_simple(17, 2, &time_stamp);
|
||||
let tc_header = PusTmSecondaryHeader::new_simple(17, 2, time_stamp);
|
||||
let ping_reply = PusTmCreator::new(&mut reply_header, tc_header, &[], true);
|
||||
let result = self
|
||||
.service_helper
|
||||
@ -95,7 +96,7 @@ impl<
|
||||
.service_helper
|
||||
.common
|
||||
.verification_handler
|
||||
.completion_success(start_token, &time_stamp)
|
||||
.completion_success(start_token, time_stamp)
|
||||
.is_err()
|
||||
{
|
||||
partial_error = Some(PartialPusHandlingError::Verification)
|
||||
@ -168,6 +169,7 @@ mod tests {
|
||||
use spacepackets::ecss::tc::{PusTcCreator, PusTcSecondaryHeader};
|
||||
use spacepackets::ecss::tm::PusTmReader;
|
||||
use spacepackets::ecss::PusPacket;
|
||||
use spacepackets::time::{cds, TimeWriter};
|
||||
use spacepackets::{SequenceFlags, SpHeader};
|
||||
|
||||
use super::PusService17TestHandler;
|
||||
@ -208,10 +210,9 @@ mod tests {
|
||||
}
|
||||
}
|
||||
impl SimplePusPacketHandler for Pus17HandlerWithStoreTester {
|
||||
delegate! {
|
||||
to self.handler {
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError>;
|
||||
}
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
let time_stamp = cds::TimeProvider::new_with_u16_days(0, 0).to_vec().unwrap();
|
||||
self.handler.handle_one_tc(&time_stamp)
|
||||
}
|
||||
}
|
||||
|
||||
@ -251,10 +252,9 @@ mod tests {
|
||||
}
|
||||
}
|
||||
impl SimplePusPacketHandler for Pus17HandlerWithVecTester {
|
||||
delegate! {
|
||||
to self.handler {
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError>;
|
||||
}
|
||||
fn handle_one_tc(&mut self) -> Result<PusPacketHandlerResult, PusPacketHandlingError> {
|
||||
let time_stamp = cds::TimeProvider::new_with_u16_days(0, 0).to_vec().unwrap();
|
||||
self.handler.handle_one_tc(&time_stamp)
|
||||
}
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user