use crate::core::{FrameLayout, ModulationParams, Protocol, ProtocolId, SyncBlock, SyncMode};
use crate::fec::Ldpc240_101;
use crate::msg::Wsjt77Message;
pub mod decode;
pub mod encode;
#[derive(Copy, Clone, Debug, Default)]
pub struct Fst4s60;
impl ModulationParams for Fst4s60 {
const NTONES: u32 = 4;
const BITS_PER_SYMBOL: u32 = 2;
const NSPS: u32 = 3_840;
const SYMBOL_DT: f32 = 0.32;
const TONE_SPACING_HZ: f32 = 3.125;
const GRAY_MAP: &'static [u8] = &[0, 1, 3, 2];
const GFSK_BT: f32 = 1.0;
const GFSK_HMOD: f32 = 1.0;
const NFFT_PER_SYMBOL_FACTOR: u32 = 2;
const NSTEP_PER_SYMBOL: u32 = 2;
const NDOWN: u32 = 192;
}
impl FrameLayout for Fst4s60 {
const N_DATA: u32 = 120;
const N_SYNC: u32 = 40; const N_SYMBOLS: u32 = 160;
const N_RAMP: u32 = 0; const SYNC_MODE: SyncMode = SyncMode::Block(&FST4_SYNC_BLOCKS);
const T_SLOT_S: f32 = 60.0;
const TX_START_OFFSET_S: f32 = 1.0;
}
impl Protocol for Fst4s60 {
type Fec = Ldpc240_101;
type Msg = Wsjt77Message;
const ID: ProtocolId = ProtocolId::Fst4;
}
const FST4_SYNC_A: [u8; 8] = [0, 1, 3, 2, 1, 0, 2, 3];
const FST4_SYNC_B: [u8; 8] = [2, 3, 1, 0, 3, 2, 0, 1];
const FST4_SYNC_BLOCKS: [SyncBlock; 5] = [
SyncBlock {
start_symbol: 0,
pattern: &FST4_SYNC_A,
},
SyncBlock {
start_symbol: 38,
pattern: &FST4_SYNC_B,
},
SyncBlock {
start_symbol: 76,
pattern: &FST4_SYNC_A,
},
SyncBlock {
start_symbol: 114,
pattern: &FST4_SYNC_B,
},
SyncBlock {
start_symbol: 152,
pattern: &FST4_SYNC_A,
},
];
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn fst4s60_trait_surface() {
assert_eq!(<Fst4s60 as ModulationParams>::NTONES, 4);
assert_eq!(<Fst4s60 as ModulationParams>::NSPS, 3_840);
assert!((<Fst4s60 as ModulationParams>::SYMBOL_DT - 0.32).abs() < 1e-6,);
assert_eq!(<Fst4s60 as FrameLayout>::N_SYMBOLS, 160);
assert_eq!(<Fst4s60 as FrameLayout>::N_DATA, 120);
assert_eq!(<Fst4s60 as FrameLayout>::N_SYNC, 40);
let blocks = <Fst4s60 as FrameLayout>::SYNC_MODE.blocks();
assert_eq!(blocks.len(), 5);
assert_eq!(
blocks.iter().map(|b| b.start_symbol).collect::<Vec<_>>(),
vec![0, 38, 76, 114, 152],
);
assert_eq!(blocks[0].pattern.len(), 8);
use crate::core::FecCodec;
assert_eq!(<<Fst4s60 as Protocol>::Fec as FecCodec>::N, 240);
assert_eq!(<<Fst4s60 as Protocol>::Fec as FecCodec>::K, 101);
}
}