Note

This is the documentation for the latest development branch and may refer to features that are not available in released versions. If you are looking for the documentation for a specific release, use the drop-down menu on the left and select the desired version.

How to Add a Display Driver#

This document describes the recommended workflow for adding a new display panel under the current display driver framework. The new framework has removed the old DSI Debugger debug path. When adding a new panel, you should first complete the display driver, pin, and panel selection in make menuconfig, and then add the code following the current connector/panel framework.

This document uses a 368(H) x 552(V) MIPI DSI panel as an example to walk through the complete process from menuconfig to code integration.

Overall Workflow#

The recommended steps for adding a new panel are:

  1. Enable the corresponding display driver in make menuconfig and configure the pins.

  2. Select an existing panel in Display Panel Drivers Configuration, or add a new panel driver for a new panel.

  3. Build and run a display sample, then use list_connector and existing samples to verify the configuration.

  4. If the panel is not yet in the SDK, add the connector_type, panel_desc, initialization sequence, and CanMV mapping following the current framework.

Configure Display Settings in menuconfig First#

Run the following from the project root directory:

make menuconfig

Navigate to:

MPP Configuration -> Display Configuration

display

Select the Display Driver Type#

Based on your hardware connection, enable the correct display driver first:

  • Enable HDMI Display Driver

  • Enable LCD Display Driver

  • Enable SPI LCD Display Driver

  • Enable QSPI LCD Display Driver

  • Enable OSPI LCD Display Driver

For a MIPI DSI LCD panel, you typically need to enable Enable LCD Display Driver.

Select the Panel Driver#

After completing the driver type and pin configuration, select the panel driver in:

Display Panel Drivers Configuration

Currently available panel/bridge chip drivers that can be selected directly in the SDK include:

  • Enable HDMI Display Panel Driver LT9611

  • Enable LCD Display Panel Driver HX8399

  • Enable LCD Display Panel Driver ST7701

  • Enable LCD Display Panel Driver ili9806

  • Enable LCD Display Panel Driver ili9881

  • Enable LCD Display Panel Driver nt35516

  • Enable LCD Display Panel Driver nt35532

  • Enable LCD Display Panel Driver gc9503

  • Enable LCD Display Panel Driver st7102

  • Enable LCD Display Panel Driver aml020t

  • Enable LCD Display Panel Driver JD9852

  • Enable SPI LCD Panel Driver ST7789

If your panel model is already listed here, enable it first and verify the pin and display link. If your model is not listed, continue with the “Adding the Panel in Project Code” section below.

display

Save the configuration and rebuild the firmware.

Verify the Current Configuration#

It is recommended to verify that the menuconfig settings are correct before writing any new code.

Enable and Build Display Samples#

In RT-Smart UserSpace Examples Configuration, enable at least:

  • Enable MPP examples

  • One or more VO/display-related samples, such as sample_vo_video or sample_vo_osd

After rebuilding the image, locate the samples on the board.

Check the Connectors Supported by the Current Firmware#

After entering the board shell, run:

list_connector

This command lists the connector types and enumeration values compiled into the current firmware. It helps you confirm:

  • Whether the panel driver selected in menuconfig has taken effect

  • Whether a newly added panel driver has made it into the final image

  • Which connector_type to pass when running a sample

Run a Display Sample#

For example:

./mpp/sample_vo_video.elf <connector_type>

If the sample can light up the enabled panel, the display link, pins, and basic timing are working. You can then add new panel code with a clearer baseline.

Information to Gather Before Adding a New Panel#

Before writing a panel driver, you typically need two categories of information:

  1. Panel timing parameters

  2. The initialization sequence provided by the panel vendor

Both will go into the panel driver source code, rather than a configuration file on the SD card as in the old workflow.

Panel Timing#

Using the example panel in this document, timing information typically includes:

pclk_hz=27000000
fps=60
lane_num=2

hactive=368
hsync=8
hbp=16
hfp=16

vactive=552
vsync=48
vbp=250
vfp=250

These values map to the timing field in panel_desc, for example:

  • pclk_hz / pclk_khz

  • hactive

  • hsync_len

  • hback_porch

  • hfront_porch

  • vactive

  • vsync_len

  • vback_porch

  • vfront_porch

You can still use the timing calculation tool to assist:

K230 MIPI DSI Connector Info Generator

This tool only validates whether timing parameters can be generated.

Initialization Sequence#

Vendors typically provide a register initialization table, for example:

{0xFF,5,{0x77,0x01,0x00,0x00,0x13}},
{0xEF,1,{0x08}},
{0xFF,5,{0x77,0x01,0x00,0x00,0x10}},
{0xC0,2,{0x44,0x00}},
{0xC1,2,{0x0B,0x02}},
{0xC2,2,{0x07,0x1F}},

In the current framework these are converted into a command sequence array in the panel source file, such as the init_sequence in mipi_st7701.c:

const k_u8 init_sequence[] = {
    0x39, 0, 6, 0xFF, 0x77, 0x01, 0x00, 0x00, 0x13,
    0x15, 0, 2, 0xEF, 0x08,
    0x39, 0, 3, 0xC0, 0x44, 0x00,
};

The command format is:

cmd_type, delay_ms, cmd_data_length, cmd_data0 ... cmd_dataN

Common cmd_type values:

  • 0x05: single-byte command, no parameters

  • 0x15: single-byte command with one parameter

  • 0x39: long command with multiple parameters

Two conversion examples:

{0xB0,16,{0x0F,0x1E,0x25,0x0D,0x11,0x06,0x12,0x08,0x08,0x2A,0x05,0x12,0x10,0x2B,0x32,0x1F}},

# Remove outer braces
# 0xB0 is the command, followed by 16 parameter bytes, so use 0x39
# Length = 1 command byte + 16 parameter bytes = 17

0x39,0,17,0xB0,0x0F,0x1E,0x25,0x0D,0x11,0x06,0x12,0x08,0x08,0x2A,0x05,0x12,0x10,0x2B,0x32,0x1F
{0x11,0,{0x00}},
{REGFLAG_DELAY,120,{}},

# This group can also be placed in the init_sequence array
# Treating it as "1 command + 1 parameter":

0x15,120,2,0x11,0x00

Adding the Panel in Project Code#

The current framework does not simply copy an old panel file and rename it. It is organized around connector_type, panel_desc, panel_ops, and panel_drv.

Define or Confirm the connector_type#

Panel type definitions are located in:

  • src/rtsmart/mpp/include/comm/k_connector_comm.h

The project uses K_CONN_TYPE(chip, bus, w, h, ver) to generate k_connector_type. When adding a new panel, first add a new type constant for the new model, following the naming style of existing definitions:

  • ST7701_480_800_DSI_V1

  • ST7701_480_854_DSI_V1

  • ST7701_480_640_DSI_V1

  • ST7701_368_544_DSI_V1

If you are adding a new resolution variant of an existing chip, prefer the existing chip naming convention rather than inventing a new one.

Add the Initialization and Descriptor in the Panel Source File#

DSI panel implementations are usually located in:

  • src/rtsmart/mpp/kernel/connector/src/panels/

For example, the ST7701 implementation is in:

  • src/rtsmart/mpp/kernel/connector/src/panels/mipi_st7701.c

A new panel typically needs at minimum:

  1. An initialization function corresponding to init_sequence

  2. A panel_ops

  3. A panel_desc

  4. A panel_drv or a new variant attached to an existing panel_drv

Key fields in panel_desc include:

  • name

  • connector_type

  • bus_type

  • timing

  • gpio

  • bus

  • bus_ops

  • ops

For a DSI panel, gpio typically references the pins configured in menuconfig:

.gpio = {
    .reset_pin = CONFIG_MPP_DSI_LCD_RESET_PIN,
    .backlight_pin = CONFIG_MPP_DSI_LCD_BACKLIGHT_PIN,
    .reset_delay_ms = 10,
    .backlight_delay_ms = 0,
    .reset_active_low = K_TRUE,
    .backlight_active_low = K_FALSE,
},

This is why you should configure the pins in Display Configuration before adding panel code.

Register the New Panel in the Driver Framework#

The connector core looks up available panels from connector_drv_list[]. The relevant logic is in:

  • src/rtsmart/mpp/kernel/connector/src/connector_dev.c

The lookup flow is:

  1. Iterate over connector_drv_list[]

  2. Iterate over each driver’s panel_variants

  3. Match the target panel by connector_type

When adding a new panel, ensure it is included in a panel_drv’s panel_variants, and that the driver itself is compiled into the image.

Wire the New Panel into Kconfig and Makefile#

After writing the panel source code, connect it to the build system.

Relevant files:

  • src/rtsmart/mpp/Kconfig

  • src/rtsmart/mpp/kernel/connector/Makefile

Kconfig exposes the new panel under:

MPP Configuration -> Display Configuration -> Display Panel Drivers Configuration

The Makefile decides whether to compile the source file based on the Kconfig option. For example, existing DSI panels are wired in as:

src-$(CONFIG_MPP_DSI_ENABLE_LCD_ST7701) += src/panels/mipi_st7701.c

Add a corresponding entry for the new panel and add the matching config entry in Kconfig.

Add CanMV Python Interface Mapping (If Needed)#

If the panel should also be selectable via the CanMV Python interface—not just in C samples—also update:

  • src/canmv/port/modules/modmedia.display.c

Two parts need updating:

  1. The PY_PANEL_TYPE_* enum

  2. The py_display_panel_map[] mapping table

Only after the new connector_type is mapped into py_display_panel_map[] can the CanMV Python layer select it by panel type and resolution.

Minimum Checklist for Adding a New Panel#

Before submitting code, verify at least the following:

  1. The new panel option is visible in make menuconfig.

  2. The reset/backlight/bus pins in Display Configuration match the actual hardware.

  3. The Makefile compiles the corresponding panel source file based on the new Kconfig option.

  4. The connector_type is defined in k_connector_comm.h.

  5. The panel_desc has timing, lane count, GPIO, and initialization sequence filled in.

  6. The connector_drv_list[] lookup path can reach the new panel.

  7. The new panel appears in list_connector on the board.

  8. sample_vo_video or another display sample can light up the panel.

  9. If Python support is needed, py_display_panel_map[] has been updated.

Troubleshooting#

A panel option is not visible in menuconfig#

Check:

  1. Whether the corresponding display driver is enabled first, e.g. Enable LCD Display Driver or Enable SPI LCD Display Driver.

  2. Whether the Kconfig entry depends on an upstream driver switch.

  3. Whether the new panel’s Kconfig configuration has been connected.

Build succeeds but list_connector does not show the new panel#

Check:

  1. Whether the Makefile compiles the panel source file.

  2. Whether the driver list in connector_dev.c includes the panel_drv for this panel.

  3. Whether the new panel_desc is actually attached to panel_variants.

list_connector is only compiled in the RTOS SDK.

Panel powers on but shows no image#

Check:

  1. Whether the reset/backlight GPIO configuration is correct.

  2. Whether the DSI lane count, pixel clock, porch, and sync parameters are correct.

  3. Whether the vendor initialization sequence is complete and delays are preserved.

  4. Whether the connector_type passed to the sample matches the new panel.

  5. Check the serial log. If the issue persists, post on the forum for help.

References#

Comments list
Comments
Log in