Skip to main content
The driver base classes and data types ship in both SDKs (ados.sdk.drivers in Python, ados_sdk::drivers in Rust), and the method contracts on these pages match them. The agent does not route drivers. It never calls discover(), open() or the iterators. register_*_driver calls return not_implemented, and the sensor.*.register capabilities are refused at grant time. A driver plugin opens and runs its own device from its lifecycle hooks, as the first-party Gimbal v2 plugin does. No Mission Control panel renders driver output.
An EscDriver reads per-motor telemetry from electronic speed controllers as a stream of EscTelemetry samples. DShot telemetry, KISS and BLHeli32 protocols share this interface. ESC drivers are read-only by design. Motor setpoints flow through the flight controller, not through the agent.

The interface

Candidates

Unlike the other kinds, EscCandidate has a required motor_count field:

Capabilities

Telemetry samples

Report 0.0 for a value the protocol does not carry, and set the matching has_* flag to False in EscCapabilities so your GCS half knows to hide it.

Opening the driver from your plugin

Your plugin calls discover(), open() and consumes telemetry_iterator itself, then publishes the samples with ctx.telemetry.extend. The pattern is on Driver layer. A direct telemetry wire needs hardware.uart; telemetry carried in the MAVLink stream needs mavlink.read.

Next steps

Driver layer

The shared contract and the manifest table.

Hardware testing

Test with a mock serial backend.

Payload actuator driver

The next driver kind.
Last modified on October 11, 2026