Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CODEOWNERS
Original file line number Diff line number Diff line change
Expand Up @@ -252,6 +252,7 @@
/drivers/counter/*esp32* @glaubermaroto
/drivers/crypto/*nrf_ecb* @maciekfabia @anangl
/drivers/display/*rm68200* @mmahadevan108
/drivers/display/display_ili9342c.* @extremegtx
/drivers/dac/ @martinjaeger
/drivers/dai/ @juimonen @marcinszkudlinski @abonislawski
/drivers/dai/intel/ @juimonen @marcinszkudlinski @abonislawski
Expand Down
1 change: 1 addition & 0 deletions drivers/display/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ zephyr_library_sources_ifdef(CONFIG_UC81XX uc81xx.c)
zephyr_library_sources_ifdef(CONFIG_ILI9XXX display_ili9xxx.c)
zephyr_library_sources_ifdef(CONFIG_ILI9340 display_ili9340.c)
zephyr_library_sources_ifdef(CONFIG_ILI9341 display_ili9341.c)
zephyr_library_sources_ifdef(CONFIG_ILI9342C display_ili9342c.c)
zephyr_library_sources_ifdef(CONFIG_ILI9488 display_ili9488.c)
zephyr_library_sources_ifdef(CONFIG_LS0XX ls0xx.c)
zephyr_library_sources_ifdef(CONFIG_MAX7219 display_max7219.c)
Expand Down
9 changes: 9 additions & 0 deletions drivers/display/Kconfig.ili9xxx
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,15 @@ config ILI9341
help
Enable driver for ILI9341 display driver.

config ILI9342C
bool "ILI9342C display driver"
default y
depends on DT_HAS_ILITEK_ILI9342C_ENABLED
select SPI
select ILI9XXX
help
Enable driver for ILI9342C display driver.

config ILI9488
bool "ILI9488 display driver"
default y
Expand Down
122 changes: 122 additions & 0 deletions drivers/display/display_ili9342c.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,122 @@
/*
* Copyright (c) 2020 Teslabs Engineering S.L.
* Copyright (c) 2021 Krivorot Oleg <[email protected]>
* Copyright (c) 2022 Konstantinos Papadopoulos <[email protected]>
* Copyright (c) 2022 Mohamed ElShahawi <[email protected]>
*
* SPDX-License-Identifier: Apache-2.0
*/

#include "display_ili9342c.h"
#include "display_ili9xxx.h"

#include <zephyr/logging/log.h>
LOG_MODULE_REGISTER(display_ili9342c, CONFIG_DISPLAY_LOG_LEVEL);

int ili9342c_regs_init(const struct device *dev)
{
const struct ili9xxx_config *config = dev->config;
const struct ili9342c_regs *regs = config->regs;
int r;

/* some commands require that SETEXTC be set first before it becomes enabled. */
LOG_HEXDUMP_DBG(regs->setextc, ILI9342C_SETEXTC_LEN, "SETEXTC");
r = ili9xxx_transmit(dev, ILI9342C_SETEXTC, regs->setextc,
ILI9342C_SETEXTC_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->gamset, ILI9342C_GAMSET_LEN, "GAMSET");
r = ili9xxx_transmit(dev, ILI9342C_GAMSET, regs->gamset,
ILI9342C_GAMSET_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->ifmode, ILI9342C_IFMODE_LEN, "IFMODE");
r = ili9xxx_transmit(dev, ILI9342C_IFMODE, regs->ifmode,
ILI9342C_IFMODE_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->frmctr1, ILI9342C_FRMCTR1_LEN, "FRMCTR1");
r = ili9xxx_transmit(dev, ILI9342C_FRMCTR1, regs->frmctr1,
ILI9342C_FRMCTR1_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->invtr, ILI9342C_INVTR_LEN, "INVTR");
r = ili9xxx_transmit(dev, ILI9342C_INVTR, regs->invtr,
ILI9342C_INVTR_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->disctrl, ILI9342C_DISCTRL_LEN, "DISCTRL");
r = ili9xxx_transmit(dev, ILI9342C_DISCTRL, regs->disctrl,
ILI9342C_DISCTRL_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->etmod, ILI9342C_ETMOD_LEN, "ETMOD");
r = ili9xxx_transmit(dev, ILI9342C_ETMOD, regs->etmod,
ILI9342C_ETMOD_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->pwctrl1, ILI9342C_PWCTRL1_LEN, "PWCTRL1");
r = ili9xxx_transmit(dev, ILI9342C_PWCTRL1, regs->pwctrl1,
ILI9342C_PWCTRL1_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->pwctrl2, ILI9342C_PWCTRL2_LEN, "PWCTRL2");
r = ili9xxx_transmit(dev, ILI9342C_PWCTRL2, regs->pwctrl2,
ILI9342C_PWCTRL2_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->pwctrl3, ILI9342C_PWCTRL3_LEN, "PWCTRL3");
r = ili9xxx_transmit(dev, ILI9342C_PWCTRL3, regs->pwctrl3,
ILI9342C_PWCTRL3_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->vmctrl1, ILI9342C_VMCTRL1_LEN, "VMCTRL1");
r = ili9xxx_transmit(dev, ILI9342C_VMCTRL1, regs->vmctrl1,
ILI9342C_VMCTRL1_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->pgamctrl, ILI9342C_PGAMCTRL_LEN, "PGAMCTRL");
r = ili9xxx_transmit(dev, ILI9342C_PGAMCTRL, regs->pgamctrl,
ILI9342C_PGAMCTRL_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->ngamctrl, ILI9342C_NGAMCTRL_LEN, "NGAMCTRL");
r = ili9xxx_transmit(dev, ILI9342C_NGAMCTRL, regs->ngamctrl,
ILI9342C_NGAMCTRL_LEN);
if (r < 0) {
return r;
}

LOG_HEXDUMP_DBG(regs->ifctl, ILI9342C_IFCTL_LEN, "IFCTL");
r = ili9xxx_transmit(dev, ILI9342C_IFCTL, regs->ifctl,
ILI9342C_IFCTL_LEN);
if (r < 0) {
return r;
}

return 0;
}
95 changes: 95 additions & 0 deletions drivers/display/display_ili9342c.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
/*
* Copyright (c) 2020 Teslabs Engineering S.L.
* Copyright (c) 2021 Krivorot Oleg <[email protected]>
* Copyright (c) 2022 Konstantinos Papadopoulos <[email protected]>
*
* SPDX-License-Identifier: Apache-2.0
*/
#ifndef ZEPHYR_DRIVERS_DISPLAY_DISPLAY_ILI9342C_H_
#define ZEPHYR_DRIVERS_DISPLAY_DISPLAY_ILI9342C_H_

#include <zephyr/device.h>

/* Commands/registers. */
#define ILI9342C_GAMSET 0x26
#define ILI9342C_IFMODE 0xB0
#define ILI9342C_FRMCTR1 0xB1
#define ILI9342C_INVTR 0xB4
#define ILI9342C_DISCTRL 0xB6
#define ILI9342C_ETMOD 0xB7
#define ILI9342C_PWCTRL1 0xC0
#define ILI9342C_PWCTRL2 0xC1
#define ILI9342C_PWCTRL3 0xC2
#define ILI9342C_VMCTRL1 0xC5
#define ILI9342C_SETEXTC 0xC8
#define ILI9342C_PGAMCTRL 0xE0
#define ILI9342C_NGAMCTRL 0xE1
#define ILI9342C_IFCTL 0xF6

/* Commands/registers length. */
#define ILI9342C_GAMSET_LEN 1U
#define ILI9342C_IFMODE_LEN 1U
#define ILI9342C_FRMCTR1_LEN 2U
#define ILI9342C_INVTR_LEN 1U
#define ILI9342C_DISCTRL_LEN 4U
#define ILI9342C_ETMOD_LEN 1U
#define ILI9342C_PWCTRL1_LEN 2U
#define ILI9342C_PWCTRL2_LEN 1U
#define ILI9342C_PWCTRL3_LEN 1U
#define ILI9342C_VMCTRL1_LEN 1U
#define ILI9342C_SETEXTC_LEN 3U
#define ILI9342C_PGAMCTRL_LEN 15U
#define ILI9342C_NGAMCTRL_LEN 15U
#define ILI9342C_IFCTL_LEN 3U

/** X resolution (pixels). */
#define ILI9342c_X_RES 320U
/** Y resolution (pixels). */
#define ILI9342c_Y_RES 240U

/** ILI9342C registers to be initialized. */
struct ili9342c_regs {
uint8_t gamset[ILI9342C_GAMSET_LEN];
uint8_t ifmode[ILI9342C_IFMODE_LEN];
uint8_t frmctr1[ILI9342C_FRMCTR1_LEN];
uint8_t invtr[ILI9342C_INVTR_LEN];
uint8_t disctrl[ILI9342C_DISCTRL_LEN];
uint8_t etmod[ILI9342C_ETMOD_LEN];
uint8_t pwctrl1[ILI9342C_PWCTRL1_LEN];
uint8_t pwctrl2[ILI9342C_PWCTRL2_LEN];
uint8_t pwctrl3[ILI9342C_PWCTRL3_LEN];
uint8_t vmctrl1[ILI9342C_VMCTRL1_LEN];
uint8_t setextc[ILI9342C_SETEXTC_LEN];
uint8_t pgamctrl[ILI9342C_PGAMCTRL_LEN];
uint8_t ngamctrl[ILI9342C_NGAMCTRL_LEN];
uint8_t ifctl[ILI9342C_IFCTL_LEN];
};

/* Initializer macro for ILI9342C registers. */
#define ILI9342c_REGS_INIT(n) \
static const struct ili9342c_regs ili9xxx_regs_##n = { \
.gamset = DT_PROP(DT_INST(n, ilitek_ili9342c), gamset), \
.ifmode = DT_PROP(DT_INST(n, ilitek_ili9342c), ifmode), \
.frmctr1 = DT_PROP(DT_INST(n, ilitek_ili9342c), frmctr1), \
.invtr = DT_PROP(DT_INST(n, ilitek_ili9342c), invtr), \
.disctrl = DT_PROP(DT_INST(n, ilitek_ili9342c), disctrl), \
.etmod = DT_PROP(DT_INST(n, ilitek_ili9342c), etmod), \
.pwctrl1 = DT_PROP(DT_INST(n, ilitek_ili9342c), pwctrl1), \
.pwctrl2 = DT_PROP(DT_INST(n, ilitek_ili9342c), pwctrl2), \
.pwctrl3 = DT_PROP(DT_INST(n, ilitek_ili9342c), pwctrl3), \
.vmctrl1 = DT_PROP(DT_INST(n, ilitek_ili9342c), vmctrl1), \
.setextc = {0xFF, 0x93, 0x42}, \
.pgamctrl = DT_PROP(DT_INST(n, ilitek_ili9342c), pgamctrl), \
.ngamctrl = DT_PROP(DT_INST(n, ilitek_ili9342c), ngamctrl), \
.ifctl = DT_PROP(DT_INST(n, ilitek_ili9342c), ifctl), \
Comment on lines +71 to +84
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

you can simplify with DT_INST_PROP

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

ili9xxx drivers doesn't include DT_DRV_COMPAT value. so I chose to follow the other variants.

};

/**
* @brief Initialize ILI9342C registers with DT values.
*
* @param dev ILI9342C device instance
* @return 0 on success, errno otherwise.
*/
int ili9342c_regs_init(const struct device *dev);

#endif /* ZEPHYR_DRIVERS_DISPLAY_DISPLAY_ILI9342C_H_ */
62 changes: 52 additions & 10 deletions drivers/display/display_ili9xxx.c
Original file line number Diff line number Diff line change
Expand Up @@ -244,20 +244,32 @@ ili9xxx_set_pixel_format(const struct device *dev,
static int ili9xxx_set_orientation(const struct device *dev,
const enum display_orientation orientation)
{
const struct ili9xxx_config *config = dev->config;
struct ili9xxx_data *data = dev->data;

int r;
uint8_t tx_data = ILI9XXX_MADCTL_BGR;

if (orientation == DISPLAY_ORIENTATION_NORMAL) {
tx_data |= ILI9XXX_MADCTL_MX;
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_90) {
tx_data |= ILI9XXX_MADCTL_MV;
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_180) {
tx_data |= ILI9XXX_MADCTL_MY;
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_270) {
tx_data |= ILI9XXX_MADCTL_MV | ILI9XXX_MADCTL_MX |
ILI9XXX_MADCTL_MY;
if (config->quirks->cmd_set == CMD_SET_1) {
if (orientation == DISPLAY_ORIENTATION_NORMAL) {
tx_data |= ILI9XXX_MADCTL_MX;
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_90) {
tx_data |= ILI9XXX_MADCTL_MV;
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_180) {
tx_data |= ILI9XXX_MADCTL_MY;
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_270) {
tx_data |= ILI9XXX_MADCTL_MV | ILI9XXX_MADCTL_MX |
ILI9XXX_MADCTL_MY;
}
} else if (config->quirks->cmd_set == CMD_SET_2) {
if (orientation == DISPLAY_ORIENTATION_NORMAL) {
/* Do nothing */
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_90) {
tx_data |= ILI9XXX_MADCTL_MV | ILI9XXX_MADCTL_MY;
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_180) {
tx_data |= ILI9XXX_MADCTL_MY | ILI9XXX_MADCTL_MX;
} else if (orientation == DISPLAY_ORIENTATION_ROTATED_270) {
tx_data |= ILI9XXX_MADCTL_MV | ILI9XXX_MADCTL_MX;
}
}

r = ili9xxx_transmit(dev, ILI9XXX_MADCTL, &tx_data, 1U);
Expand Down Expand Up @@ -420,12 +432,37 @@ static const struct display_driver_api ili9xxx_api = {
.set_orientation = ili9xxx_set_orientation,
};

#ifdef CONFIG_ILI9340
static const struct ili9xxx_quirks ili9340_quirks = {
.cmd_set = CMD_SET_1,
};
#endif

#ifdef CONFIG_ILI9341
static const struct ili9xxx_quirks ili9341_quirks = {
.cmd_set = CMD_SET_1,
};
#endif

#ifdef CONFIG_ILI9342C
static const struct ili9xxx_quirks ili9342c_quirks = {
.cmd_set = CMD_SET_2,
};
#endif

#ifdef CONFIG_ILI9488
static const struct ili9xxx_quirks ili9488_quirks = {
.cmd_set = CMD_SET_1,
};
#endif

#define INST_DT_ILI9XXX(n, t) DT_INST(n, ilitek_ili##t)

#define ILI9XXX_INIT(n, t) \
ILI##t##_REGS_INIT(n); \
\
static const struct ili9xxx_config ili9xxx_config_##n = { \
.quirks = &ili##t##_quirks, \
.spi = SPI_DT_SPEC_GET(INST_DT_ILI9XXX(n, t), \
SPI_OP_MODE_MASTER | SPI_WORD_SET(8), \
0), \
Expand Down Expand Up @@ -462,6 +499,11 @@ DT_INST_FOREACH_ILI9XXX_STATUS_OKAY(9340);
DT_INST_FOREACH_ILI9XXX_STATUS_OKAY(9341);
#endif

#ifdef CONFIG_ILI9342C
#include "display_ili9342c.h"
DT_INST_FOREACH_ILI9XXX_STATUS_OKAY(9342c);
#endif

#ifdef CONFIG_ILI9488
#include "display_ili9488.h"
DT_INST_FOREACH_ILI9XXX_STATUS_OKAY(9488);
Expand Down
11 changes: 11 additions & 0 deletions drivers/display/display_ili9xxx.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,7 +54,18 @@
/** Reset wait time (ms), ref 15.4 of ILI9XXX manual. */
#define ILI9XXX_RESET_WAIT_TIME 5

enum madctl_cmd_set {
CMD_SET_1, /* Default for most of ILI9xxx display controllers */
CMD_SET_2, /* Used by ILI9342c */
};

struct ili9xxx_quirks {
enum madctl_cmd_set cmd_set;
};

struct ili9xxx_config {
const struct ili9xxx_quirks *quirks;

struct spi_dt_spec spi;
struct gpio_dt_spec cmd_data;
struct gpio_dt_spec reset;
Expand Down
Loading