Skip to content

Commit

Permalink
Merge pull request #46 from delft-hyperloop/routeplanning
Browse files Browse the repository at this point in the history
Route Planning + Propulsion + Levi
  • Loading branch information
andtsa authored Jun 26, 2024
2 parents 271ffe9 + 9868a7e commit 5b0e6ee
Show file tree
Hide file tree
Showing 71 changed files with 1,731 additions and 399 deletions.
66 changes: 52 additions & 14 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,22 +1,60 @@
# Delft Hyperloop - Helios III
*sponsored by goose*

./app ->> Main Application Source Code
./gs ->> Ground Station Backend Code
- `./app` → main application source code
- `./gs` → ground station frontend code
- `./gs/station` → ground station backend code

So far we have the idea of splitting ground station code into the functional backend that we can work with,
and the pretty frontend that maybe the design engineers can work with
# Running
this project is built on `rustc 1.79.0 (129f3b996 2024-06-10)` and is needed for all components.

./config has the configuration files, such as:
- static IP address assignment for
- Ground station
- Main PCB
- Levi Drives
- Prop drives?
- Messaging interfaces: what do the packets sent from ground station to pod and vice versa look like?
- this should be a non-technical readable file, maybe we even other departments can look at it and understand
- ...
## Main application
flashing & running the main application requires
- [probe-rs](https://probe.rs),
- [`rustup target thumbv7em-none-eabihf`](https://doc.rust-lang.org/nightly/rustc/platform-support/thumbv7em-none-eabi.html)
- a connected `STM32H743ZIT6` device

`cargo run` will generate debug symbols and enable logging, `cargo run --release` will disable all logging.

® andreas & kiko, 2024
## Ground station
The ground station backend can no longer be run independently, and thus it needs a frontend.

There's 2 to pick from, a *text-based user interface* and a *graphical user interface*.

To run the graphical user interface run
```
cd ./gs/
npm i
npm run tauri dev
```
(obviously requires NPM as well)

To run the more lightweight TUI
```
cd ./gs/station/
cargo run --no-default-features --features tui
```
(only rust needed)

# Maintaining

## Main application
PANICKING IS NOT ALLOWED!!
if you `.unwrap()` anywhere i will find you

## Ground station
The ground station backend functionality entirely resides in
```
./gs/station/src/backend.rs
```
in the `struct Backend`.

To implement a frontend, all you need to do is `Backend::new()`, create listeners for the `broadcast::channel`s, receive `Message`s and send `Command`s.


----------------------------------------------------------

```rust
© 2024 Andreas Tsatsanis, Fransisco Amaro, Kiril Panayotov
```

5 changes: 3 additions & 2 deletions app/.cargo/config.toml
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
[target.thumbv7em-none-eabihf]

runner = 'probe-rs run --chip STM32H743ZITx'
# runner = 'probe-run --chip STM32H743ZIT6 --probe 0483:3754' #

[build]
target = "thumbv7em-none-eabihf" # Cortex-M4F and Cortex-M7F (with FPU)

[env]
DEFMT_LOG = "trace"
#DEFMT_LOG = "off"
#DEFMT_LOG = "trace"
19 changes: 10 additions & 9 deletions app/build.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ extern crate serde;
use std::env;
use std::fs;
use std::path::Path;
use std::sync::Mutex;
use goose_utils::check_ids;

use goose_utils::ip::configure_gs_ip;
use serde::Deserialize;
Expand Down Expand Up @@ -69,15 +69,22 @@ pub const COMMANDS_PATH: &str = "../config/commands.toml";
pub const EVENTS_PATH: &str = "../config/events.toml";

fn main() {
if cfg!(debug_assertions) {
env::set_var("DEFMT_LOG", "trace");
} else {
env::set_var("DEFMT_LOG", "off");
}

let out_dir = env::var("OUT_DIR").unwrap();
let id_list = Mutex::new(Vec::new());
let dest_path = Path::new(&out_dir).join("config.rs");

let ip_file = fs::read_to_string(CONFIG_PATH).unwrap();
let config: Config = toml::from_str(&ip_file).unwrap();

let mut content = String::new();

let _ = check_ids(DATATYPES_PATH, COMMANDS_PATH, EVENTS_PATH);

content.push_str(&configure_ip(&config));
content.push_str(&configure_gs_ip(
config.gs.ip,
Expand All @@ -87,17 +94,14 @@ fn main() {
content.push_str(&configure_pod(&config));
content.push_str(&configure_internal(&config));
content.push_str(&goose_utils::commands::generate_commands(
&id_list,
COMMANDS_PATH,
true,
));
content.push_str(&goose_utils::datatypes::generate_datatypes(
&id_list,
DATATYPES_PATH,
false,
));
content.push_str(&goose_utils::events::generate_events(
&id_list,
EVENTS_PATH,
true,
));
Expand Down Expand Up @@ -155,10 +159,7 @@ fn configure_pod(config: &Config) -> String {
) + &*format!(
"pub const KEEP_ALIVE: u64 = {};\n",
config.pod.net.keep_alive
) + &*format!(
"pub const HEARTBEAT: u64 = {};\n",
config.gs.heartbeat
)
) + &*format!("pub const HEARTBEAT: u64 = {};\n", config.gs.heartbeat)
}

fn configure_internal(config: &Config) -> String {
Expand Down
8 changes: 2 additions & 6 deletions app/src/core/communication/can.rs
Original file line number Diff line number Diff line change
Expand Up @@ -66,21 +66,16 @@ pub async fn can_receiving_handler(
frame.data()
);
if DATA_IDS.contains(&id) {
debug!("first if");
if BATTERY_GFD_IDS.contains(&id) && utils.is_some() {
debug!("second if");
let ut = utils.as_mut().unwrap();
if HV_IDS.contains(&id) {
debug!("hv if");
ut.hv_controller
.bms_can_handle(id, frame.data(), data_sender, timestamp.as_ticks())
.await;
} else if LV_IDS.contains(&id) {
debug!("lv if");
ut.lv_controller
.bms_can_handle(id, frame.data(), data_sender, timestamp.as_ticks())
.await;
// event_sender.send(Event::ConnectionEstablishedEvent).await;
} else if GFD_IDS.contains(&id) {
if id == Datatype::IMDVoltageDetails.to_id() {
ground_fault_detection_isolation_details(
Expand All @@ -101,6 +96,7 @@ pub async fn can_receiving_handler(
}
}
} else {
info!("#{}", bytes_to_u64(frame.data()));
data_sender
.send(Datapoint::new(
Datatype::from_id(id),
Expand Down Expand Up @@ -137,6 +133,6 @@ pub async fn can_receiving_handler(
// # VERY IMPORTANT
// without this, our main pcb is magically converted to an adhd CAN pcb
// with no mind for anything else. Tread carefully around it
Timer::after_millis(1).await;
Timer::after_millis(2).await;
}
}
12 changes: 11 additions & 1 deletion app/src/core/communication/tcp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -237,7 +237,17 @@ pub async fn tcp_connection_handler(
Command::Heartbeat(x) => {
#[cfg(debug_assertions)]
info!("[tcp] Heartbeat command received {} :)", x);
match socket.write_all(&Datapoint::new(Datatype::ResponseHeartbeat, x, embassy_time::Instant::now().as_ticks()).as_bytes()).await {
match socket
.write_all(
&Datapoint::new(
Datatype::ResponseHeartbeat,
x,
embassy_time::Instant::now().as_ticks(),
)
.as_bytes(),
)
.await
{
Ok(_) => {}
Err(e) => {
error!("Couldn't respond to heartbeat: {}", e);
Expand Down
6 changes: 1 addition & 5 deletions app/src/core/controllers/battery_controller.rs
Original file line number Diff line number Diff line change
Expand Up @@ -368,11 +368,7 @@ impl BatteryController {
.send(Datapoint::new(battery_current_dt, current, timestamp))
.await;
self.data_sender
.send(Datapoint::new(
charge_state_dt,
state_of_charge,
timestamp,
))
.send(Datapoint::new(charge_state_dt, state_of_charge, timestamp))
.await;
self.data_sender
.send(Datapoint::new(
Expand Down
3 changes: 2 additions & 1 deletion app/src/core/controllers/breaking_controller.rs
Original file line number Diff line number Diff line change
Expand Up @@ -58,7 +58,7 @@ impl BrakingController {
pb8: peripherals::PB8,
pg1: peripherals::PG1,
pf12: peripherals::PF12,
pb0: peripherals::PB0,
_pb0: peripherals::PB0,
_pd5: peripherals::PD5,
_ptime: TIM16,
) -> Self {
Expand Down Expand Up @@ -112,6 +112,7 @@ impl BrakingController {
false
}

#[allow(dead_code)]
pub fn start_run_brake_precondition(&mut self) {
// todo run this before any run
self.braking_rearm.set_high();
Expand Down
8 changes: 3 additions & 5 deletions app/src/core/controllers/can_controller.rs
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,6 @@ use crate::CanSender;
use crate::CanTwoInterrupts;
use crate::DataReceiver;
use crate::DataSender;
use crate::Event;
use crate::EventSender;

pub struct CanPins {
Expand Down Expand Up @@ -65,7 +64,7 @@ impl CanController {
pins.pb6_pin, /* pb6=can2 TX */
CanTwoInterrupts,
);
can1.config().protocol_exception_handling = false;
can1.config().protocol_exception_handling = true;
can2.config().protocol_exception_handling = false;

can1.set_bitrate(1_000_000);
Expand All @@ -79,15 +78,14 @@ impl CanController {
c1_tx
.write(&can::frame::Frame::new_standard(0x123, &[1, 2, 3, 4]).unwrap())
.await;

try_spawn!(
event_sender,
x.spawn(can_receiving_handler(
x,
event_sender,
can_one_receiver,
data_sender,
c1_rx,
c2_rx,
None
))
);
Expand All @@ -98,7 +96,7 @@ impl CanController {
event_sender,
can_two_receiver,
data_sender,
c2_rx,
c1_rx,
Some(CanTwoUtils {
can_sender: can_two_sender,
hv_controller,
Expand Down
16 changes: 6 additions & 10 deletions app/src/core/controllers/ethernet_controller.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
use defmt::{debug, trace};
use defmt_rtt as _;
use defmt::info;
use embassy_executor::Spawner;
use embassy_net::Stack;
use embassy_net::StackResources;
Expand All @@ -16,7 +16,6 @@ use static_cell::StaticCell;
use crate::core::communication::tcp::tcp_connection_handler;
use crate::try_spawn;
use crate::DataReceiver;
use crate::Event;
use crate::EventSender;
use crate::Irqs;
use crate::POD_MAC_ADDRESS;
Expand Down Expand Up @@ -55,11 +54,11 @@ impl EthernetController {
let mut seed = [0; 8];
rng.fill_bytes(&mut seed);
let seed = u64::from_le_bytes(seed);
debug!("Seed: {:?}", seed);
let mac_addr = POD_MAC_ADDRESS;

debug!("MAC Address: {:?}", mac_addr);
static PACKETS: StaticCell<PacketQueue<16, 16>> = StaticCell::new();

info!("eth 6");
let device: Device = Ethernet::new(
PACKETS.init(PacketQueue::<16, 16>::new()),
pins.eth_pin,
Expand All @@ -76,34 +75,31 @@ info!("eth 6");
GenericSMI::new(0),
mac_addr,
);
trace!("MAC Address: {:?}", mac_addr);

info!("eth 7");
let eth_config: embassy_net::Config = embassy_net::Config::dhcpv4(Default::default());
// let eth_config: embassy_net::Config = embassy_net::Config::ipv4_static(
info!("eth 8");
// StaticConfigV4 {
// address: ip_cidr_from_config(POD_IP_ADDRESS),
// gateway: None,
// dns_servers: Default::default(),
// }
// );
trace!("MAC Address: {:?}", mac_addr);

static STACK: StaticCell<Stack<Device>> = StaticCell::new();

info!("eth 9");
static RESOURCES: StaticCell<StackResources<3>> = StaticCell::new();
info!("eth 10");
let stack: &Stack<Device> = &*STACK.init(Stack::new(
device,
eth_config,
RESOURCES.init(StackResources::<3>::new()),
seed,
));

info!("eth 11");
let ethernet_controller = Self {};

try_spawn!(sender, x.spawn(net_task(stack)));
try_spawn!(sender, x.spawn(net_task(stack)));

try_spawn!(
sender,
Expand Down
Loading

0 comments on commit 5b0e6ee

Please sign in to comment.