Flexible I/O: Auxiliary port configuration

In the last post, I covered the goals behind more flexible I/O support in the moteus brushless controller. This time, I’ll start to cover the configuration model that I implemented to make that support work. It is broken up into 3 distinct phases, auxiliary ports, sources, and sinks.

Slightly simplified I/O structure flow diagram

Auxiliary port pin configuration

To begin with, the available connectors and external pins on moteus are organized into “auxiliary ports”. For the moteus r4.3/4.5/4.8/4.11, the correspondence is that the external primary encoder connector, if present (r4.8 and newer), is “auxiliary port 1”. The ABS port and some on-board debug pads are “auxiliary port 2”. For each port, there are two levels of configuration, at the pin level and the function level.

At the pin level, each pin can be assigned to exactly one possible function from the available set. The possibilities include each of the possible encoder functions, as well as digital input output, or analog input. For each board, not all pins are capable of all functions, if an unsupported configuration is attempted, it just results in a runtime error. The current set of capabilities for the connectors available on moteus r4.11 looks like:

Some modes can be assigned to any pin no matter the board version. These modes are digital input or output, hall effect input, software based quadrature, and index input.

The pin configuration is selected by a single enumeration for each pin, located at aux[12].pins.X.mode. Additionally, a pull-down, pull-up, or open-collector can be configured for each pin at aux[12].pins.X.pull, although not all functions and pins support all pull-up values. For instance, analog inputs do not support pull-up or open-collector, and digital outputs support no pulls at all.

Note that the pin number in configuration is the “logical pin” number and is listed in the “Aux” column of the above table. It basically counts from 0 starting at the first pin available for input or output.

Auxiliary port function configuration

After the pins are configured, each of the possible functions on an auxiliary port has a configuration section which allows it to be enabled, and in most cases provides additional options as well. If a function is enabled, but pins with appropriate capabilities are not configured for that function, then a runtime error is generated.

The functions that are currently implemented and their configuration options are:

  • SPI: Whether an AS5047 or a iC-PZ encoder is present, and what bit-rate the SPI bus should operate at.
  • UART: The only supported type currently is the RLS AksIM-2. The baud rate and polling rate can be configured.
  • Quadrature: The counts per revolution.
  • Hall effect: A bitfield describing the polarity of the 3 hall effect inputs.
  • Index: None
  • Sine/Cosine: The neutral value can be configured as measured by a 4096 count ADC converter (this usually must be calibrated).
  • I2C: The I2C bitrate and mode can be configured, along with up to 3 different I2C devices. For each device, the address and polling rate can be selected. Currently available devices are the AS5600 or the AS5048A.

Notably, with the exception of I2C, only one instance of each function can be enabled for a given auxiliary port. Thus it is not possible to have two independent quadrature encoders connected to a single auxiliary port, even if the available pins would otherwise permit it. Digital input, digital output and analog input do not require a “function”, so as many of those may exist as desired.

Next up

In the next post, I’ll cover how the sources section of the above diagram is configured.