tweaking to fix misc. fake pic errors
This commit is contained in:
@ -147,6 +147,8 @@ impl BleServer {
|
||||
.on_write(closure!(clone sender, |args: &mut OnWriteArgs| {
|
||||
on_bluetooth_cmd(&sender, args, Commands::BluetoothDown {data: Button::Released})
|
||||
}));
|
||||
let button_down_name = button_down.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
button_down_name.lock().set_value(b"Command Down");
|
||||
// --- Button Stop Bluetooth GATT --------------------------------------------------------
|
||||
let button_stop = lift_service.lock().create_characteristic(
|
||||
UUID_BUTTON_STOP,
|
||||
@ -156,6 +158,8 @@ impl BleServer {
|
||||
.on_write(closure!(clone sender, |args: &mut OnWriteArgs| {
|
||||
on_bluetooth_cmd(&sender, args, Commands::BluetoothStop {data: Button::Released})
|
||||
}));
|
||||
let button_stop_name = button_stop.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
button_stop_name.lock().set_value(b"Command Stop");
|
||||
// --- Button Aux Bluetooth GATT --------------------------------------------------------
|
||||
let button_aux = lift_service.lock().create_characteristic(
|
||||
UUID_BUTTON_AUX,
|
||||
@ -165,6 +169,8 @@ impl BleServer {
|
||||
.on_write(closure!(clone sender, |args: &mut OnWriteArgs| {
|
||||
on_bluetooth_cmd(&sender, args, Commands::BluetoothAux {data: Button::Released})
|
||||
}));
|
||||
let button_aux_name = button_aux.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
button_aux_name.lock().set_value(b"Command Aux");
|
||||
// --- Button Learn Bluetooth GATT --------------------------------------------------------
|
||||
let button_learn = lift_service.lock().create_characteristic(
|
||||
UUID_BUTTON_LEARN,
|
||||
@ -174,6 +180,8 @@ impl BleServer {
|
||||
.on_write(closure!(clone sender, |args: &mut OnWriteArgs| {
|
||||
on_bluetooth_cmd(&sender, args, Commands::BluetoothLearn {data: Button::Released})
|
||||
}));
|
||||
let button_learn_name = button_learn.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
button_learn_name.lock().set_value(b"Command Learn");
|
||||
// --- Button Auto Bluetooth GATT --------------------------------------------------------
|
||||
let button_auto = lift_service.lock().create_characteristic(
|
||||
UUID_BUTTON_AUTO,
|
||||
@ -183,6 +191,8 @@ impl BleServer {
|
||||
.on_write(closure!(clone sender, |args: &mut OnWriteArgs| {
|
||||
on_bluetooth_cmd(&sender, args, Commands::BluetoothAuto {data: Button::Released})
|
||||
}));
|
||||
let button_auto_name = button_auto.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
button_auto_name.lock().set_value(b"Command Learn");
|
||||
// --- Device Name Bluetooth GATT --------------------------------------------------------
|
||||
let device_name = lift_service.lock().create_characteristic(
|
||||
UUID_BLUETOOTH_NAME,
|
||||
@ -197,21 +207,29 @@ impl BleServer {
|
||||
UUID_STATUS_LIMITS,
|
||||
NimbleProperties::READ | NimbleProperties::INDICATE,
|
||||
);
|
||||
let status_limits_name = status_limits.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
status_limits_name.lock().set_value(b"Status of limits");
|
||||
// --- Status Motor Bluetooth GATT --------------------------------------------------------
|
||||
let status_motor = lift_service.lock().create_characteristic(
|
||||
UUID_STATUS_MOTOR,
|
||||
NimbleProperties::READ | NimbleProperties::INDICATE,
|
||||
);
|
||||
let status_motor_name = status_limits.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
status_motor_name.lock().set_value(b"Status of motors");
|
||||
// --- Status Status Bluetooth GATT --------------------------------------------------------
|
||||
let status_status = lift_service.lock().create_characteristic(
|
||||
UUID_STATUS_STATUS,
|
||||
NimbleProperties::READ | NimbleProperties::INDICATE,
|
||||
);
|
||||
let status_status_name = status_limits.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
status_status_name.lock().set_value(b"Status flags");
|
||||
// --- Status Reason Bluetooth GATT --------------------------------------------------------
|
||||
let status_reason = lift_service.lock().create_characteristic(
|
||||
UUID_STATUS_REASON,
|
||||
NimbleProperties::READ | NimbleProperties::INDICATE,
|
||||
);
|
||||
let status_reason_name = status_limits.lock().create_descriptor(BleUuid::Uuid16(0x2901), DescriptorProperties::READ);
|
||||
status_reason_name.lock().set_value(b"Status reason");
|
||||
|
||||
// Default to not pairable
|
||||
self.advertise_unpairable()?;
|
||||
|
||||
@ -100,6 +100,7 @@ impl<Q: PartialEq, S: Clone> MessageTimer<Q, S> {
|
||||
Err(_) => {
|
||||
trace!("Timeout reached");
|
||||
self.send_q.send(self.done.clone()).await.expect("Failed to send timeout");
|
||||
self.state = State::Stopped;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -23,14 +23,14 @@ use ::{
|
||||
//time::Duration, // could also use core::time::Duration?
|
||||
},
|
||||
core::time::Duration,
|
||||
std::sync::Arc,
|
||||
};
|
||||
|
||||
use async_channel::Sender;
|
||||
use log::*; //{trace, debug, info, warn, error}
|
||||
|
||||
use gem_remotes_lib::{
|
||||
Button,
|
||||
Commands
|
||||
Button, Commands, LimitStatus, EMPTY_LIMITS
|
||||
};
|
||||
|
||||
#[derive(Command)]
|
||||
@ -61,10 +61,37 @@ pub enum Menu{//<'a> {
|
||||
/// 0 for not pressed, 1 for pressed
|
||||
data: u8,
|
||||
},
|
||||
/// Send a bluetooth characteristic: Limits
|
||||
BluetoothTopLimit { data: u8 },
|
||||
/// Send a bluetooth characteristic: Limits
|
||||
BluetoothBottomLimit { data: u8 },
|
||||
/// Send a bluetooth characteristic: Aux
|
||||
BluetoothAux {
|
||||
/// 0 for not pressed, 1 for pressed
|
||||
data: u8,
|
||||
},
|
||||
/// Send command from Fake PIC to toggle Aux
|
||||
FPicAux,
|
||||
/// Send command from Fake PIC to toggle Auto
|
||||
FPicAuto,
|
||||
/// Send command from Fake PIC to trigger learn mode
|
||||
FPicLearn,
|
||||
/// Send command from Fake PIC that is button press Up
|
||||
FPicUp,
|
||||
/// Send command from Fake PIC that is button press Down
|
||||
FPicDown,
|
||||
/// Send command from Fake PIC that is button press Stop (Can also be used as Up or Down release)
|
||||
FPicStop,
|
||||
/// Send command from Fake PIC to toggle Panic
|
||||
FPicPanic,
|
||||
/// Send command from Fake PIC to engage Lockout
|
||||
FPicLockout,
|
||||
/// Clear limit for first limit
|
||||
FPicLimitClear1,
|
||||
/// Activate top limit for first limit
|
||||
FPicLimitTop1,
|
||||
/// Activate bottom limit for first limit
|
||||
FPicLimitBottom1,
|
||||
/// Set hardware fault (Reason will be given as "test fault")
|
||||
FPicFault,
|
||||
/// Have the fake PIC output its internal state
|
||||
FPicOutput,
|
||||
|
||||
/// Send a bluetooth characteristic: Wifi SSID
|
||||
//BluetoothWifiSsid { ssid: &'a str },
|
||||
@ -132,25 +159,81 @@ pub fn process_menu(
|
||||
}
|
||||
}
|
||||
Menu::BluetoothLearn { data } => {
|
||||
cli.writer()
|
||||
.write_str("TODO: simulate bluetooth characteristic change")?;
|
||||
let _ = data;
|
||||
let but = input_to_button(data);
|
||||
match but {
|
||||
Some(d) => {
|
||||
println!("Sending PicRecvUp command");
|
||||
let _ = dispatch.send_blocking(Commands::BluetoothLearn{data: d});
|
||||
}
|
||||
None => {println!("Incorrect value; enter 0 or 1")}
|
||||
}
|
||||
}
|
||||
Menu::BluetoothAuto { data } => {
|
||||
cli.writer()
|
||||
.write_str("TODO: simulate bluetooth characteristic change")?;
|
||||
let _ = data;
|
||||
let but = input_to_button(data);
|
||||
match but {
|
||||
Some(d) => {
|
||||
println!("Sending PicRecvUp command");
|
||||
let _ = dispatch.send_blocking(Commands::BluetoothAuto{data: d});
|
||||
}
|
||||
Menu::BluetoothTopLimit { data } => {
|
||||
cli.writer()
|
||||
.write_str("TODO: simulate bluetooth characteristic change")?;
|
||||
let _ = data;
|
||||
None => {println!("Incorrect value; enter 0 or 1")}
|
||||
}
|
||||
Menu::BluetoothBottomLimit { data } => {
|
||||
cli.writer()
|
||||
.write_str("TODO: simulate bluetooth characteristic change")?;
|
||||
let _ = data;
|
||||
}
|
||||
Menu::BluetoothAux { data } => {
|
||||
let but = input_to_button(data);
|
||||
match but {
|
||||
Some(d) => {
|
||||
println!("Sending PicRecvUp command");
|
||||
let _ = dispatch.send_blocking(Commands::BluetoothAux{data: d});
|
||||
}
|
||||
None => {println!("Incorrect value; enter 0 or 1")}
|
||||
}
|
||||
}
|
||||
Menu::FPicAux => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicToggleAux);
|
||||
}
|
||||
Menu::FPicAuto => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicToggleAuto);
|
||||
}
|
||||
Menu::FPicLearn => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicPressLearn);
|
||||
}
|
||||
Menu::FPicUp => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicPressUp);
|
||||
}
|
||||
Menu::FPicDown => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicPressDown);
|
||||
}
|
||||
Menu::FPicStop => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicPressStop);
|
||||
}
|
||||
Menu::FPicPanic => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicTogglePanic);
|
||||
}
|
||||
Menu::FPicLockout => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicLockout);
|
||||
}
|
||||
Menu::FPicFault => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicFault { data: Arc::new("Test Fault".to_string()) });
|
||||
}
|
||||
Menu::FPicOutput => {
|
||||
let _ = dispatch.send_blocking(Commands::FPicOutput);
|
||||
}
|
||||
Menu::FPicLimitClear1 => {
|
||||
let mut lim = EMPTY_LIMITS;
|
||||
lim.only_starboard_bow = LimitStatus::NotActive;
|
||||
let _ = dispatch.send_blocking(Commands::FPicLimit { data: lim });
|
||||
}
|
||||
Menu::FPicLimitTop1 => {
|
||||
let mut lim = EMPTY_LIMITS;
|
||||
lim.only_starboard_bow = LimitStatus::TopActive;
|
||||
let _ = dispatch.send_blocking(Commands::FPicLimit { data: lim });
|
||||
}
|
||||
Menu::FPicLimitBottom1 => {
|
||||
let mut lim = EMPTY_LIMITS;
|
||||
lim.only_starboard_bow = LimitStatus::BottomActive;
|
||||
let _ = dispatch.send_blocking(Commands::FPicLimit { data: lim });
|
||||
}
|
||||
|
||||
/*Menu::BluetoothWifiSsid { ssid } => {
|
||||
cli.writer()
|
||||
.write_str("TODO: simulate bluetooth characteristic change")?;
|
||||
|
||||
@ -26,6 +26,7 @@ pub enum Commands {
|
||||
FPicLockout,
|
||||
FPicFault {data: Arc<String>}, // String is cause. Send empty string to clear fault.
|
||||
FPicLimit {data: Limits},
|
||||
FPicOutput,
|
||||
|
||||
// TODO: real hardware buttons - consider re-sending occasionally when pressed, so that transitions like holding up -> stopping -> holding down -> stopped -> (should go down but gets no new notice) work.
|
||||
|
||||
|
||||
@ -49,6 +49,7 @@ impl FakePic {
|
||||
Commands::PairTimerExpired,
|
||||
Commands::StopTimerExpired,
|
||||
Commands::ButtonTimerExpired,
|
||||
Commands::FPicOutput,
|
||||
];
|
||||
FakePic {
|
||||
motor_state: Motors{
|
||||
@ -99,11 +100,11 @@ impl FakePic {
|
||||
Ok(())
|
||||
}
|
||||
pub async fn press_up(&mut self) -> Result<()> {
|
||||
if self.status_state.union(Statuses::PANIC).is_empty() || self.status_state.union(Statuses::LOCKOUT).is_empty(){
|
||||
if !self.status_state.intersection(Statuses::PANIC| Statuses::LOCKOUT).is_empty() {
|
||||
warn!("Ignoring commands while in panic or lockout mode!")
|
||||
}
|
||||
if self.motor_state.are_cooldown() {
|
||||
info!("Ignoring commands while motors cool down")
|
||||
else if self.motor_state.are_cooldown() {
|
||||
warn!("Ignoring commands while motors cool down")
|
||||
}
|
||||
else if self.motor_state.going_down() {
|
||||
warn!("Reversing from down to up; entering cooldown!");
|
||||
@ -120,11 +121,11 @@ impl FakePic {
|
||||
Ok(())
|
||||
}
|
||||
pub async fn press_down(&mut self) -> Result<()> {
|
||||
if self.status_state.union(Statuses::PANIC).is_empty() || self.status_state.union(Statuses::LOCKOUT).is_empty() {
|
||||
if !self.status_state.intersection(Statuses::PANIC| Statuses::LOCKOUT).is_empty() {
|
||||
warn!("Ignoring commands while in panic or lockout mode!")
|
||||
}
|
||||
else if self.motor_state.are_cooldown() {
|
||||
info!("Ignoring commands while motors cool down")
|
||||
warn!("Ignoring commands while motors cool down")
|
||||
}
|
||||
else if self.motor_state.going_up() {
|
||||
warn!("Reversing from up to down; entering cooldown!");
|
||||
@ -143,18 +144,25 @@ impl FakePic {
|
||||
pub async fn press_stop(&mut self) -> Result<()> {
|
||||
self.motor_state.stop();
|
||||
self.send_q.send(Commands::BluetoothStatusMotor { data: self.motor_state }).await?;
|
||||
//self.send_q.send(Commands::ButtonTimerClear).await?; // Stop waiting on button timeouts
|
||||
Ok(())
|
||||
}
|
||||
pub async fn toggle_panic(&mut self) -> Result<()> {
|
||||
self.status_state ^= Statuses::PANIC;
|
||||
self.status_state = self.status_state.symmetric_difference(Statuses::PANIC);
|
||||
if self.status_state.intersection(Statuses::PANIC).is_empty(){
|
||||
warn!("Clearing Panic status")
|
||||
} else {
|
||||
warn!("Entering panic status")
|
||||
}
|
||||
self.motor_state.stop();
|
||||
self.send_q.send(Commands::BluetoothStatusStatus { data: self.status_state }).await?;
|
||||
self.send_q.send(Commands::BluetoothStatusMotor { data: self.motor_state }).await?;
|
||||
//self.send_q.send(Commands::BluetoothStatusMotor { data: self.motor_state }).await?;
|
||||
Ok(())
|
||||
}
|
||||
pub async fn lockout(&mut self) -> Result<()> {
|
||||
self.status_state &= Statuses::LOCKOUT; // No toggle; lockout can only be cleared by reboot per spec
|
||||
self.motor_state.stop();
|
||||
warn!("Locking out all movement controls until device is reset!");
|
||||
self.send_q.send(Commands::BluetoothStatusStatus { data: self.status_state }).await?;
|
||||
self.send_q.send(Commands::BluetoothStatusMotor { data: self.motor_state }).await?;
|
||||
Ok(())
|
||||
@ -167,6 +175,7 @@ impl FakePic {
|
||||
}
|
||||
self.fault_cause = cause;
|
||||
self.send_q.send(Commands::BluetoothStatusStatus { data: self.status_state }).await?;
|
||||
self.send_q.send(Commands::BluetoothStatusReason { data: Arc::new(self.fault_cause.clone())}).await?;
|
||||
Ok(())
|
||||
}
|
||||
pub async fn change_limit(&mut self, limits: Limits) -> Result<()> {
|
||||
@ -182,55 +191,91 @@ impl FakePic {
|
||||
|
||||
// === Handle events from event manager =====================================================
|
||||
pub async fn run(&mut self) -> Result<()> {
|
||||
loop {
|
||||
let cmd = self.recv_q.recv().await.expect("PIC simulator failed waiting for messages");
|
||||
match cmd {
|
||||
// Commands from testing and user
|
||||
Commands::FPicToggleAux => {self.toggle_aux().await}
|
||||
Commands::FPicToggleAuto => {self.toggle_auto().await}
|
||||
Commands::FPicPressLearn => {self.press_learn().await}
|
||||
Commands::FPicPressUp => {self.press_up().await}
|
||||
Commands::FPicPressDown => {self.press_down().await}
|
||||
Commands::FPicPressStop => {self.press_stop().await}
|
||||
Commands::FPicTogglePanic => {self.toggle_panic().await}
|
||||
Commands::FPicLockout => {self.lockout().await}
|
||||
Commands::FPicFault{data} => {self.fault(data.to_string()).await}
|
||||
Commands::FPicLimit { data } => {self.change_limit(data).await}
|
||||
Commands::FPicToggleAux => {self.toggle_aux().await?}
|
||||
Commands::FPicToggleAuto => {self.toggle_auto().await?}
|
||||
Commands::FPicPressLearn => {self.press_learn().await?}
|
||||
Commands::FPicPressUp => {self.press_up().await?}
|
||||
Commands::FPicPressDown => {self.press_down().await?}
|
||||
Commands::FPicPressStop => {self.press_stop().await?}
|
||||
Commands::FPicTogglePanic => {self.toggle_panic().await?}
|
||||
Commands::FPicLockout => {self.lockout().await?}
|
||||
Commands::FPicFault{data} => {self.fault(data.to_string()).await?}
|
||||
Commands::FPicLimit { data } => {self.change_limit(data).await?}
|
||||
// Commands from bluetooth
|
||||
Commands::BluetoothAuto { data } => {
|
||||
if data.is_pressed() {
|
||||
self.toggle_auto().await?;
|
||||
} Ok(())
|
||||
}
|
||||
}
|
||||
Commands::BluetoothAux { data } => {
|
||||
if data.is_pressed() {
|
||||
self.toggle_aux().await?;
|
||||
} Ok(())
|
||||
}
|
||||
}
|
||||
Commands::BluetoothLearn { data } => {
|
||||
if data.is_pressed() {
|
||||
self.press_learn().await?;
|
||||
} Ok(())
|
||||
}
|
||||
}
|
||||
Commands::BluetoothUp { data } => {
|
||||
if data.is_pressed() {
|
||||
self.press_up().await?;
|
||||
} else {
|
||||
self.press_stop().await?; // Releasing up is equivalent to stop
|
||||
} Ok(())
|
||||
}
|
||||
}
|
||||
Commands::BluetoothDown { data } => {
|
||||
if data.is_pressed() {
|
||||
self.press_down().await?;
|
||||
} else {
|
||||
self.press_stop().await?; // Releasing down is equivalent to stop
|
||||
} Ok(())
|
||||
}
|
||||
Commands::BluetoothStop { .. } => {self.press_stop().await} // Stopping on release of stop button is a noop but safe.
|
||||
}
|
||||
Commands::BluetoothStop { .. } => {self.press_stop().await?} // Stopping on release of stop button is a noop but safe.
|
||||
// Commands from timers
|
||||
Commands::PairTimerExpired => {self.exit_learn().await}
|
||||
Commands::StopTimerExpired => {self.exit_cooldown().await}
|
||||
Commands::ButtonTimerExpired => {self.press_stop().await}
|
||||
_ => {warn!("Unknown command received by Fake PIC simulator!"); Ok(())}
|
||||
Commands::PairTimerExpired => {self.exit_learn().await?}
|
||||
Commands::StopTimerExpired => {self.exit_cooldown().await?}
|
||||
Commands::ButtonTimerExpired => {self.press_stop().await?}
|
||||
Commands::FPicOutput => {
|
||||
warn!("== Fake PIC internal state ==---------------");
|
||||
if self.status_state.intersection(Statuses::LOCKOUT).is_empty() {
|
||||
info!("Lockout flag: Off");
|
||||
} else {
|
||||
error!("Lockout flag: On");
|
||||
}
|
||||
if self.status_state.intersection(Statuses::PANIC).is_empty() {
|
||||
info!("Panic flag: Off");
|
||||
} else {
|
||||
warn!("Panic flag: On");
|
||||
}
|
||||
if self.status_state.intersection(Statuses::FAULT).is_empty() {
|
||||
info!("Fault flag: Off");
|
||||
} else {
|
||||
warn!("Fault flag: On");
|
||||
}
|
||||
if self.status_state.intersection(Statuses::LEARN).is_empty() {
|
||||
info!("Learn flag: Off");
|
||||
} else {
|
||||
info!("Learn flag: On");
|
||||
}
|
||||
if self.status_state.intersection(Statuses::AUTO).is_empty() {
|
||||
info!("Auto flag: Off");
|
||||
} else {
|
||||
info!("Auto flag: On");
|
||||
}
|
||||
if self.status_state.intersection(Statuses::AUX).is_empty() {
|
||||
info!("Aux flag: Off");
|
||||
} else {
|
||||
warn!("Aux flag: On");
|
||||
}
|
||||
warn!("==------------------------------------------");
|
||||
}
|
||||
_ => {warn!("Unknown command received by Fake PIC simulator!");}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user