Added first draft wspr transmission routine
This commit is contained in:
parent
37cc576678
commit
75992bfe79
|
@ -1,10 +1,12 @@
|
|||
use cortex_m::prelude::*;
|
||||
use cortex_m::{asm::wfi, prelude::*};
|
||||
use embedded_hal::digital::v2::{OutputPin, ToggleableOutputPin};
|
||||
use nb::{self, block};
|
||||
use nmea0183::{ParseResult, Parser};
|
||||
use stm32f1xx_hal::{
|
||||
delay::Delay,
|
||||
gpio::{gpiob, gpioc, Alternate, Floating, Input, Output, PushPull},
|
||||
gpio::{gpiob, gpioc, Alternate, Floating, Input, OpenDrain, Output, PushPull},
|
||||
i2c::BlockingI2c,
|
||||
pac::I2C1,
|
||||
prelude::*,
|
||||
serial::Serial,
|
||||
stm32,
|
||||
|
@ -18,6 +20,28 @@ pub use setup::setup;
|
|||
|
||||
use crate::si5153;
|
||||
use crate::time;
|
||||
use crate::wspr;
|
||||
|
||||
pub struct App {
|
||||
delay: Delay,
|
||||
board_led: gpioc::PC13<Output<PushPull>>,
|
||||
serial: Serial<
|
||||
stm32::USART3,
|
||||
(
|
||||
gpiob::PB10<Alternate<PushPull>>,
|
||||
gpiob::PB11<Input<Floating>>,
|
||||
),
|
||||
>,
|
||||
i2c: BlockingI2c<
|
||||
I2C1,
|
||||
(
|
||||
gpiob::PB6<Alternate<OpenDrain>>,
|
||||
gpiob::PB7<Alternate<OpenDrain>>,
|
||||
),
|
||||
>,
|
||||
gps_parser: Parser,
|
||||
locator: arrayvec::ArrayString<6>,
|
||||
}
|
||||
|
||||
// For PLL with 800MHz
|
||||
const WSPR_SYMBOLS: [si5153::PllParams; 4] = [
|
||||
|
@ -51,28 +75,62 @@ const WSPR_SYMBOLS: [si5153::PllParams; 4] = [
|
|||
},
|
||||
];
|
||||
|
||||
pub struct App {
|
||||
delay: Delay,
|
||||
board_led: gpioc::PC13<Output<PushPull>>,
|
||||
serial: Serial<
|
||||
stm32::USART3,
|
||||
(
|
||||
gpiob::PB10<Alternate<PushPull>>,
|
||||
gpiob::PB11<Input<Floating>>,
|
||||
),
|
||||
>,
|
||||
gps_parser: Parser,
|
||||
locator: arrayvec::ArrayString<6>,
|
||||
}
|
||||
|
||||
impl App {
|
||||
pub fn run(mut self) -> ! {
|
||||
let callsign = arrayvec::ArrayString::<6>::from("DL1SSK").unwrap();
|
||||
|
||||
defmt::info!("Application Startup!");
|
||||
|
||||
let mut last_ts = 0;
|
||||
let mut si_pll = si5153::Si5153::new(&self.i2c);
|
||||
si_pll.init(&mut self.i2c, 25000000, 800000000, 800000000);
|
||||
si_pll.set_ms_source(&mut self.i2c, si5153::Multisynth::MS0, si5153::PLL::A);
|
||||
|
||||
defmt::info!("PLL setup complete.");
|
||||
|
||||
let mut transmitting = false;
|
||||
let mut symbol_start = time::get();
|
||||
let mut symbol_idx: usize = 0;
|
||||
let mut message: [u8; 162] = [0; 162];
|
||||
|
||||
loop {
|
||||
self.poll_gps();
|
||||
|
||||
if !transmitting {
|
||||
let ts = time::get();
|
||||
if self.locator.len() > 0
|
||||
&& ts.minutes % 2 == 0
|
||||
&& ts.seconds > 1.0
|
||||
&& ts.seconds < 2.0
|
||||
{
|
||||
defmt::info!("Starting tranmission");
|
||||
message = wspr::encode_message(&callsign, &self.locator, 27);
|
||||
symbol_start = ts;
|
||||
symbol_idx = 0;
|
||||
si_pll.write_synth_params(
|
||||
&mut self.i2c,
|
||||
si5153::Multisynth::MS0,
|
||||
&WSPR_SYMBOLS[message[symbol_idx] as usize],
|
||||
);
|
||||
si_pll.enable_ms_output(&mut self.i2c, si5153::Multisynth::MS0);
|
||||
}
|
||||
} else {
|
||||
let ts = time::get();
|
||||
if (ts.seconds - symbol_start.seconds) >= 0.683 {
|
||||
symbol_start = ts;
|
||||
symbol_idx += 1;
|
||||
if symbol_idx < 162 {
|
||||
si_pll.write_synth_params(
|
||||
&mut self.i2c,
|
||||
si5153::Multisynth::MS0,
|
||||
&WSPR_SYMBOLS[message[symbol_idx] as usize],
|
||||
);
|
||||
} else {
|
||||
si_pll.disable_ms_output(&mut self.i2c, si5153::Multisynth::MS0);
|
||||
transmitting = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
wfi();
|
||||
}
|
||||
|
||||
//exit();
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
use stm32f1xx_hal::{
|
||||
delay::Delay,
|
||||
i2c,
|
||||
pac::Interrupt,
|
||||
prelude::*,
|
||||
serial::{Config, Serial},
|
||||
|
@ -59,12 +60,30 @@ pub fn setup(cp: cortex_m::peripheral::Peripherals, dp: stm32::Peripherals) -> A
|
|||
|
||||
let gps_parser = Parser::new();
|
||||
|
||||
let scl = gpiob.pb6.into_alternate_open_drain(&mut gpiob.crl);
|
||||
let sda = gpiob.pb7.into_alternate_open_drain(&mut gpiob.crl);
|
||||
let mut i2c = i2c::BlockingI2c::i2c1(
|
||||
dp.I2C1,
|
||||
(scl, sda),
|
||||
&mut afio.mapr,
|
||||
i2c::Mode::Standard {
|
||||
frequency: 400_000.hz(),
|
||||
},
|
||||
clocks,
|
||||
&mut rcc.apb1,
|
||||
5,
|
||||
1,
|
||||
5,
|
||||
5,
|
||||
);
|
||||
|
||||
time::setup(dp.TIM2, &clocks, &mut rcc.apb1);
|
||||
|
||||
App {
|
||||
delay,
|
||||
board_led,
|
||||
serial,
|
||||
i2c,
|
||||
gps_parser,
|
||||
locator: arrayvec::ArrayString::new(),
|
||||
}
|
||||
|
|
|
@ -150,7 +150,7 @@ where
|
|||
}
|
||||
}
|
||||
|
||||
pub fn write_params(&self, i2c: &mut I2C, base: u8, params: &PllParams) {
|
||||
fn write_params(&self, i2c: &mut I2C, base: u8, params: &PllParams) {
|
||||
let data: [u8; 9] = [
|
||||
base,
|
||||
((params.p3 & 0x00FF00) >> 8) as u8,
|
||||
|
@ -168,4 +168,8 @@ where
|
|||
panic!("i2c write failed. regAdder: {}", base)
|
||||
}
|
||||
}
|
||||
|
||||
pub fn write_synth_params(&self, i2c: &mut I2C, synth: Multisynth, params: &PllParams) {
|
||||
self.write_params(i2c, synth.base_address(), params);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -128,7 +128,7 @@ fn add_sync(symbols: &mut [u8; WSPR_LENGTH]) {
|
|||
}
|
||||
}
|
||||
|
||||
pub fn endcode_message(
|
||||
pub fn encode_message(
|
||||
call_sign: &arrayvec::ArrayString<6>,
|
||||
locator: &arrayvec::ArrayString<6>,
|
||||
power: u8,
|
||||
|
|
|
@ -15,7 +15,7 @@ mod tests {
|
|||
fn test_encoding() {
|
||||
let call_sign = ArrayString::<6>::from(" K1ABC").unwrap();
|
||||
let loc = ArrayString::<6>::from("FN42").unwrap();
|
||||
let symbols = wspr::endcode_message(&call_sign, &loc, 37);
|
||||
let symbols = wspr::encode_message(&call_sign, &loc, 37);
|
||||
|
||||
let expected_symbols: [u8; 162] = [
|
||||
3, 3, 0, 0, 2, 0, 0, 0, 1, 0, 2, 0, 1, 3, 1, 2, 2, 2, 1, 0, 0, 3, 2, 3, 1, 3, 3, 2, 2,
|
||||
|
|
Loading…
Reference in New Issue