Change rak4631 feature to sx126x, removing use in board-specific processing; simplify the P2P examples; correct RSSI computation.

This commit is contained in:
ceekdee
2022-10-10 12:35:42 -05:00
parent 79ba20d315
commit 327d3cf0df
7 changed files with 61 additions and 127 deletions

View File

@ -18,7 +18,7 @@ embassy-nrf = { version = "0.1.0", path = "../../embassy-nrf", features = ["defm
embassy-net = { version = "0.1.0", path = "../../embassy-net", features = ["defmt", "tcp", "dhcpv4", "medium-ethernet", "pool-16"], optional = true }
embassy-usb = { version = "0.1.0", path = "../../embassy-usb", features = ["defmt"], optional = true }
embedded-io = "0.3.0"
embassy-lora = { version = "0.1.0", path = "../../embassy-lora", features = ["rak4631", "time", "defmt"], optional = true }
embassy-lora = { version = "0.1.0", path = "../../embassy-lora", features = ["sx126x", "time", "defmt"], optional = true }
lorawan-device = { version = "0.8.0", default-features = false, features = ["async"], optional = true }
lorawan = { version = "0.7.1", default-features = false, features = ["default-crypto"], optional = true }

View File

@ -1,4 +1,6 @@
//! This example runs on the RAK4631 WisBlock, which has an nRF52840 MCU and Semtech Sx126x radio.
//! Other nrf/sx126x combinations may work with appropriate pin modifications.
//! It demonstates LORA P2P functionality in conjunction with example lora_p2p_sense.rs.
#![no_std]
#![no_main]
#![macro_use]
@ -18,7 +20,7 @@ use {defmt_rtt as _, panic_probe as _};
async fn main(_spawner: Spawner) {
let p = embassy_nrf::init(Default::default());
let mut spi_config = spim::Config::default();
spi_config.frequency = spim::Frequency::M1; // M16 ???
spi_config.frequency = spim::Frequency::M16;
let mut radio = {
let irq = interrupt::take!(SPIM1_SPIS1_TWIM1_TWIS1_SPI1_TWI1);
@ -47,38 +49,30 @@ async fn main(_spawner: Spawner) {
Timer::after(Duration::from_secs(5)).await;
start_indicator.set_low();
match radio.lora.sleep().await {
Ok(()) => info!("Sleep successful"),
Err(err) => info!("Sleep unsuccessful = {}", err),
loop {
let rf_config = RfConfig {
frequency: 903900000, // channel in Hz
bandwidth: Bandwidth::_250KHz,
spreading_factor: SpreadingFactor::_10,
coding_rate: CodingRate::_4_8,
};
let mut buffer = [00u8; 100];
// P2P receive
match radio.rx(rf_config, &mut buffer).await {
Ok((buffer_len, rx_quality)) => info!(
"RX received = {:?} with length = {} rssi = {} snr = {}",
&buffer[0..buffer_len],
buffer_len,
rx_quality.rssi(),
rx_quality.snr()
),
Err(err) => info!("RX error = {}", err),
}
debug_indicator.set_high();
Timer::after(Duration::from_secs(2)).await;
debug_indicator.set_low();
}
let rf_config = RfConfig {
frequency: 903900000, // channel in Hz
bandwidth: Bandwidth::_250KHz,
spreading_factor: SpreadingFactor::_10,
coding_rate: CodingRate::_4_8,
};
let mut buffer = [00u8; 100];
// P2P receive
match radio.rx(rf_config, &mut buffer).await {
Ok((buffer_len, rx_quality)) => info!(
"RX received = {:?} with length = {} rssi = {} snr = {}",
&buffer[0..buffer_len],
buffer_len,
rx_quality.rssi(),
rx_quality.snr()
),
Err(err) => info!("RX error = {}", err),
}
match radio.lora.sleep().await {
Ok(()) => info!("Sleep successful"),
Err(err) => info!("Sleep unsuccessful = {}", err),
}
debug_indicator.set_high();
Timer::after(Duration::from_secs(5)).await;
debug_indicator.set_low();
}

View File

@ -1,4 +1,6 @@
//! This example runs on the RAK4631 WisBlock, which has an nRF52840 MCU and Semtech Sx126x radio.
//! Other nrf/sx126x combinations may work with appropriate pin modifications.
//! It demonstates LORA P2P functionality in conjunction with example lora_p2p_report.rs.
#![no_std]
#![no_main]
#![macro_use]
@ -9,8 +11,7 @@
use defmt::*;
use embassy_executor::Spawner;
use embassy_lora::sx126x::*;
use embassy_nrf::gpio::{AnyPin, Input, Level, Output, OutputDrive, Pin as _, Pull};
use embassy_nrf::temp::Temp;
use embassy_nrf::gpio::{Input, Level, Output, OutputDrive, Pin as _, Pull};
use embassy_nrf::{interrupt, spim};
use embassy_sync::blocking_mutex::raw::CriticalSectionRawMutex;
use embassy_sync::pubsub::{PubSubChannel, Publisher};
@ -18,10 +19,6 @@ use embassy_time::{Duration, Timer};
use lorawan_device::async_device::radio::{Bandwidth, CodingRate, PhyRxTx, RfConfig, SpreadingFactor, TxConfig};
use {defmt_rtt as _, panic_probe as _, panic_probe as _};
// Sensor packet constants
const TEMPERATURE_UID: u8 = 0x01;
const MOTION_UID: u8 = 0x02;
// Message bus: queue of 2, 1 subscriber (Lora P2P), 2 publishers (temperature, motion detection)
static MESSAGE_BUS: PubSubChannel<CriticalSectionRawMutex, Message, 2, 1, 2> = PubSubChannel::new();
@ -32,53 +29,20 @@ enum Message {
}
#[embassy_executor::task]
async fn temperature_task(
mut temperature: Temp<'static>,
publisher: Publisher<'static, CriticalSectionRawMutex, Message, 2, 1, 2>,
) {
Timer::after(Duration::from_secs(45)).await; // stabilize for 45 seconds
let mut temperature_reporting_threshhold = 10;
async fn temperature_task(publisher: Publisher<'static, CriticalSectionRawMutex, Message, 2, 1, 2>) {
// Publish a fake temperature every 43 seconds, minimizing LORA traffic.
loop {
let value = temperature.read().await;
let mut temperature_val = value.to_num::<i32>();
info!("Temperature: {}", temperature_val);
// only report every 2 degree Celsius drops, from 9 through 5, but starting at 3 always report
if temperature_val == 8 || temperature_val == 6 || temperature_val == 4 {
temperature_val += 1;
}
if temperature_reporting_threshhold > temperature_val
&& (temperature_val == 9 || temperature_val == 7 || temperature_val == 5)
{
temperature_reporting_threshhold = temperature_val;
publisher.publish(Message::Temperature(temperature_val)).await;
} else if temperature_val <= 3 {
publisher.publish(Message::Temperature(temperature_val)).await;
}
Timer::after(Duration::from_secs(20 * 60)).await;
Timer::after(Duration::from_secs(43)).await;
publisher.publish(Message::Temperature(9)).await;
}
}
#[embassy_executor::task]
async fn motion_detection_task(
mut pir_pin: Input<'static, AnyPin>,
publisher: Publisher<'static, CriticalSectionRawMutex, Message, 2, 1, 2>,
) {
Timer::after(Duration::from_secs(30)).await; // stabilize for 30 seconds
async fn motion_detection_task(publisher: Publisher<'static, CriticalSectionRawMutex, Message, 2, 1, 2>) {
// Publish a fake motion detection every 79 seconds, minimizing LORA traffic.
loop {
// wait for motion detection
pir_pin.wait_for_low().await;
Timer::after(Duration::from_secs(79)).await;
publisher.publish(Message::MotionDetected).await;
// wait a minute before setting up for more motion detection
Timer::after(Duration::from_secs(60)).await;
}
}
@ -91,7 +55,7 @@ async fn main(spawner: Spawner) {
let motion_detection_publisher = unwrap!(MESSAGE_BUS.publisher());
let mut spi_config = spim::Config::default();
spi_config.frequency = spim::Frequency::M1; // M16 ???
spi_config.frequency = spim::Frequency::M16;
let mut radio = {
let irq = interrupt::take!(SPIM1_SPIS1_TWIM1_TWIS1_SPI1_TWI1);
@ -113,15 +77,7 @@ async fn main(spawner: Spawner) {
}
};
// set up for the temperature task
let temperature_irq = interrupt::take!(TEMP);
let temperature = Temp::new(p.TEMP, temperature_irq);
// set the motion detection pin
let pir_pin = Input::new(p.P0_10.degrade(), Pull::Up);
let mut start_indicator = Output::new(p.P1_04, Level::Low, OutputDrive::Standard);
let mut debug_indicator = Output::new(p.P1_03, Level::Low, OutputDrive::Standard);
start_indicator.set_high();
Timer::after(Duration::from_secs(5)).await;
@ -132,15 +88,15 @@ async fn main(spawner: Spawner) {
Err(err) => info!("Sleep unsuccessful = {}", err),
}
unwrap!(spawner.spawn(temperature_task(temperature, temperature_publisher)));
unwrap!(spawner.spawn(motion_detection_task(pir_pin, motion_detection_publisher)));
unwrap!(spawner.spawn(temperature_task(temperature_publisher)));
unwrap!(spawner.spawn(motion_detection_task(motion_detection_publisher)));
loop {
let message = lora_tx_subscriber.next_message_pure().await;
let tx_config = TxConfig {
// 11 byte maximum payload for Bandwidth 125 and SF 10
pw: 20, // up to 20 // 5 ???
pw: 10, // up to 20
rf: RfConfig {
frequency: 903900000, // channel in Hz, not MHz
bandwidth: Bandwidth::_250KHz,
@ -149,13 +105,13 @@ async fn main(spawner: Spawner) {
},
};
let mut buffer = [TEMPERATURE_UID, 0xffu8, MOTION_UID, 0x00u8];
let mut buffer = [0x00u8];
match message {
Message::Temperature(temperature) => buffer[1] = temperature as u8,
Message::MotionDetected => buffer[3] = 0x01u8,
Message::Temperature(temperature) => buffer[0] = temperature as u8,
Message::MotionDetected => buffer[0] = 0x01u8,
};
// crypto for text ???
// unencrypted
match radio.tx(tx_config, &buffer).await {
Ok(ret_val) => info!("TX ret_val = {}", ret_val),
Err(err) => info!("TX error = {}", err),
@ -165,9 +121,5 @@ async fn main(spawner: Spawner) {
Ok(()) => info!("Sleep successful"),
Err(err) => info!("Sleep unsuccessful = {}", err),
}
debug_indicator.set_high();
Timer::after(Duration::from_secs(5)).await;
debug_indicator.set_low();
}
}