diff --git a/controls/README.md b/controls/README.md index 29c4bc1e2d9d0bced898e76bbd4448fad85b9172..8a1d285f263eea8ecc25b67f4ec5d80e7ee04709 100644 --- a/controls/README.md +++ b/controls/README.md @@ -3,4 +3,5 @@ This folder contains the files used in developing the model of the quadcopter. ## Documentation -[Measuring Motor Resistance](documentation/MeasuringMotorResistance.pdf) \ No newline at end of file +[Measuring Motor Resistance](documentation/MeasuringMotorResistance.pdf) +[Simulink Model](documentation/SimulinkModel.md) \ No newline at end of file diff --git a/controls/documentation/SimulinkModel.md b/controls/documentation/SimulinkModel.md new file mode 100644 index 0000000000000000000000000000000000000000..5deb8593aef0ea67688ed9b7c1554781684efd90 --- /dev/null +++ b/controls/documentation/SimulinkModel.md @@ -0,0 +1,142 @@ +# Simulink Model + +This documentation is about the Simulink model of the quadcopter found in `controls/model/`. +Specifically, the description and images are from the file +[`Quadcopter_Model_R2015A.mdl`](../model/Quadcopter_Model_R2015_A.mdl). + +## 1 Top Level + +![Top-Level Simulink Model][top_level] + +At the top level Simulink model (shown above), there are three primary components: + +- Control System +- Actuation +- Sensors + +There is also the input of setpoints, a vector of the four setpoint values: x, y, z, and yaw. + +### 1.1 Variables +The variables used at the top level of the model are as follows: + +- $`\Theta_{\text{filtered}}`$ - The current vector of roll, pitch, and yaw +- $`\frac{d\Theta_{\text{gyro}}}{dt}`$ - Time derivative of $`\Theta`$, as gvien by the gyro +- $`^Er_0`$ - Position of the quad with respect to the static reference frame +- $`P`$ - Vector of PWM percentages sent to the ESCs +- $`^B\Omega`$ - Vector of angular velocities around $`b_x, b_y, b_z`$ +- $`\Theta`$ - Roll, pitch, and yaw in the inertal reference frame +- $`\frac{d^Bv_0}{dt}`$ - Time derivative of velocity in quadcopter reference frame +- $`^Bg`$ - Gravity in quadcopter reference frame + +The three components are further discussed in the sections below : + +## 2 Control System +![Control System Simulink Model][control_sys] + +The two central components of the Control System are the Controller and the +Signal Mixer. + +### 2.1 Variables +The variables used in the controls system not listed above are enumerated below: + +- $`u_T`$ - Controller output for thrust +- $`u_A`$ - Controller output for "ailerons", used to control pitch +- $`u_E`$ - Controller output for "elevators", used to control roll +- $`u_R`$ - Controller output for "rudder", used to control yaw + +### 2.2 Controller +The controller contains the actual PIDs for each element of the setpoint, +and outputs control values to the signal mixer. + +<!---TODO ADR make new doc or write more about controller---> + +### 2.3 Signal Mixer +The Signal Mixer is simply a $`4 \times 4`$ matrix that is multiplied by the vector +$`\begin{pmatrix}u_T & u_A & u_E & u_R\end{pmatrix}^\top`$ to produce a vector +of PWM commands for the motor. As such, each row of the matrix corresponds to one +of the rotors, while each column corresponds to one of the elements of the input vector. +```math +S = \left(\begin{array}{rrrr} +1 & -1 & -1 & -1\\ +1 & 1 & -1 & 1\\ +1 & -1 & 1 & 1\\ +1 & 1 & 1 & -1 +\end{array}\right) +``` +For example, the fourth column is $`\begin{pmatrix}-1 & 1 & 1 & -1\end{pmatrix}^\top`$, +so when the controller commands a positive rudder (i.e. positive change in yaw), +the speed of rotors 1 and 4 decrease and 2 and 3 increase. + +<!---TODO ADR The matrix is copied from MATLAB, but that example can't be right---> + +## 3 Actuation +![Actuation Simulink Model][act_sys] + +The Actuation component of the model takes the PWM percentages as inputs +and simulates the motion of the quadcopter after being given a command from the control system. + +### 3.1 Variables +The variables in Actuation that haven't previously been covered are below: + +- $`^EF_g, ^BF_g`$ - Force of gravity on the quad, in inertial and body reference frames, respectively +- $`V_{b_\text{eff}}`$ - Effective batter voltage, explained further in the ESC subsection +- $`\omega`$ - Vector of angular speeds of the motors +- $`\alpha`$ - Vector of angular accelerations of the motors +- $`L_{BE}`$ - Matrix to transform a vector from the inertial reference frame to the quad's frame +- $`L_{EB}`$ - The transpose (and thus inverse) of $`L_{BE}`$; transforms from the quad's reference frame to the inertial frame +- $`A_{EB}`$ - Matrix to transform a vector of angular velocities from the quad body reference frame to the derivative of the Euler angles + + +### 3.2 ESC System +The ESC System takes in the input vector of PWM percents, +scales them between the max and min allowable duty cycles, and then calculates +the effective battery voltage given to each motor (The motors are brushless, so effective +voltage is the DC voltage that would need to be applied to a similar brushed motor to +achieve the same output). + +### 3.3 Motor System +Given the vector of effective voltages and a vector of current angular velocities +for each motor, this block computes the angular acceleration for each. + +### 3.4 Rotor System +The Rotor System first computes the total force and torque acting on the quadcopter body. +The force consists of the thrust produced by the rotors as well as the downward +force from gravity. The torque consists of components caused by in-plane drag, +changes in rotor angular momentum, and thrusts at a distance from the center of mass. +These values are then used to compute the outputs: the linear and angular accelerations +in the quadcopter body frame of reference + +### 3.5 Other Components +There are a number of smaller components in the Actuation model. +There are several blocks that simply perform multiplication of the transformation +matrices (covered in the Variables subsection) and a block that outputs a constant +gravity vector. +In addition to this, there are several integrators that accumulate linear and +angular velocity and acceleration to accumulate current values for +velocities and position/orientation. + +## 4 Sensors +![Sensors Simulink Model][sensor_sys] + +The Sensors component of the model performs no calculations (except for some basic +trigonometry to convert gyroscope accelerometer values). +All components of this function to simulate the actual system that the +data would be sent through. +These simulation components add noise to an input value (calculated in the Actuation +phase), sample, quantize, and delay their readings. +Without these, the Simulink model would only be good to prove math, and would not +actually provide valuable insight into the physical system. + +### 4.1 Variables +There are no new quantities that haven't already been explained in a previous section. + +## 5 Theoretical Foundations +A good resource to better understand the mathematical process of this model can be found +in Matthew Rich's 2012 thesis, +[Model development, system identification, and control of a quadrotor helicopter][model_dev]. + +[top_level]: ../../documentation/images/simulink_top_level.png +[control_sys]: ../../documentation/images/simulink_control_sys.png +[act_sys]: ../../documentation/images/simulink_act_sys.png +[sensor_sys]: ../../documentation/images/simulink_sensor_sys.png +[model_dev]: http://lib.dr.iastate.edu/cgi/viewcontent.cgi?article=3777&context=etd diff --git a/controls/model/README.md b/controls/model/README.md deleted file mode 100644 index ace46416279e601fc30ce98cb975978d5194c0db..0000000000000000000000000000000000000000 --- a/controls/model/README.md +++ /dev/null @@ -1 +0,0 @@ -# Model \ No newline at end of file diff --git a/documentation/images/comp_graph_ex1.png b/documentation/images/comp_graph_ex1.png new file mode 100644 index 0000000000000000000000000000000000000000..8c60e5c77a4ecf57ed38d6abe1ec3b9d809047ab Binary files /dev/null and b/documentation/images/comp_graph_ex1.png differ diff --git a/documentation/images/comp_graph_ex1_simu.png b/documentation/images/comp_graph_ex1_simu.png new file mode 100644 index 0000000000000000000000000000000000000000..eb147abb0a7c88c0368e6f5370c7bd969e4d3ad9 Binary files /dev/null and b/documentation/images/comp_graph_ex1_simu.png differ diff --git a/documentation/images/comp_graph_reset.png b/documentation/images/comp_graph_reset.png new file mode 100644 index 0000000000000000000000000000000000000000..60270e7df9805f43705224c0c37534cf3de0b3a6 Binary files /dev/null and b/documentation/images/comp_graph_reset.png differ diff --git a/documentation/images/simulink_act_sys.png b/documentation/images/simulink_act_sys.png new file mode 100644 index 0000000000000000000000000000000000000000..0ab33008ab63759d5a46c348dd491aa4c1ba3a5e Binary files /dev/null and b/documentation/images/simulink_act_sys.png differ diff --git a/documentation/images/simulink_control_sys.png b/documentation/images/simulink_control_sys.png new file mode 100644 index 0000000000000000000000000000000000000000..a27baacab776e0378dcbf4ba8db516c97c79afd4 Binary files /dev/null and b/documentation/images/simulink_control_sys.png differ diff --git a/documentation/images/simulink_sensor_sys.png b/documentation/images/simulink_sensor_sys.png new file mode 100644 index 0000000000000000000000000000000000000000..9aee76afa3766413919aead937dac47526eb6d48 Binary files /dev/null and b/documentation/images/simulink_sensor_sys.png differ diff --git a/documentation/images/simulink_top_level.png b/documentation/images/simulink_top_level.png new file mode 100644 index 0000000000000000000000000000000000000000..be065fdef2f60666f6bb674082788e1cf4df377d Binary files /dev/null and b/documentation/images/simulink_top_level.png differ diff --git a/quad/README.md b/quad/README.md index 37de29e98c0fe38858f413328df50d2e7695ebc0..896b2aa3b69e723ebb8f849357e6dc8b56596549 100644 --- a/quad/README.md +++ b/quad/README.md @@ -4,15 +4,48 @@ The `quad/` directory contains all code that programs the quadcopter. This includes any C libraries we have written, any HDL to program the Zybo on the quad, and the XSDK main project that runs on the Zybo. -## Brief Intro +## Intro -The main quad application is located at `src/quad_app/`. +There are three main portions to the system that runs the quad + +- Quad Hardware +- Quad Software Drivers +- Control Loop + + +#### Quad Hardware +The quad hardware is located at `xsdk_workspace/system_hw_platform`. This +consists of the vhdl and associated wrapper code that specifies the hardware on +the FPGA. + +Below is a block diagram of the hardware/software implementation: + + + +#### Quad Software Drivers +The quad software drivers is all of the code that interacts with the sensors of + the quad and collects the data for the control loop to use. +For example receiving coordinates over wifi and reading measurements from the + accelerometer. To run this application on the Zybo, we need to implement the hardware drivers, -and provide a `main` function. This is done in `xsdk_workspace/real_quad/src`. +and provide a `main` function. +This is done in `xsdk_workspace/real_quad/src` To build the XSDK project, +refer to the [XSDK instructions](xsdk_workspace/README.md). + +We can also run this application on our own laptops for testing. +We call this implementation the "virtual quad". +This is modified in `src/virt_quad`. -We can also run this application on our own laptops for testing. We call this -implementation the "virtual quad". This is done in `src/virt_quad`. +#### Control Loop +The control loop is the algorithm that runs within the quad software drivers. +This code determines what the code should do to keep the quad flying and as +close to the waypoint + as possible. + +The main quad control application is located at `src/quad_app/`. +This entails a group of C and header files that work as drivers/interfaces to +the various sensors and communications that are on the quad. ## Building @@ -29,12 +62,9 @@ directories: cd src/<project> && make ``` -**NOTE**: All build artifacts will be placed in `lib` or `bin` (depending on +**NOTE**: All build artifacts will be placed in `lib` or `bin` (depending on whether it is a library or executable, respectively) -#### XSDK Project (embedded project that runs on the Zybo) -To build the XSDK project, refer to the [XSDK instructions](xsdk_workspace/README.md). - ## Testing #### Automated Tests @@ -46,13 +76,13 @@ make test ``` And glad to hear you are interested in writing your own unit tests! Look at the -[README](src/test/README.md) and examples in our simple testing library at +[README](src/test/README.md) and examples in our simple testing library at `src/test`. #### Manually testing the hardware interface Of course, we cannot run automated tests on code that needs the Zybo. But -we have manual tests that you can use to test each specific driver in the +we have manual tests that you can use to test each specific driver in the hardware interface. Look in `xsdk_workspace/real_quad/src/hw_impl_zybo_tests.c` for instructions. @@ -65,5 +95,6 @@ Ideally, you would run these tests from the XSDK IDE. * [XSDK Instructions](xsdk_workspace/README.md) ## Other Documents +* [Hardware Block Diagram](doc/images/FPGA_Diagram.png) * [Zybo Pinout Assignments](doc/zybo_pinout_assignments.md) -* [How to use Xilinx software tools](doc/how_to_use_xilinx_tools.pdf) +* [How to use Xilinx software tools](doc/how_to_use_XSDK.md) diff --git a/quad/doc/how_to_use_XSDK.md b/quad/doc/how_to_use_XSDK.md new file mode 100644 index 0000000000000000000000000000000000000000..81e247a13c7abf9f264003225b8adccf0f48dc6a --- /dev/null +++ b/quad/doc/how_to_use_XSDK.md @@ -0,0 +1,182 @@ +# How to use XSDK + +## Introduction + +In this guide we will cover the following topics regarding XSDK: +- What Is XSDK +- How to open XSDK +- How to create a BSP +- How to create a new application project +- How to configure JTAG +- How to launch an Application Project +- How to boot using an SD card + + +## What is XSDK? + +XSDK stands for Xilinx Software Development Kit and it does exactly that. +It builds the project C files and necessary packages into files that allow the + developer to program the Zybo board to whatever he/she desires granted it meets + the system constraints. + +There are three main things required for a project: + 1. A system hardware platform (automatically exporting design from XPS) + 1. A Board Support Package (Contains software functions for interacting with + the Processing System controllers i.e. UART and I2C or logic cores on the FPGA) + 1. An Application Project (A simple hello world, an NES emulator, or something else) + +As mentioned above the system_hw_platform is imported for us by XPS when we +export our bitstream file to the XSDK. We’ll walkthrough the other two items +as well as programming the FPGA from within the XSDK. + +## Opening XSDK + +Setting up access to the Xilinx tools is fairly straight forward given the +machine the user is on. This guide +will cover three types of machines: Coover 3050-11 and -12 computers +(highly recommended), ISU’s +Remote Linux Servers, and a user’s own PC + +1. Coover 3050-11 and -12 +Two machines in the Distributed Sensing and Decision Making Lab (Coover 3050) +come with the +tools already installed. However, the following steps need to be taken in +order to launch the +program + - In a terminal, enter `source /opt/Xilinx/14.7/ISE_DS/settings64.sh` + - In terminal type `xsdk &` +1. ISU Remote Linux Servers (linux-X, research-x.ece.iastate.edu) + - `source Xilinx_Tools/setup_scripts/remote_servers/setup.sh` + - In terminal type `xsdk &` (Note: these servers are not good for + programming the Zybo board when it comes time to launch a program on the board) +1. User PC + Some users may opt to download the Xilinx tools on their own PCs for + development, but this is not recommended. + - Download the ISE Design Suite [here](https://www.xilinx.com/support/download/index.html/content/xilinx/en/downloadNav/design-tools.html) (~6GB) + - Run XSDK + + +## Creating a new Board Support Package (bsp) + +The BSP package is responsible for grabbing all necessary Xilinx library files +so they can be called by your program. In other words, it holds the drivers +necessary to interface with the hardware on the board. + 1. Click File and select New->Board Support Package + 1. In the New Board Support Package Project, enter a project name + (system_bsp in the example). + 1. Ensure system_hw_platform and ps7_cortexa9_0 are selected in Target Hardware + 1. Ensure “standalone†is selected. + 1. Click Finish to create the BSP + + __IMPORTANT:__ If UART0 is enabled, follow the steps below, otherwise ensure + these are set properly anyway. + 1. Click on “standalone†and change the + value of stdin AND stdout to ps7_uart_1 + 1. Click OK when done, you should now see the BSP in the project explorer + +## Creating a new Application Project +Lastly, we have the software program that will run on the board. This is the +last piece to the Zybo puzzle, and we’re almost there. Projects can be written +in C or C++, and can use some standard libraries like stdio, stdlib, string, +and otherse. HOWEVER, some libraries (often from Linux) are not implemented +(like time.h), and alternate methods must be used for some things an OS would +normally handle. Hopefully you do not run into these instances. +(Off topic hint: If you need timing things, check out xtime_l.h) +1. Click File -> New -> Application Project to open the New Project box +1. Enter a project name, and select the “Use existing†radio button for the +BSP. We want to use our newly created one rather than create one. +1. Click next and select a template (Hello World is probably best) and hit Finish +1. The new project should appear on the Project Explorer. Expand the project, +src, and open the helloworld.c + +## Configuring JTAG + +We now have all the components, we’re now ready to program the board, but wait, + we haven’t setup how we’re going to communicate with the board. You may now + plug in the board to the development computer (yours, Coover machine, etc.) + Flip the switch to power on the board. + + 1. In the menu bar, click Xilinx Tools -> Configure JTAG + 1. If the board is plugged into Coover 3050-11,-12 or a personal PC, then use + Auto Detect (It is ill-advised to be programming the Zybo board from a remote + linux machine at this point) + 1. Click OK + +## Launching an Application Project +With all our pieces ready to go, we can finally program the board and launch + our software program. + +_IMPORTANT:_ A COM terminal should be open after the board has been turned on +AND before launching the program. Either go through Putty on Windows (COMn + Baud 115200) or if through a linux machine (sudo screen /dev/ttyUSB1 115200). + +1. On the menu bar, click Xilinx Tools -> Program FPGA, and click Program to +start the process +1. If the JTAG configurations and setup were correct, the bitstream should +load onto the board and a blue LED should turn on indicating the board +is DONE programming. +1. With the board program, we can now launch our software, click on the +Application Project we want to launch and click the Green Play Arrow button + to start. +1. View the data received from the board through the COM terminal. + +## Booting on SD + +The `boot.bin` file is the file that the ZYBO board used on the quad uses to +produce the hardware platform and run the software for our program to run. +In a standalone application(no operating system) this should be the only +file placed on the SD-card. +### What to Do Before + +To correctly make a boot.bin file (using no operating system) you must have +the following: +- System hardware platform `.bit` file + - Output of hardware toolset (ISE for now) + - Path: `MicroCART/quad/xsdk_workspace/sytem_hw_platform/system.bit` +- Application Project `.elf` file + - Be sure to confirm project is built in XSDK + - Path: `MicroCART/quad/xsdk_workspace/real_quad/Realease/real_quad.elf` +- Board Support Package `.elf` file + - The current boot loader is a default a standalone for the Zybo board + - Be sure to confirm project is built in XSDK + - Path: `MicroCART/quad/xsdk_workspace/zybo_fsbl/Realease/zybo_fsbl.elf` + +NOTE: None of the `.elf` files are on GIT to reduce clutter + +### Instructions + +In order to correctly create the boot file you must have all the above files +updated. + +Within XSDK: + 1. Project -> Create Boot Image. Alternatively right-click on the project in + the Project Explorer and -> Create Boot Image + 1. Select `MicroCART/quad/xsdk_workspace/zybo_fsbl/Realease/` as the `.bif` + 1. Click add + 1. Select `MicroCART/quad/xsdk_workspace/zybo_fsbl/Realease/zybo_fsbl.elf` + 1. Confirm bootloader is checked and add the file to the Boot Image + 1. Click add + 1. Select `MicroCART/quad/xsdk_workspace/sytem_hw_platform/system.bit` + 1. Add the file to the Boot Image + 1. Click add + 1. Select `MicroCART/quad/xsdk_workspace/real_quad/Realease/real_quad.elf` + 1. Add the file to the Boot Image + 1. Copy `Boot.bin` file at `MicroCART/quad/xsdk_workspace/zybo_fsbl/Realease/` to SD Card + 1. Plus SD card into quad and power on board + +_NOTE:_ If anything here is unclear there is a deeper explanation in +[Xilinx: how to create a Boot Image](https://www.xilinx.com/support/documentation/sw_manuals/xilinx14_7/SDK_Doc/tasks/sdk_t_create_zynq_boot_image.htm) + +## XSDK Quirks + + The Xilinx SDK has a few quirks that are important to watch out for: + - From the [documentation](https://www.xilinx.com/support/documentation/sw_manuals/xilinx14_7/SDK_Doc/tasks/sdk_t_tcf_limitations_faq.htm) + , if you abort program execution while at a breakpoint inside an interrupt + handler, when re-running the program, interrupts don’t fire. You have to do + a hard reset of the board (cycle power) to have interrupts work again. + - After doing a `git pull` or `git checkout`, refresh the files by right- + clicking on the project in the sidebar and clicking "Refresh" + - The project does not detect changes in header files, so if you modify a + `.h` file, you should do a clean before re-building, otherwise you may + experience unexpected behavior. We got into the habit of always doing a + clean before a build whenever creating code that will be put on the quadcopter. diff --git a/quad/doc/images/FPGA_Diagram.png b/quad/doc/images/FPGA_Diagram.png new file mode 100644 index 0000000000000000000000000000000000000000..e9a07eef1be46ff26e2fcc0e9b7a06bcdd25d0a3 Binary files /dev/null and b/quad/doc/images/FPGA_Diagram.png differ diff --git a/quad/src/computation_graph/README.md b/quad/src/computation_graph/README.md index 4d205affa8caf17e9b6264cc930448cd20556bba..9d0867e1f05680e001fbafe3b90a987ed02f8077 100644 --- a/quad/src/computation_graph/README.md +++ b/quad/src/computation_graph/README.md @@ -1,9 +1,75 @@ # Computation Graph -* What is a computation graph -* NaNs -* How to configure: Configuration is complicated - suggest solutions -* Reset propogataion -* graph_blocks library - suggest decoupling -* Suggest future ideas - pre-parsing computation order -* Arbitrary IDs are supported for the ground station, but is not really a true implementation. Need an actual hashmap +A computation graph is a way to organize a large function into smaller, reusable functions, and easily visualize how data flows from one step of calculation to another. We chose to implement the control algorithm in this manner because as the complexity of the controller grew (deeper PID nesting, more filtering, etc.), it became very difficult to understand exactly how the sensor data was being processed and used. Our final design is partially inspired by Simulink, in an effort to draw parallels between the actual implementation of a controller and how they are often designed by control engineers. + +## Example +To help understand the basics of the computation graph, we will walk through a simple example. Below is a possibly graph configuration, along with a representative Simulink diagram. Each node represents a computation step which takes in inputs, and produces outputs. Each node also potentially has configuration parameters. + + + + +In this example, there are four different types of nodes: + - Constant + - Addition + - Gain + - Multiplication + + #### Constant + A constant block, as defined in [node_constant.c](../graph_blocks/node_constant.c) and [node_constant.h](../graph_blocks/node_constant.h) has: + - 0 Inputs + - 1 Output + - CONST_VAL + - 1 Parameter + - CONST_SET + +When its computation is executed, it simply sets the output to be the value of the parameter CONST_SET. + +#### Addition +An addition block is defined in [node_add.c](../graph_blocks/node_add.c) and [node_add.h](../graph_blocks/node_add.h) has + - 2 Inputs + - ADD_SUMMAND1 + - ADD_SUMMAND2 + - 1 Output + - ADD_SUM + - 0 Parameters + + During its computation step, it calculates the difference between the values passed into ADD_SUMMAND1 and ADD_SUMMAND1, putting the result in ADD_SUM. + + #### Gain, Multiplication + Both of these blocks have implementations (node_gain, node_mult). They are both simple blocks that perform a single operation. + + ## Storing State + The blocks introduced above are purely functional: Every input combination maps to a single output combination, regardless of past inputs. To implement controllers and filters, we need something more powerful --- Introducing block state. + + A block implementation can define a custom struct for storing any sort of data it would like. Each new instantiation of a block allocates memory for the struct, and the block execution function gets a `void*` passed into it, which the execution function is responsible for casting and using. + + ### A simple stateful block + To help explain these ideas, we'll go through a simple block that uses state: An accumulator node ([node_accumulator.c](../graph_blocks/node_accumulator.c) and [node_accumulator.h](../graph_blocks/node_accumulator.h)). + + This block performs the following operation: Every time its `execute` function is called, it outputs the sum of its previous output with the current input. i.e., it computes $`\sum_{t=1}^{T}{x_t}`$. + + Clearly, our state needs to store the total summation so far. In the implementation, you will see that the `accum_state` struct has a single field which contains a double representing the accumulated value. The accumulate block also contains a reset function, which sets the accumulated value to 0. + + You may wonder why a `node_integrator` block exists in addition to the accumulator block. The integrator block computes a proper integral, taking into account the time difference between calls, $`dt`$, and is used for the optical flow calculations. The accumualtor block is actually only used for automated testing. + + +### Initializing State +If a block has state, we probably want a way to initialize the state in some way. If the initialization were to only occur once, we might have left it up to the block implementation to keep a flag in the state struct representing whether it has been initialized. But because blocks can be disconnected and reconnected during runtime (e.g. switching from manual to autonomous flight), the initialization may need to run multiple times, so we allow a block definition to provide a function that will be called upon block initialization (`reset` field in `grah_node_type` struct). + +### Reset Propagation +When a block is connected to the graph, we want it to be reset. Because it is part of a chain of computations, we usually want its ancestors to be reset also. Consider the graph below. When D is connected, both B and A will have their `reset` functions called. + + + +## Things to Note + +### Updated Flag +In the quadcopter, some sensors update at different rates (e.g. VRPN data comes at 100Hz, but accelerometer data is at 200Hz). Therefore, some PID blocks need to update at different rates, too. To account for this, every block has an `updated` flag that gets set whenever its data changes. Things that could cause its data to change are setting a new source, updating a parameter, or being reset. During the graph traversal for calculation, if a node isn't marked as `updated`, then its `execute` function will not be called. This allows PIDs to automatically run at the correct rate to match their sensor inputs, since a sensor will only be marked `updated` when new data is set. + +### Floating Point +The computation graph uses doubles for all data. This was decided because the Zynq-7000 has double-precision FPUs, so we knew could take advantage of the higher precision, rather than using single-precision floats. + +Because we are using floating points for values, NaN values must be handled carefully. Data flows forward in the graph, so if a NaN is set somewhere, there is a very good chance that all of its dependents will also output NaNs after the next computation pass. If one of the blocks in the chain has a state, then it could cause that block to continually output NaNs until being reset. This is very bad, of course, so if the block has the possibility to output a NaN (e.g. it does a division by one of its inputs, which could be zero), then you should put a check to prevent that. (See [node_pid.c](../graph_blocks/node_pid.c)). + +### Node IDs +When creating new blocks from the quad code, use the `graph_add_defined_block` function, which returns an integer representing the new ID. (or -1 if it failed to create it). You can also add a node with a specific ID, using the `graph_add_node_id` function, but this is only to allow the ground station to re-create the quadcopter's graph. Nodes with arbitrary IDs should not be created, since the computation graph uses a lazy way to map node IDs to nodes. It just keeps an array, where the index holds the node at that index ID. So adding a node with an ID of 5000 means that space for more than 5000 nodes will be allocated. diff --git a/quad/src/computation_graph/computation_graph.c b/quad/src/computation_graph/computation_graph.c index 6cbaf22abfea088f51e127688f15d0aeee801c87..634823ed0934b51eca500558d55ba509748fc62d 100644 --- a/quad/src/computation_graph/computation_graph.c +++ b/quad/src/computation_graph/computation_graph.c @@ -32,7 +32,6 @@ static void reset_node_rec(struct computation_graph* graph, int node_id, int dep return; } struct graph_node* node = &graph->nodes[node_id]; - // Don't reset nodes that are already connected to something else // Don't reset nodes that have already been reset or discovered if (node->processed_state != UNPROCESSED) { return; diff --git a/quad/xsdk_workspace/README.md b/quad/xsdk_workspace/README.md index 4446d841e5115470787347ed0a57e843d4f7901c..bddc1b7c516480ba8fbc0ebd55a17849fcdef748 100644 --- a/quad/xsdk_workspace/README.md +++ b/quad/xsdk_workspace/README.md @@ -1,9 +1,18 @@ # XSDK Workspace -This directory is reserved for XSDK projects. +This directory is reserved for Xilinx XSDK projects and their respective hardware platforms. + +## What is XSDK + +XSDK is a development tool made by Xilinx to create the files necessary to boot + the hardware and software on the FPGA. It includes a test editor based on + eclipse so the tools should feel vaguely familiar. + Use our [how to use XSDK document](../doc/how_to_use_XSDK.md) or + [XSDK documentation webpage](https://www.xilinx.com/support/documentation/sw_manuals/xilinx2015_1/SDK_Doc/index.html) + ## Setup -XSDK, being based on Ecplise, is rather fragile, so do yourself a favor +XSDK, being based on Eclipse, is rather fragile, so do yourself a favor and read this section so things get setup correctly. 1. When you first open eclipse, select this directory, `xsdk_workspace`, as @@ -13,17 +22,9 @@ and read this section so things get setup correctly. add these projects, right-click on the project pane, and click on something like "import projects". - 1. Select "Import Existing Projects" (whereever that is) - 2. And then select the xsd_workspace as the folder where you want to import + 1. Select "Import Existing Projects" (wherever that is) + 2. And then select the xsdk_workspace as the folder where you want to import projects. Add them all. -3. If things are going swimmingly, then you should be able to build everyhing +3. If things are going swimmingly, then you should be able to build everything and be off on your merry embedded endeavors. - -## XSDK FYIs -Definitely first read the [Xilinx How-To](../doc/how_to_use_xilinx_tools.pdf). - -The XIlinx SDK has a few quirks that are important to watch out for: - 1. From the [documentation](https://www.xilinx.com/support/documentation/sw_manuals/xilinx14_7/SDK_Doc/tasks/sdk_t_tcf_limitations_faq.htm), if you abort program execution while at a breakpoint inside an interrupt handler, when re-running the program, interrupts don’t fire. You have to do a hard reset of the board (cycle power) to have interrupts work again. - 2. After doing a `git pull` or `git checkout`, refresh the files by right-clicking on the project in the sidebar and clicking "Refresh" - 3. The project does not detect changes in header files, so if you modify a `.h` file, you should do a clean before re-building, otherwise you may experience unexpected behavior. We got into the habit of always doing a clean before a build whenever creating code that will be put on the quadcopter. diff --git a/quad/xsdk_workspace/real_quad/README.md b/quad/xsdk_workspace/real_quad/README.md index a1a44b1ead8f1d9663bc8ec9a7942f9daaf339d0..88089fe73a20d66069f58a28385db78db8ebed51 100644 --- a/quad/xsdk_workspace/real_quad/README.md +++ b/quad/xsdk_workspace/real_quad/README.md @@ -2,9 +2,9 @@ _It is real, because it flies._ Welcome to the most lame README in MicroCART. Everything we are about to say -has already been said elsewhere, including [here][1], [here][2], and [here][3]. +has already been said elsewhere, including [Our quad folder README][1], [xsdk_workspace README][2], and [HOW_TO_USE_XSDK markdown][3]. So we aren't saying it here. Hence, this README is pretty empty. Hence... lame. [1]: ../README.md -[2]: ../../README.md#brief-intro -[3]: ../../doc/how_to_use_xilinx_tools.pdf \ No newline at end of file +[2]: ../../README.md +[3]: ../../doc/how_to_use_XSDK.md