You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@nuttx.apache.org by pk...@apache.org on 2022/06/29 21:32:09 UTC

[incubator-nuttx] 01/03: xtensa/esp32s2: Add driver for I2C peripheral in Master mode

This is an automated email from the ASF dual-hosted git repository.

pkarashchenko pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/incubator-nuttx.git

commit 0657621848648f20149c550da45cc32e3321a499
Author: Gustavo Henrique Nihei <gu...@espressif.com>
AuthorDate: Wed Jun 15 15:35:54 2022 -0300

    xtensa/esp32s2: Add driver for I2C peripheral in Master mode
    
    Signed-off-by: Gustavo Henrique Nihei <gu...@espressif.com>
---
 arch/xtensa/src/esp32s2/Kconfig                   |   58 +
 arch/xtensa/src/esp32s2/Make.defs                 |    4 +
 arch/xtensa/src/esp32s2/esp32s2_i2c.c             | 1702 ++++++++++++++++++
 arch/xtensa/src/esp32s2/esp32s2_i2c.h             |   91 +
 arch/xtensa/src/esp32s2/hardware/esp32s2_i2c.h    | 1992 +++++++++++++++++++++
 arch/xtensa/src/esp32s2/hardware/esp32s2_soc.h    |    2 +-
 arch/xtensa/src/esp32s2/hardware/esp32s2_system.h |   91 +-
 7 files changed, 3893 insertions(+), 47 deletions(-)

diff --git a/arch/xtensa/src/esp32s2/Kconfig b/arch/xtensa/src/esp32s2/Kconfig
index 3f1de8c51a..01c68a72b4 100644
--- a/arch/xtensa/src/esp32s2/Kconfig
+++ b/arch/xtensa/src/esp32s2/Kconfig
@@ -15,6 +15,7 @@ config ARCH_CHIP_ESP32S2WROVER
 	bool "ESP32-S2-WROVER"
 	select ESP32S2_FLASH_4M
 	select ESP32S2_PSRAM_2M
+	select ARCH_HAVE_I2CRESET
 	---help---
 		Generic module with an embedded ESP32-S2
 
@@ -232,6 +233,10 @@ config ESP32S2_UART
 	bool
 	default n
 
+config ESP32S2_I2C
+	bool
+	default n
+
 config ESP32S2_TIMER
 	bool
 	default n
@@ -320,6 +325,18 @@ config ESP32S2_UART1
 	select UART1_SERIALDRIVER
 	select ARCH_HAVE_SERIAL_TERMIOS
 
+config ESP32S2_I2C0
+	bool "I2C 0"
+	default n
+	select ESP32S2_I2C
+	select I2C
+
+config ESP32S2_I2C1
+	bool "I2C 1"
+	default n
+	select ESP32S2_I2C
+	select I2C
+
 config ESP32S2_RT_TIMER
 	bool "Real-time Timer"
 	select ESP32S2_TIMER
@@ -401,6 +418,47 @@ endif # ESP32S2_UART1
 
 endmenu # UART Configuration
 
+menu "I2C Configuration"
+	depends on ESP32S2_I2C
+
+if ESP32S2_I2C0
+
+config ESP32S2_I2C0_SCLPIN
+	int "I2C0 SCL Pin"
+	default 19
+	range 0 46
+
+config ESP32S2_I2C0_SDAPIN
+	int "I2C0 SDA Pin"
+	default 18
+	range 0 46
+
+endif # ESP32S2_I2C0
+
+if ESP32S2_I2C1
+
+config ESP32S2_I2C1_SCLPIN
+	int "I2C1 SCL Pin"
+	default 6
+	range 0 46
+
+config ESP32S2_I2C1_SDAPIN
+	int "I2C1 SDA Pin"
+	default 7
+	range 0 46
+
+endif # ESP32S2_I2C1
+
+config ESP32S2_I2CTIMEOSEC
+	int "Timeout seconds"
+	default 0
+
+config ESP32S2_I2CTIMEOMS
+	int "Timeout milliseconds"
+	default 500
+
+endmenu # I2C Configuration
+
 menu "SPI Flash Configuration"
 	depends on ESP32S2_SPIFLASH
 
diff --git a/arch/xtensa/src/esp32s2/Make.defs b/arch/xtensa/src/esp32s2/Make.defs
index c94c293526..46d6f1c847 100644
--- a/arch/xtensa/src/esp32s2/Make.defs
+++ b/arch/xtensa/src/esp32s2/Make.defs
@@ -84,6 +84,10 @@ ifeq ($(CONFIG_ESP32S2_RNG),y)
 CHIP_CSRCS += esp32s2_rng.c
 endif
 
+ifeq ($(CONFIG_ESP32S2_I2C),y)
+CHIP_CSRCS += esp32s2_i2c.c
+endif
+
 ifeq ($(CONFIG_ESP32S2_TIMER),y)
 CHIP_CSRCS += esp32s2_tim.c
 ifeq ($(CONFIG_TIMER),y)
diff --git a/arch/xtensa/src/esp32s2/esp32s2_i2c.c b/arch/xtensa/src/esp32s2/esp32s2_i2c.c
new file mode 100644
index 0000000000..6fde13a276
--- /dev/null
+++ b/arch/xtensa/src/esp32s2/esp32s2_i2c.c
@@ -0,0 +1,1702 @@
+/****************************************************************************
+ * arch/xtensa/src/esp32s2/esp32s2_i2c.c
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#ifdef CONFIG_ESP32S2_I2C
+
+#include <assert.h>
+#include <debug.h>
+#include <errno.h>
+#include <stdbool.h>
+#include <stdint.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <sys/time.h>
+#include <sys/types.h>
+#include <time.h>
+
+#include <nuttx/arch.h>
+#include <nuttx/clock.h>
+#include <nuttx/irq.h>
+#include <nuttx/i2c/i2c_master.h>
+#include <nuttx/semaphore.h>
+
+#include <arch/board/board.h>
+
+#include "esp32s2_gpio.h"
+#include "esp32s2_i2c.h"
+#include "esp32s2_irq.h"
+
+#include "xtensa.h"
+#include "hardware/esp32s2_gpio_sigmap.h"
+#include "hardware/esp32s2_i2c.h"
+#include "hardware/esp32s2_soc.h"
+#include "hardware/esp32s2_system.h"
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/* Command format */
+
+#define I2C_BASE_CMD(_cmd, _check_ack) (((_cmd) << 11) | \
+                                        ((_check_ack) << 8))
+
+#define I2C_SEND_CMD(_cmd, _check_ack, _bytes) (((_cmd) << 11) | \
+                                                ((_check_ack) << 8) | \
+                                                (_bytes))
+
+#define I2C_RECV_CMD(_cmd, _ack_val, _bytes) (((_cmd) << 11) | \
+                                              ((_ack_val) << 10) | \
+                                              (_bytes))
+
+/* Helper */
+
+#ifdef CONFIG_I2C_POLLED
+#define TIMESPEC_TO_US(sec, nano)  ((sec) * USEC_PER_SEC + (nano) / NSEC_PER_USEC)
+#endif
+
+#define ESP32S2_I2CTIMEOTICKS \
+    (SEC2TICK(CONFIG_ESP32S2_I2CTIMEOSEC) + MSEC2TICK(CONFIG_ESP32S2_I2CTIMEOMS))
+
+/* Default option */
+
+#define I2C_FIFO_SIZE (32)
+
+#define I2C_FILTER_CYC_NUM_DEF (7)
+
+#define I2C_CLK_FREQ_DEF (100 * 1000)
+
+#define I2C_INT_ERR_MASK (I2C_NACK_INT_ENA | \
+                          I2C_TIME_OUT_INT_ENA | \
+                          I2C_ARBITRATION_LOST_INT_ENA)
+
+#define I2C_SCL_CYC_NUM_DEF 9
+
+/* Access I2C FIFO Data registers via Peripheral Bus 2 (PeriBus2).
+ * Refer to ESP32-S2 Technical Reference Manual, section 3.3.5 for further
+ * details.
+ */
+
+#define FIFO_DATA_REG(i) (0x60013000 + (i) * 0x14000 + 0x001c)
+
+/* I2C event trace logic.
+ * NOTE: trace uses the internal, non-standard, low-level debug interface
+ * syslog() but does not require that any other debug is enabled.
+ */
+
+#ifndef CONFIG_I2C_TRACE
+#  define i2c_tracereset(p)
+#  define i2c_tracenew(p,s)
+#  define i2c_traceevent(p,e,a,s)
+#  define i2c_tracedump(p)
+#endif
+
+#ifndef CONFIG_I2C_NTRACE
+#  define CONFIG_I2C_NTRACE 32
+#endif
+
+/****************************************************************************
+ * Private Types
+ ****************************************************************************/
+
+/* I2C state */
+
+enum esp32s2_i2cstate_e
+{
+  I2CSTATE_IDLE = 0,
+  I2CSTATE_PROC,
+  I2CSTATE_STOP,
+#ifndef CONFIG_I2C_POLLED
+  I2CSTATE_FINISH,
+#endif
+  I2CSTATE_ERROR
+};
+
+/* I2C hardware command */
+
+enum i2c_opmode_e
+{
+  I2C_CMD_RESTART = 0,        /* I2C restart command */
+  I2C_CMD_WRITE,              /* I2C write command */
+  I2C_CMD_READ,               /* I2C read command */
+  I2C_CMD_STOP,               /* I2C stop command */
+  I2C_CMD_END                 /* I2C end command */
+};
+
+#ifdef CONFIG_I2C_TRACE
+
+/* Trace events */
+
+enum esp32s2_trace_e
+{
+  I2CEVENT_NONE = 0,      /* No events have occurred with this status */
+  I2CEVENT_SENDADDR,      /* Start/Master bit set and address sent, param = addr */
+  I2CEVENT_SENDBYTE,      /* Send byte, param = bytes */
+  I2CEVENT_RCVMODEEN,     /* Receive mode enabled, param = 0 */
+  I2CEVENT_RCVBYTE,       /* Read more dta, param = bytes */
+  I2CEVENT_STOP,          /* Last byte sten, send stop, param = length */
+  I2CEVENT_ERROR          /* Error occurred, param = 0 */
+};
+
+/* Trace data */
+
+struct esp32s2_trace_s
+{
+  uint32_t status;            /* I2C 32-bit SR status */
+  uint32_t count;             /* Interrupt count when status change */
+  enum esp32s2_trace_e event; /* Last event that occurred with this status */
+  uint32_t parm;              /* Parameter associated with the event */
+  clock_t time;               /* First of event or first status */
+};
+
+#endif /* CONFIG_I2C_TRACE */
+
+/* I2C Device hardware configuration */
+
+struct esp32s2_i2c_config_s
+{
+  uint32_t clk_freq;          /* Clock frequency */
+
+  uint8_t scl_pin;            /* GPIO configuration for SCL as SCL */
+  uint8_t sda_pin;            /* GPIO configuration for SDA as SDA */
+
+#ifndef CONFIG_I2C_POLLED
+  uint8_t periph;             /* Peripheral ID */
+  uint8_t irq;                /* Interrupt ID */
+#endif
+
+  uint32_t clk_bit;           /* Clock enable bit */
+  uint32_t rst_bit;           /* I2C reset bit */
+
+  uint32_t scl_insig;         /* I2C SCL input signal index */
+  uint32_t scl_outsig;        /* I2C SCL output signal index */
+
+  uint32_t sda_insig;         /* I2C SDA input signal index */
+  uint32_t sda_outsig;        /* I2C SDA output signal index */
+};
+
+/* I2C Device Private Data */
+
+struct esp32s2_i2c_priv_s
+{
+  const struct i2c_ops_s *ops; /* Standard I2C operations */
+
+  uint32_t id;                 /* I2C instance */
+
+  /* Port configuration */
+
+  const struct esp32s2_i2c_config_s *config;
+  int refs;                    /* Reference count */
+  sem_t sem_excl;              /* Mutual exclusion semaphore */
+
+#ifndef CONFIG_I2C_POLLED
+  sem_t sem_isr;               /* Interrupt wait semaphore */
+  int cpuint;                  /* CPU interrupt assigned to this I2C */
+#endif
+
+  /* I2C work state (see enum esp32s2_i2cstate_e) */
+
+  volatile enum esp32s2_i2cstate_e i2cstate;
+
+  struct i2c_msg_s *msgv;      /* Message list */
+
+  uint8_t msgid;               /* Current message ID */
+  ssize_t bytes;               /* Processed data bytes */
+
+  uint32_t error;              /* I2C transform error */
+
+  bool ready_read;             /* If I2C has read data */
+
+  uint32_t clk_freq;           /* Current I2C Clock frequency */
+
+#ifdef CONFIG_I2C_TRACE
+  /* I2C trace support */
+
+  int tndx;                    /* Trace array index */
+  clock_t start_time;          /* Time when the trace was started */
+
+  /* The actual trace data */
+
+  struct esp32s2_trace_s trace[CONFIG_I2C_NTRACE];
+#endif
+};
+
+/****************************************************************************
+ * Private Function Prototypes
+ ****************************************************************************/
+
+static void i2c_init_clock(struct esp32s2_i2c_priv_s *priv,
+                           uint32_t clock);
+static void i2c_init(struct esp32s2_i2c_priv_s *priv);
+static void i2c_deinit(struct esp32s2_i2c_priv_s *priv);
+static int i2c_transfer(struct i2c_master_s *dev, struct i2c_msg_s *msgs,
+                        int count);
+static inline void i2c_process(struct esp32s2_i2c_priv_s *priv,
+                               uint32_t status);
+static void i2c_sem_init(struct esp32s2_i2c_priv_s *priv);
+static void i2c_sem_destroy(struct esp32s2_i2c_priv_s *priv);
+static void i2c_sem_post(struct esp32s2_i2c_priv_s *priv);
+static int i2c_sem_wait(struct esp32s2_i2c_priv_s *priv);
+#ifndef CONFIG_I2C_POLLED
+static int i2c_sem_waitdone(struct esp32s2_i2c_priv_s *priv);
+#endif
+#ifdef CONFIG_I2C_POLLED
+static int i2c_polling_waitdone(struct esp32s2_i2c_priv_s *priv);
+#endif
+static void i2c_clear_bus(struct esp32s2_i2c_priv_s *priv);
+static void i2c_reset_fsmc(struct esp32s2_i2c_priv_s *priv);
+#ifdef CONFIG_I2C_RESET
+static int i2c_reset(struct i2c_master_s *dev);
+#endif
+
+#ifdef CONFIG_I2C_TRACE
+static void i2c_tracereset(struct esp32s2_i2c_priv_s *priv);
+static void i2c_tracenew(struct esp32s2_i2c_priv_s *priv, uint32_t status);
+static void i2c_traceevent(struct esp32s2_i2c_priv_s *priv,
+                           enum esp32s2_trace_e event,
+                           uint32_t parm,
+                           uint32_t status);
+static void i2c_tracedump(struct esp32s2_i2c_priv_s *priv);
+#endif /* CONFIG_I2C_TRACE */
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+/* I2C interface */
+
+static const struct i2c_ops_s g_esp32s2_i2c_ops =
+{
+  .transfer = i2c_transfer
+#ifdef CONFIG_I2C_RESET
+  , .reset  = i2c_reset
+#endif
+};
+
+/* I2C device structures */
+
+#ifdef CONFIG_ESP32S2_I2C0
+static const struct esp32s2_i2c_config_s g_esp32s2_i2c0_config =
+{
+  .clk_freq   = I2C_CLK_FREQ_DEF,
+  .scl_pin    = CONFIG_ESP32S2_I2C0_SCLPIN,
+  .sda_pin    = CONFIG_ESP32S2_I2C0_SDAPIN,
+#ifndef CONFIG_I2C_POLLED
+  .periph     = ESP32S2_PERIPH_I2C_EXT0,
+  .irq        = ESP32S2_IRQ_I2C_EXT0,
+#endif
+  .clk_bit    = SYSTEM_I2C_EXT0_CLK_EN,
+  .rst_bit    = SYSTEM_I2C_EXT0_RST,
+  .scl_insig  = I2CEXT0_SCL_IN_IDX,
+  .scl_outsig = I2CEXT0_SCL_OUT_IDX,
+  .sda_insig  = I2CEXT0_SDA_IN_IDX,
+  .sda_outsig = I2CEXT0_SDA_OUT_IDX
+};
+
+static struct esp32s2_i2c_priv_s g_esp32s2_i2c0_priv =
+{
+  .ops        = &g_esp32s2_i2c_ops,
+  .id         = ESP32S2_I2C0,
+  .config     = &g_esp32s2_i2c0_config,
+  .refs       = 0,
+  .i2cstate   = I2CSTATE_IDLE,
+  .msgv       = NULL,
+  .msgid      = 0,
+  .bytes      = 0,
+  .ready_read = false
+};
+#endif /* CONFIG_ESP32S2_I2C0 */
+
+#ifdef CONFIG_ESP32S2_I2C1
+static const struct esp32s2_i2c_config_s g_esp32s2_i2c1_config =
+{
+  .clk_freq   = I2C_CLK_FREQ_DEF,
+  .scl_pin    = CONFIG_ESP32S2_I2C1_SCLPIN,
+  .sda_pin    = CONFIG_ESP32S2_I2C1_SDAPIN,
+#ifndef CONFIG_I2C_POLLED
+  .periph     = ESP32S2_PERIPH_I2C_EXT1,
+  .irq        = ESP32S2_IRQ_I2C_EXT1,
+#endif
+  .clk_bit    = SYSTEM_I2C_EXT1_CLK_EN,
+  .rst_bit    = SYSTEM_I2C_EXT1_RST,
+  .scl_insig  = I2CEXT1_SCL_IN_IDX,
+  .scl_outsig = I2CEXT1_SCL_OUT_IDX,
+  .sda_insig  = I2CEXT1_SDA_IN_IDX,
+  .sda_outsig = I2CEXT1_SDA_OUT_IDX
+};
+
+static struct esp32s2_i2c_priv_s g_esp32s2_i2c1_priv =
+{
+  .ops        = &g_esp32s2_i2c_ops,
+  .id         = ESP32S2_I2C1,
+  .config     = &g_esp32s2_i2c1_config,
+  .refs       = 0,
+  .i2cstate   = I2CSTATE_IDLE,
+  .msgv       = NULL,
+  .msgid      = 0,
+  .bytes      = 0,
+  .ready_read = false
+};
+#endif /* CONFIG_ESP32S2_I2C1 */
+
+/* Trace events strings */
+
+#ifdef CONFIG_I2C_TRACE
+static const char *g_trace_names[] =
+{
+  "NONE      ",
+  "SENDADDR  ",
+  "SENDBYTE  ",
+  "RCVMODEEN ",
+  "RCVBYTE   ",
+  "STOP      ",
+  "ERROR     "
+};
+#endif
+
+/****************************************************************************
+ * Private Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: i2c_reset_fifo
+ *
+ * Description:
+ *   Reset I2C RX and TX hardware FIFO.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_reset_fifo(struct esp32s2_i2c_priv_s *priv)
+{
+  uint32_t bits = I2C_TX_FIFO_RST | I2C_RX_FIFO_RST;
+
+  modifyreg32(I2C_FIFO_CONF_REG(priv->id), 0, bits);
+  modifyreg32(I2C_FIFO_CONF_REG(priv->id), bits, 0);
+}
+
+/****************************************************************************
+ * Name: i2c_intr_enable
+ *
+ * Description:
+ *   Enable I2C interrupts.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_intr_enable(struct esp32s2_i2c_priv_s *priv)
+{
+  putreg32(UINT32_MAX, I2C_INT_CLR_REG(priv->id));
+
+  putreg32(I2C_TRANS_COMPLETE_INT_ENA | I2C_END_DETECT_INT_ENA |
+           I2C_INT_ERR_MASK, I2C_INT_ENA_REG(priv->id));
+}
+
+/****************************************************************************
+ * Name: i2c_intr_disable
+ *
+ * Description:
+ *   Disable I2C interrupts.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_intr_disable(struct esp32s2_i2c_priv_s *priv)
+{
+  putreg32(0, I2C_INT_ENA_REG(priv->id));
+
+  putreg32(UINT32_MAX, I2C_INT_CLR_REG(priv->id));
+}
+
+/****************************************************************************
+ * Name: i2c_sendstart
+ *
+ * Description:
+ *   Send I2C start signal.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_sendstart(struct esp32s2_i2c_priv_s *priv)
+{
+  struct i2c_msg_s *msg = &priv->msgv[priv->msgid];
+
+  /* Write I2C command registers */
+
+  putreg32(I2C_BASE_CMD(I2C_CMD_RESTART, 0), I2C_COMD0_REG(priv->id));
+  putreg32(I2C_SEND_CMD(I2C_CMD_WRITE, 1, 1), I2C_COMD1_REG(priv->id));
+  putreg32(I2C_BASE_CMD(I2C_CMD_END, 0), I2C_COMD2_REG(priv->id));
+
+  /* Write data to FIFO register */
+
+  if ((msg->flags & I2C_M_READ) == 0)
+    {
+      putreg32(I2C_WRITEADDR8(msg->addr), FIFO_DATA_REG(priv->id));
+    }
+  else
+    {
+      putreg32(I2C_READADDR8(msg->addr), FIFO_DATA_REG(priv->id));
+    }
+
+  /* Enable I2C master TX interrupt */
+
+  i2c_intr_enable(priv);
+
+  /* Configure the I2C to trigger a transaction */
+
+  modifyreg32(I2C_CTR_REG(priv->id), 0, I2C_TRANS_START);
+}
+
+/****************************************************************************
+ * Name: i2c_senddata
+ *
+ * Description:
+ *   Send I2C data.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_senddata(struct esp32s2_i2c_priv_s *priv)
+{
+  struct i2c_msg_s *msg = &priv->msgv[priv->msgid];
+  int n = msg->length - priv->bytes;
+
+  n = n < I2C_FIFO_SIZE ? n : I2C_FIFO_SIZE;
+
+  putreg32(I2C_SEND_CMD(I2C_CMD_WRITE, 1, n), I2C_COMD0_REG(priv->id));
+  putreg32(I2C_BASE_CMD(I2C_CMD_END, 0), I2C_COMD1_REG(priv->id));
+
+  for (int i = 0; i < n; i++)
+    {
+      putreg32(msg->buffer[priv->bytes + i], FIFO_DATA_REG(priv->id));
+    }
+
+  priv->bytes += n;
+
+  /* Enable I2C master TX interrupt */
+
+  i2c_intr_enable(priv);
+
+  /* Configure the I2C to trigger a transaction */
+
+  modifyreg32(I2C_CTR_REG(priv->id), 0, I2C_TRANS_START);
+}
+
+/****************************************************************************
+ * Name: i2c_recvdata
+ *
+ * Description:
+ *   Transfer data from the FIFO to the driver buffer.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_recvdata(struct esp32s2_i2c_priv_s *priv)
+{
+  struct i2c_msg_s *msg = &priv->msgv[priv->msgid];
+  uint32_t cmd = getreg32(I2C_COMD0_REG(priv->id));
+  uint8_t n = cmd & 0xff;
+  uint32_t data = 0;
+
+  for (int i = 0; i < n; i++)
+    {
+      data = getreg32(FIFO_DATA_REG(priv->id));
+      msg->buffer[priv->bytes + i] = data & 0xff;
+    }
+
+  priv->bytes += n;
+}
+
+/****************************************************************************
+ * Name: i2c_startrecv
+ *
+ * Description:
+ *   Configure I2C to prepare receiving data and it will create an interrupt
+ *   to receive real data.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_startrecv(struct esp32s2_i2c_priv_s *priv)
+{
+  int ack_value;
+  struct i2c_msg_s *msg = &priv->msgv[priv->msgid];
+  int n = msg->length - priv->bytes;
+
+  if (n > 1)
+    {
+      n -= 1;
+      n = n < I2C_FIFO_SIZE ? n : I2C_FIFO_SIZE;
+      ack_value = 0;
+    }
+  else
+    {
+      ack_value = 1;
+    }
+
+  putreg32(I2C_RECV_CMD(I2C_CMD_READ, ack_value, n),
+           I2C_COMD0_REG(priv->id));
+  putreg32(I2C_BASE_CMD(I2C_CMD_END, 0), I2C_COMD1_REG(priv->id));
+
+  /* Enable I2C master RX interrupt */
+
+  i2c_intr_enable(priv);
+
+  /* Configure the I2C to trigger a transaction */
+
+  modifyreg32(I2C_CTR_REG(priv->id), 0, I2C_TRANS_START);
+}
+
+/****************************************************************************
+ * Name: i2c_sendstop
+ *
+ * Description:
+ *   Send I2C STOP signal.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_sendstop(struct esp32s2_i2c_priv_s *priv)
+{
+  putreg32(I2C_BASE_CMD(I2C_CMD_STOP, 0), I2C_COMD0_REG(priv->id));
+
+  /* Enable I2C master TX interrupt */
+
+  i2c_intr_enable(priv);
+
+  /* Configure the I2C to trigger a transaction */
+
+  modifyreg32(I2C_CTR_REG(priv->id), 0, I2C_TRANS_START);
+}
+
+/****************************************************************************
+ * Name: i2c_init_clock
+ *
+ * Description:
+ *   Initialize I2C hardware clock.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *   bus_freq      - Clock frequency of the I2C bus in Hz.
+ *
+ ****************************************************************************/
+
+static void i2c_init_clock(struct esp32s2_i2c_priv_s *priv,
+                           uint32_t bus_freq)
+{
+  if (bus_freq == priv->clk_freq)
+    {
+      return;
+    }
+
+  uint32_t reg_value = 0;
+  uint32_t scl_low = 0;
+  uint32_t scl_high = 0;
+  uint32_t scl_wait_high = 0;
+  uint32_t sda_hold = 0;
+  uint32_t sda_sample = 0;
+  uint32_t setup = 0;
+  uint32_t hold = 0;
+  uint32_t timeout = 0;
+  uint32_t source_clk = APB_CLK_FREQ;
+  uint32_t half_cycle = source_clk / bus_freq / 2;
+
+  scl_low       = half_cycle - 1;
+  putreg32(scl_low, I2C_SCL_LOW_PERIOD_REG(priv->id));
+
+  /* By default, scl_wait_high must be less than scl_high */
+
+  scl_high      = half_cycle / 2 + 2;
+  scl_wait_high = half_cycle - scl_high;
+
+  reg_value     = VALUE_TO_FIELD(scl_high, I2C_SCL_HIGH_PERIOD);
+  reg_value    |= VALUE_TO_FIELD(scl_wait_high, I2C_SCL_WAIT_HIGH_PERIOD);
+  putreg32(reg_value, I2C_SCL_HIGH_PERIOD_REG(priv->id));
+
+  sda_hold      = half_cycle / 2;
+  putreg32(sda_hold, I2C_SDA_HOLD_REG(priv->id));
+
+  /* scl_wait_high < sda_sample <= scl_high */
+
+  sda_sample    = half_cycle / 2 - 1;
+  putreg32(sda_sample, I2C_SDA_SAMPLE_REG(priv->id));
+
+  setup         = half_cycle;
+  putreg32(setup, I2C_SCL_RSTART_SETUP_REG(priv->id));
+  putreg32(setup, I2C_SCL_STOP_SETUP_REG(priv->id));
+
+  hold          = half_cycle;
+  putreg32(hold - 1, I2C_SCL_START_HOLD_REG(priv->id));
+  putreg32(hold, I2C_SCL_STOP_HOLD_REG(priv->id));
+
+  /* By default, we set the timeout value to 10 bus cycles */
+
+  timeout       = half_cycle * 20;
+  reg_value     = I2C_TIME_OUT_EN;
+  reg_value    |= VALUE_TO_FIELD(timeout, I2C_TIME_OUT_VALUE);
+  putreg32(reg_value, I2C_TO_REG(priv->id));
+
+  /* Set current bus clock frequency */
+
+  priv->clk_freq = bus_freq;
+}
+
+/****************************************************************************
+ * Name: i2c_init
+ *
+ * Description:
+ *   Initialize I2C hardware.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_init(struct esp32s2_i2c_priv_s *priv)
+{
+  const struct esp32s2_i2c_config_s *config = priv->config;
+
+  esp32s2_gpiowrite(config->scl_pin, 1);
+  esp32s2_configgpio(config->scl_pin, INPUT_PULLUP | OUTPUT_OPEN_DRAIN);
+  esp32s2_gpio_matrix_out(config->scl_pin, config->scl_outsig, 0, 0);
+  esp32s2_gpio_matrix_in(config->scl_pin, config->scl_insig, 0);
+
+  esp32s2_gpiowrite(config->sda_pin, 1);
+  esp32s2_configgpio(config->sda_pin, INPUT_PULLUP | OUTPUT_OPEN_DRAIN);
+  esp32s2_gpio_matrix_out(config->sda_pin, config->sda_outsig, 0, 0);
+  esp32s2_gpio_matrix_in(config->sda_pin, config->sda_insig, 0);
+
+  /* Enable I2C hardware */
+
+  modifyreg32(SYSTEM_PERIP_CLK_EN0_REG, 0, config->clk_bit);
+  modifyreg32(SYSTEM_PERIP_RST_EN0_REG, config->rst_bit, 0);
+
+  /* Disable I2C interrupts */
+
+  i2c_intr_disable(priv);
+
+  /* Initialize I2C Master */
+
+  putreg32(I2C_MS_MODE | I2C_CLK_EN | I2C_SCL_FORCE_OUT | I2C_SDA_FORCE_OUT,
+           I2C_CTR_REG(priv->id));
+
+  /* Set FIFO mode */
+
+  modifyreg32(I2C_FIFO_CONF_REG(priv->id), I2C_NONFIFO_EN, 0);
+
+  /* Ensure I2C data mode is set to MSB */
+
+  modifyreg32(I2C_CTR_REG(priv->id), I2C_TX_LSB_FIRST | I2C_RX_LSB_FIRST, 0);
+
+  i2c_reset_fifo(priv);
+
+  /* Configure the hardware filter function */
+
+  putreg32(I2C_SCL_FILTER_EN |
+             VALUE_TO_FIELD(I2C_FILTER_CYC_NUM_DEF, I2C_SCL_FILTER_THRES),
+           I2C_SCL_FILTER_CFG_REG(priv->id));
+  putreg32(I2C_SDA_FILTER_EN |
+             VALUE_TO_FIELD(I2C_FILTER_CYC_NUM_DEF, I2C_SDA_FILTER_THRES),
+           I2C_SDA_FILTER_CFG_REG(priv->id));
+
+  /* Set I2C source clock */
+
+  modifyreg32(I2C_CTR_REG(priv->id), 0, I2C_REF_ALWAYS_ON);
+
+  /* Configure I2C bus frequency */
+
+  i2c_init_clock(priv, config->clk_freq);
+}
+
+/****************************************************************************
+ * Name: i2c_deinit
+ *
+ * Description:
+ *   Disable I2C hardware.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_deinit(struct esp32s2_i2c_priv_s *priv)
+{
+  const struct esp32s2_i2c_config_s *config = priv->config;
+
+  priv->clk_freq = 0;
+
+  modifyreg32(SYSTEM_PERIP_RST_EN0_REG, 0, config->rst_bit);
+  modifyreg32(SYSTEM_PERIP_CLK_EN0_REG, config->clk_bit, 0);
+}
+
+/****************************************************************************
+ * Name: i2c_reset_fsmc
+ *
+ * Description:
+ *   Reset I2C hardware state machine and registers.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_reset_fsmc(struct esp32s2_i2c_priv_s *priv)
+{
+  /* Reset FSM machine */
+
+  modifyreg32(I2C_CTR_REG(priv->id), 0, I2C_FSM_RST);
+
+  i2c_clear_bus(priv);
+}
+
+/****************************************************************************
+ * Name: i2c_sem_waitdone
+ *
+ * Description:
+ *   Wait for a transfer to complete.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ * Returned Value:
+ *   Zero (OK) is returned on success. A negated errno value is returned on
+ *   failure.
+ *
+ ****************************************************************************/
+
+#ifndef CONFIG_I2C_POLLED
+static int i2c_sem_waitdone(struct esp32s2_i2c_priv_s *priv)
+{
+  /* Wait on ISR semaphore */
+
+  return nxsem_tickwait_uninterruptible(&priv->sem_isr,
+                                        ESP32S2_I2CTIMEOTICKS);
+}
+#endif
+
+/****************************************************************************
+ * Name: i2c_polling_waitdone
+ *
+ * Description:
+ *   Wait for a transfer to complete by polling status interrupt registers,
+ *   which indicates the status of the I2C operations. This function is only
+ *   used in polling driven mode.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ * Returned Values:
+ *   Zero (OK) is returned on successfull transfer. -ETIMEDOUT is returned
+ *   in case a transfer didn't finish within the timeout interval. And ERROR
+ *   is returned in case of any I2C error during the transfer has happened.
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_I2C_POLLED
+static int i2c_polling_waitdone(struct esp32s2_i2c_priv_s *priv)
+{
+  int ret;
+  clock_t current;
+  clock_t timeout;
+  uint32_t status = 0;
+
+  /* Get the current absolute time and add an offset as timeout.
+   * Preferable to use monotonic, so in case the time changes,
+   * the time reference is kept, i.e., current time can't jump
+   * forward and backwards.
+   */
+
+  current = clock_systime_ticks();
+  timeout = current + SEC2TICK(10);
+
+  /* Loop while a transfer is in progress
+   * and an error didn't occur within the timeout
+   */
+
+  while ((current < timeout) && (priv->error == 0))
+    {
+      /* Check if any interrupt triggered, clear them
+       * process the operation.
+       */
+
+      status = getreg32(I2C_INT_STATUS_REG(priv->id));
+      if (status != 0)
+        {
+          /* Check if the stop operation ended. Don't use
+           * I2CSTATE_FINISH, because it is set before the stop
+           * signal really ends. This works for interrupts because
+           * the i2c_state is checked in the next interrupt when
+           * stop signal has concluded. This is not the case of
+           * polling.
+           */
+
+          if ((status & I2C_TRANS_COMPLETE_INT_ST) != 0)
+            {
+              putreg32(status, I2C_INT_CLR_REG(priv->id));
+              break;
+            }
+
+          putreg32(status, I2C_INT_CLR_REG(priv->id));
+          i2c_process(priv, status);
+        }
+
+      /* Update current time */
+
+      current = clock_systime_ticks();
+    }
+
+  /* Return a negated value in case of timeout, and in the other scenarios
+   * return a positive value.
+   * The transfer function will check the status of priv to check the other
+   * scenarios.
+   */
+
+  if (current >= timeout)
+    {
+      ret = -ETIMEDOUT;
+    }
+  else if (priv->error != 0)
+    {
+      ret = ERROR;
+    }
+  else
+    {
+      ret = OK;
+    }
+
+  /* Disable all interrupts */
+
+  i2c_intr_disable(priv);
+
+  return ret;
+}
+#endif
+
+/****************************************************************************
+ * Name: i2c_sem_wait
+ *
+ * Description:
+ *   Take the exclusive access, waiting as necessary.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ * Returned Value:
+ *   Zero (OK) is returned on success. A negated errno value is returned on
+ *   failure.
+ *
+ ****************************************************************************/
+
+static int i2c_sem_wait(struct esp32s2_i2c_priv_s *priv)
+{
+  return nxsem_wait_uninterruptible(&priv->sem_excl);
+}
+
+/****************************************************************************
+ * Name: i2c_sem_post
+ *
+ * Description:
+ *   Release the mutual exclusion semaphore.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_sem_post(struct esp32s2_i2c_priv_s *priv)
+{
+  nxsem_post(&priv->sem_excl);
+}
+
+/****************************************************************************
+ * Name: i2c_sem_destroy
+ *
+ * Description:
+ *   Destroy semaphores.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_sem_destroy(struct esp32s2_i2c_priv_s *priv)
+{
+  nxsem_destroy(&priv->sem_excl);
+#ifndef CONFIG_I2C_POLLED
+  nxsem_destroy(&priv->sem_isr);
+#endif
+}
+
+/****************************************************************************
+ * Name: i2c_sem_init
+ *
+ * Description:
+ *   Initialize semaphores.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_sem_init(struct esp32s2_i2c_priv_s *priv)
+{
+  nxsem_init(&priv->sem_excl, 0, 1);
+
+  /* This semaphore is used for signaling and, hence, should not have
+   * priority inheritance enabled.
+   */
+
+#ifndef CONFIG_I2C_POLLED
+  nxsem_init(&priv->sem_isr, 0, 0);
+  nxsem_set_protocol(&priv->sem_isr, SEM_PRIO_NONE);
+#endif
+}
+
+/****************************************************************************
+ * Device Driver Operations
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: i2c_transfer
+ *
+ * Description:
+ *   Generic I2C transfer function.
+ *
+ * Parameters:
+ *   dev           - Device-specific state data
+ *   msgs          - A pointer to a set of message descriptors
+ *   count         - The number of transfers to perform
+ *
+ * Returned Value:
+ *   Zero (OK) is returned on success. A negated errno value is returned on
+ *   failure.
+ *
+ ****************************************************************************/
+
+static int i2c_transfer(struct i2c_master_s *dev, struct i2c_msg_s *msgs,
+                        int count)
+{
+  int ret = OK;
+  struct esp32s2_i2c_priv_s *priv = (struct esp32s2_i2c_priv_s *)dev;
+
+  DEBUGASSERT(count > 0);
+
+  ret = i2c_sem_wait(priv);
+  if (ret < 0)
+    {
+      return ret;
+    }
+
+  /* If previous state is different than idle,
+   * reset the FSMC to the idle state.
+   */
+
+  if (priv->i2cstate != I2CSTATE_IDLE)
+    {
+      i2c_reset_fsmc(priv);
+      priv->i2cstate = I2CSTATE_IDLE;
+    }
+
+  /* Transfer the messages to the internal struct
+   * and loop count times to make all transfers.
+   */
+
+  priv->msgv = msgs;
+
+  for (int i = 0; i < count; i++)
+    {
+      /* Clear TX and RX FIFOs. */
+
+      i2c_reset_fifo(priv);
+
+      priv->bytes      = 0;
+      priv->msgid      = i;
+      priv->ready_read = false;
+      priv->error      = 0;
+      priv->i2cstate   = I2CSTATE_PROC;
+
+      /* Set the SCLK frequency for the current msg. */
+
+      i2c_init_clock(priv, msgs[i].frequency);
+
+      if ((msgs[i].flags & I2C_M_NOSTART) != 0)
+        {
+          i2c_traceevent(priv, I2CEVENT_SENDBYTE, priv->bytes,
+                         getreg32(I2C_SR_REG(priv->id)));
+          i2c_senddata(priv);
+
+          if (priv->bytes == msgs[i].length)
+            {
+              if ((msgs[i].flags & I2C_M_NOSTOP) == 0)
+                {
+                  priv->i2cstate = I2CSTATE_STOP;
+                }
+#ifndef CONFIG_I2C_POLLED
+              else
+                {
+                  priv->i2cstate = I2CSTATE_FINISH;
+                }
+#endif
+            }
+        }
+      else
+        {
+          /* Reset I2C trace logic */
+
+          i2c_tracereset(priv);
+
+          i2c_traceevent(priv, I2CEVENT_SENDADDR, msgs[i].addr,
+                         getreg32(I2C_SR_REG(priv->id)));
+
+          i2c_sendstart(priv);
+        }
+
+#ifndef CONFIG_I2C_POLLED
+      if (i2c_sem_waitdone(priv) < 0)
+        {
+          /* Timed out - transfer was not completed within the timeout */
+
+          i2cerr("Message %" PRIu8 " timed out.\n", priv->msgid);
+          ret = -ETIMEDOUT;
+          break;
+        }
+      else
+        {
+          if (priv->error != 0)
+            {
+              /* An error occurred */
+
+              i2cerr("Transfer error %" PRIu32 "\n", priv->error);
+              ret = -EIO;
+              break;
+            }
+          else
+            {
+              /* Successful transfer, update the I2C state to idle */
+
+              priv->i2cstate = I2CSTATE_IDLE;
+              ret = OK;
+            }
+        }
+#else
+      ret = i2c_polling_waitdone(priv);
+      if (ret < 0)
+        {
+          if (ret == -ETIMEDOUT)
+            {
+              break;
+            }
+          else
+            {
+              ret = -EIO;
+              break;
+            }
+        }
+      else
+        {
+          /* Successful transfer, update the I2C state to idle */
+
+          priv->i2cstate = I2CSTATE_IDLE;
+          ret = OK;
+        }
+#endif
+
+      i2cinfo("Message %" PRIu8 " transfer complete.\n", priv->msgid);
+    }
+
+  /* Dump the trace result */
+
+  i2c_tracedump(priv);
+
+  i2c_sem_post(priv);
+
+  return ret;
+}
+
+/****************************************************************************
+ * Name: i2c_clear_bus
+ *
+ * Description:
+ *   Clear I2C bus, when the slave is stuck in a deadlock and keeps pulling
+ *   the bus low, master can control the SCL bus to generate 9 CLKs.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+static void i2c_clear_bus(struct esp32s2_i2c_priv_s *priv)
+{
+  modifyreg32(I2C_SCL_SP_CONF_REG(priv->id),
+              I2C_SCL_RST_SLV_EN | I2C_SCL_RST_SLV_NUM_M,
+              VALUE_TO_FIELD(I2C_SCL_CYC_NUM_DEF, I2C_SCL_RST_SLV_NUM));
+
+  modifyreg32(I2C_SCL_SP_CONF_REG(priv->id), 0, I2C_SCL_RST_SLV_EN);
+}
+
+/****************************************************************************
+ * Name: i2c_reset
+ *
+ * Description:
+ *   Perform an I2C bus reset in an attempt to break loose stuck I2C devices.
+ *
+ * Input Parameters:
+ *   dev   - Device-specific state data
+ *
+ * Returned Value:
+ *   Zero (OK) on success; a negated errno value on failure.
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_I2C_RESET
+static int i2c_reset(struct i2c_master_s *dev)
+{
+  irqstate_t flags;
+  struct esp32s2_i2c_priv_s *priv = (struct esp32s2_i2c_priv_s *)dev;
+
+  DEBUGASSERT(dev != NULL);
+  DEBUGASSERT(priv->refs > 0);
+
+  flags = enter_critical_section();
+
+  i2c_reset_fsmc(priv);
+
+  /* Clear bus */
+
+  i2c_clear_bus(priv);
+
+  priv->i2cstate   = I2CSTATE_IDLE;
+  priv->msgid      = 0;
+  priv->bytes      = 0;
+  priv->ready_read = false;
+
+  leave_critical_section(flags);
+
+  return OK;
+}
+#endif
+
+/****************************************************************************
+ * Name: i2c_traceclear
+ *
+ * Description:
+ *   Set I2C trace fields to default value.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_I2C_TRACE
+static void i2c_traceclear(struct esp32s2_i2c_priv_s *priv)
+{
+  struct esp32s2_trace_s *trace = &priv->trace[priv->tndx];
+
+  trace->status = 0;
+  trace->count  = 0;
+  trace->event  = I2CEVENT_NONE;
+  trace->parm   = 0;
+  trace->time   = 0;
+}
+#endif /* CONFIG_I2C_TRACE */
+
+/****************************************************************************
+ * Name: i2c_tracereset
+ *
+ * Description:
+ *   Reset the trace info for a new data collection.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_I2C_TRACE
+static void i2c_tracereset(struct esp32s2_i2c_priv_s *priv)
+{
+  priv->tndx       = 0;
+  priv->start_time = clock_systime_ticks();
+  i2c_traceclear(priv);
+}
+#endif /* CONFIG_I2C_TRACE */
+
+/****************************************************************************
+ * Name: i2c_tracenew
+ *
+ * Description:
+ *   Create a new trace entry.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *   status        - Current value of I2C status register.
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_I2C_TRACE
+static void i2c_tracenew(struct esp32s2_i2c_priv_s *priv, uint32_t status)
+{
+  struct esp32s2_trace_s *trace = &priv->trace[priv->tndx];
+
+  /* Check if the current entry is already initialized or if its status had
+   * already changed
+   */
+
+  if (trace->count == 0 || status != trace->status)
+    {
+      /* Check whether the status changed */
+
+      if (trace->count != 0)
+        {
+          /* Bump up the trace index (unless we are out of trace entries) */
+
+          if (priv->tndx >= (CONFIG_I2C_NTRACE - 1))
+            {
+              i2cerr("ERROR: Trace table overflow\n");
+              return;
+            }
+
+          priv->tndx++;
+          trace = &priv->trace[priv->tndx];
+        }
+
+      /* Initialize the new trace entry */
+
+      i2c_traceclear(priv);
+      trace->status = status;
+      trace->count  = 1;
+      trace->time   = clock_systime_ticks();
+    }
+  else
+    {
+      /* Just increment the count of times that we have seen this status */
+
+      trace->count++;
+    }
+}
+#endif /* CONFIG_I2C_TRACE */
+
+/****************************************************************************
+ * Name: i2c_traceevent
+ *
+ * Description:
+ *   Record a new trace event.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *   event         - Event to be recorded on the trace.
+ *   parm          - Parameter associated with the event.
+ *   status        - Current value of I2C status register.
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_I2C_TRACE
+static void i2c_traceevent(struct esp32s2_i2c_priv_s *priv,
+                           enum esp32s2_trace_e event,
+                           uint32_t parm,
+                           uint32_t status)
+{
+  /* Check for new trace setup */
+
+  i2c_tracenew(priv, status);
+
+  if (event != I2CEVENT_NONE)
+    {
+      struct esp32s2_trace_s *trace = &priv->trace[priv->tndx];
+
+      /* Initialize the new trace entry */
+
+      trace->event  = event;
+      trace->parm   = parm;
+
+      /* Bump up the trace index (unless we are out of trace entries) */
+
+      if (priv->tndx >= (CONFIG_I2C_NTRACE - 1))
+        {
+          i2cerr("ERROR: Trace table overflow\n");
+          return;
+        }
+
+      priv->tndx++;
+      i2c_traceclear(priv);
+    }
+}
+#endif /* CONFIG_I2C_TRACE */
+
+/****************************************************************************
+ * Name: i2c_tracedump
+ *
+ * Description:
+ *   Dump the trace results.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *
+ ****************************************************************************/
+
+#ifdef CONFIG_I2C_TRACE
+static void i2c_tracedump(struct esp32s2_i2c_priv_s *priv)
+{
+  syslog(LOG_DEBUG, "Elapsed time: %" PRIu32 "\n",
+         clock_systime_ticks() - priv->start_time);
+
+  for (int i = 0; i < priv->tndx; i++)
+    {
+      struct esp32s2_trace_s *trace = &priv->trace[i];
+      syslog(LOG_DEBUG,
+             "%2d. STATUS: %08" PRIx32 " COUNT: %3" PRIu32 " EVENT: %s(%2d)"
+             " PARM: %08" PRIx32 " TIME: %" PRIu32 "\n",
+             i + 1, trace->status, trace->count, g_trace_names[trace->event],
+             trace->event, trace->parm, trace->time - priv->start_time);
+    }
+}
+#endif /* CONFIG_I2C_TRACE */
+
+/****************************************************************************
+ * Name: i2c_irq
+ *
+ * Description:
+ *   This is the common I2C interrupt handler. It will be invoked when an
+ *   interrupt is received on the device.
+ *
+ * Parameters:
+ *   cpuint        - CPU interrupt index
+ *   context       - Context data from the ISR
+ *   arg           - Opaque pointer to the internal driver state structure.
+ *
+ * Returned Value:
+ *   Zero (OK) is returned on success. A negated errno value is returned on
+ *   failure.
+ *
+ ****************************************************************************/
+
+#ifndef CONFIG_I2C_POLLED
+static int i2c_irq(int cpuint, void *context, void *arg)
+{
+  struct esp32s2_i2c_priv_s *priv = (struct esp32s2_i2c_priv_s *)arg;
+
+  /* Get the interrupt status and clear the interrupts that
+   * triggered.
+   */
+
+  uint32_t irq_status = getreg32(I2C_INT_STATUS_REG(priv->id));
+  putreg32(irq_status, I2C_INT_CLR_REG(priv->id));
+
+  i2c_process(priv, irq_status);
+
+  return OK;
+}
+#endif
+
+/****************************************************************************
+ * Name: i2c_process
+ *
+ * Description:
+ *   This routine manages the transfer. It's called after some specific
+ *   commands from the I2C controller are executed or in case of errors.
+ *   It's responsible for writing/reading operations and transferring data
+ *   from/to FIFO.
+ *   It's called in the interrupt and polled driven mode.
+ *
+ * Parameters:
+ *   priv          - Pointer to the internal driver state structure.
+ *   status        - The current interrupt status register.
+ *
+ ****************************************************************************/
+
+static void i2c_process(struct esp32s2_i2c_priv_s *priv, uint32_t status)
+{
+  struct i2c_msg_s *msg = &priv->msgv[priv->msgid];
+
+  /* Check for any errors */
+
+  if ((I2C_INT_ERR_MASK & status) != 0)
+    {
+      /* Save the errors, register the error event, disable interrupts
+       * and release the semaphore to conclude the transfer.
+       */
+
+      priv->error = status & I2C_INT_ERR_MASK;
+      priv->i2cstate = I2CSTATE_ERROR;
+      i2c_traceevent(priv, I2CEVENT_ERROR, priv->error,
+                     getreg32(I2C_SR_REG(priv->id)));
+      i2c_intr_disable(priv);
+#ifndef CONFIG_I2C_POLLED
+      nxsem_post(&priv->sem_isr);
+#endif
+    }
+  else /* If no error */
+    {
+      /* If a transfer has just initialized */
+
+      if (priv->i2cstate == I2CSTATE_PROC)
+        {
+          /* Check the flags to perform a read or write operation */
+
+          if ((msg->flags & I2C_M_READ) != 0)
+            {
+              /* RX FIFO has available data */
+
+              if (priv->ready_read)
+                {
+                  i2c_traceevent(priv, I2CEVENT_RCVBYTE, priv->bytes,
+                                 getreg32(I2C_SR_REG(priv->id)));
+                  i2c_recvdata(priv);
+
+                  priv->ready_read = false;
+                }
+
+              /* Received all data. Finish the transaction
+               * and update the I2C state.
+               */
+
+              if (priv->bytes == msg->length)
+                {
+                  i2c_traceevent(priv, I2CEVENT_STOP, msg->length,
+                                 getreg32(I2C_SR_REG(priv->id)));
+                  i2c_sendstop(priv);
+#ifndef CONFIG_I2C_POLLED
+                  priv->i2cstate = I2CSTATE_FINISH;
+#endif
+                }
+              else /* Start a receive operation */
+                {
+                  i2c_traceevent(priv, I2CEVENT_RCVMODEEN, 0,
+                                 getreg32(I2C_SR_REG(priv->id)));
+                  i2c_startrecv(priv);
+
+                  priv->ready_read = true;
+                }
+            }
+          else /* Write operation */
+            {
+              i2c_traceevent(priv, I2CEVENT_SENDBYTE, priv->bytes,
+                             getreg32(I2C_SR_REG(priv->id)));
+              i2c_senddata(priv);
+
+              /* Finally sent the entire message. Update the I2C state to
+               * send a stop signal in the next interrupt.
+               */
+
+              if (priv->bytes == msg->length)
+                {
+                  if ((msg->flags & I2C_M_NOSTOP) == 0)
+                    {
+                      priv->i2cstate = I2CSTATE_STOP;
+                    }
+#ifndef CONFIG_I2C_POLLED
+                  else
+                    {
+                      priv->i2cstate = I2CSTATE_FINISH;
+                    }
+#endif
+                }
+            }
+        }
+      else if (priv->i2cstate == I2CSTATE_STOP)
+        {
+          /* Transmitted all data. Finish the transaction sending a stop
+           * and update the I2C state.
+           */
+
+          i2c_traceevent(priv, I2CEVENT_STOP, msg->length,
+                         getreg32(I2C_SR_REG(priv->id)));
+          i2c_sendstop(priv);
+#ifndef CONFIG_I2C_POLLED
+          priv->i2cstate = I2CSTATE_FINISH;
+#endif
+        }
+#ifndef CONFIG_I2C_POLLED
+      else if (priv->i2cstate == I2CSTATE_FINISH)
+        {
+          /* Disable all interrupts and release the semaphore */
+
+          i2c_intr_disable(priv);
+          nxsem_post(&priv->sem_isr);
+        }
+#endif
+    }
+}
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: esp32s2_i2cbus_initialize
+ *
+ * Description:
+ *   Initialize the selected I2C port. And return a pointer to an unique
+ *   instance of struct i2c_master_s. This function may be called to obtain
+ *   multiple instances of the interface, each of which may be set up with a
+ *   different frequency and slave address.
+ *
+ * Parameters:
+ *   port          - Port number of the I2C interface to be initialized.
+ *
+ * Returned Value:
+ *   Pointer to valid I2C device structure is returned on success.
+ *   A NULL pointer is returned on failure.
+ *
+ ****************************************************************************/
+
+struct i2c_master_s *esp32s2_i2cbus_initialize(int port)
+{
+  irqstate_t flags;
+  struct esp32s2_i2c_priv_s *priv;
+#ifndef CONFIG_I2C_POLLED
+  const struct esp32s2_i2c_config_s *config;
+  int ret;
+#endif
+
+  switch (port)
+    {
+#ifdef CONFIG_ESP32S2_I2C0
+      case ESP32S2_I2C0:
+        priv = &g_esp32s2_i2c0_priv;
+        break;
+#endif
+#ifdef CONFIG_ESP32S2_I2C1
+      case ESP32S2_I2C1:
+        priv = &g_esp32s2_i2c1_priv;
+        break;
+#endif
+      default:
+        return NULL;
+    }
+
+  flags = enter_critical_section();
+
+  if (priv->refs++ != 0)
+    {
+      leave_critical_section(flags);
+
+      return (struct i2c_master_s *)priv;
+    }
+
+#ifndef CONFIG_I2C_POLLED
+  config = priv->config;
+
+  /* Set up to receive peripheral interrupts on the current CPU */
+
+  priv->cpuint = esp32s2_setup_irq(config->periph, 1, ESP32S2_CPUINT_LEVEL);
+  if (priv->cpuint < 0)
+    {
+      /* Failed to allocate a CPU interrupt of this type */
+
+      leave_critical_section(flags);
+
+      return NULL;
+    }
+
+  ret = irq_attach(config->irq, i2c_irq, priv);
+  if (ret != OK)
+    {
+      esp32s2_teardown_irq(config->periph, priv->cpuint);
+
+      leave_critical_section(flags);
+
+      return NULL;
+    }
+
+  up_enable_irq(config->irq);
+#endif
+
+  i2c_sem_init(priv);
+
+  i2c_init(priv);
+
+  leave_critical_section(flags);
+
+  return (struct i2c_master_s *)priv;
+}
+
+/****************************************************************************
+ * Name: esp32s2_i2cbus_uninitialize
+ *
+ * Description:
+ *   De-initialize the selected I2C port and power down the device.
+ *
+ * Parameters:
+ *   dev           - Device structure as returned by
+ *                   esp32s2_i2cbus_initialize()
+ *
+ * Returned Value:
+ *   OK is returned on success. ERROR is returned when internal reference
+ *   count mismatches or dev points to invalid hardware device.
+ *
+ ****************************************************************************/
+
+int esp32s2_i2cbus_uninitialize(struct i2c_master_s *dev)
+{
+  irqstate_t flags;
+  struct esp32s2_i2c_priv_s *priv = (struct esp32s2_i2c_priv_s *)dev;
+
+  DEBUGASSERT(dev != NULL);
+
+  if (priv->refs == 0)
+    {
+      return ERROR;
+    }
+
+  flags = enter_critical_section();
+
+  if (--priv->refs)
+    {
+      leave_critical_section(flags);
+      return OK;
+    }
+
+  leave_critical_section(flags);
+
+#ifndef CONFIG_I2C_POLLED
+  up_disable_irq(priv->config->irq);
+  esp32s2_teardown_irq(priv->config->periph, priv->cpuint);
+#endif
+
+  i2c_deinit(priv);
+
+  i2c_sem_destroy(priv);
+
+  return OK;
+}
+
+#endif /* CONFIG_ESP32S2_I2C */
diff --git a/arch/xtensa/src/esp32s2/esp32s2_i2c.h b/arch/xtensa/src/esp32s2/esp32s2_i2c.h
new file mode 100644
index 0000000000..51df9472f6
--- /dev/null
+++ b/arch/xtensa/src/esp32s2/esp32s2_i2c.h
@@ -0,0 +1,91 @@
+/****************************************************************************
+ * arch/xtensa/src/esp32s2/esp32s2_i2c.h
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#ifndef __ARCH_XTENSA_SRC_ESP32S2_ESP32S2_I2C_H
+#define __ARCH_XTENSA_SRC_ESP32S2_ESP32S2_I2C_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <nuttx/i2c/i2c_master.h>
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+#ifndef __ASSEMBLY__
+
+#ifdef CONFIG_ESP32S2_I2C0
+#  define ESP32S2_I2C0 0
+#endif
+
+#ifdef CONFIG_ESP32S2_I2C1
+#  define ESP32S2_I2C1 1
+#endif
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: esp32s2_i2cbus_initialize
+ *
+ * Description:
+ *   Initialize the selected I2C port. And return a unique instance of struct
+ *   struct i2c_master_s.  This function may be called to obtain multiple
+ *   instances of the interface, each of which may be set up with a
+ *   different frequency and slave address.
+ *
+ * Input Parameters:
+ *   Port number (for hardware that has multiple I2C interfaces)
+ *
+ * Returned Value:
+ *   Valid I2C device structure reference on success; a NULL on failure
+ *
+ ****************************************************************************/
+
+struct i2c_master_s *esp32s2_i2cbus_initialize(int port);
+
+/****************************************************************************
+ * Name: esp32s2_i2cbus_uninitialize
+ *
+ * Description:
+ *   De-initialize the selected I2C port, and power down the device.
+ *
+ * Input Parameters:
+ *   Device structure as returned by the esp32s2_i2cbus_initialize()
+ *
+ * Returned Value:
+ *   OK on success, ERROR when internal reference count mismatch or dev
+ *   points to invalid hardware device.
+ *
+ ****************************************************************************/
+
+int esp32s2_i2cbus_uninitialize(struct i2c_master_s *dev);
+
+#endif /* __ASSEMBLY__ */
+#endif /* __ARCH_XTENSA_SRC_ESP32S2_ESP32S2_I2C_H */
diff --git a/arch/xtensa/src/esp32s2/hardware/esp32s2_i2c.h b/arch/xtensa/src/esp32s2/hardware/esp32s2_i2c.h
new file mode 100644
index 0000000000..15487731d2
--- /dev/null
+++ b/arch/xtensa/src/esp32s2/hardware/esp32s2_i2c.h
@@ -0,0 +1,1992 @@
+/****************************************************************************
+ * arch/xtensa/src/esp32s2/hardware/esp32s2_i2c.h
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+#ifndef __ARCH_XTENSA_SRC_ESP32S2_HARDWARE_ESP32S2_I2C_H
+#define __ARCH_XTENSA_SRC_ESP32S2_HARDWARE_ESP32S2_I2C_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include "esp32s2_soc.h"
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/* I2C_SCL_LOW_PERIOD_REG register
+ * Configures the low level width of the SCL clock
+ */
+
+#define I2C_SCL_LOW_PERIOD_REG(i) (REG_I2C_BASE(i) + 0x0)
+
+/* I2C_SCL_LOW_PERIOD : R/W; bitpos: [13:0]; default: 0;
+ * This register is used to configure for how long SCL remains low in master
+ * mode, in I2C module clock cycles.
+ */
+
+#define I2C_SCL_LOW_PERIOD    0x00003fff
+#define I2C_SCL_LOW_PERIOD_M  (I2C_SCL_LOW_PERIOD_V << I2C_SCL_LOW_PERIOD_S)
+#define I2C_SCL_LOW_PERIOD_V  0x00003fff
+#define I2C_SCL_LOW_PERIOD_S  0
+
+/* I2C_CTR_REG register
+ * Transmission setting
+ */
+
+#define I2C_CTR_REG(i) (REG_I2C_BASE(i) + 0x4)
+
+/* I2C_REF_ALWAYS_ON : R/W; bitpos: [11]; default: 1;
+ * This register is used to control the REF_TICK.
+ */
+
+#define I2C_REF_ALWAYS_ON    (BIT(11))
+#define I2C_REF_ALWAYS_ON_M  (I2C_REF_ALWAYS_ON_V << I2C_REF_ALWAYS_ON_S)
+#define I2C_REF_ALWAYS_ON_V  0x00000001
+#define I2C_REF_ALWAYS_ON_S  11
+
+/* I2C_FSM_RST : R/W; bitpos: [10]; default: 0;
+ * This register is used to reset the SCL_FSM.
+ */
+
+#define I2C_FSM_RST    (BIT(10))
+#define I2C_FSM_RST_M  (I2C_FSM_RST_V << I2C_FSM_RST_S)
+#define I2C_FSM_RST_V  0x00000001
+#define I2C_FSM_RST_S  10
+
+/* I2C_ARBITRATION_EN : R/W; bitpos: [9]; default: 1;
+ * This is the enable bit for I2C bus arbitration function.
+ */
+
+#define I2C_ARBITRATION_EN    (BIT(9))
+#define I2C_ARBITRATION_EN_M  (I2C_ARBITRATION_EN_V << I2C_ARBITRATION_EN_S)
+#define I2C_ARBITRATION_EN_V  0x00000001
+#define I2C_ARBITRATION_EN_S  9
+
+/* I2C_CLK_EN : R/W; bitpos: [8]; default: 0;
+ * Reserved.
+ */
+
+#define I2C_CLK_EN    (BIT(8))
+#define I2C_CLK_EN_M  (I2C_CLK_EN_V << I2C_CLK_EN_S)
+#define I2C_CLK_EN_V  0x00000001
+#define I2C_CLK_EN_S  8
+
+/* I2C_RX_LSB_FIRST : R/W; bitpos: [7]; default: 0;
+ * This bit is used to control the storage mode for received data.
+ *
+ * 1: receive data from the least significant bit.
+ *
+ * 0: receive data from the most significant bit.
+ */
+
+#define I2C_RX_LSB_FIRST    (BIT(7))
+#define I2C_RX_LSB_FIRST_M  (I2C_RX_LSB_FIRST_V << I2C_RX_LSB_FIRST_S)
+#define I2C_RX_LSB_FIRST_V  0x00000001
+#define I2C_RX_LSB_FIRST_S  7
+
+/* I2C_TX_LSB_FIRST : R/W; bitpos: [6]; default: 0;
+ * This bit is used to control the sending mode for data needing to be sent.
+ *
+ * 1: send data from the least significant bit.
+ *
+ * 0: send data from the most significant bit.
+ */
+
+#define I2C_TX_LSB_FIRST    (BIT(6))
+#define I2C_TX_LSB_FIRST_M  (I2C_TX_LSB_FIRST_V << I2C_TX_LSB_FIRST_S)
+#define I2C_TX_LSB_FIRST_V  0x00000001
+#define I2C_TX_LSB_FIRST_S  6
+
+/* I2C_TRANS_START : R/W; bitpos: [5]; default: 0;
+ * Set this bit to start sending the data in TX FIFO.
+ */
+
+#define I2C_TRANS_START    (BIT(5))
+#define I2C_TRANS_START_M  (I2C_TRANS_START_V << I2C_TRANS_START_S)
+#define I2C_TRANS_START_V  0x00000001
+#define I2C_TRANS_START_S  5
+
+/* I2C_MS_MODE : R/W; bitpos: [4]; default: 0;
+ * Set this bit to configure the module as an I2C Master. Clear this bit to
+ * configure the module as an I2C Slave.
+ */
+
+#define I2C_MS_MODE    (BIT(4))
+#define I2C_MS_MODE_M  (I2C_MS_MODE_V << I2C_MS_MODE_S)
+#define I2C_MS_MODE_V  0x00000001
+#define I2C_MS_MODE_S  4
+
+/* I2C_RX_FULL_ACK_LEVEL : R/W; bitpos: [3]; default: 1;
+ * This register is used to configure the ACK value that need to sent by
+ * master when the rx_fifo_cnt has reached the threshold.
+ */
+
+#define I2C_RX_FULL_ACK_LEVEL    (BIT(3))
+#define I2C_RX_FULL_ACK_LEVEL_M  (I2C_RX_FULL_ACK_LEVEL_V << I2C_RX_FULL_ACK_LEVEL_S)
+#define I2C_RX_FULL_ACK_LEVEL_V  0x00000001
+#define I2C_RX_FULL_ACK_LEVEL_S  3
+
+/* I2C_SAMPLE_SCL_LEVEL : R/W; bitpos: [2]; default: 0;
+ * This register is used to select the sample mode.
+ *
+ * 1: sample SDA data on the SCL low level.
+ *
+ * 0: sample SDA data on the SCL high level.
+ */
+
+#define I2C_SAMPLE_SCL_LEVEL    (BIT(2))
+#define I2C_SAMPLE_SCL_LEVEL_M  (I2C_SAMPLE_SCL_LEVEL_V << I2C_SAMPLE_SCL_LEVEL_S)
+#define I2C_SAMPLE_SCL_LEVEL_V  0x00000001
+#define I2C_SAMPLE_SCL_LEVEL_S  2
+
+/* I2C_SCL_FORCE_OUT : R/W; bitpos: [1]; default: 1;
+ * 0: direct output. 1: open drain output.
+ */
+
+#define I2C_SCL_FORCE_OUT    (BIT(1))
+#define I2C_SCL_FORCE_OUT_M  (I2C_SCL_FORCE_OUT_V << I2C_SCL_FORCE_OUT_S)
+#define I2C_SCL_FORCE_OUT_V  0x00000001
+#define I2C_SCL_FORCE_OUT_S  1
+
+/* I2C_SDA_FORCE_OUT : R/W; bitpos: [0]; default: 1;
+ * 0: direct output. 1: open drain output.
+ */
+
+#define I2C_SDA_FORCE_OUT    (BIT(0))
+#define I2C_SDA_FORCE_OUT_M  (I2C_SDA_FORCE_OUT_V << I2C_SDA_FORCE_OUT_S)
+#define I2C_SDA_FORCE_OUT_V  0x00000001
+#define I2C_SDA_FORCE_OUT_S  0
+
+/* I2C_SR_REG register
+ * Describe I2C work status
+ */
+
+#define I2C_SR_REG(i) (REG_I2C_BASE(i) + 0x8)
+
+/* I2C_SCL_STATE_LAST : RO; bitpos: [30:28]; default: 0;
+ * This field indicates the states of the state machine used to produce SCL.
+ *
+ * 0: Idle. 1: Start. 2: Negative edge. 3: Low. 4: Positive edge. 5: High.
+ * 6: Stop
+ */
+
+#define I2C_SCL_STATE_LAST    0x00000007
+#define I2C_SCL_STATE_LAST_M  (I2C_SCL_STATE_LAST_V << I2C_SCL_STATE_LAST_S)
+#define I2C_SCL_STATE_LAST_V  0x00000007
+#define I2C_SCL_STATE_LAST_S  28
+
+/* I2C_SCL_MAIN_STATE_LAST : RO; bitpos: [26:24]; default: 0;
+ * This field indicates the states of the I2C module state machine.
+ *
+ * 0: Idle. 1: Address shift. 2: ACK address. 3: RX data. 4: TX data. 5:
+ * Send ACK. 6: Wait ACK
+ */
+
+#define I2C_SCL_MAIN_STATE_LAST    0x00000007
+#define I2C_SCL_MAIN_STATE_LAST_M  (I2C_SCL_MAIN_STATE_LAST_V << I2C_SCL_MAIN_STATE_LAST_S)
+#define I2C_SCL_MAIN_STATE_LAST_V  0x00000007
+#define I2C_SCL_MAIN_STATE_LAST_S  24
+
+/* I2C_TXFIFO_CNT : RO; bitpos: [23:18]; default: 0;
+ * This field stores the amount of received data in RAM.
+ */
+
+#define I2C_TXFIFO_CNT    0x0000003f
+#define I2C_TXFIFO_CNT_M  (I2C_TXFIFO_CNT_V << I2C_TXFIFO_CNT_S)
+#define I2C_TXFIFO_CNT_V  0x0000003f
+#define I2C_TXFIFO_CNT_S  18
+
+/* I2C_STRETCH_CAUSE : RO; bitpos: [15:14]; default: 0;
+ * The cause of stretching SCL low in slave mode. 0:  stretching SCL low at
+ * the beginning of I2C read data state. 1: stretching SCL low when I2C TX
+ * FIFO is empty in slave mode. 2: stretching SCL low when I2C RX FIFO is
+ * full in slave mode.
+ */
+
+#define I2C_STRETCH_CAUSE    0x00000003
+#define I2C_STRETCH_CAUSE_M  (I2C_STRETCH_CAUSE_V << I2C_STRETCH_CAUSE_S)
+#define I2C_STRETCH_CAUSE_V  0x00000003
+#define I2C_STRETCH_CAUSE_S  14
+
+/* I2C_RXFIFO_CNT : RO; bitpos: [13:8]; default: 0;
+ * This field represents the amount of data needed to be sent.
+ */
+
+#define I2C_RXFIFO_CNT    0x0000003f
+#define I2C_RXFIFO_CNT_M  (I2C_RXFIFO_CNT_V << I2C_RXFIFO_CNT_S)
+#define I2C_RXFIFO_CNT_V  0x0000003f
+#define I2C_RXFIFO_CNT_S  8
+
+/* I2C_BYTE_TRANS : RO; bitpos: [6]; default: 0;
+ * This field changes to 1 when one byte is transferred.
+ */
+
+#define I2C_BYTE_TRANS    (BIT(6))
+#define I2C_BYTE_TRANS_M  (I2C_BYTE_TRANS_V << I2C_BYTE_TRANS_S)
+#define I2C_BYTE_TRANS_V  0x00000001
+#define I2C_BYTE_TRANS_S  6
+
+/* I2C_SLAVE_ADDRESSED : RO; bitpos: [5]; default: 0;
+ * When configured as an I2C Slave, and the address sent by the master is
+ * equal to the address of the slave, then this bit will be of high level.
+ */
+
+#define I2C_SLAVE_ADDRESSED    (BIT(5))
+#define I2C_SLAVE_ADDRESSED_M  (I2C_SLAVE_ADDRESSED_V << I2C_SLAVE_ADDRESSED_S)
+#define I2C_SLAVE_ADDRESSED_V  0x00000001
+#define I2C_SLAVE_ADDRESSED_S  5
+
+/* I2C_BUS_BUSY : RO; bitpos: [4]; default: 0;
+ * 1: the I2C bus is busy transferring data. 0: the I2C bus is in idle state.
+ */
+
+#define I2C_BUS_BUSY    (BIT(4))
+#define I2C_BUS_BUSY_M  (I2C_BUS_BUSY_V << I2C_BUS_BUSY_S)
+#define I2C_BUS_BUSY_V  0x00000001
+#define I2C_BUS_BUSY_S  4
+
+/* I2C_ARB_LOST : RO; bitpos: [3]; default: 0;
+ * When the I2C controller loses control of SCL line, this register changes
+ * to 1.
+ */
+
+#define I2C_ARB_LOST    (BIT(3))
+#define I2C_ARB_LOST_M  (I2C_ARB_LOST_V << I2C_ARB_LOST_S)
+#define I2C_ARB_LOST_V  0x00000001
+#define I2C_ARB_LOST_S  3
+
+/* I2C_TIME_OUT : RO; bitpos: [2]; default: 0;
+ * When the I2C controller takes more than I2C_TIME_OUT clocks to receive a
+ * data bit, this field changes to 1.
+ */
+
+#define I2C_TIME_OUT    (BIT(2))
+#define I2C_TIME_OUT_M  (I2C_TIME_OUT_V << I2C_TIME_OUT_S)
+#define I2C_TIME_OUT_V  0x00000001
+#define I2C_TIME_OUT_S  2
+
+/* I2C_SLAVE_RW : RO; bitpos: [1]; default: 0;
+ * When in slave mode, 1: master reads from slave. 0: master writes to slave.
+ */
+
+#define I2C_SLAVE_RW    (BIT(1))
+#define I2C_SLAVE_RW_M  (I2C_SLAVE_RW_V << I2C_SLAVE_RW_S)
+#define I2C_SLAVE_RW_V  0x00000001
+#define I2C_SLAVE_RW_S  1
+
+/* I2C_RESP_REC : RO; bitpos: [0]; default: 0;
+ * The received ACK value in master mode or slave mode. 0: ACK. 1: NACK.
+ */
+
+#define I2C_RESP_REC    (BIT(0))
+#define I2C_RESP_REC_M  (I2C_RESP_REC_V << I2C_RESP_REC_S)
+#define I2C_RESP_REC_V  0x00000001
+#define I2C_RESP_REC_S  0
+
+/* I2C_TO_REG register
+ * Setting time out control for receiving data
+ */
+
+#define I2C_TO_REG(i) (REG_I2C_BASE(i) + 0xc)
+
+/* I2C_TIME_OUT_EN : R/W; bitpos: [24]; default: 0;
+ * This is the enable bit for time out control.
+ */
+
+#define I2C_TIME_OUT_EN    (BIT(24))
+#define I2C_TIME_OUT_EN_M  (I2C_TIME_OUT_EN_V << I2C_TIME_OUT_EN_S)
+#define I2C_TIME_OUT_EN_V  0x00000001
+#define I2C_TIME_OUT_EN_S  24
+
+/* I2C_TIME_OUT_VALUE : R/W; bitpos: [23:0]; default: 0;
+ * This register is used to configure the timeout for receiving a data bit
+ * in APB clock cycles.
+ */
+
+#define I2C_TIME_OUT_VALUE    0x00ffffff
+#define I2C_TIME_OUT_VALUE_M  (I2C_TIME_OUT_VALUE_V << I2C_TIME_OUT_VALUE_S)
+#define I2C_TIME_OUT_VALUE_V  0x00ffffff
+#define I2C_TIME_OUT_VALUE_S  0
+
+/* I2C_SLAVE_ADDR_REG register
+ * Local slave address setting
+ */
+
+#define I2C_SLAVE_ADDR_REG(i) (REG_I2C_BASE(i) + 0x10)
+
+/* I2C_ADDR_10BIT_EN : R/W; bitpos: [31]; default: 0;
+ * This field is used to enable the slave 10-bit addressing mode in master
+ * mode.
+ */
+
+#define I2C_ADDR_10BIT_EN    (BIT(31))
+#define I2C_ADDR_10BIT_EN_M  (I2C_ADDR_10BIT_EN_V << I2C_ADDR_10BIT_EN_S)
+#define I2C_ADDR_10BIT_EN_V  0x00000001
+#define I2C_ADDR_10BIT_EN_S  31
+
+/* I2C_SLAVE_ADDR : R/W; bitpos: [14:0]; default: 0;
+ * When configured as an I2C Slave, this field is used to configure the
+ * slave address.
+ */
+
+#define I2C_SLAVE_ADDR    0x00007fff
+#define I2C_SLAVE_ADDR_M  (I2C_SLAVE_ADDR_V << I2C_SLAVE_ADDR_S)
+#define I2C_SLAVE_ADDR_V  0x00007fff
+#define I2C_SLAVE_ADDR_S  0
+
+/* I2C_FIFO_ST_REG register
+ * FIFO status register
+ */
+
+#define I2C_FIFO_ST_REG(i) (REG_I2C_BASE(i) + 0x14)
+
+/* I2C_SLAVE_RW_POINT : RO; bitpos: [29:22]; default: 0;
+ * The received data in I2C slave mode.
+ */
+
+#define I2C_SLAVE_RW_POINT    0x000000ff
+#define I2C_SLAVE_RW_POINT_M  (I2C_SLAVE_RW_POINT_V << I2C_SLAVE_RW_POINT_S)
+#define I2C_SLAVE_RW_POINT_V  0x000000ff
+#define I2C_SLAVE_RW_POINT_S  22
+
+/* I2C_TX_UPDATE : WO; bitpos: [21]; default: 0;
+ * Write 0 or 1 to I2C_TX_UPDATE to update the value of I2C_TXFIFO_END_ADDR
+ * and I2C_TXFIFO_START_ADDR.
+ */
+
+#define I2C_TX_UPDATE    (BIT(21))
+#define I2C_TX_UPDATE_M  (I2C_TX_UPDATE_V << I2C_TX_UPDATE_S)
+#define I2C_TX_UPDATE_V  0x00000001
+#define I2C_TX_UPDATE_S  21
+
+/* I2C_RX_UPDATE : WO; bitpos: [20]; default: 0;
+ * Write 0 or 1 to I2C_RX_UPDATE to update the value of I2C_RXFIFO_END_ADDR
+ * and I2C_RXFIFO_START_ADDR.
+ */
+
+#define I2C_RX_UPDATE    (BIT(20))
+#define I2C_RX_UPDATE_M  (I2C_RX_UPDATE_V << I2C_RX_UPDATE_S)
+#define I2C_RX_UPDATE_V  0x00000001
+#define I2C_RX_UPDATE_S  20
+
+/* I2C_TXFIFO_END_ADDR : RO; bitpos: [19:15]; default: 0;
+ * This is the offset address of the last sent data, as described in
+ * I2C_NONFIFO_TX_THRES.
+ *
+ * The value refreshes when an I2C_TXFIFO_OVF_INT or I2C_TRANS_COMPLETE_INT
+ * interrupt is generated.
+ */
+
+#define I2C_TXFIFO_END_ADDR    0x0000001f
+#define I2C_TXFIFO_END_ADDR_M  (I2C_TXFIFO_END_ADDR_V << I2C_TXFIFO_END_ADDR_S)
+#define I2C_TXFIFO_END_ADDR_V  0x0000001f
+#define I2C_TXFIFO_END_ADDR_S  15
+
+/* I2C_TXFIFO_START_ADDR : RO; bitpos: [14:10]; default: 0;
+ * This is the offset address of the first sent data, as described in
+ * I2C_NONFIFO_TX_THRES.
+ */
+
+#define I2C_TXFIFO_START_ADDR    0x0000001f
+#define I2C_TXFIFO_START_ADDR_M  (I2C_TXFIFO_START_ADDR_V << I2C_TXFIFO_START_ADDR_S)
+#define I2C_TXFIFO_START_ADDR_V  0x0000001f
+#define I2C_TXFIFO_START_ADDR_S  10
+
+/* I2C_RXFIFO_END_ADDR : RO; bitpos: [9:5]; default: 0;
+ * This is the offset address of the last received data, as described in
+ * I2C_NONFIFO_RX_THRES. This value refreshes when an I2C_RXFIFO_UDF_INT or
+ * I2C_TRANS_COMPLETE_INT interrupt is generated.
+ */
+
+#define I2C_RXFIFO_END_ADDR    0x0000001f
+#define I2C_RXFIFO_END_ADDR_M  (I2C_RXFIFO_END_ADDR_V << I2C_RXFIFO_END_ADDR_S)
+#define I2C_RXFIFO_END_ADDR_V  0x0000001f
+#define I2C_RXFIFO_END_ADDR_S  5
+
+/* I2C_RXFIFO_START_ADDR : RO; bitpos: [4:0]; default: 0;
+ * This is the offset address of the last received data, as described in
+ * I2C_NONFIFO_RX_THRES.
+ */
+
+#define I2C_RXFIFO_START_ADDR    0x0000001f
+#define I2C_RXFIFO_START_ADDR_M  (I2C_RXFIFO_START_ADDR_V << I2C_RXFIFO_START_ADDR_S)
+#define I2C_RXFIFO_START_ADDR_V  0x0000001f
+#define I2C_RXFIFO_START_ADDR_S  0
+
+/* I2C_FIFO_CONF_REG register
+ * FIFO configuration register
+ */
+
+#define I2C_FIFO_CONF_REG(i) (REG_I2C_BASE(i) + 0x18)
+
+/* I2C_FIFO_PRT_EN : R/W; bitpos: [26]; default: 1;
+ * The control enable bit of FIFO pointer in non-FIFO mode. This bit
+ * controls the valid bits and the interrupts of TX/RX FIFO overflow,
+ * underflow, full and empty.
+ */
+
+#define I2C_FIFO_PRT_EN    (BIT(26))
+#define I2C_FIFO_PRT_EN_M  (I2C_FIFO_PRT_EN_V << I2C_FIFO_PRT_EN_S)
+#define I2C_FIFO_PRT_EN_V  0x00000001
+#define I2C_FIFO_PRT_EN_S  26
+
+/* I2C_NONFIFO_TX_THRES : R/W; bitpos: [25:20]; default: 21;
+ * When I2C sends more than I2C_NONFIFO_TX_THRES bytes of data, it will
+ * generate an I2C_TXFIFO_OVF_INT interrupt and update the current offset
+ * address of the sent data.
+ */
+
+#define I2C_NONFIFO_TX_THRES    0x0000003f
+#define I2C_NONFIFO_TX_THRES_M  (I2C_NONFIFO_TX_THRES_V << I2C_NONFIFO_TX_THRES_S)
+#define I2C_NONFIFO_TX_THRES_V  0x0000003f
+#define I2C_NONFIFO_TX_THRES_S  20
+
+/* I2C_NONFIFO_RX_THRES : R/W; bitpos: [19:14]; default: 21;
+ * When I2C receives more than I2C_NONFIFO_RX_THRES bytes of data, it will
+ * generate an I2C_RXFIFO_UDF_INT interrupt and update the current offset
+ * address of the received data.
+ */
+
+#define I2C_NONFIFO_RX_THRES    0x0000003f
+#define I2C_NONFIFO_RX_THRES_M  (I2C_NONFIFO_RX_THRES_V << I2C_NONFIFO_RX_THRES_S)
+#define I2C_NONFIFO_RX_THRES_V  0x0000003f
+#define I2C_NONFIFO_RX_THRES_S  14
+
+/* I2C_TX_FIFO_RST : R/W; bitpos: [13]; default: 0;
+ * Set this bit to reset TX FIFO.
+ */
+
+#define I2C_TX_FIFO_RST    (BIT(13))
+#define I2C_TX_FIFO_RST_M  (I2C_TX_FIFO_RST_V << I2C_TX_FIFO_RST_S)
+#define I2C_TX_FIFO_RST_V  0x00000001
+#define I2C_TX_FIFO_RST_S  13
+
+/* I2C_RX_FIFO_RST : R/W; bitpos: [12]; default: 0;
+ * Set this bit to reset RX FIFO.
+ */
+
+#define I2C_RX_FIFO_RST    (BIT(12))
+#define I2C_RX_FIFO_RST_M  (I2C_RX_FIFO_RST_V << I2C_RX_FIFO_RST_S)
+#define I2C_RX_FIFO_RST_V  0x00000001
+#define I2C_RX_FIFO_RST_S  12
+
+/* I2C_FIFO_ADDR_CFG_EN : R/W; bitpos: [11]; default: 0;
+ * When this bit is set to 1, the byte received after the I2C address byte
+ * represents the offset address in the I2C Slave RAM.
+ */
+
+#define I2C_FIFO_ADDR_CFG_EN    (BIT(11))
+#define I2C_FIFO_ADDR_CFG_EN_M  (I2C_FIFO_ADDR_CFG_EN_V << I2C_FIFO_ADDR_CFG_EN_S)
+#define I2C_FIFO_ADDR_CFG_EN_V  0x00000001
+#define I2C_FIFO_ADDR_CFG_EN_S  11
+
+/* I2C_NONFIFO_EN : R/W; bitpos: [10]; default: 0;
+ * Set this bit to enable APB non-FIFO mode.
+ */
+
+#define I2C_NONFIFO_EN    (BIT(10))
+#define I2C_NONFIFO_EN_M  (I2C_NONFIFO_EN_V << I2C_NONFIFO_EN_S)
+#define I2C_NONFIFO_EN_V  0x00000001
+#define I2C_NONFIFO_EN_S  10
+
+/* I2C_TXFIFO_WM_THRHD : R/W; bitpos: [9:5]; default: 4;
+ * The water mark threshold of TX FIFO in non-FIFO mode. When
+ * I2C_FIFO_PRT_EN is 1 and TX FIFO counter is smaller than
+ * I2C_TXFIFO_WM_THRHD[4:0], I2C_TXFIFO_WM_INT_RAW bit will be valid.
+ */
+
+#define I2C_TXFIFO_WM_THRHD    0x0000001f
+#define I2C_TXFIFO_WM_THRHD_M  (I2C_TXFIFO_WM_THRHD_V << I2C_TXFIFO_WM_THRHD_S)
+#define I2C_TXFIFO_WM_THRHD_V  0x0000001f
+#define I2C_TXFIFO_WM_THRHD_S  5
+
+/* I2C_RXFIFO_WM_THRHD : R/W; bitpos: [4:0]; default: 11;
+ * The water mark threshold of RX FIFO in non-FIFO mode. When
+ * I2C_FIFO_PRT_EN is 1 and RX FIFO counter is bigger than
+ * I2C_RXFIFO_WM_THRHD[4:0], I2C_RXFIFO_WM_INT_RAW bit will be valid.
+ */
+
+#define I2C_RXFIFO_WM_THRHD    0x0000001f
+#define I2C_RXFIFO_WM_THRHD_M  (I2C_RXFIFO_WM_THRHD_V << I2C_RXFIFO_WM_THRHD_S)
+#define I2C_RXFIFO_WM_THRHD_V  0x0000001f
+#define I2C_RXFIFO_WM_THRHD_S  0
+
+/* I2C_DATA_REG register
+ * RX FIFO read data
+ */
+
+#define I2C_DATA_REG(i) (REG_I2C_BASE(i) + 0x1c)
+
+/* I2C_FIFO_RDATA : RO; bitpos: [7:0]; default: 0;
+ * The value of RX FIFO read data.
+ */
+
+#define I2C_FIFO_RDATA    0x000000ff
+#define I2C_FIFO_RDATA_M  (I2C_FIFO_RDATA_V << I2C_FIFO_RDATA_S)
+#define I2C_FIFO_RDATA_V  0x000000ff
+#define I2C_FIFO_RDATA_S  0
+
+/* I2C_INT_RAW_REG register
+ * Raw interrupt status
+ */
+
+#define I2C_INT_RAW_REG(i) (REG_I2C_BASE(i) + 0x20)
+
+/* I2C_SLAVE_STRETCH_INT_RAW : RO; bitpos: [16]; default: 0;
+ * The raw interrupt bit for I2C_SLAVE_STRETCH_INT interrupt.
+ */
+
+#define I2C_SLAVE_STRETCH_INT_RAW    (BIT(16))
+#define I2C_SLAVE_STRETCH_INT_RAW_M  (I2C_SLAVE_STRETCH_INT_RAW_V << I2C_SLAVE_STRETCH_INT_RAW_S)
+#define I2C_SLAVE_STRETCH_INT_RAW_V  0x00000001
+#define I2C_SLAVE_STRETCH_INT_RAW_S  16
+
+/* I2C_DET_START_INT_RAW : RO; bitpos: [15]; default: 0;
+ * The raw interrupt bit for I2C_DET_START_INT interrupt.
+ */
+
+#define I2C_DET_START_INT_RAW    (BIT(15))
+#define I2C_DET_START_INT_RAW_M  (I2C_DET_START_INT_RAW_V << I2C_DET_START_INT_RAW_S)
+#define I2C_DET_START_INT_RAW_V  0x00000001
+#define I2C_DET_START_INT_RAW_S  15
+
+/* I2C_SCL_MAIN_ST_TO_INT_RAW : RO; bitpos: [14]; default: 0;
+ * The raw interrupt bit for I2C_SCL_MAIN_ST_TO_INT interrupt.
+ */
+
+#define I2C_SCL_MAIN_ST_TO_INT_RAW    (BIT(14))
+#define I2C_SCL_MAIN_ST_TO_INT_RAW_M  (I2C_SCL_MAIN_ST_TO_INT_RAW_V << I2C_SCL_MAIN_ST_TO_INT_RAW_S)
+#define I2C_SCL_MAIN_ST_TO_INT_RAW_V  0x00000001
+#define I2C_SCL_MAIN_ST_TO_INT_RAW_S  14
+
+/* I2C_SCL_ST_TO_INT_RAW : RO; bitpos: [13]; default: 0;
+ * The raw interrupt bit for I2C_SCL_ST_TO_INT interrupt.
+ */
+
+#define I2C_SCL_ST_TO_INT_RAW    (BIT(13))
+#define I2C_SCL_ST_TO_INT_RAW_M  (I2C_SCL_ST_TO_INT_RAW_V << I2C_SCL_ST_TO_INT_RAW_S)
+#define I2C_SCL_ST_TO_INT_RAW_V  0x00000001
+#define I2C_SCL_ST_TO_INT_RAW_S  13
+
+/* I2C_RXFIFO_UDF_INT_RAW : RO; bitpos: [12]; default: 0;
+ * The raw interrupt bit for I2C_RXFIFO_UDF_INT  interrupt.
+ */
+
+#define I2C_RXFIFO_UDF_INT_RAW    (BIT(12))
+#define I2C_RXFIFO_UDF_INT_RAW_M  (I2C_RXFIFO_UDF_INT_RAW_V << I2C_RXFIFO_UDF_INT_RAW_S)
+#define I2C_RXFIFO_UDF_INT_RAW_V  0x00000001
+#define I2C_RXFIFO_UDF_INT_RAW_S  12
+
+/* I2C_TXFIFO_OVF_INT_RAW : RO; bitpos: [11]; default: 0;
+ * The raw interrupt bit for I2C_TXFIFO_OVF_INT interrupt.
+ */
+
+#define I2C_TXFIFO_OVF_INT_RAW    (BIT(11))
+#define I2C_TXFIFO_OVF_INT_RAW_M  (I2C_TXFIFO_OVF_INT_RAW_V << I2C_TXFIFO_OVF_INT_RAW_S)
+#define I2C_TXFIFO_OVF_INT_RAW_V  0x00000001
+#define I2C_TXFIFO_OVF_INT_RAW_S  11
+
+/* I2C_NACK_INT_RAW : RO; bitpos: [10]; default: 0;
+ * The raw interrupt bit for I2C_SLAVE_STRETCH_INT interrupt.
+ */
+
+#define I2C_NACK_INT_RAW    (BIT(10))
+#define I2C_NACK_INT_RAW_M  (I2C_NACK_INT_RAW_V << I2C_NACK_INT_RAW_S)
+#define I2C_NACK_INT_RAW_V  0x00000001
+#define I2C_NACK_INT_RAW_S  10
+
+/* I2C_TRANS_START_INT_RAW : RO; bitpos: [9]; default: 0;
+ * The raw interrupt bit for the I2C_TRANS_START_INT interrupt.
+ */
+
+#define I2C_TRANS_START_INT_RAW    (BIT(9))
+#define I2C_TRANS_START_INT_RAW_M  (I2C_TRANS_START_INT_RAW_V << I2C_TRANS_START_INT_RAW_S)
+#define I2C_TRANS_START_INT_RAW_V  0x00000001
+#define I2C_TRANS_START_INT_RAW_S  9
+
+/* I2C_TIME_OUT_INT_RAW : RO; bitpos: [8]; default: 0;
+ * The raw interrupt bit for the I2C_TIME_OUT_INT interrupt.
+ */
+
+#define I2C_TIME_OUT_INT_RAW    (BIT(8))
+#define I2C_TIME_OUT_INT_RAW_M  (I2C_TIME_OUT_INT_RAW_V << I2C_TIME_OUT_INT_RAW_S)
+#define I2C_TIME_OUT_INT_RAW_V  0x00000001
+#define I2C_TIME_OUT_INT_RAW_S  8
+
+/* I2C_TRANS_COMPLETE_INT_RAW : RO; bitpos: [7]; default: 0;
+ * The raw interrupt bit for the I2C_TRANS_COMPLETE_INT interrupt.
+ */
+
+#define I2C_TRANS_COMPLETE_INT_RAW    (BIT(7))
+#define I2C_TRANS_COMPLETE_INT_RAW_M  (I2C_TRANS_COMPLETE_INT_RAW_V << I2C_TRANS_COMPLETE_INT_RAW_S)
+#define I2C_TRANS_COMPLETE_INT_RAW_V  0x00000001
+#define I2C_TRANS_COMPLETE_INT_RAW_S  7
+
+/* I2C_MST_TXFIFO_UDF_INT_RAW : RO; bitpos: [6]; default: 0;
+ * The raw interrupt bit for I2C_TRANS_COMPLETE_INT interrupt.
+ */
+
+#define I2C_MST_TXFIFO_UDF_INT_RAW    (BIT(6))
+#define I2C_MST_TXFIFO_UDF_INT_RAW_M  (I2C_MST_TXFIFO_UDF_INT_RAW_V << I2C_MST_TXFIFO_UDF_INT_RAW_S)
+#define I2C_MST_TXFIFO_UDF_INT_RAW_V  0x00000001
+#define I2C_MST_TXFIFO_UDF_INT_RAW_S  6
+
+/* I2C_ARBITRATION_LOST_INT_RAW : RO; bitpos: [5]; default: 0;
+ * The raw interrupt bit for the I2C_ARBITRATION_LOST_INT interrupt.
+ */
+
+#define I2C_ARBITRATION_LOST_INT_RAW    (BIT(5))
+#define I2C_ARBITRATION_LOST_INT_RAW_M  (I2C_ARBITRATION_LOST_INT_RAW_V << I2C_ARBITRATION_LOST_INT_RAW_S)
+#define I2C_ARBITRATION_LOST_INT_RAW_V  0x00000001
+#define I2C_ARBITRATION_LOST_INT_RAW_S  5
+
+/* I2C_BYTE_TRANS_DONE_INT_RAW : RO; bitpos: [4]; default: 0;
+ * The raw interrupt bit for the I2C_END_DETECT_INT interrupt.
+ */
+
+#define I2C_BYTE_TRANS_DONE_INT_RAW    (BIT(4))
+#define I2C_BYTE_TRANS_DONE_INT_RAW_M  (I2C_BYTE_TRANS_DONE_INT_RAW_V << I2C_BYTE_TRANS_DONE_INT_RAW_S)
+#define I2C_BYTE_TRANS_DONE_INT_RAW_V  0x00000001
+#define I2C_BYTE_TRANS_DONE_INT_RAW_S  4
+
+/* I2C_END_DETECT_INT_RAW : RO; bitpos: [3]; default: 0;
+ * The raw interrupt bit for the I2C_END_DETECT_INT interrupt.
+ */
+
+#define I2C_END_DETECT_INT_RAW    (BIT(3))
+#define I2C_END_DETECT_INT_RAW_M  (I2C_END_DETECT_INT_RAW_V << I2C_END_DETECT_INT_RAW_S)
+#define I2C_END_DETECT_INT_RAW_V  0x00000001
+#define I2C_END_DETECT_INT_RAW_S  3
+
+/* I2C_RXFIFO_OVF_INT_RAW : RO; bitpos: [2]; default: 0;
+ * The raw interrupt bit for I2C_RXFIFO_OVF_INT interrupt.
+ */
+
+#define I2C_RXFIFO_OVF_INT_RAW    (BIT(2))
+#define I2C_RXFIFO_OVF_INT_RAW_M  (I2C_RXFIFO_OVF_INT_RAW_V << I2C_RXFIFO_OVF_INT_RAW_S)
+#define I2C_RXFIFO_OVF_INT_RAW_V  0x00000001
+#define I2C_RXFIFO_OVF_INT_RAW_S  2
+
+/* I2C_TXFIFO_WM_INT_RAW : RO; bitpos: [1]; default: 0;
+ * The raw interrupt bit for I2C_TXFIFO_WM_INT interrupt.
+ */
+
+#define I2C_TXFIFO_WM_INT_RAW    (BIT(1))
+#define I2C_TXFIFO_WM_INT_RAW_M  (I2C_TXFIFO_WM_INT_RAW_V << I2C_TXFIFO_WM_INT_RAW_S)
+#define I2C_TXFIFO_WM_INT_RAW_V  0x00000001
+#define I2C_TXFIFO_WM_INT_RAW_S  1
+
+/* I2C_RXFIFO_WM_INT_RAW : RO; bitpos: [0]; default: 0;
+ * The raw interrupt bit for I2C_RXFIFO_WM_INT interrupt.
+ */
+
+#define I2C_RXFIFO_WM_INT_RAW    (BIT(0))
+#define I2C_RXFIFO_WM_INT_RAW_M  (I2C_RXFIFO_WM_INT_RAW_V << I2C_RXFIFO_WM_INT_RAW_S)
+#define I2C_RXFIFO_WM_INT_RAW_V  0x00000001
+#define I2C_RXFIFO_WM_INT_RAW_S  0
+
+/* I2C_INT_CLR_REG register
+ * Interrupt clear bits
+ */
+
+#define I2C_INT_CLR_REG(i) (REG_I2C_BASE(i) + 0x24)
+
+/* I2C_SLAVE_STRETCH_INT_CLR : WO; bitpos: [16]; default: 0;
+ * Set this bit to clear I2C_SLAVE_STRETCH_INT interrupt.
+ */
+
+#define I2C_SLAVE_STRETCH_INT_CLR    (BIT(16))
+#define I2C_SLAVE_STRETCH_INT_CLR_M  (I2C_SLAVE_STRETCH_INT_CLR_V << I2C_SLAVE_STRETCH_INT_CLR_S)
+#define I2C_SLAVE_STRETCH_INT_CLR_V  0x00000001
+#define I2C_SLAVE_STRETCH_INT_CLR_S  16
+
+/* I2C_DET_START_INT_CLR : WO; bitpos: [15]; default: 0;
+ * Set this bit to clear I2C_DET_START_INT interrupt.
+ */
+
+#define I2C_DET_START_INT_CLR    (BIT(15))
+#define I2C_DET_START_INT_CLR_M  (I2C_DET_START_INT_CLR_V << I2C_DET_START_INT_CLR_S)
+#define I2C_DET_START_INT_CLR_V  0x00000001
+#define I2C_DET_START_INT_CLR_S  15
+
+/* I2C_SCL_MAIN_ST_TO_INT_CLR : WO; bitpos: [14]; default: 0;
+ * Set this bit to clear I2C_SCL_MAIN_ST_TO_INT interrupt.
+ */
+
+#define I2C_SCL_MAIN_ST_TO_INT_CLR    (BIT(14))
+#define I2C_SCL_MAIN_ST_TO_INT_CLR_M  (I2C_SCL_MAIN_ST_TO_INT_CLR_V << I2C_SCL_MAIN_ST_TO_INT_CLR_S)
+#define I2C_SCL_MAIN_ST_TO_INT_CLR_V  0x00000001
+#define I2C_SCL_MAIN_ST_TO_INT_CLR_S  14
+
+/* I2C_SCL_ST_TO_INT_CLR : WO; bitpos: [13]; default: 0;
+ * Set this bit to clear I2C_SCL_ST_TO_INT interrupt.
+ */
+
+#define I2C_SCL_ST_TO_INT_CLR    (BIT(13))
+#define I2C_SCL_ST_TO_INT_CLR_M  (I2C_SCL_ST_TO_INT_CLR_V << I2C_SCL_ST_TO_INT_CLR_S)
+#define I2C_SCL_ST_TO_INT_CLR_V  0x00000001
+#define I2C_SCL_ST_TO_INT_CLR_S  13
+
+/* I2C_RXFIFO_UDF_INT_CLR : WO; bitpos: [12]; default: 0;
+ * Set this bit to clear I2C_RXFIFO_UDF_INT  interrupt.
+ */
+
+#define I2C_RXFIFO_UDF_INT_CLR    (BIT(12))
+#define I2C_RXFIFO_UDF_INT_CLR_M  (I2C_RXFIFO_UDF_INT_CLR_V << I2C_RXFIFO_UDF_INT_CLR_S)
+#define I2C_RXFIFO_UDF_INT_CLR_V  0x00000001
+#define I2C_RXFIFO_UDF_INT_CLR_S  12
+
+/* I2C_TXFIFO_OVF_INT_CLR : WO; bitpos: [11]; default: 0;
+ * Set this bit to clear I2C_TXFIFO_OVF_INT interrupt.
+ */
+
+#define I2C_TXFIFO_OVF_INT_CLR    (BIT(11))
+#define I2C_TXFIFO_OVF_INT_CLR_M  (I2C_TXFIFO_OVF_INT_CLR_V << I2C_TXFIFO_OVF_INT_CLR_S)
+#define I2C_TXFIFO_OVF_INT_CLR_V  0x00000001
+#define I2C_TXFIFO_OVF_INT_CLR_S  11
+
+/* I2C_NACK_INT_CLR : WO; bitpos: [10]; default: 0;
+ * Set this bit to clear I2C_SLAVE_STRETCH_INT interrupt.
+ */
+
+#define I2C_NACK_INT_CLR    (BIT(10))
+#define I2C_NACK_INT_CLR_M  (I2C_NACK_INT_CLR_V << I2C_NACK_INT_CLR_S)
+#define I2C_NACK_INT_CLR_V  0x00000001
+#define I2C_NACK_INT_CLR_S  10
+
+/* I2C_TRANS_START_INT_CLR : WO; bitpos: [9]; default: 0;
+ * Set this bit to clear the I2C_TRANS_START_INT interrupt.
+ */
+
+#define I2C_TRANS_START_INT_CLR    (BIT(9))
+#define I2C_TRANS_START_INT_CLR_M  (I2C_TRANS_START_INT_CLR_V << I2C_TRANS_START_INT_CLR_S)
+#define I2C_TRANS_START_INT_CLR_V  0x00000001
+#define I2C_TRANS_START_INT_CLR_S  9
+
+/* I2C_TIME_OUT_INT_CLR : WO; bitpos: [8]; default: 0;
+ * Set this bit to clear the I2C_TIME_OUT_INT interrupt.
+ */
+
+#define I2C_TIME_OUT_INT_CLR    (BIT(8))
+#define I2C_TIME_OUT_INT_CLR_M  (I2C_TIME_OUT_INT_CLR_V << I2C_TIME_OUT_INT_CLR_S)
+#define I2C_TIME_OUT_INT_CLR_V  0x00000001
+#define I2C_TIME_OUT_INT_CLR_S  8
+
+/* I2C_TRANS_COMPLETE_INT_CLR : WO; bitpos: [7]; default: 0;
+ * Set this bit to clear the I2C_TRANS_COMPLETE_INT interrupt.
+ */
+
+#define I2C_TRANS_COMPLETE_INT_CLR    (BIT(7))
+#define I2C_TRANS_COMPLETE_INT_CLR_M  (I2C_TRANS_COMPLETE_INT_CLR_V << I2C_TRANS_COMPLETE_INT_CLR_S)
+#define I2C_TRANS_COMPLETE_INT_CLR_V  0x00000001
+#define I2C_TRANS_COMPLETE_INT_CLR_S  7
+
+/* I2C_MST_TXFIFO_UDF_INT_CLR : WO; bitpos: [6]; default: 0;
+ * Set this bit to clear I2C_TRANS_COMPLETE_INT interrupt.
+ */
+
+#define I2C_MST_TXFIFO_UDF_INT_CLR    (BIT(6))
+#define I2C_MST_TXFIFO_UDF_INT_CLR_M  (I2C_MST_TXFIFO_UDF_INT_CLR_V << I2C_MST_TXFIFO_UDF_INT_CLR_S)
+#define I2C_MST_TXFIFO_UDF_INT_CLR_V  0x00000001
+#define I2C_MST_TXFIFO_UDF_INT_CLR_S  6
+
+/* I2C_ARBITRATION_LOST_INT_CLR : WO; bitpos: [5]; default: 0;
+ * Set this bit to clear the I2C_ARBITRATION_LOST_INT interrupt.
+ */
+
+#define I2C_ARBITRATION_LOST_INT_CLR    (BIT(5))
+#define I2C_ARBITRATION_LOST_INT_CLR_M  (I2C_ARBITRATION_LOST_INT_CLR_V << I2C_ARBITRATION_LOST_INT_CLR_S)
+#define I2C_ARBITRATION_LOST_INT_CLR_V  0x00000001
+#define I2C_ARBITRATION_LOST_INT_CLR_S  5
+
+/* I2C_BYTE_TRANS_DONE_INT_CLR : WO; bitpos: [4]; default: 0;
+ * Set this bit to clear the I2C_END_DETECT_INT interrupt.
+ */
+
+#define I2C_BYTE_TRANS_DONE_INT_CLR    (BIT(4))
+#define I2C_BYTE_TRANS_DONE_INT_CLR_M  (I2C_BYTE_TRANS_DONE_INT_CLR_V << I2C_BYTE_TRANS_DONE_INT_CLR_S)
+#define I2C_BYTE_TRANS_DONE_INT_CLR_V  0x00000001
+#define I2C_BYTE_TRANS_DONE_INT_CLR_S  4
+
+/* I2C_END_DETECT_INT_CLR : WO; bitpos: [3]; default: 0;
+ * Set this bit to clear the I2C_END_DETECT_INT interrupt.
+ */
+
+#define I2C_END_DETECT_INT_CLR    (BIT(3))
+#define I2C_END_DETECT_INT_CLR_M  (I2C_END_DETECT_INT_CLR_V << I2C_END_DETECT_INT_CLR_S)
+#define I2C_END_DETECT_INT_CLR_V  0x00000001
+#define I2C_END_DETECT_INT_CLR_S  3
+
+/* I2C_RXFIFO_OVF_INT_CLR : WO; bitpos: [2]; default: 0;
+ * Set this bit to clear I2C_RXFIFO_OVF_INT interrupt.
+ */
+
+#define I2C_RXFIFO_OVF_INT_CLR    (BIT(2))
+#define I2C_RXFIFO_OVF_INT_CLR_M  (I2C_RXFIFO_OVF_INT_CLR_V << I2C_RXFIFO_OVF_INT_CLR_S)
+#define I2C_RXFIFO_OVF_INT_CLR_V  0x00000001
+#define I2C_RXFIFO_OVF_INT_CLR_S  2
+
+/* I2C_TXFIFO_WM_INT_CLR : WO; bitpos: [1]; default: 0;
+ * Set this bit to clear I2C_TXFIFO_WM_INT interrupt.
+ */
+
+#define I2C_TXFIFO_WM_INT_CLR    (BIT(1))
+#define I2C_TXFIFO_WM_INT_CLR_M  (I2C_TXFIFO_WM_INT_CLR_V << I2C_TXFIFO_WM_INT_CLR_S)
+#define I2C_TXFIFO_WM_INT_CLR_V  0x00000001
+#define I2C_TXFIFO_WM_INT_CLR_S  1
+
+/* I2C_RXFIFO_WM_INT_CLR : WO; bitpos: [0]; default: 0;
+ * Set this bit to clear I2C_RXFIFO_WM_INT interrupt.
+ */
+
+#define I2C_RXFIFO_WM_INT_CLR    (BIT(0))
+#define I2C_RXFIFO_WM_INT_CLR_M  (I2C_RXFIFO_WM_INT_CLR_V << I2C_RXFIFO_WM_INT_CLR_S)
+#define I2C_RXFIFO_WM_INT_CLR_V  0x00000001
+#define I2C_RXFIFO_WM_INT_CLR_S  0
+
+/* I2C_INT_ENA_REG register
+ * Interrupt enable bits
+ */
+
+#define I2C_INT_ENA_REG(i) (REG_I2C_BASE(i) + 0x28)
+
+/* I2C_SLAVE_STRETCH_INT_ENA : R/W; bitpos: [16]; default: 0;
+ * The raw interrupt bit for I2C_SLAVE_STRETCH_INT interrupt.
+ */
+
+#define I2C_SLAVE_STRETCH_INT_ENA    (BIT(16))
+#define I2C_SLAVE_STRETCH_INT_ENA_M  (I2C_SLAVE_STRETCH_INT_ENA_V << I2C_SLAVE_STRETCH_INT_ENA_S)
+#define I2C_SLAVE_STRETCH_INT_ENA_V  0x00000001
+#define I2C_SLAVE_STRETCH_INT_ENA_S  16
+
+/* I2C_DET_START_INT_ENA : R/W; bitpos: [15]; default: 0;
+ * The raw interrupt bit for I2C_DET_START_INT interrupt.
+ */
+
+#define I2C_DET_START_INT_ENA    (BIT(15))
+#define I2C_DET_START_INT_ENA_M  (I2C_DET_START_INT_ENA_V << I2C_DET_START_INT_ENA_S)
+#define I2C_DET_START_INT_ENA_V  0x00000001
+#define I2C_DET_START_INT_ENA_S  15
+
+/* I2C_SCL_MAIN_ST_TO_INT_ENA : R/W; bitpos: [14]; default: 0;
+ * The raw interrupt bit for I2C_SCL_MAIN_ST_TO_INT interrupt.
+ */
+
+#define I2C_SCL_MAIN_ST_TO_INT_ENA    (BIT(14))
+#define I2C_SCL_MAIN_ST_TO_INT_ENA_M  (I2C_SCL_MAIN_ST_TO_INT_ENA_V << I2C_SCL_MAIN_ST_TO_INT_ENA_S)
+#define I2C_SCL_MAIN_ST_TO_INT_ENA_V  0x00000001
+#define I2C_SCL_MAIN_ST_TO_INT_ENA_S  14
+
+/* I2C_SCL_ST_TO_INT_ENA : R/W; bitpos: [13]; default: 0;
+ * The raw interrupt bit for I2C_SCL_ST_TO_INT interrupt.
+ */
+
+#define I2C_SCL_ST_TO_INT_ENA    (BIT(13))
+#define I2C_SCL_ST_TO_INT_ENA_M  (I2C_SCL_ST_TO_INT_ENA_V << I2C_SCL_ST_TO_INT_ENA_S)
+#define I2C_SCL_ST_TO_INT_ENA_V  0x00000001
+#define I2C_SCL_ST_TO_INT_ENA_S  13
+
+/* I2C_RXFIFO_UDF_INT_ENA : R/W; bitpos: [12]; default: 0;
+ * The raw interrupt bit for I2C_RXFIFO_UDF_INT  interrupt.
+ */
+
+#define I2C_RXFIFO_UDF_INT_ENA    (BIT(12))
+#define I2C_RXFIFO_UDF_INT_ENA_M  (I2C_RXFIFO_UDF_INT_ENA_V << I2C_RXFIFO_UDF_INT_ENA_S)
+#define I2C_RXFIFO_UDF_INT_ENA_V  0x00000001
+#define I2C_RXFIFO_UDF_INT_ENA_S  12
+
+/* I2C_TXFIFO_OVF_INT_ENA : R/W; bitpos: [11]; default: 0;
+ * The raw interrupt bit for I2C_TXFIFO_OVF_INT interrupt.
+ */
+
+#define I2C_TXFIFO_OVF_INT_ENA    (BIT(11))
+#define I2C_TXFIFO_OVF_INT_ENA_M  (I2C_TXFIFO_OVF_INT_ENA_V << I2C_TXFIFO_OVF_INT_ENA_S)
+#define I2C_TXFIFO_OVF_INT_ENA_V  0x00000001
+#define I2C_TXFIFO_OVF_INT_ENA_S  11
+
+/* I2C_NACK_INT_ENA : R/W; bitpos: [10]; default: 0;
+ * The raw interrupt bit for I2C_SLAVE_STRETCH_INT interrupt.
+ */
+
+#define I2C_NACK_INT_ENA    (BIT(10))
+#define I2C_NACK_INT_ENA_M  (I2C_NACK_INT_ENA_V << I2C_NACK_INT_ENA_S)
+#define I2C_NACK_INT_ENA_V  0x00000001
+#define I2C_NACK_INT_ENA_S  10
+
+/* I2C_TRANS_START_INT_ENA : R/W; bitpos: [9]; default: 0;
+ * The raw interrupt bit for the I2C_TRANS_START_INT interrupt.
+ */
+
+#define I2C_TRANS_START_INT_ENA    (BIT(9))
+#define I2C_TRANS_START_INT_ENA_M  (I2C_TRANS_START_INT_ENA_V << I2C_TRANS_START_INT_ENA_S)
+#define I2C_TRANS_START_INT_ENA_V  0x00000001
+#define I2C_TRANS_START_INT_ENA_S  9
+
+/* I2C_TIME_OUT_INT_ENA : R/W; bitpos: [8]; default: 0;
+ * The raw interrupt bit for the I2C_TIME_OUT_INT interrupt.
+ */
+
+#define I2C_TIME_OUT_INT_ENA    (BIT(8))
+#define I2C_TIME_OUT_INT_ENA_M  (I2C_TIME_OUT_INT_ENA_V << I2C_TIME_OUT_INT_ENA_S)
+#define I2C_TIME_OUT_INT_ENA_V  0x00000001
+#define I2C_TIME_OUT_INT_ENA_S  8
+
+/* I2C_TRANS_COMPLETE_INT_ENA : R/W; bitpos: [7]; default: 0;
+ * The raw interrupt bit for the I2C_TRANS_COMPLETE_INT interrupt.
+ */
+
+#define I2C_TRANS_COMPLETE_INT_ENA    (BIT(7))
+#define I2C_TRANS_COMPLETE_INT_ENA_M  (I2C_TRANS_COMPLETE_INT_ENA_V << I2C_TRANS_COMPLETE_INT_ENA_S)
+#define I2C_TRANS_COMPLETE_INT_ENA_V  0x00000001
+#define I2C_TRANS_COMPLETE_INT_ENA_S  7
+
+/* I2C_MST_TXFIFO_UDF_INT_ENA : R/W; bitpos: [6]; default: 0;
+ * The raw interrupt bit for I2C_TRANS_COMPLETE_INT interrupt.
+ */
+
+#define I2C_MST_TXFIFO_UDF_INT_ENA    (BIT(6))
+#define I2C_MST_TXFIFO_UDF_INT_ENA_M  (I2C_MST_TXFIFO_UDF_INT_ENA_V << I2C_MST_TXFIFO_UDF_INT_ENA_S)
+#define I2C_MST_TXFIFO_UDF_INT_ENA_V  0x00000001
+#define I2C_MST_TXFIFO_UDF_INT_ENA_S  6
+
+/* I2C_ARBITRATION_LOST_INT_ENA : R/W; bitpos: [5]; default: 0;
+ * The raw interrupt bit for the I2C_ARBITRATION_LOST_INT interrupt.
+ */
+
+#define I2C_ARBITRATION_LOST_INT_ENA    (BIT(5))
+#define I2C_ARBITRATION_LOST_INT_ENA_M  (I2C_ARBITRATION_LOST_INT_ENA_V << I2C_ARBITRATION_LOST_INT_ENA_S)
+#define I2C_ARBITRATION_LOST_INT_ENA_V  0x00000001
+#define I2C_ARBITRATION_LOST_INT_ENA_S  5
+
+/* I2C_BYTE_TRANS_DONE_INT_ENA : R/W; bitpos: [4]; default: 0;
+ * The raw interrupt bit for the I2C_END_DETECT_INT interrupt.
+ */
+
+#define I2C_BYTE_TRANS_DONE_INT_ENA    (BIT(4))
+#define I2C_BYTE_TRANS_DONE_INT_ENA_M  (I2C_BYTE_TRANS_DONE_INT_ENA_V << I2C_BYTE_TRANS_DONE_INT_ENA_S)
+#define I2C_BYTE_TRANS_DONE_INT_ENA_V  0x00000001
+#define I2C_BYTE_TRANS_DONE_INT_ENA_S  4
+
+/* I2C_END_DETECT_INT_ENA : R/W; bitpos: [3]; default: 0;
+ * The raw interrupt bit for the I2C_END_DETECT_INT interrupt.
+ */
+
+#define I2C_END_DETECT_INT_ENA    (BIT(3))
+#define I2C_END_DETECT_INT_ENA_M  (I2C_END_DETECT_INT_ENA_V << I2C_END_DETECT_INT_ENA_S)
+#define I2C_END_DETECT_INT_ENA_V  0x00000001
+#define I2C_END_DETECT_INT_ENA_S  3
+
+/* I2C_RXFIFO_OVF_INT_ENA : R/W; bitpos: [2]; default: 0;
+ * The raw interrupt bit for I2C_RXFIFO_OVF_INT interrupt.
+ */
+
+#define I2C_RXFIFO_OVF_INT_ENA    (BIT(2))
+#define I2C_RXFIFO_OVF_INT_ENA_M  (I2C_RXFIFO_OVF_INT_ENA_V << I2C_RXFIFO_OVF_INT_ENA_S)
+#define I2C_RXFIFO_OVF_INT_ENA_V  0x00000001
+#define I2C_RXFIFO_OVF_INT_ENA_S  2
+
+/* I2C_TXFIFO_WM_INT_ENA : R/W; bitpos: [1]; default: 0;
+ * The raw interrupt bit for I2C_TXFIFO_WM_INT interrupt.
+ */
+
+#define I2C_TXFIFO_WM_INT_ENA    (BIT(1))
+#define I2C_TXFIFO_WM_INT_ENA_M  (I2C_TXFIFO_WM_INT_ENA_V << I2C_TXFIFO_WM_INT_ENA_S)
+#define I2C_TXFIFO_WM_INT_ENA_V  0x00000001
+#define I2C_TXFIFO_WM_INT_ENA_S  1
+
+/* I2C_RXFIFO_WM_INT_ENA : R/W; bitpos: [0]; default: 0;
+ * The raw interrupt bit for I2C_RXFIFO_WM_INT interrupt.
+ */
+
+#define I2C_RXFIFO_WM_INT_ENA    (BIT(0))
+#define I2C_RXFIFO_WM_INT_ENA_M  (I2C_RXFIFO_WM_INT_ENA_V << I2C_RXFIFO_WM_INT_ENA_S)
+#define I2C_RXFIFO_WM_INT_ENA_V  0x00000001
+#define I2C_RXFIFO_WM_INT_ENA_S  0
+
+/* I2C_INT_STATUS_REG register
+ * Status of captured I2C communication events
+ */
+
+#define I2C_INT_STATUS_REG(i) (REG_I2C_BASE(i) + 0x2c)
+
+/* I2C_SLAVE_STRETCH_INT_ST : RO; bitpos: [16]; default: 0;
+ * The masked interrupt status bit for I2C_SLAVE_STRETCH_INT interrupt.
+ */
+
+#define I2C_SLAVE_STRETCH_INT_ST    (BIT(16))
+#define I2C_SLAVE_STRETCH_INT_ST_M  (I2C_SLAVE_STRETCH_INT_ST_V << I2C_SLAVE_STRETCH_INT_ST_S)
+#define I2C_SLAVE_STRETCH_INT_ST_V  0x00000001
+#define I2C_SLAVE_STRETCH_INT_ST_S  16
+
+/* I2C_DET_START_INT_ST : RO; bitpos: [15]; default: 0;
+ * The masked interrupt status bit for I2C_DET_START_INT interrupt.
+ */
+
+#define I2C_DET_START_INT_ST    (BIT(15))
+#define I2C_DET_START_INT_ST_M  (I2C_DET_START_INT_ST_V << I2C_DET_START_INT_ST_S)
+#define I2C_DET_START_INT_ST_V  0x00000001
+#define I2C_DET_START_INT_ST_S  15
+
+/* I2C_SCL_MAIN_ST_TO_INT_ST : RO; bitpos: [14]; default: 0;
+ * The masked interrupt status bit for I2C_SCL_MAIN_ST_TO_INT interrupt.
+ */
+
+#define I2C_SCL_MAIN_ST_TO_INT_ST    (BIT(14))
+#define I2C_SCL_MAIN_ST_TO_INT_ST_M  (I2C_SCL_MAIN_ST_TO_INT_ST_V << I2C_SCL_MAIN_ST_TO_INT_ST_S)
+#define I2C_SCL_MAIN_ST_TO_INT_ST_V  0x00000001
+#define I2C_SCL_MAIN_ST_TO_INT_ST_S  14
+
+/* I2C_SCL_ST_TO_INT_ST : RO; bitpos: [13]; default: 0;
+ * The masked interrupt status bit for I2C_SCL_ST_TO_INT interrupt.
+ */
+
+#define I2C_SCL_ST_TO_INT_ST    (BIT(13))
+#define I2C_SCL_ST_TO_INT_ST_M  (I2C_SCL_ST_TO_INT_ST_V << I2C_SCL_ST_TO_INT_ST_S)
+#define I2C_SCL_ST_TO_INT_ST_V  0x00000001
+#define I2C_SCL_ST_TO_INT_ST_S  13
+
+/* I2C_RXFIFO_UDF_INT_ST : RO; bitpos: [12]; default: 0;
+ * The masked interrupt status bit for I2C_RXFIFO_UDF_INT  interrupt.
+ */
+
+#define I2C_RXFIFO_UDF_INT_ST    (BIT(12))
+#define I2C_RXFIFO_UDF_INT_ST_M  (I2C_RXFIFO_UDF_INT_ST_V << I2C_RXFIFO_UDF_INT_ST_S)
+#define I2C_RXFIFO_UDF_INT_ST_V  0x00000001
+#define I2C_RXFIFO_UDF_INT_ST_S  12
+
+/* I2C_TXFIFO_OVF_INT_ST : RO; bitpos: [11]; default: 0;
+ * The masked interrupt status bit for I2C_TXFIFO_OVF_INT interrupt.
+ */
+
+#define I2C_TXFIFO_OVF_INT_ST    (BIT(11))
+#define I2C_TXFIFO_OVF_INT_ST_M  (I2C_TXFIFO_OVF_INT_ST_V << I2C_TXFIFO_OVF_INT_ST_S)
+#define I2C_TXFIFO_OVF_INT_ST_V  0x00000001
+#define I2C_TXFIFO_OVF_INT_ST_S  11
+
+/* I2C_NACK_INT_ST : RO; bitpos: [10]; default: 0;
+ * The masked interrupt status bit for I2C_SLAVE_STRETCH_INT interrupt.
+ */
+
+#define I2C_NACK_INT_ST    (BIT(10))
+#define I2C_NACK_INT_ST_M  (I2C_NACK_INT_ST_V << I2C_NACK_INT_ST_S)
+#define I2C_NACK_INT_ST_V  0x00000001
+#define I2C_NACK_INT_ST_S  10
+
+/* I2C_TRANS_START_INT_ST : RO; bitpos: [9]; default: 0;
+ * The masked interrupt status bit for the I2C_TRANS_START_INT interrupt.
+ */
+
+#define I2C_TRANS_START_INT_ST    (BIT(9))
+#define I2C_TRANS_START_INT_ST_M  (I2C_TRANS_START_INT_ST_V << I2C_TRANS_START_INT_ST_S)
+#define I2C_TRANS_START_INT_ST_V  0x00000001
+#define I2C_TRANS_START_INT_ST_S  9
+
+/* I2C_TIME_OUT_INT_ST : RO; bitpos: [8]; default: 0;
+ * The masked interrupt status bit for the I2C_TIME_OUT_INT interrupt.
+ */
+
+#define I2C_TIME_OUT_INT_ST    (BIT(8))
+#define I2C_TIME_OUT_INT_ST_M  (I2C_TIME_OUT_INT_ST_V << I2C_TIME_OUT_INT_ST_S)
+#define I2C_TIME_OUT_INT_ST_V  0x00000001
+#define I2C_TIME_OUT_INT_ST_S  8
+
+/* I2C_TRANS_COMPLETE_INT_ST : RO; bitpos: [7]; default: 0;
+ * The masked interrupt status bit for the I2C_TRANS_COMPLETE_INT interrupt.
+ */
+
+#define I2C_TRANS_COMPLETE_INT_ST    (BIT(7))
+#define I2C_TRANS_COMPLETE_INT_ST_M  (I2C_TRANS_COMPLETE_INT_ST_V << I2C_TRANS_COMPLETE_INT_ST_S)
+#define I2C_TRANS_COMPLETE_INT_ST_V  0x00000001
+#define I2C_TRANS_COMPLETE_INT_ST_S  7
+
+/* I2C_MST_TXFIFO_UDF_INT_ST : RO; bitpos: [6]; default: 0;
+ * The masked interrupt status bit for I2C_TRANS_COMPLETE_INT interrupt.
+ */
+
+#define I2C_MST_TXFIFO_UDF_INT_ST    (BIT(6))
+#define I2C_MST_TXFIFO_UDF_INT_ST_M  (I2C_MST_TXFIFO_UDF_INT_ST_V << I2C_MST_TXFIFO_UDF_INT_ST_S)
+#define I2C_MST_TXFIFO_UDF_INT_ST_V  0x00000001
+#define I2C_MST_TXFIFO_UDF_INT_ST_S  6
+
+/* I2C_ARBITRATION_LOST_INT_ST : RO; bitpos: [5]; default: 0;
+ * The masked interrupt status bit for the I2C_ARBITRATION_LOST_INT
+ * interrupt.
+ */
+
+#define I2C_ARBITRATION_LOST_INT_ST    (BIT(5))
+#define I2C_ARBITRATION_LOST_INT_ST_M  (I2C_ARBITRATION_LOST_INT_ST_V << I2C_ARBITRATION_LOST_INT_ST_S)
+#define I2C_ARBITRATION_LOST_INT_ST_V  0x00000001
+#define I2C_ARBITRATION_LOST_INT_ST_S  5
+
+/* I2C_BYTE_TRANS_DONE_INT_ST : RO; bitpos: [4]; default: 0;
+ * The masked interrupt status bit for the I2C_END_DETECT_INT interrupt.
+ */
+
+#define I2C_BYTE_TRANS_DONE_INT_ST    (BIT(4))
+#define I2C_BYTE_TRANS_DONE_INT_ST_M  (I2C_BYTE_TRANS_DONE_INT_ST_V << I2C_BYTE_TRANS_DONE_INT_ST_S)
+#define I2C_BYTE_TRANS_DONE_INT_ST_V  0x00000001
+#define I2C_BYTE_TRANS_DONE_INT_ST_S  4
+
+/* I2C_END_DETECT_INT_ST : RO; bitpos: [3]; default: 0;
+ * The masked interrupt status bit for the I2C_END_DETECT_INT interrupt.
+ */
+
+#define I2C_END_DETECT_INT_ST    (BIT(3))
+#define I2C_END_DETECT_INT_ST_M  (I2C_END_DETECT_INT_ST_V << I2C_END_DETECT_INT_ST_S)
+#define I2C_END_DETECT_INT_ST_V  0x00000001
+#define I2C_END_DETECT_INT_ST_S  3
+
+/* I2C_RXFIFO_OVF_INT_ST : RO; bitpos: [2]; default: 0;
+ * The masked interrupt status bit for I2C_RXFIFO_OVF_INT interrupt.
+ */
+
+#define I2C_RXFIFO_OVF_INT_ST    (BIT(2))
+#define I2C_RXFIFO_OVF_INT_ST_M  (I2C_RXFIFO_OVF_INT_ST_V << I2C_RXFIFO_OVF_INT_ST_S)
+#define I2C_RXFIFO_OVF_INT_ST_V  0x00000001
+#define I2C_RXFIFO_OVF_INT_ST_S  2
+
+/* I2C_TXFIFO_WM_INT_ST : RO; bitpos: [1]; default: 0;
+ * The masked interrupt status bit for I2C_TXFIFO_WM_INT interrupt.
+ */
+
+#define I2C_TXFIFO_WM_INT_ST    (BIT(1))
+#define I2C_TXFIFO_WM_INT_ST_M  (I2C_TXFIFO_WM_INT_ST_V << I2C_TXFIFO_WM_INT_ST_S)
+#define I2C_TXFIFO_WM_INT_ST_V  0x00000001
+#define I2C_TXFIFO_WM_INT_ST_S  1
+
+/* I2C_RXFIFO_WM_INT_ST : RO; bitpos: [0]; default: 0;
+ * The masked interrupt status bit for I2C_RXFIFO_WM_INT interrupt.
+ */
+
+#define I2C_RXFIFO_WM_INT_ST    (BIT(0))
+#define I2C_RXFIFO_WM_INT_ST_M  (I2C_RXFIFO_WM_INT_ST_V << I2C_RXFIFO_WM_INT_ST_S)
+#define I2C_RXFIFO_WM_INT_ST_V  0x00000001
+#define I2C_RXFIFO_WM_INT_ST_S  0
+
+/* I2C_SDA_HOLD_REG register
+ * Configures the hold time after a negative SCL edge
+ */
+
+#define I2C_SDA_HOLD_REG(i) (REG_I2C_BASE(i) + 0x30)
+
+/* I2C_SDA_HOLD_TIME : R/W; bitpos: [9:0]; default: 0;
+ * This register is used to configure the interval between changing the SDA
+ * output level and the falling edge of SCL, in I2C module clock cycles.
+ */
+
+#define I2C_SDA_HOLD_TIME    0x000003ff
+#define I2C_SDA_HOLD_TIME_M  (I2C_SDA_HOLD_TIME_V << I2C_SDA_HOLD_TIME_S)
+#define I2C_SDA_HOLD_TIME_V  0x000003ff
+#define I2C_SDA_HOLD_TIME_S  0
+
+/* I2C_SDA_SAMPLE_REG register
+ * Configures the sample time after a positive SCL edge
+ */
+
+#define I2C_SDA_SAMPLE_REG(i) (REG_I2C_BASE(i) + 0x34)
+
+/* I2C_SDA_SAMPLE_TIME : R/W; bitpos: [9:0]; default: 0;
+ * This register is used to configure the interval between the rising edge
+ * of SCL and the level sampling time of SDA, in I2C module clock cycles.
+ */
+
+#define I2C_SDA_SAMPLE_TIME    0x000003ff
+#define I2C_SDA_SAMPLE_TIME_M  (I2C_SDA_SAMPLE_TIME_V << I2C_SDA_SAMPLE_TIME_S)
+#define I2C_SDA_SAMPLE_TIME_V  0x000003ff
+#define I2C_SDA_SAMPLE_TIME_S  0
+
+/* I2C_SCL_HIGH_PERIOD_REG register
+ * Configures the high level width of the SCL clock
+ */
+
+#define I2C_SCL_HIGH_PERIOD_REG(i) (REG_I2C_BASE(i) + 0x38)
+
+/* I2C_SCL_WAIT_HIGH_PERIOD : R/W; bitpos: [27:14]; default: 0;
+ * This register is used to configure for the SCL_FSM's waiting period for
+ * SCL to go high in master mode, in I2C module clock cycles.
+ */
+
+#define I2C_SCL_WAIT_HIGH_PERIOD    0x00003fff
+#define I2C_SCL_WAIT_HIGH_PERIOD_M  (I2C_SCL_WAIT_HIGH_PERIOD_V << I2C_SCL_WAIT_HIGH_PERIOD_S)
+#define I2C_SCL_WAIT_HIGH_PERIOD_V  0x00003fff
+#define I2C_SCL_WAIT_HIGH_PERIOD_S  14
+
+/* I2C_SCL_HIGH_PERIOD : R/W; bitpos: [13:0]; default: 0;
+ * This register is used to configure for how long SCL remains high in
+ * master mode, in I2C module clock cycles.
+ */
+
+#define I2C_SCL_HIGH_PERIOD    0x00003fff
+#define I2C_SCL_HIGH_PERIOD_M  (I2C_SCL_HIGH_PERIOD_V << I2C_SCL_HIGH_PERIOD_S)
+#define I2C_SCL_HIGH_PERIOD_V  0x00003fff
+#define I2C_SCL_HIGH_PERIOD_S  0
+
+/* I2C_SCL_START_HOLD_REG register
+ * Configures the interval between pulling SDA low and pulling SCL low when
+ * the master generates a START condition
+ */
+
+#define I2C_SCL_START_HOLD_REG(i) (REG_I2C_BASE(i) + 0x40)
+
+/* I2C_SCL_START_HOLD_TIME : R/W; bitpos: [9:0]; default: 8;
+ * This register is used to configure  interval between pulling SDA low and
+ * pulling SCL low when the master generates a START condition, in I2C
+ * module clock cycles.
+ */
+
+#define I2C_SCL_START_HOLD_TIME    0x000003ff
+#define I2C_SCL_START_HOLD_TIME_M  (I2C_SCL_START_HOLD_TIME_V << I2C_SCL_START_HOLD_TIME_S)
+#define I2C_SCL_START_HOLD_TIME_V  0x000003ff
+#define I2C_SCL_START_HOLD_TIME_S  0
+
+/* I2C_SCL_RSTART_SETUP_REG register
+ * Configures the interval between the positive edge of SCL and the negative
+ * edge of SDA
+ */
+
+#define I2C_SCL_RSTART_SETUP_REG(i) (REG_I2C_BASE(i) + 0x44)
+
+/* I2C_SCL_RSTART_SETUP_TIME : R/W; bitpos: [9:0]; default: 8;
+ * This register is used to configure the interval between the positive edge
+ * of SCL and the negative edge of SDA for a RESTART condition, in I2C
+ * module clock cycles.
+ */
+
+#define I2C_SCL_RSTART_SETUP_TIME    0x000003ff
+#define I2C_SCL_RSTART_SETUP_TIME_M  (I2C_SCL_RSTART_SETUP_TIME_V << I2C_SCL_RSTART_SETUP_TIME_S)
+#define I2C_SCL_RSTART_SETUP_TIME_V  0x000003ff
+#define I2C_SCL_RSTART_SETUP_TIME_S  0
+
+/* I2C_SCL_STOP_HOLD_REG register
+ * Configures the delay after the SCL clock edge for a stop condition
+ */
+
+#define I2C_SCL_STOP_HOLD_REG(i) (REG_I2C_BASE(i) + 0x48)
+
+/* I2C_SCL_STOP_HOLD_TIME : R/W; bitpos: [13:0]; default: 0;
+ * This register is used to configure the delay after the STOP condition, in
+ * I2C module clock cycles.
+ */
+
+#define I2C_SCL_STOP_HOLD_TIME    0x00003fff
+#define I2C_SCL_STOP_HOLD_TIME_M  (I2C_SCL_STOP_HOLD_TIME_V << I2C_SCL_STOP_HOLD_TIME_S)
+#define I2C_SCL_STOP_HOLD_TIME_V  0x00003fff
+#define I2C_SCL_STOP_HOLD_TIME_S  0
+
+/* I2C_SCL_STOP_SETUP_REG register
+ * Configures the delay between the SDA and SCL positive edge for a stop
+ * condition
+ */
+
+#define I2C_SCL_STOP_SETUP_REG(i) (REG_I2C_BASE(i) + 0x4c)
+
+/* I2C_SCL_STOP_SETUP_TIME : R/W; bitpos: [9:0]; default: 0;
+ * This register is used to configure the time between the positive edge of
+ * SCL and the positive edge of SDA, in I2C module clock cycles.
+ */
+
+#define I2C_SCL_STOP_SETUP_TIME    0x000003ff
+#define I2C_SCL_STOP_SETUP_TIME_M  (I2C_SCL_STOP_SETUP_TIME_V << I2C_SCL_STOP_SETUP_TIME_S)
+#define I2C_SCL_STOP_SETUP_TIME_V  0x000003ff
+#define I2C_SCL_STOP_SETUP_TIME_S  0
+
+/* I2C_SCL_FILTER_CFG_REG register
+ * SCL filter configuration register
+ */
+
+#define I2C_SCL_FILTER_CFG_REG(i) (REG_I2C_BASE(i) + 0x50)
+
+/* I2C_SCL_FILTER_EN : R/W; bitpos: [4]; default: 1;
+ * This is the filter enable bit for SCL.
+ */
+
+#define I2C_SCL_FILTER_EN    (BIT(4))
+#define I2C_SCL_FILTER_EN_M  (I2C_SCL_FILTER_EN_V << I2C_SCL_FILTER_EN_S)
+#define I2C_SCL_FILTER_EN_V  0x00000001
+#define I2C_SCL_FILTER_EN_S  4
+
+/* I2C_SCL_FILTER_THRES : R/W; bitpos: [3:0]; default: 0;
+ * When a pulse on the SCL input has smaller width than this register value
+ * in I2C module clock cycles, the I2C controller will ignore that pulse.
+ */
+
+#define I2C_SCL_FILTER_THRES    0x0000000f
+#define I2C_SCL_FILTER_THRES_M  (I2C_SCL_FILTER_THRES_V << I2C_SCL_FILTER_THRES_S)
+#define I2C_SCL_FILTER_THRES_V  0x0000000f
+#define I2C_SCL_FILTER_THRES_S  0
+
+/* I2C_SDA_FILTER_CFG_REG register
+ * SDA filter configuration register
+ */
+
+#define I2C_SDA_FILTER_CFG_REG(i) (REG_I2C_BASE(i) + 0x54)
+
+/* I2C_SDA_FILTER_EN : R/W; bitpos: [4]; default: 1;
+ * This is the filter enable bit for SDA.
+ */
+
+#define I2C_SDA_FILTER_EN    (BIT(4))
+#define I2C_SDA_FILTER_EN_M  (I2C_SDA_FILTER_EN_V << I2C_SDA_FILTER_EN_S)
+#define I2C_SDA_FILTER_EN_V  0x00000001
+#define I2C_SDA_FILTER_EN_S  4
+
+/* I2C_SDA_FILTER_THRES : R/W; bitpos: [3:0]; default: 0;
+ * When a pulse on the SDA input has smaller width than this register value
+ * in I2C module clock cycles, the I2C controller will ignore that pulse.
+ */
+
+#define I2C_SDA_FILTER_THRES    0x0000000f
+#define I2C_SDA_FILTER_THRES_M  (I2C_SDA_FILTER_THRES_V << I2C_SDA_FILTER_THRES_S)
+#define I2C_SDA_FILTER_THRES_V  0x0000000f
+#define I2C_SDA_FILTER_THRES_S  0
+
+/* I2C_COMD0_REG register
+ * I2C command register 0
+ */
+
+#define I2C_COMD0_REG(i) (REG_I2C_BASE(i) + 0x58)
+
+/* I2C_COMMAND0_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 0 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND0_DONE    (BIT(31))
+#define I2C_COMMAND0_DONE_M  (I2C_COMMAND0_DONE_V << I2C_COMMAND0_DONE_S)
+#define I2C_COMMAND0_DONE_V  0x00000001
+#define I2C_COMMAND0_DONE_S  31
+
+/* I2C_COMMAND0 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 0. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND0    0x00003fff
+#define I2C_COMMAND0_M  (I2C_COMMAND0_V << I2C_COMMAND0_S)
+#define I2C_COMMAND0_V  0x00003fff
+#define I2C_COMMAND0_S  0
+
+/* I2C_COMD1_REG register
+ * I2C command register 1
+ */
+
+#define I2C_COMD1_REG(i) (REG_I2C_BASE(i) + 0x5c)
+
+/* I2C_COMMAND1_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 1 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND1_DONE    (BIT(31))
+#define I2C_COMMAND1_DONE_M  (I2C_COMMAND1_DONE_V << I2C_COMMAND1_DONE_S)
+#define I2C_COMMAND1_DONE_V  0x00000001
+#define I2C_COMMAND1_DONE_S  31
+
+/* I2C_COMMAND1 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 1. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND1    0x00003fff
+#define I2C_COMMAND1_M  (I2C_COMMAND1_V << I2C_COMMAND1_S)
+#define I2C_COMMAND1_V  0x00003fff
+#define I2C_COMMAND1_S  0
+
+/* I2C_COMD2_REG register
+ * I2C command register 2
+ */
+
+#define I2C_COMD2_REG(i) (REG_I2C_BASE(i) + 0x60)
+
+/* I2C_COMMAND2_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 2 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND2_DONE    (BIT(31))
+#define I2C_COMMAND2_DONE_M  (I2C_COMMAND2_DONE_V << I2C_COMMAND2_DONE_S)
+#define I2C_COMMAND2_DONE_V  0x00000001
+#define I2C_COMMAND2_DONE_S  31
+
+/* I2C_COMMAND2 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 2. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND2    0x00003fff
+#define I2C_COMMAND2_M  (I2C_COMMAND2_V << I2C_COMMAND2_S)
+#define I2C_COMMAND2_V  0x00003fff
+#define I2C_COMMAND2_S  0
+
+/* I2C_COMD3_REG register
+ * I2C command register 3
+ */
+
+#define I2C_COMD3_REG(i) (REG_I2C_BASE(i) + 0x64)
+
+/* I2C_COMMAND3_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 3 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND3_DONE    (BIT(31))
+#define I2C_COMMAND3_DONE_M  (I2C_COMMAND3_DONE_V << I2C_COMMAND3_DONE_S)
+#define I2C_COMMAND3_DONE_V  0x00000001
+#define I2C_COMMAND3_DONE_S  31
+
+/* I2C_COMMAND3 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 3. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND3    0x00003fff
+#define I2C_COMMAND3_M  (I2C_COMMAND3_V << I2C_COMMAND3_S)
+#define I2C_COMMAND3_V  0x00003fff
+#define I2C_COMMAND3_S  0
+
+/* I2C_COMD4_REG register
+ * I2C command register 4
+ */
+
+#define I2C_COMD4_REG(i) (REG_I2C_BASE(i) + 0x68)
+
+/* I2C_COMMAND4_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 4 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND4_DONE    (BIT(31))
+#define I2C_COMMAND4_DONE_M  (I2C_COMMAND4_DONE_V << I2C_COMMAND4_DONE_S)
+#define I2C_COMMAND4_DONE_V  0x00000001
+#define I2C_COMMAND4_DONE_S  31
+
+/* I2C_COMMAND4 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 4. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND4    0x00003fff
+#define I2C_COMMAND4_M  (I2C_COMMAND4_V << I2C_COMMAND4_S)
+#define I2C_COMMAND4_V  0x00003fff
+#define I2C_COMMAND4_S  0
+
+/* I2C_COMD5_REG register
+ * I2C command register 5
+ */
+
+#define I2C_COMD5_REG(i) (REG_I2C_BASE(i) + 0x6c)
+
+/* I2C_COMMAND5_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 5 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND5_DONE    (BIT(31))
+#define I2C_COMMAND5_DONE_M  (I2C_COMMAND5_DONE_V << I2C_COMMAND5_DONE_S)
+#define I2C_COMMAND5_DONE_V  0x00000001
+#define I2C_COMMAND5_DONE_S  31
+
+/* I2C_COMMAND5 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 5. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND5    0x00003fff
+#define I2C_COMMAND5_M  (I2C_COMMAND5_V << I2C_COMMAND5_S)
+#define I2C_COMMAND5_V  0x00003fff
+#define I2C_COMMAND5_S  0
+
+/* I2C_COMD6_REG register
+ * I2C command register 6
+ */
+
+#define I2C_COMD6_REG(i) (REG_I2C_BASE(i) + 0x70)
+
+/* I2C_COMMAND6_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 6 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND6_DONE    (BIT(31))
+#define I2C_COMMAND6_DONE_M  (I2C_COMMAND6_DONE_V << I2C_COMMAND6_DONE_S)
+#define I2C_COMMAND6_DONE_V  0x00000001
+#define I2C_COMMAND6_DONE_S  31
+
+/* I2C_COMMAND6 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 6. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND6    0x00003fff
+#define I2C_COMMAND6_M  (I2C_COMMAND6_V << I2C_COMMAND6_S)
+#define I2C_COMMAND6_V  0x00003fff
+#define I2C_COMMAND6_S  0
+
+/* I2C_COMD7_REG register
+ * I2C command register 7
+ */
+
+#define I2C_COMD7_REG(i) (REG_I2C_BASE(i) + 0x74)
+
+/* I2C_COMMAND7_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 7 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND7_DONE    (BIT(31))
+#define I2C_COMMAND7_DONE_M  (I2C_COMMAND7_DONE_V << I2C_COMMAND7_DONE_S)
+#define I2C_COMMAND7_DONE_V  0x00000001
+#define I2C_COMMAND7_DONE_S  31
+
+/* I2C_COMMAND7 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 7. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND7    0x00003fff
+#define I2C_COMMAND7_M  (I2C_COMMAND7_V << I2C_COMMAND7_S)
+#define I2C_COMMAND7_V  0x00003fff
+#define I2C_COMMAND7_S  0
+
+/* I2C_COMD8_REG register
+ * I2C command register 8
+ */
+
+#define I2C_COMD8_REG(i) (REG_I2C_BASE(i) + 0x78)
+
+/* I2C_COMMAND8_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 8 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND8_DONE    (BIT(31))
+#define I2C_COMMAND8_DONE_M  (I2C_COMMAND8_DONE_V << I2C_COMMAND8_DONE_S)
+#define I2C_COMMAND8_DONE_V  0x00000001
+#define I2C_COMMAND8_DONE_S  31
+
+/* I2C_COMMAND8 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 8. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND8    0x00003fff
+#define I2C_COMMAND8_M  (I2C_COMMAND8_V << I2C_COMMAND8_S)
+#define I2C_COMMAND8_V  0x00003fff
+#define I2C_COMMAND8_S  0
+
+/* I2C_COMD9_REG register
+ * I2C command register 9
+ */
+
+#define I2C_COMD9_REG(i) (REG_I2C_BASE(i) + 0x7c)
+
+/* I2C_COMMAND9_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 9 is done in I2C Master mode, this bit changes to high level.
+ */
+
+#define I2C_COMMAND9_DONE    (BIT(31))
+#define I2C_COMMAND9_DONE_M  (I2C_COMMAND9_DONE_V << I2C_COMMAND9_DONE_S)
+#define I2C_COMMAND9_DONE_V  0x00000001
+#define I2C_COMMAND9_DONE_S  31
+
+/* I2C_COMMAND9 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 9. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND9    0x00003fff
+#define I2C_COMMAND9_M  (I2C_COMMAND9_V << I2C_COMMAND9_S)
+#define I2C_COMMAND9_V  0x00003fff
+#define I2C_COMMAND9_S  0
+
+/* I2C_COMD10_REG register
+ * I2C command register 10
+ */
+
+#define I2C_COMD10_REG(i) (REG_I2C_BASE(i) + 0x80)
+
+/* I2C_COMMAND10_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 10 is done in I2C Master mode, this bit changes to high
+ * level.
+ */
+
+#define I2C_COMMAND10_DONE    (BIT(31))
+#define I2C_COMMAND10_DONE_M  (I2C_COMMAND10_DONE_V << I2C_COMMAND10_DONE_S)
+#define I2C_COMMAND10_DONE_V  0x00000001
+#define I2C_COMMAND10_DONE_S  31
+
+/* I2C_COMMAND10 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 10. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND10    0x00003fff
+#define I2C_COMMAND10_M  (I2C_COMMAND10_V << I2C_COMMAND10_S)
+#define I2C_COMMAND10_V  0x00003fff
+#define I2C_COMMAND10_S  0
+
+/* I2C_COMD11_REG register
+ * I2C command register 11
+ */
+
+#define I2C_COMD11_REG(i) (REG_I2C_BASE(i) + 0x84)
+
+/* I2C_COMMAND11_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 11 is done in I2C Master mode, this bit changes to high
+ * level.
+ */
+
+#define I2C_COMMAND11_DONE    (BIT(31))
+#define I2C_COMMAND11_DONE_M  (I2C_COMMAND11_DONE_V << I2C_COMMAND11_DONE_S)
+#define I2C_COMMAND11_DONE_V  0x00000001
+#define I2C_COMMAND11_DONE_S  31
+
+/* I2C_COMMAND11 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 11. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND11    0x00003fff
+#define I2C_COMMAND11_M  (I2C_COMMAND11_V << I2C_COMMAND11_S)
+#define I2C_COMMAND11_V  0x00003fff
+#define I2C_COMMAND11_S  0
+
+/* I2C_COMD12_REG register
+ * I2C command register 12
+ */
+
+#define I2C_COMD12_REG(i) (REG_I2C_BASE(i) + 0x88)
+
+/* I2C_COMMAND12_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 12 is done in I2C Master mode, this bit changes to high
+ * level.
+ */
+
+#define I2C_COMMAND12_DONE    (BIT(31))
+#define I2C_COMMAND12_DONE_M  (I2C_COMMAND12_DONE_V << I2C_COMMAND12_DONE_S)
+#define I2C_COMMAND12_DONE_V  0x00000001
+#define I2C_COMMAND12_DONE_S  31
+
+/* I2C_COMMAND12 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 12. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND12    0x00003fff
+#define I2C_COMMAND12_M  (I2C_COMMAND12_V << I2C_COMMAND12_S)
+#define I2C_COMMAND12_V  0x00003fff
+#define I2C_COMMAND12_S  0
+
+/* I2C_COMD13_REG register
+ * I2C command register 13
+ */
+
+#define I2C_COMD13_REG(i) (REG_I2C_BASE(i) + 0x8c)
+
+/* I2C_COMMAND13_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 13 is done in I2C Master mode, this bit changes to high
+ * level.
+ */
+
+#define I2C_COMMAND13_DONE    (BIT(31))
+#define I2C_COMMAND13_DONE_M  (I2C_COMMAND13_DONE_V << I2C_COMMAND13_DONE_S)
+#define I2C_COMMAND13_DONE_V  0x00000001
+#define I2C_COMMAND13_DONE_S  31
+
+/* I2C_COMMAND13 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 13. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND13    0x00003fff
+#define I2C_COMMAND13_M  (I2C_COMMAND13_V << I2C_COMMAND13_S)
+#define I2C_COMMAND13_V  0x00003fff
+#define I2C_COMMAND13_S  0
+
+/* I2C_COMD14_REG register
+ * I2C command register 14
+ */
+
+#define I2C_COMD14_REG(i) (REG_I2C_BASE(i) + 0x90)
+
+/* I2C_COMMAND14_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 14 is done in I2C Master mode, this bit changes to high
+ * level.
+ */
+
+#define I2C_COMMAND14_DONE    (BIT(31))
+#define I2C_COMMAND14_DONE_M  (I2C_COMMAND14_DONE_V << I2C_COMMAND14_DONE_S)
+#define I2C_COMMAND14_DONE_V  0x00000001
+#define I2C_COMMAND14_DONE_S  31
+
+/* I2C_COMMAND14 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 14. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND14    0x00003fff
+#define I2C_COMMAND14_M  (I2C_COMMAND14_V << I2C_COMMAND14_S)
+#define I2C_COMMAND14_V  0x00003fff
+#define I2C_COMMAND14_S  0
+
+/* I2C_COMD15_REG register
+ * I2C command register 15
+ */
+
+#define I2C_COMD15_REG(i) (REG_I2C_BASE(i) + 0x94)
+
+/* I2C_COMMAND15_DONE : R/W; bitpos: [31]; default: 0;
+ * When command 15 is done in I2C Master mode, this bit changes to high
+ * level.
+ */
+
+#define I2C_COMMAND15_DONE    (BIT(31))
+#define I2C_COMMAND15_DONE_M  (I2C_COMMAND15_DONE_V << I2C_COMMAND15_DONE_S)
+#define I2C_COMMAND15_DONE_V  0x00000001
+#define I2C_COMMAND15_DONE_S  31
+
+/* I2C_COMMAND15 : R/W; bitpos: [13:0]; default: 0;
+ * This is the content of command 15. It consists of three parts:
+ *
+ * op_code is the command, 0: RSTART. 1: WRITE. 2: READ. 3: STOP. 4: END.
+ *
+ * byte_num represents the number of bytes that need to be sent or received.
+ *
+ * ack_check_en, ack_exp and ack are used to control the ACK bit. See I2C
+ * cmd structure for more information.
+ */
+
+#define I2C_COMMAND15    0x00003fff
+#define I2C_COMMAND15_M  (I2C_COMMAND15_V << I2C_COMMAND15_S)
+#define I2C_COMMAND15_V  0x00003fff
+#define I2C_COMMAND15_S  0
+
+/* I2C_SCL_ST_TIME_OUT_REG register
+ * SCL status time out register
+ */
+
+#define I2C_SCL_ST_TIME_OUT_REG(i) (REG_I2C_BASE(i) + 0x98)
+
+/* I2C_SCL_ST_TO : R/W; bitpos: [23:0]; default: 256;
+ * The threshold value of SCL_FSM state unchanged period.
+ */
+
+#define I2C_SCL_ST_TO    0x00ffffff
+#define I2C_SCL_ST_TO_M  (I2C_SCL_ST_TO_V << I2C_SCL_ST_TO_S)
+#define I2C_SCL_ST_TO_V  0x00ffffff
+#define I2C_SCL_ST_TO_S  0
+
+/* I2C_SCL_MAIN_ST_TIME_OUT_REG register
+ * SCL main status time out register
+ */
+
+#define I2C_SCL_MAIN_ST_TIME_OUT_REG(i) (REG_I2C_BASE(i) + 0x9c)
+
+/* I2C_SCL_MAIN_ST_TO : R/W; bitpos: [23:0]; default: 256;
+ * The threshold value of SCL_MAIN_FSM state unchanged period.
+ */
+
+#define I2C_SCL_MAIN_ST_TO    0x00ffffff
+#define I2C_SCL_MAIN_ST_TO_M  (I2C_SCL_MAIN_ST_TO_V << I2C_SCL_MAIN_ST_TO_S)
+#define I2C_SCL_MAIN_ST_TO_V  0x00ffffff
+#define I2C_SCL_MAIN_ST_TO_S  0
+
+/* I2C_SCL_SP_CONF_REG register
+ * Power configuration register
+ */
+
+#define I2C_SCL_SP_CONF_REG(i) (REG_I2C_BASE(i) + 0xa0)
+
+/* I2C_SDA_PD_EN : R/W; bitpos: [7]; default: 0;
+ * The power down enable bit for the I2C output SDA line. 1: Power down. 0:
+ * Not power down. Set I2C_SDA_FORCE_OUT and I2C_SDA_PD_EN to 1 to stretch
+ * SDA low.
+ */
+
+#define I2C_SDA_PD_EN    (BIT(7))
+#define I2C_SDA_PD_EN_M  (I2C_SDA_PD_EN_V << I2C_SDA_PD_EN_S)
+#define I2C_SDA_PD_EN_V  0x00000001
+#define I2C_SDA_PD_EN_S  7
+
+/* I2C_SCL_PD_EN : R/W; bitpos: [6]; default: 0;
+ * The power down enable bit for the I2C output SCL line. 1: Power down. 0:
+ * Not power down. Set I2C_SCL_FORCE_OUT and I2C_SCL_PD_EN to 1 to stretch
+ * SCL low.
+ */
+
+#define I2C_SCL_PD_EN    (BIT(6))
+#define I2C_SCL_PD_EN_M  (I2C_SCL_PD_EN_V << I2C_SCL_PD_EN_S)
+#define I2C_SCL_PD_EN_V  0x00000001
+#define I2C_SCL_PD_EN_S  6
+
+/* I2C_SCL_RST_SLV_NUM : R/W; bitpos: [5:1]; default: 0;
+ * Configure the pulses of SCL generated in I2C master mode. Valid when
+ * I2C_SCL_RST_SLV_EN is 1.
+ */
+
+#define I2C_SCL_RST_SLV_NUM    0x0000001f
+#define I2C_SCL_RST_SLV_NUM_M  (I2C_SCL_RST_SLV_NUM_V << I2C_SCL_RST_SLV_NUM_S)
+#define I2C_SCL_RST_SLV_NUM_V  0x0000001f
+#define I2C_SCL_RST_SLV_NUM_S  1
+
+/* I2C_SCL_RST_SLV_EN : R/W; bitpos: [0]; default: 0;
+ * When I2C master is IDLE, set this bit to send out SCL pulses. The number
+ * of pulses equals to I2C_SCL_RST_SLV_NUM[4:0].
+ */
+
+#define I2C_SCL_RST_SLV_EN    (BIT(0))
+#define I2C_SCL_RST_SLV_EN_M  (I2C_SCL_RST_SLV_EN_V << I2C_SCL_RST_SLV_EN_S)
+#define I2C_SCL_RST_SLV_EN_V  0x00000001
+#define I2C_SCL_RST_SLV_EN_S  0
+
+/* I2C_SCL_STRETCH_CONF_REG register
+ * Set SCL stretch of I2C slave
+ */
+
+#define I2C_SCL_STRETCH_CONF_REG(i) (REG_I2C_BASE(i) + 0xa4)
+
+/* I2C_SLAVE_SCL_STRETCH_CLR : WO; bitpos: [11]; default: 0;
+ * Set this bit to clear the I2C slave SCL stretch function.
+ */
+
+#define I2C_SLAVE_SCL_STRETCH_CLR    (BIT(11))
+#define I2C_SLAVE_SCL_STRETCH_CLR_M  (I2C_SLAVE_SCL_STRETCH_CLR_V << I2C_SLAVE_SCL_STRETCH_CLR_S)
+#define I2C_SLAVE_SCL_STRETCH_CLR_V  0x00000001
+#define I2C_SLAVE_SCL_STRETCH_CLR_S  11
+
+/* I2C_SLAVE_SCL_STRETCH_EN : R/W; bitpos: [10]; default: 0;
+ * The enable bit for slave SCL stretch function. 1: Enable. 0: Disable. The
+ * SCL output line will be stretched low when I2C_SLAVE_SCL_STRETCH_EN is 1
+ * and stretch event happens. The stretch cause can be seen in
+ * I2C_STRETCH_CAUSE.
+ */
+
+#define I2C_SLAVE_SCL_STRETCH_EN    (BIT(10))
+#define I2C_SLAVE_SCL_STRETCH_EN_M  (I2C_SLAVE_SCL_STRETCH_EN_V << I2C_SLAVE_SCL_STRETCH_EN_S)
+#define I2C_SLAVE_SCL_STRETCH_EN_V  0x00000001
+#define I2C_SLAVE_SCL_STRETCH_EN_S  10
+
+/* I2C_STRETCH_PROTECT_NUM : R/W; bitpos: [9:0]; default: 0;
+ * Configure the period of I2C slave stretching SCL line.
+ */
+
+#define I2C_STRETCH_PROTECT_NUM    0x000003ff
+#define I2C_STRETCH_PROTECT_NUM_M  (I2C_STRETCH_PROTECT_NUM_V << I2C_STRETCH_PROTECT_NUM_S)
+#define I2C_STRETCH_PROTECT_NUM_V  0x000003ff
+#define I2C_STRETCH_PROTECT_NUM_S  0
+
+/* I2C_DATE_REG register
+ * Version control register
+ */
+
+#define I2C_DATE_REG(i) (REG_I2C_BASE(i) + 0xf8)
+
+/* I2C_DATE : R/W; bitpos: [31:0]; default: 419766272;
+ * This is the the version control register.
+ */
+
+#define I2C_DATE    0xffffffff
+#define I2C_DATE_M  (I2C_DATE_V << I2C_DATE_S)
+#define I2C_DATE_V  0xffffffff
+#define I2C_DATE_S  0
+
+#endif /* __ARCH_XTENSA_SRC_ESP32S2_HARDWARE_ESP32S2_I2C_H */
diff --git a/arch/xtensa/src/esp32s2/hardware/esp32s2_soc.h b/arch/xtensa/src/esp32s2/hardware/esp32s2_soc.h
index 4850a3a128..9276d98d7a 100644
--- a/arch/xtensa/src/esp32s2/hardware/esp32s2_soc.h
+++ b/arch/xtensa/src/esp32s2/hardware/esp32s2_soc.h
@@ -190,7 +190,7 @@
 
 /* Helper to place a value in a field */
 
-#define VALUE_TO_FIELD(_value, _field) ((_value << (_field##_S)) & (_field##_M))
+#define VALUE_TO_FIELD(_value, _field) (((_value) << (_field##_S)) & (_field##_M))
 
 /* Periheral Clock */
 
diff --git a/arch/xtensa/src/esp32s2/hardware/esp32s2_system.h b/arch/xtensa/src/esp32s2/hardware/esp32s2_system.h
index 884298bc19..60351db7ad 100644
--- a/arch/xtensa/src/esp32s2/hardware/esp32s2_system.h
+++ b/arch/xtensa/src/esp32s2/hardware/esp32s2_system.h
@@ -80,9 +80,9 @@
  * This field is used to force on clock gate of internal SRAM.
  */
 
-#define SYSTEM_SRAM_FO    0x003FFFFF
+#define SYSTEM_SRAM_FO    0x003fffff
 #define SYSTEM_SRAM_FO_M  (SYSTEM_SRAM_FO_V << SYSTEM_SRAM_FO_S)
-#define SYSTEM_SRAM_FO_V  0x003FFFFF
+#define SYSTEM_SRAM_FO_V  0x003fffff
 #define SYSTEM_SRAM_FO_S  0
 
 /* SYSTEM_SRAM_CTRL_1_REG register
@@ -95,9 +95,9 @@
  * This field is used to power down internal SRAM.
  */
 
-#define SYSTEM_SRAM_FORCE_PD    0x003FFFFF
+#define SYSTEM_SRAM_FORCE_PD    0x003fffff
 #define SYSTEM_SRAM_FORCE_PD_M  (SYSTEM_SRAM_FORCE_PD_V << SYSTEM_SRAM_FORCE_PD_S)
-#define SYSTEM_SRAM_FORCE_PD_V  0x003FFFFF
+#define SYSTEM_SRAM_FORCE_PD_V  0x003fffff
 #define SYSTEM_SRAM_FORCE_PD_S  0
 
 /* SYSTEM_CPU_PERI_CLK_EN_REG register
@@ -135,16 +135,15 @@
  */
 
 #define SYSTEM_CPU_PER_CONF_REG (DR_REG_SYSTEM_BASE + 0x18)
-#define DPORT_CPU_PER_CONF_REG  (DR_REG_SYSTEM_BASE + 0x018) /* old name */
 
 /* SYSTEM_CPU_WAITI_DELAY_NUM : R/W; bitpos: [7:4]; default: 0;
  * Sets the number of delay cycles to enter CPU wait mode after a WAITI
  * instruction.
  */
 
-#define SYSTEM_CPU_WAITI_DELAY_NUM    0x0000000F
+#define SYSTEM_CPU_WAITI_DELAY_NUM    0x0000000f
 #define SYSTEM_CPU_WAITI_DELAY_NUM_M  (SYSTEM_CPU_WAITI_DELAY_NUM_V << SYSTEM_CPU_WAITI_DELAY_NUM_S)
-#define SYSTEM_CPU_WAITI_DELAY_NUM_V  0x0000000F
+#define SYSTEM_CPU_WAITI_DELAY_NUM_V  0x0000000f
 #define SYSTEM_CPU_WAITI_DELAY_NUM_S  4
 
 /* SYSTEM_CPU_WAIT_MODE_FORCE_ON : R/W; bitpos: [3]; default: 1;
@@ -188,9 +187,9 @@
  * temporary disable of eFuse to JTAG.
  */
 
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_0    0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_0    0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_0_M  (SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_0_V << SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_0_S)
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_0_V  0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_0_V  0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_0_S  0
 
 /* SYSTEM_JTAG_CTRL_1_REG register
@@ -205,9 +204,9 @@
  * temporary disable of eFuse to JTAG.
  */
 
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_1    0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_1    0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_1_M  (SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_1_V << SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_1_S)
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_1_V  0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_1_V  0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_1_S  0
 
 /* SYSTEM_JTAG_CTRL_2_REG register
@@ -222,9 +221,9 @@
  * temporary disable of eFuse to JTAG.
  */
 
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_2    0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_2    0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_2_M  (SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_2_V << SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_2_S)
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_2_V  0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_2_V  0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_2_S  0
 
 /* SYSTEM_JTAG_CTRL_3_REG register
@@ -239,9 +238,9 @@
  * temporary disable of eFuse to JTAG.
  */
 
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_3    0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_3    0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_3_M  (SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_3_V << SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_3_S)
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_3_V  0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_3_V  0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_3_S  0
 
 /* SYSTEM_JTAG_CTRL_4_REG register
@@ -256,9 +255,9 @@
  * temporary disable of eFuse to JTAG.
  */
 
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_4    0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_4    0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_4_M  (SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_4_V << SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_4_S)
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_4_V  0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_4_V  0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_4_S  0
 
 /* SYSTEM_JTAG_CTRL_5_REG register
@@ -273,9 +272,9 @@
  * temporary disable of eFuse to JTAG.
  */
 
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_5    0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_5    0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_5_M  (SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_5_V << SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_5_S)
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_5_V  0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_5_V  0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_5_S  0
 
 /* SYSTEM_JTAG_CTRL_6_REG register
@@ -290,9 +289,9 @@
  * temporary disable of eFuse to JTAG.
  */
 
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_6    0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_6    0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_6_M  (SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_6_V << SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_6_S)
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_6_V  0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_6_V  0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_6_S  0
 
 /* SYSTEM_JTAG_CTRL_7_REG register
@@ -307,9 +306,9 @@
  * temporary disable of eFuse to JTAG.
  */
 
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_7    0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_7    0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_7_M  (SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_7_V << SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_7_S)
-#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_7_V  0xFFFFFFFF
+#define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_7_V  0xffffffff
 #define SYSTEM_CANCEL_EFUSE_DISABLE_JTAG_TEMPORARY_7_S  0
 
 /* SYSTEM_MEM_PD_MASK_REG register
@@ -1043,12 +1042,12 @@
 #define SYSTEM_LPCK_DIV_INT_REG (DR_REG_SYSTEM_BASE + 0x50)
 
 /* SYSTEM_LPCK_DIV_NUM : R/W; bitpos: [11:0]; default: 255;
- * This register is used to set the integer number of divider.
+ * This field is used to set the integer number of the divider value.
  */
 
-#define SYSTEM_LPCK_DIV_NUM    0x00000FFF
+#define SYSTEM_LPCK_DIV_NUM    0x00000fff
 #define SYSTEM_LPCK_DIV_NUM_M  (SYSTEM_LPCK_DIV_NUM_V << SYSTEM_LPCK_DIV_NUM_S)
-#define SYSTEM_LPCK_DIV_NUM_V  0x00000FFF
+#define SYSTEM_LPCK_DIV_NUM_V  0x00000fff
 #define SYSTEM_LPCK_DIV_NUM_S  0
 
 /* SYSTEM_BT_LPCK_DIV_FRAC_REG register
@@ -1313,18 +1312,18 @@
  * address.
  */
 
-#define SYSTEM_RTC_MEM_CRC_LEN    0x000007FF
+#define SYSTEM_RTC_MEM_CRC_LEN    0x000007ff
 #define SYSTEM_RTC_MEM_CRC_LEN_M  (SYSTEM_RTC_MEM_CRC_LEN_V << SYSTEM_RTC_MEM_CRC_LEN_S)
-#define SYSTEM_RTC_MEM_CRC_LEN_V  0x000007FF
+#define SYSTEM_RTC_MEM_CRC_LEN_V  0x000007ff
 #define SYSTEM_RTC_MEM_CRC_LEN_S  20
 
 /* SYSTEM_RTC_MEM_CRC_ADDR : R/W; bitpos: [19:9]; default: 0;
  * This field is used to set address of RTC memory for CRC.
  */
 
-#define SYSTEM_RTC_MEM_CRC_ADDR    0x000007FF
+#define SYSTEM_RTC_MEM_CRC_ADDR    0x000007ff
 #define SYSTEM_RTC_MEM_CRC_ADDR_M  (SYSTEM_RTC_MEM_CRC_ADDR_V << SYSTEM_RTC_MEM_CRC_ADDR_S)
-#define SYSTEM_RTC_MEM_CRC_ADDR_V  0x000007FF
+#define SYSTEM_RTC_MEM_CRC_ADDR_V  0x000007ff
 #define SYSTEM_RTC_MEM_CRC_ADDR_S  9
 
 /* SYSTEM_RTC_MEM_CRC_START : R/W; bitpos: [8]; default: 0;
@@ -1346,9 +1345,9 @@
  * This field stores the CRC result of RTC memory.
  */
 
-#define SYSTEM_RTC_MEM_CRC_RES    0xFFFFFFFF
+#define SYSTEM_RTC_MEM_CRC_RES    0xffffffff
 #define SYSTEM_RTC_MEM_CRC_RES_M  (SYSTEM_RTC_MEM_CRC_RES_V << SYSTEM_RTC_MEM_CRC_RES_S)
-#define SYSTEM_RTC_MEM_CRC_RES_V  0xFFFFFFFF
+#define SYSTEM_RTC_MEM_CRC_RES_V  0xffffffff
 #define SYSTEM_RTC_MEM_CRC_RES_S  0
 
 /* SYSTEM_Redundant_ECO_Ctrl_REG register
@@ -1400,9 +1399,9 @@
  * This field is used to power up internal SRAM.
  */
 
-#define SYSTEM_SRAM_FORCE_PU    0x003FFFFF
+#define SYSTEM_SRAM_FORCE_PU    0x003fffff
 #define SYSTEM_SRAM_FORCE_PU_M  (SYSTEM_SRAM_FORCE_PU_V << SYSTEM_SRAM_FORCE_PU_S)
-#define SYSTEM_SRAM_FORCE_PU_V  0x003FFFFF
+#define SYSTEM_SRAM_FORCE_PU_V  0x003fffff
 #define SYSTEM_SRAM_FORCE_PU_S  0
 
 /* SYSTEM_SYSCLK_CONF_REG register
@@ -1424,9 +1423,9 @@
  * This field is used to read XTAL frequency in MHz.
  */
 
-#define SYSTEM_CLK_XTAL_FREQ    0x0000007F
+#define SYSTEM_CLK_XTAL_FREQ    0x0000007f
 #define SYSTEM_CLK_XTAL_FREQ_M  (SYSTEM_CLK_XTAL_FREQ_V << SYSTEM_CLK_XTAL_FREQ_S)
-#define SYSTEM_CLK_XTAL_FREQ_V  0x0000007F
+#define SYSTEM_CLK_XTAL_FREQ_V  0x0000007f
 #define SYSTEM_CLK_XTAL_FREQ_S  12
 
 /* SYSTEM_SOC_CLK_SEL : R/W; bitpos: [11:10]; default: 0;
@@ -1442,24 +1441,24 @@
  * This field is used to set the count of prescaler of XTAL\_CLK.
  */
 
-#define SYSTEM_PRE_DIV_CNT    0x000003FF
+#define SYSTEM_PRE_DIV_CNT    0x000003ff
 #define SYSTEM_PRE_DIV_CNT_M  (SYSTEM_PRE_DIV_CNT_V << SYSTEM_PRE_DIV_CNT_S)
-#define SYSTEM_PRE_DIV_CNT_V  0x000003FF
+#define SYSTEM_PRE_DIV_CNT_V  0x000003ff
 #define SYSTEM_PRE_DIV_CNT_S  0
 
-/* SYSTEM_REG_DATE_REG register
+/* SYSTEM_DATE_REG register
  * Version control register
  */
 
-#define SYSTEM_REG_DATE_REG (DR_REG_SYSTEM_BASE + 0xffc)
+#define SYSTEM_DATE_REG (DR_REG_SYSTEM_BASE + 0xffc)
 
-/* SYSTEM_SYSTEM_REG_DATE : R/W; bitpos: [27:0]; default: 26247200;
- * This is the date version register.
+/* SYSTEM_DATE : R/W; bitpos: [27:0]; default: 26247200;
+ * Version control register.
  */
 
-#define SYSTEM_SYSTEM_REG_DATE    0x0FFFFFFF
-#define SYSTEM_SYSTEM_REG_DATE_M  (SYSTEM_SYSTEM_REG_DATE_V << SYSTEM_SYSTEM_REG_DATE_S)
-#define SYSTEM_SYSTEM_REG_DATE_V  0x0FFFFFFF
-#define SYSTEM_SYSTEM_REG_DATE_S  0
+#define SYSTEM_DATE    0x0fffffff
+#define SYSTEM_DATE_M  (SYSTEM_DATE_V << SYSTEM_DATE_S)
+#define SYSTEM_DATE_V  0x0fffffff
+#define SYSTEM_DATE_S  0
 
 #endif /* __ARCH_XTENSA_SRC_ESP32S2_HARDWARE_ESP32S2_SYSTEM_H */