MAVLink Generator (C/C++, Python)

MAVLink is distributed with a common set of messages. Custom messages can be generated and included as a replacement for the common message set or as extension to it. See the minimal.xml for a minimal example and pixhawk.xml for an example of using the common message set with some project-specific extensions.

MAVLINK Generator Window

Generator Steps

  1. Load XML file, from mavlink/message_definitions
  2. Edit XML file on the right side where needed
  3. Select output directory, e.g. mavlink/include
  4. Click “Save and Generate”
  5. Use the new headers in your project

Commandline Interface and Python Output

In addition to the QGroundControl GUI, custom messages can be generated with the Python generator from Andrew Tridgell, located at the Github repository linked below. The Python generator is also internally used by QGroundControl.

Main features

  • generates both python and C implementations with one generator
  • generates either the 0.9 wire protocol or the 1.0 wire protocol
  • template based code generation for easier maintainence
  • optionally allows for data and large functions to be split into a library
  • works with either little or big endian CPUs with either protocol
  • takes full advantage of a match between CPU byte order and protocol byte order
  • more compact code generation than previous generator

Usage Instructions

Create the output directories:

mkdir -p ../mavlink/include/mavlink/v1.0
mkdir -p ../mavlink/include/mavlink/v0.9

This will generate a C implementation with the 1.0 wire protocol:

pymavlink/generator/mavgen.py --lang=C --output=../mavlink/include/mavlink/v1.0 message_definitions/v1.0/common.xml --wire-protocol=1.0

and this will generate it for the 0.9 wire protocol:

pymavlink/generator/mavgen.py --lang=C --output=../mavlink/include/mavlink/v0.9 message_definitions/v0.9/common.xml --wire-protocol=0.9

this will generate a Python implementation (in mavlink.py) for the 1.0 protocol:

pymavlink/generator/mavgen.py --lang=python --output=../mavlink/share/pyshared/pymavlink message_definitions/v1.0/common.xml --wire-protocol=1.0

and this for the (outdated) 0.9 protocol:

pymavlink/generator/mavgen.py --lang=python --output=../mavlink/share/pyshared/pymavlink message_definitions/v0.9/common.xml --wire-protocol=0.9

Optional Features

You can optionally enable some new features. These are not required by default, but make the execution of MAVLink more efficient or flexible. For example, using this:

#define MAVLINK_SEPARATE_HELPERS

will allow you to build the larger protocol functions and data in a separate library, which makes it safe to include mavlink headers in multiple modules in your program.

If you define MAVLINK_SEND_UART_BYTES() like this:

#define MAVLINK_SEND_UART_BYTES(chan, buffer, len) my_comm_send_uart_bytes(chan, buffer, len)

then you will get a single function call for sending a whole message onto the wire when using the *_send() convenience functions (you write your own my_comm_send_uart_bytes() function).

You can also optionally put the CRC array for protocol 1.0 in the right segment on systems that need that by defining your own MAVLINK_MESSAGE_CRCS macro, like this:

#ifdef MAVLINK_MESSAGE_CRCS
static const uint8_t mavlink_message_crcs[] PROGMEM = MAVLINK_MESSAGE_CRCS;
#define MAVLINK_MESSAGE_CRC(msgid) pgm_read_byte(&mavlink_message_crcs[msgid])
#endif