@@ -411,6 +411,65 @@ static const uint32_t mipi_dbi_formats[] = {
DRM_FORMAT_XRGB8888,
};
+/**
+ * mipi_dbi_init_with_formats - MIPI DBI initialization with custom formats
+ * @mipi: &mipi_dbi structure to initialize
+ * @funcs: Display pipe functions
+ * @formats: Array of supported formats (DRM_FORMAT\_\*).
+ * @format_count: Number of elements in @formats
+ * @mode: Display mode
+ * @rotation: Initial rotation in degrees Counter Clock Wise
+ * @tx_buf_size: Allocate a transmit buffer of this size.
+ *
+ * This function sets up a &drm_simple_display_pipe with a &drm_connector that
+ * has one fixed &drm_display_mode which is rotated according to @rotation.
+ * This mode is used to set the mode config min/max width/height properties.
+ *
+ * Use mipi_dbi_init() if you don't need custom formats.
+ *
+ * Note:
+ * Some of the helper functions expects RGB565 to be the default format and the
+ * transmit buffer sized to fit that.
+ *
+ * Returns:
+ * Zero on success, negative error code on failure.
+ */
+int mipi_dbi_init_with_formats(struct mipi_dbi *mipi,
+ const struct drm_simple_display_pipe_funcs *funcs,
+ const uint32_t *formats, unsigned int format_count,
+ const struct drm_display_mode *mode,
+ unsigned int rotation, size_t tx_buf_size)
+{
+ struct drm_device *drm = &mipi->drm;
+ int ret;
+
+ if (!mipi->command)
+ return -EINVAL;
+
+ mutex_init(&mipi->cmdlock);
+
+ mipi->tx_buf = devm_kmalloc(drm->dev, tx_buf_size, GFP_KERNEL);
+ if (!mipi->tx_buf)
+ return -ENOMEM;
+
+ ret = tinydrm_display_pipe_init(drm, &mipi->pipe, funcs,
+ DRM_MODE_CONNECTOR_SPI,
+ formats, format_count, mode,
+ rotation);
+ if (ret)
+ return ret;
+
+ drm_plane_enable_fb_damage_clips(&mipi->pipe.plane);
+
+ drm->mode_config.funcs = &mipi_dbi_mode_config_funcs;
+ mipi->rotation = rotation;
+
+ DRM_DEBUG_KMS("rotation = %u\n", rotation);
+
+ return 0;
+}
+EXPORT_SYMBOL(mipi_dbi_init_with_formats);
+
/**
* mipi_dbi_init - MIPI DBI initialization
* @mipi: &mipi_dbi structure to initialize
@@ -433,36 +492,12 @@ int mipi_dbi_init(struct mipi_dbi *mipi,
const struct drm_display_mode *mode, unsigned int rotation)
{
size_t bufsize = mode->vdisplay * mode->hdisplay * sizeof(u16);
- struct drm_device *drm = &mipi->drm;
- int ret;
- if (!mipi->command)
- return -EINVAL;
+ mipi->drm.mode_config.preferred_depth = 16;
- mutex_init(&mipi->cmdlock);
-
- mipi->tx_buf = devm_kmalloc(drm->dev, bufsize, GFP_KERNEL);
- if (!mipi->tx_buf)
- return -ENOMEM;
-
- ret = tinydrm_display_pipe_init(drm, &mipi->pipe, funcs,
- DRM_MODE_CONNECTOR_SPI,
- mipi_dbi_formats,
- ARRAY_SIZE(mipi_dbi_formats), mode,
- rotation);
- if (ret)
- return ret;
-
- drm_plane_enable_fb_damage_clips(&mipi->pipe.plane);
-
- drm->mode_config.funcs = &mipi_dbi_mode_config_funcs;
- drm->mode_config.preferred_depth = 16;
- mipi->rotation = rotation;
-
- DRM_DEBUG_KMS("preferred_depth=%u, rotation = %u\n",
- drm->mode_config.preferred_depth, rotation);
-
- return 0;
+ return mipi_dbi_init_with_formats(mipi, funcs, mipi_dbi_formats,
+ ARRAY_SIZE(mipi_dbi_formats), mode,
+ rotation, bufsize);
}
EXPORT_SYMBOL(mipi_dbi_init);
@@ -24,7 +24,6 @@
#include <drm/drm_rect.h>
#include <drm/drm_vblank.h>
#include <drm/tinydrm/mipi-dbi.h>
-#include <drm/tinydrm/tinydrm-helpers.h>
/* controller-specific commands */
#define ST7586_DISP_MODE_GRAY 0x38
@@ -283,12 +282,6 @@ static const struct drm_simple_display_pipe_funcs st7586_pipe_funcs = {
.prepare_fb = drm_gem_fb_simple_display_pipe_prepare_fb,
};
-static const struct drm_mode_config_funcs st7586_mode_config_funcs = {
- .fb_create = drm_gem_fb_create_with_dirty,
- .atomic_check = drm_atomic_helper_check,
- .atomic_commit = drm_atomic_helper_commit,
-};
-
static const struct drm_display_mode st7586_mode = {
DRM_SIMPLE_MODE(178, 128, 37, 27),
};
@@ -342,15 +335,8 @@ static int st7586_probe(struct spi_device *spi)
}
drm_mode_config_init(drm);
- drm->mode_config.preferred_depth = 32;
- drm->mode_config.funcs = &st7586_mode_config_funcs;
-
- mutex_init(&mipi->cmdlock);
bufsize = (st7586_mode.vdisplay + 2) / 3 * st7586_mode.hdisplay;
- mipi->tx_buf = devm_kmalloc(dev, bufsize, GFP_KERNEL);
- if (!mipi->tx_buf)
- return -ENOMEM;
mipi->reset = devm_gpiod_get(dev, "reset", GPIOD_OUT_HIGH);
if (IS_ERR(mipi->reset)) {
@@ -374,6 +360,12 @@ static int st7586_probe(struct spi_device *spi)
/* Cannot read from this controller via SPI */
mipi->read_commands = NULL;
+ ret = mipi_dbi_init_with_formats(mipi, &st7586_pipe_funcs,
+ st7586_formats, ARRAY_SIZE(st7586_formats),
+ &st7586_mode, rotation, bufsize);
+ if (ret)
+ return ret;
+
/*
* we are using 8-bit data, so we are not actually swapping anything,
* but setting mipi->swap_bytes makes mipi_dbi_typec3_command() do the
@@ -383,15 +375,6 @@ static int st7586_probe(struct spi_device *spi)
*/
mipi->swap_bytes = true;
- ret = tinydrm_display_pipe_init(drm, &mipi->pipe, &st7586_pipe_funcs,
- DRM_MODE_CONNECTOR_SPI,
- st7586_formats, ARRAY_SIZE(st7586_formats),
- &st7586_mode, rotation);
- if (ret)
- return ret;
-
- drm_plane_enable_fb_damage_clips(&mipi->pipe.plane);
-
drm_mode_config_reset(drm);
ret = drm_dev_register(drm, 0);
@@ -400,9 +383,6 @@ static int st7586_probe(struct spi_device *spi)
spi_set_drvdata(spi, drm);
- DRM_DEBUG_KMS("preferred_depth=%u, rotation = %u\n",
- drm->mode_config.preferred_depth, rotation);
-
drm_fbdev_generic_setup(drm, 0);
return 0;
@@ -67,6 +67,11 @@ static inline struct mipi_dbi *drm_to_mipi_dbi(struct drm_device *drm)
return container_of(drm, struct mipi_dbi, drm);
}
+int mipi_dbi_init_with_formats(struct mipi_dbi *mipi,
+ const struct drm_simple_display_pipe_funcs *funcs,
+ const uint32_t *formats, unsigned int format_count,
+ const struct drm_display_mode *mode,
+ unsigned int rotation, size_t tx_buf_size);
int mipi_dbi_init(struct mipi_dbi *mipi,
const struct drm_simple_display_pipe_funcs *funcs,
const struct drm_display_mode *mode, unsigned int rotation);
The MIPI DBI standard support more pixel formats than what this helper supports. Add an init function that lets the driver use different format(s). This avoids open coding mipi_dbi_init() in st7586. st7586 sets preferred_depth but this is not necessary since it only supports one format. Cc: David Lechner <david@lechnology.com> Signed-off-by: Noralf Trønnes <noralf@tronnes.org> --- drivers/gpu/drm/tinydrm/mipi-dbi.c | 91 +++++++++++++++++++++--------- drivers/gpu/drm/tinydrm/st7586.c | 32 ++--------- include/drm/tinydrm/mipi-dbi.h | 5 ++ 3 files changed, 74 insertions(+), 54 deletions(-)