Last time, we explained the mathematical principles of the L1 Controller. In this article, which is FC20, we will cover SITL (Software In The Loop). We will explain how to build a simulation environment that allows you to verify ArduPilot operations without using actual hardware, as well as practical ways to utilize it for parameter tuning and new feature development.
What is SITL?
SITL is a mechanism that compiles ArduPilot flight code on a host PC and uses simulated sensor data and a physics engine to verify flight logic without the need for actual hardware.
While standard ArduPilot builds are cross-compiled for target MCUs such as the STM32, SITL builds are compiled as native code (x86_64 or ARM) for the host PC. Since the same flight code (attitude control, EKF, navigation logic) is executed as-is, it features high consistency in behavior with the actual hardware.
The problem that SITL solves is the acceleration of the development cycle. You can verify the effects of new parameters, the logic of new features, and fail-safe operations without actual test flights, and you can also test extreme conditions (strong winds, sensor failures) without the risk of crashing.
SITL Architecture
The SITL system consists of multiple components.
The ArduPilot flight code communicates with the simulation environment via a sensor abstraction layer (AP_HAL_SITL). In SITL, sensors that would be connected via SPI/I2C on actual hardware are replaced by calculated values from the physics simulation.
The physics simulation engine calculates the dynamics model of the aircraft. While the default ArduPilot SITL uses a simple built-in physics model (a simple rigid body dynamics + motor thrust model for Quadcopters), external simulators such as Gazebo, jMAVSim, or RealFlight are linked for more precise simulation.
The Ground Control Station (GCS), such as Mission Planner or QGroundControl, connects to SITL via UDP/TCP to perform telemetry display and parameter settings just as it would with actual hardware.
MAVProxy is a lightweight, command-line-based GCS that works well with SITL and is used for integration with automated test scripts.
SITL Installation and Basic Setup
We will explain the setup following the official ArduPilot build instructions.
bash
# ArduPilotリポジトリのクローン
git clone https://github.com/ArduPilot/ardupilot.git
cd ardupilot
git submodule update --init --recursive
# 依存関係のインストール(Ubuntu)
Tools/environment_install/install-prereqs-ubuntu.sh -y
. ~/.profile
# SITLビルド(Copter)
./waf configure --board sitl
./waf copter
copy**
Use the dedicated script to start the simulation:
bash
cd ArduCopter
sim_vehicle.py -v ArduCopter --console --map
copy**
Use --console to open the MAVProxy console and --map to enable the map display. Upon the first launch, EKF initialization (equivalent to gyro calibration) and GPS Fix standby will occur, after which arming and takeoff become possible.
Verifying basic flight commands:
STABILIZE> mode guided
GUIDED> arm throttle
GUIDED> takeoff 10
copy**
This executes a basic flight sequence in the simulation where the aircraft ascends 10m in GUIDED mode.
Testing in conjunction with parameters
I will show a practical example of parameter tuning verification using SITL.
We will use the L1 Controller parameter verification explained previously as an example. Start the SITL for a fixed-wing aircraft (ArduPlane) and compare the convergence characteristics of the cross-track error while changing NAVL1_PERIOD.
bash
sim_vehicle.py -v ArduPlane --console --map
copy**
# パラメータ変更
param set NAVL1_PERIOD 15
# ミッション飛行を実行してログ記録
mode auto
# 飛行後、ログのNTUNメッセージでxtrack errorを確認
copy**
By repeating flights with different NAVL1_PERIOD values (15, 20, 25 seconds) and comparing the convergence time of the cross-track error and the presence of oscillations through log analysis, you can estimate the optimal value before actual flight.
Wind simulation is also an important verification:
param set SIM_WIND_SPD 10
param set SIM_WIND_DIR 90
copy**
You can evaluate the tracking performance of the L1 Controller in a 10 m/s crosswind and determine the necessity of NAVL1_XTRACK_I.
Sensor noise and failure simulation
SITL can also simulate sensor imperfections, which can be used to verify EKF tuning (FC14).
GPS noise and loss simulation:
param set SIM_GPS_NOISE 3.0
param set SIM_GPS_GLITCH_X 5.0
copy**
Inject noise and glitches (instantaneous position jumps) into the GPS signal to verify whether the EKF's GPS glitch detection (EK3_GLITCH_RAD) functions correctly.
Complete loss of GPS signal:
param set SIM_GPS_DISABLE 1
copy**
You can safely verify fail-safe operations (such as switching from RTL to LAND) in GPS-denied environments (refer to NAV1 to NAV19) using SITL.
IMU noise adjustment:
param set SIM_ACC1_RND 0.05
param set SIM_GYR1_RND 0.02
copy**
Change the random noise levels of the accelerometer and gyro to evaluate whether the EKF's process noise parameters (such as EK3_GYRO_P_NSE) are tuned appropriately.
Wind disturbances and motor failure:
param set SIM_ENGINE_FAIL 1
copy**
Confirm the operation of ArduPilot's failure detection and fail-safe logic with a single-motor failure simulation for a multicopter.
Verification of multiple aircraft and multiple sensor configurations
SITL supports testing by switching between multiple aircraft configurations.
Changing frame types:
bash
sim_vehicle.py -v ArduCopter -f hexa --console --map
copy**
You can test by switching frame types from the default quadcopter to hexacopters, octocopters, and more. You can compare and verify how behavior during motor failure differs depending on the frame type.
Integration with a custom hwdef.dat can be utilized for verifying the custom FC development explained in the Fundamentals series. You can compile a custom board build with a newly defined hwdef.dat in the SITL environment and discover logical errors in peripheral settings before testing on actual hardware. However, since hardware-specific behavior (such as actual SPI communication timing) cannot be verified in SITL, final real-world testing is essential.
Multi-vehicle simulation (Swarm/Formation):
bash
sim_vehicle.py -v ArduCopter -I0 --console
sim_vehicle.py -v ArduCopter -I1 --console
copy**
You can launch multiple SITL instances with different instance numbers (-I) to verify logic for formation flight or multi-vehicle missions.
Integration with Gazebo—High-Precision Physics Simulation
When more precise physics simulation is required, integration with Gazebo is the standard choice.
By using the ArduPilot Gazebo Plugin, you integrate Gazebo's rigid body dynamics engine (ODE, Bullet, etc.) with ArduPilot's flight code. You can simulate more detailed aerodynamics (propeller interaction, ground effect, etc.) than the default SITL physics model.
Integration with ROS2 is a major advantage of adopting Gazebo. You can test ROS2 nodes (image processing, SLAM, path planning) in the Gazebo simulation environment, enabling integration testing that is close to the real machine. Gazebo+SITL is utilized for the development and verification of the ROS2 stacks explained in NAV11 (VIO) and NAV12 (LiDAR SLAM).
Camera and LiDAR simulation are realized using Gazebo sensor plugins. It is also possible to place ArUco markers (FC17 Precision Landing) in the virtual environment and test detection algorithms with a simulated camera.
Automated testing framework—autotest
The official ArduPilot repository includes autotest (an automated regression testing framework), which is used for continuous quality assurance.
bash
Tools/autotest/autotest.py build.Copter test.Copter
copy**
This command automatically executes the Copter build and a defined series of test scenarios (takeoff, hovering, various flight mode transitions, failsafe behavior).
Custom tests are implemented as Python-based test scripts. You can define test cases for your own hwdef.dat or specific mission scenarios and build a development process that executes automated regression tests every time the vehicle software is updated.
Combining this with GitHub Actions or similar tools for CI/CD integration is also practical for executing SITL-based automated tests every time code is changed. When maintaining an ArduPilot fork (a custom modified version) for custom FC development, this automated testing framework becomes the foundation for quality assurance.
MAVLink Message Injection
The SITL environment also supports sensor simulation through the injection of MAVLink messages.
In external navigation simulation (see NAV11 VIO, NAV12 LiDAR SLAM), you can send VISION_POSITION_ESTIMATE messages to SITL via a Python script to verify ExternalNav integration logic without an actual VIO/SLAM system.
python
from pymavlink import mavutil
master = mavutil.mavlink_connection('udp:127.0.0.1:14550')
master.mav.vision_position_estimate_send(
time_usec, x, y, z, roll, pitch, yaw
)
copy**
This approach is effective for unit testing the external sensor integration explained in FC15 (GPS-INS integration) and FC17 (Precision Landing). Even when the actual hardware or algorithm implementation is incomplete, you can verify the integration logic on the EKF side in advance.
Limitations of SITL
It is also important to clarify the areas that SITL cannot verify.
Actual hardware timing is not reproduced in SITL. The actual latency of SPI/I2C communication, priority conflicts in interrupt processing, and the real-time behavior of DMA transfers cannot be accurately reproduced in a simulation on a host PC. These require Hardware-in-the-Loop (HITL) testing or actual flight testing.
Electrical issues (EMI, power noise, vibration) are theoretically impossible to verify in SITL. The effectiveness of EMI countermeasures and IMU vibration countermeasures explained in the previous series can only be confirmed on the actual hardware.
Since the models in SITL are idealized, sensor non-linearity and individual differences are also simplified, meaning the actual complexity of real-world IMU bias characteristics and GPS multipath in real environments is reduced.
Given these limitations, it is practical to incorporate SITL into the development process with a clear division of roles: SITL is optimal for verifying the 'correctness of logic,' while actual hardware testing is indispensable for verifying the 'correctness of physical implementation.'
Summary
SITL is a development platform that executes actual flight code on a host PC and verifies ArduPilot's operation in a simulated sensor and physical environment. It allows for safe execution of parameter tuning, fail-safe logic, and sensor integration verification without the need for actual hardware, and integration with Gazebo enables high-precision simulation including the ROS2 stack. While automated regression testing using the autotest framework is effective for quality assurance in custom FC development, physical issues such as hardware timing and EMI cannot be verified in SITL, necessitating a division of roles with actual hardware testing. In the next installment, FC21, we will explain the power architecture design for the entire FC as the first part of the Hardware Design series.
