Skip to content

Commit

Permalink
Merge branch 'main' into Sub-Zero-Altitude
Browse files Browse the repository at this point in the history
  • Loading branch information
nikiexpo committed Jun 3, 2023
2 parents 1c2a6b4 + 7dca8d8 commit c9f20d7
Show file tree
Hide file tree
Showing 66 changed files with 169,311 additions and 243 deletions.
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -9,4 +9,5 @@ docs/html
.DS_Store
/test/native/test_altitude_conversion/altPressure.csv
launch_data/20_11_2022/__pycache__/
out.txt
out.txt
*.autosave
66 changes: 33 additions & 33 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,33 +1,33 @@
# !!! WARNING !!! AUTO-GENERATED FILE, PLEASE DO NOT MODIFY IT AND USE
# https://docs.platformio.org/page/projectconf/section_env_build.html#build-flags
#
# If you need to override existing CMake configuration or add extra,
# please create `CMakeListsUser.txt` in the root of project.
# The `CMakeListsUser.txt` will not be overwritten by PlatformIO.

cmake_minimum_required(VERSION 3.13)
set(CMAKE_SYSTEM_NAME Generic)
set(CMAKE_C_COMPILER_WORKS 1)
set(CMAKE_CXX_COMPILER_WORKS 1)

project("MRAS" C CXX)

include(CMakeListsPrivate.txt)

if(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/CMakeListsUser.txt)
include(CMakeListsUser.txt)
endif()

add_custom_target(
Production ALL
COMMAND platformio -c clion run "$<$<NOT:$<CONFIG:All>>:-e${CMAKE_BUILD_TYPE}>"
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
)

add_custom_target(
Debug ALL
COMMAND platformio -c clion debug "$<$<NOT:$<CONFIG:All>>:-e${CMAKE_BUILD_TYPE}>"
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
)

add_executable(Z_DUMMY_TARGET ${SRC_LIST})
# !!! WARNING !!! AUTO-GENERATED FILE, PLEASE DO NOT MODIFY IT AND USE
# https://docs.platformio.org/page/projectconf/section_env_build.html#build-flags
#
# If you need to override existing CMake configuration or add extra,
# please create `CMakeListsUser.txt` in the root of project.
# The `CMakeListsUser.txt` will not be overwritten by PlatformIO.

cmake_minimum_required(VERSION 3.13)
set(CMAKE_SYSTEM_NAME Generic)
set(CMAKE_C_COMPILER_WORKS 1)
set(CMAKE_CXX_COMPILER_WORKS 1)

project("MRAS" C CXX)

include(CMakeListsPrivate.txt)

if(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/CMakeListsUser.txt)
include(CMakeListsUser.txt)
endif()

add_custom_target(
Production ALL
COMMAND platformio -c clion run "$<$<NOT:$<CONFIG:All>>:-e${CMAKE_BUILD_TYPE}>"
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
)

add_custom_target(
Debug ALL
COMMAND platformio -c clion debug "$<$<NOT:$<CONFIG:All>>:-e${CMAKE_BUILD_TYPE}>"
WORKING_DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
)

add_executable(Z_DUMMY_TARGET ${SRC_LIST})
4 changes: 3 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@

![](docs/images/sunride_mras.png)

![](docs/images/sponsors.png)

MRAS (Multi Rocket Avionics System) is a flight computer that contains a high-performance microcontroller, high-G
accelerometer, Inertial Measurement Unit (IMU), Magnetometer, GNSS receiver,
Barometer, and a Telemetry system. It has been designed to provide a robust and reliable avionics package that can be
Expand Down Expand Up @@ -52,7 +54,7 @@ Rear side
- RF Solutions LAMBDA62 Module for telemetry
- Adafruit adalogger Feather M0 for data logging
- 2x WS2812B "NeoPixels" for displaying status information
- Buzzer
- ArduinoBuzzer
- XT30 connector for 2s-4s LiPo battery
- I2C QWIIC / STEMMA QT connectors for expansion
- Expansion port for upper "display board" (yet to be developed)
Expand Down
38 changes: 38 additions & 0 deletions docs/HIL_in_MRAS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
# Hardware-In-the-Loop testing in MRAS
#### -- Nikilesh Ramesh

### Introduction
Hardware-In-the-Loop (hereinafter HIL) is a way of testing embedded systems software. Stream simulated data over from either a deicated test rig or a computer to then measure the output to test if the system performs as expected. More information can be found [here](https://uk.mathworks.com/discovery/hardware-in-the-loop-hil.html).


### Simulink Model Explanation
Simulink is used to test MRAS. Data is streamed over serial to MRAS from the launch data collected during previous flights. Launch data is saved as csv file. `From spreadsheet` block in Simulink can be used to read the csv file. *Note: csv file needs to be formatted as per SIMULINK requirements see [here](https://uk.mathworks.com/help/simulink/slref/fromspreadsheet.html)*

The `pressure` and `y_accel` (acceleration y direction, up) is then concatenated using the `vector concatenate` block. They are then casted to floating points with `cast to single` block. Then `Byte pack` is used to convert them into bytes.

Simulink's Instument Control blockset provides a neat way of communicating with the board without much restrictions on the software, only a module that can read and write to serial is needed to communicate using this blockeset therfore this was chosen instead of Simulink's Arduino support package.

To send this data, first a `Serial Configuration` block must be added to the model. Set the baud rate, COM port and other essential details here. Then use `Serial Send` to stream data over to the board (again set the parameters as required and you are recommened by the author to skip the headers/break section for this block as it does not provide much added value if you are only testing a small system). How this data is proccessed on MRAS will be discussed in the next section.

Now `Serial Recieve` block provides the interface to read the data that MRAS outputs again in bytes. Configure the parameters as necessary, important parameters include `Serial Port`, `Input` and `Headers` (Headers are recommended here as Simulink deals with it so why not). Then cast to double before using the `Mux` block to divide the input vector into two values (the order of values depends on how you handle it in MRAS)

![Simulink model](docs/images/SimulinkSS.png)

### MRAS rocketHIL env Explanation

On MRAS a new `env` has been added dedicated for HIL testing named `rocketHIL`, checkout the `platformio.ini` and `main-rocketHIL.cpp` files. A new `Subsystem` has been added (if you are not familiar with MRAS subsystems you are encouranged to checkout either [Architecture overview](https://mras.sunride.space/md_docs_software_architecture_overview.html) or [a beginner guide to MRAS](https://mras.sunride.space/md_docs_BeginnerExplanation.html)) to interface with Simulink called `SimulinkDataLogger`. It logs recieves data from Simulink, casts it to the appropriate internal `SystemMessage`, then "publishes" it. The `StateEstimator` (more about this [here](https://mras.sunride.space/md_docs_state_estimation.html))is the sole subscriber to the said message. It proccess this message and then itself publishes a new `StateEstimatorMsg`. `SimulinkDataLogger` (it is subscribed to `StateEstimator`, thus making a two-way connection) then formats this message into the required format and then writes to Serial.

Well to convert data to bytes and vice-versa is an excellent use-case of `Union` data type that `c++` provides. An union is basically a struct but all its members define the same value (recommended watch [Cherno](https://www.youtube.com/watch?v=6uqU9Y578n4)).

```cpp
typedef union{
float number;
uint8_t bytes[4];
} FLOATUNION_t;
```

Here the `float number` and `uint8_t bytes[4]` define the same value. A `float` is made up of 4 bytes, `uint8_t` or `char` type is made of 1 byte, now an array of four `char` is then 4 bytes. So we can now represent a `float` as an array of four `uint8_t`. Then use Arduino framework's `Serial.write()` to write the **bytes** but to read it use the `Serial.read()` into `number` (c++ automatically changes the `bytes` array everytime `number` is re-assigned).

### References

Best source of reference for the Simulink side of things is the [Mathworks Documentation](https://uk.mathworks.com/products/simulink.html). For the interface there is an excellent [github repository](https://github.com/leomariga/Simulink-Arduino-Serial) with examples you can try out. Additionally [Cherno's C++ series](https://www.youtube.com/playlist?list=PLlrATfBNZ98dudnM48yfGUldqGD0S4FFb) was helpful.
Binary file added docs/images/SimulinkSS.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added docs/images/mras_all_white.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added docs/images/source_files/mras_all_white.pdn
Binary file not shown.
Binary file added docs/images/source_files/sponsors.pdn
Binary file not shown.
Binary file added docs/images/sponsors.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
2 changes: 1 addition & 1 deletion docs/state_estimation.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ where \f$ s, v, a and t \f$ position, velocity, acceleration and time step respe
But these are for continous funcitons, \f$ t \f$ would be replaced with \f$ \Delta t \f$ to discretize it. For ease of computation, these functions need to be in matrix form. But the the function must be decoupled from the measurement so we could update the `state`.

$$
state = \begin{bmatrix} position \\\ velocity \end{bmatrix} + \begin{bmatrix} \frac{1}{2} {\Delta t}^2 \\\ \Delta t \end{bmatrix} (acceleration + g)
state = \begin{bmatrix} 1 & dt \\\ 0 & 1 \end{bmatrix} \begin{bmatrix} position \\\ velocity \end{bmatrix} + \begin{bmatrix} \frac{1}{2} {\Delta t}^2 \\\ \Delta t \end{bmatrix} (acceleration + g)
$$

where \f$ g = -9.81 \f$ which accounts for gravity, as accelerometers don't account for it.
Expand Down
Loading

0 comments on commit c9f20d7

Please sign in to comment.