CFDP extracted to library #201
@ -31,7 +31,7 @@ default-features = false
|
||||
version = "0.12"
|
||||
default-features = false
|
||||
git = "https://egit.irs.uni-stuttgart.de/rust/spacepackets"
|
||||
branch = "file-data-pdu-update"
|
||||
branch = "eof-pdu-update"
|
||||
|
||||
[dependencies.cobs]
|
||||
git = "https://github.com/robamu/cobs.rs.git"
|
||||
|
@ -4,11 +4,13 @@ use spacepackets::{
|
||||
cfdp::{
|
||||
lv::Lv,
|
||||
pdu::{
|
||||
eof::EofPdu,
|
||||
file_data::FileDataPduCreatorWithReservedDatafield,
|
||||
metadata::{MetadataGenericParams, MetadataPduCreator},
|
||||
CfdpPdu, CommonPduConfig, FileDirectiveType, PduError, PduHeader, WritablePduPacket,
|
||||
},
|
||||
Direction, LargeFileFlag, PduType, SegmentMetadataFlag, SegmentationControl,
|
||||
ConditionCode, Direction, LargeFileFlag, PduType, SegmentMetadataFlag, SegmentationControl,
|
||||
NULL_CHECKSUM_U32,
|
||||
},
|
||||
util::{UnsignedByteField, UnsignedEnum},
|
||||
ByteConversionError,
|
||||
@ -44,12 +46,23 @@ pub enum TransactionStep {
|
||||
pub struct FileParams {
|
||||
pub progress: u64,
|
||||
pub segment_len: u64,
|
||||
//pub crc32: Option<[u8; 4]>,
|
||||
pub crc32: [u8; 4],
|
||||
pub metadata_only: bool,
|
||||
pub file_size: u64,
|
||||
pub empty_file: bool,
|
||||
}
|
||||
|
||||
impl FileParams {
|
||||
pub fn reset(&mut self) {
|
||||
self.progress = 0;
|
||||
self.segment_len = 0;
|
||||
self.crc32 = NULL_CHECKSUM_U32;
|
||||
self.metadata_only = false;
|
||||
self.file_size = 0;
|
||||
self.empty_file = false;
|
||||
}
|
||||
}
|
||||
|
||||
pub struct StateHelper {
|
||||
state: super::State,
|
||||
step: TransactionStep,
|
||||
@ -62,6 +75,7 @@ pub struct TransferState {
|
||||
remote_cfg: RemoteEntityConfig,
|
||||
transmission_mode: super::TransmissionMode,
|
||||
closure_requested: bool,
|
||||
cond_code_eof: Option<ConditionCode>,
|
||||
}
|
||||
|
||||
impl Default for StateHelper {
|
||||
@ -272,6 +286,7 @@ impl<
|
||||
*remote_cfg,
|
||||
transmission_mode,
|
||||
closure_requested,
|
||||
None,
|
||||
));
|
||||
Ok(())
|
||||
}
|
||||
@ -299,6 +314,10 @@ impl<
|
||||
return Ok(result);
|
||||
}
|
||||
}
|
||||
if self.state_helper.step == TransactionStep::SendingEof {
|
||||
// TODO: Checksum calculation using VFS.
|
||||
self.prepare_and_send_eof_pdu(0)?;
|
||||
}
|
||||
Ok(0)
|
||||
}
|
||||
|
||||
@ -306,6 +325,7 @@ impl<
|
||||
&mut self,
|
||||
cfdp_user: &mut impl CfdpUser,
|
||||
) -> Result<(), SourceError> {
|
||||
self.fparams.reset();
|
||||
let tstate = &self.tstate.expect("transfer state unexpectedly empty");
|
||||
if !self.put_request_cacher.has_source_file() {
|
||||
self.fparams.metadata_only = true;
|
||||
@ -361,7 +381,10 @@ impl<
|
||||
}
|
||||
|
||||
fn prepare_and_send_metadata_pdu(&mut self) -> Result<(), PduError> {
|
||||
let tstate = &self.tstate.expect("transfer state unexpectedly empty");
|
||||
let tstate = self
|
||||
.tstate
|
||||
.as_ref()
|
||||
.expect("transfer state unexpectedly empty");
|
||||
let metadata_params = MetadataGenericParams::new(
|
||||
tstate.closure_requested,
|
||||
tstate.remote_cfg.default_crc_type,
|
||||
@ -375,7 +398,7 @@ impl<
|
||||
Lv::new_empty(),
|
||||
self.put_request_cacher.opts_slice(),
|
||||
);
|
||||
return self.pdu_send_helper(metadata_pdu);
|
||||
return self.pdu_send_helper(&metadata_pdu);
|
||||
}
|
||||
let metadata_pdu = MetadataPduCreator::new(
|
||||
PduHeader::new_no_file_data(self.pdu_conf, 0),
|
||||
@ -384,7 +407,7 @@ impl<
|
||||
Lv::new_from_str(self.put_request_cacher.dest_file().unwrap()).unwrap(),
|
||||
self.put_request_cacher.opts_slice(),
|
||||
);
|
||||
self.pdu_send_helper(metadata_pdu)
|
||||
self.pdu_send_helper(&metadata_pdu)
|
||||
}
|
||||
|
||||
fn file_data_fsm(&mut self) -> Result<ControlFlow<u32>, SourceError> {
|
||||
@ -397,9 +420,10 @@ impl<
|
||||
{
|
||||
return Ok(ControlFlow::Break(1));
|
||||
}
|
||||
if self.fparams.empty_file {
|
||||
if self.fparams.empty_file || self.fparams.progress >= self.fparams.file_size {
|
||||
// EOF is still expected.
|
||||
self.state_helper.step = TransactionStep::SendingEof;
|
||||
self.tstate.as_mut().unwrap().cond_code_eof = Some(ConditionCode::NoError);
|
||||
} else if self.fparams.metadata_only {
|
||||
// Special case: Metadata Only, no EOF required.
|
||||
if self.tstate.as_ref().unwrap().closure_requested {
|
||||
@ -492,7 +516,36 @@ impl<
|
||||
Ok(true)
|
||||
}
|
||||
|
||||
fn pdu_send_helper(&self, pdu: impl WritablePduPacket + CfdpPdu) -> Result<(), PduError> {
|
||||
fn prepare_and_send_eof_pdu(&mut self, checksum: u32) -> Result<(), PduError> {
|
||||
let tstate = self
|
||||
.tstate
|
||||
.as_ref()
|
||||
.expect("transfer state unexpectedly empty");
|
||||
//let checksum_u32 = u32::from_be_bytes(self.fparams.crc32);
|
||||
let eof_pdu = EofPdu::new(
|
||||
PduHeader::new_no_file_data(self.pdu_conf, 0),
|
||||
tstate.cond_code_eof.unwrap_or(ConditionCode::NoError),
|
||||
checksum,
|
||||
self.fparams.file_size,
|
||||
None,
|
||||
);
|
||||
self.pdu_send_helper(&eof_pdu)?;
|
||||
/*
|
||||
*
|
||||
assert self._params.cond_code_eof is not None
|
||||
self._add_packet_to_be_sent(
|
||||
EofPdu(
|
||||
file_checksum=checksum,
|
||||
file_size=self._params.fp.progress,
|
||||
pdu_conf=self._params.pdu_conf,
|
||||
condition_code=self._params.cond_code_eof,
|
||||
)
|
||||
)
|
||||
*/
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn pdu_send_helper(&self, pdu: &(impl WritablePduPacket + CfdpPdu)) -> Result<(), PduError> {
|
||||
let mut pdu_buffer_mut = self.pdu_buffer.borrow_mut();
|
||||
let written_len = pdu.write_to_bytes(&mut pdu_buffer_mut)?;
|
||||
self.pdu_sender.send_pdu(
|
||||
|
Loading…
Reference in New Issue
Block a user