diff options
-rw-r--r-- | chip/it83xx/build.mk | 3 | ||||
-rw-r--r-- | chip/it83xx/config_chip.h | 1 | ||||
-rw-r--r-- | chip/it83xx/i2c.c | 6 | ||||
-rw-r--r-- | chip/it83xx/i2c_slave.c | 320 | ||||
-rw-r--r-- | chip/it83xx/intc.c | 30 | ||||
-rw-r--r-- | chip/it83xx/intc.h | 3 | ||||
-rw-r--r-- | chip/it83xx/registers.h | 46 | ||||
-rw-r--r-- | core/nds32/ec.lds.S | 11 | ||||
-rw-r--r-- | include/i2c_slave.h | 21 |
9 files changed, 427 insertions, 14 deletions
diff --git a/chip/it83xx/build.mk b/chip/it83xx/build.mk index 365a993113..5ce2bc8397 100644 --- a/chip/it83xx/build.mk +++ b/chip/it83xx/build.mk @@ -24,4 +24,5 @@ chip-$(CONFIG_HOSTCMD_ESPI)+=espi.o chip-$(CONFIG_SPI_MASTER)+=spi_master.o chip-$(CONFIG_PECI)+=peci.o chip-$(HAS_TASK_KEYSCAN)+=keyboard_raw.o -chip-$(CONFIG_I2C)+=i2c.o +chip-$(CONFIG_I2C_MASTER)+=i2c.o +chip-$(CONFIG_I2C_SLAVE)+=i2c_slave.o diff --git a/chip/it83xx/config_chip.h b/chip/it83xx/config_chip.h index 2e71fb3ef6..d0edfe6eb9 100644 --- a/chip/it83xx/config_chip.h +++ b/chip/it83xx/config_chip.h @@ -27,6 +27,7 @@ * There are three i2c enhanced ports. */ #define I2C_STANDARD_PORT_COUNT 3 +#define I2C_ENHANCED_PORT_COUNT 3 /****************************************************************************/ /* Memory mapping */ diff --git a/chip/it83xx/i2c.c b/chip/it83xx/i2c.c index 56f805b9f6..48d13d5fdd 100644 --- a/chip/it83xx/i2c.c +++ b/chip/it83xx/i2c.c @@ -18,12 +18,6 @@ #define CPRINTS(format, args...) cprints(CC_I2C, format, ## args) -/* - * The count number of the counter for 25 ms register. - * The 25 ms register is calculated by (count number *1.024 kHz). - */ -#define I2C_CLK_LOW_TIMEOUT 255 /* ~=249 ms */ - /* Default maximum time we allow for an I2C transfer */ #define I2C_TIMEOUT_DEFAULT_US (100 * MSEC) diff --git a/chip/it83xx/i2c_slave.c b/chip/it83xx/i2c_slave.c new file mode 100644 index 0000000000..066ea6334a --- /dev/null +++ b/chip/it83xx/i2c_slave.c @@ -0,0 +1,320 @@ +/* Copyright 2019 The Chromium OS Authors. All rights reserved. + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +/* I2C module for Chrome EC */ + +#include "clock.h" +#include "compile_time_macros.h" +#include "console.h" +#include "gpio.h" +#include "hooks.h" +#include "i2c_slave.h" +#include "registers.h" +#include <stddef.h> +#include <string.h> +#include "task.h" + +/* Console output macros */ +#define CPRINTS(format, args...) cprints(CC_I2C, format, ## args) + +/* The size must be a power of 2 */ +#define I2C_MAX_BUFFER_SIZE 0x100 +#define I2C_SIZE_MASK (I2C_MAX_BUFFER_SIZE - 1) + +#define I2C_READ_MAXFIFO_DATA 16 +#define I2C_ENHANCED_CH_INTERVAL 0x80 + +/* Store master to slave data of channel D, E, F by DMA */ +static uint8_t in_data[I2C_ENHANCED_PORT_COUNT][I2C_MAX_BUFFER_SIZE] + __attribute__((section(".h2ram.pool.i2cslv"))); +/* Store slave to master data of channel D, E, F by DMA */ +static uint8_t out_data[I2C_ENHANCED_PORT_COUNT][I2C_MAX_BUFFER_SIZE] + __attribute__((section(".h2ram.pool.i2cslv"))); +/* Store read and write data of channel A by FIFO mode */ +static uint8_t pbuffer[I2C_MAX_BUFFER_SIZE]; + +static uint32_t w_index; +static uint32_t r_index; +static int wr_done[I2C_ENHANCED_PORT_COUNT]; + +void buffer_index_reset(void) +{ + /* Reset write buffer index */ + w_index = 0; + /* Reset read buffer index */ + r_index = 0; +} + +/* Data structure to define I2C slave control configuration. */ +struct i2c_slv_ctrl_t { + int irq; /* slave irq */ + /* offset from base 0x00F03500 register; -1 means unused. */ + int offset; + enum clock_gate_offsets clock_gate; + int dma_index; +}; + +/* I2C slave control */ +const struct i2c_slv_ctrl_t i2c_slv_ctrl[] = { + [IT83XX_I2C_CH_A] = {.irq = IT83XX_IRQ_SMB_A, .offset = -1, + .clock_gate = CGC_OFFSET_SMBA, .dma_index = -1}, + [IT83XX_I2C_CH_D] = {.irq = IT83XX_IRQ_SMB_D, .offset = 0x180, + .clock_gate = CGC_OFFSET_SMBD, .dma_index = 0}, + [IT83XX_I2C_CH_E] = {.irq = IT83XX_IRQ_SMB_E, .offset = 0x0, + .clock_gate = CGC_OFFSET_SMBE, .dma_index = 1}, + [IT83XX_I2C_CH_F] = {.irq = IT83XX_IRQ_SMB_F, .offset = 0x80, + .clock_gate = CGC_OFFSET_SMBF, .dma_index = 2}, +}; + +void i2c_slave_read_write_data(int port) +{ + int slv_status, i; + + /* I2C slave channel A FIFO mode */ + if (port < I2C_STANDARD_PORT_COUNT) { + int count; + + slv_status = IT83XX_SMB_SLSTA; + + /* bit0-4 : FIFO byte count */ + count = IT83XX_SMB_SFFSTA & 0x1F; + + /* Slave data register is waiting for read or write. */ + if (slv_status & IT83XX_SMB_SDS) { + /* Master to read data */ + if (slv_status & IT83XX_SMB_RCS) { + for (i = 0; i < I2C_READ_MAXFIFO_DATA; i++) + /* Return buffer data to master */ + IT83XX_SMB_SLDA = + pbuffer[(i + r_index) & I2C_SIZE_MASK]; + + /* Index to next 16 bytes of read buffer */ + r_index += I2C_READ_MAXFIFO_DATA; + } + /* Master to write data */ + else { + /* FIFO Full */ + if (IT83XX_SMB_SFFSTA & IT83XX_SMB_SFFFULL) { + for (i = 0; i < count; i++) + /* Get data from master to buffer */ + pbuffer[(w_index + i) & + I2C_SIZE_MASK] = IT83XX_SMB_SLDA; + } + + /* Index to next byte of write buffer */ + w_index += count; + } + } + /* Stop condition, indicate stop condition detected. */ + if (slv_status & IT83XX_SMB_SPDS) { + /* Read data less 16 bytes status */ + if (slv_status & IT83XX_SMB_RCS) { + /* Disable FIFO mode to clear left count */ + IT83XX_SMB_SFFCTL &= ~IT83XX_SMB_SAFE; + + /* Slave A FIFO Enable */ + IT83XX_SMB_SFFCTL |= IT83XX_SMB_SAFE; + } + /* Master to write data */ + else { + for (i = 0; i < count; i++) + /* Get data from master to buffer */ + pbuffer[(i + w_index) & + I2C_SIZE_MASK] = IT83XX_SMB_SLDA; + } + + /* Reset read and write buffer index */ + buffer_index_reset(); + } + /* Slave time status, timeout status occurs. */ + if (slv_status & IT83XX_SMB_STS) { + /* Reset read and write buffer index */ + buffer_index_reset(); + } + + /* Write clear the slave status */ + IT83XX_SMB_SLSTA = slv_status; + } + /* Enhanced I2C slave channel D, E, F DMA mode */ + else { + int ch, idx; + + /* Get enhanced i2c channel */ + ch = i2c_slv_ctrl[port].offset / I2C_ENHANCED_CH_INTERVAL; + + idx = i2c_slv_ctrl[port].dma_index; + + /* Interrupt pending */ + if (IT83XX_I2C_STR(ch) & IT83XX_I2C_INTPEND) { + + slv_status = IT83XX_I2C_IRQ_ST(ch); + + /* Master to read data */ + if (slv_status & IT83XX_I2C_IDR_CLR) { + /* + * TODO(b:129360157): Return buffer data by + * "out_data" array. + * Ex: Write data to buffer from 0x00 to 0xFF + */ + for (i = 0; i < I2C_MAX_BUFFER_SIZE; i++) + out_data[idx][i] = i; + } + /* Master to write data */ + if (slv_status & IT83XX_I2C_IDW_CLR) { + /* Master to write data finish flag */ + wr_done[idx] = 1; + } + /* Slave finish */ + if (slv_status & IT83XX_I2C_P_CLR) { + if (wr_done[idx]) { + /* + * TODO(b:129360157): Handle master write + * data by "in_data" array. + */ + CPRINTS("WData: %.*h\n", + I2C_MAX_BUFFER_SIZE, in_data[idx]); + wr_done[idx] = 0; + } + } + + /* Write clear the slave status */ + IT83XX_I2C_IRQ_ST(ch) = slv_status; + } + + /* Hardware reset */ + IT83XX_I2C_CTR(ch) |= IT83XX_I2C_HALT; + } +} + +void i2c_slv_interrupt(int port) +{ + /* Slave to read and write fifo data */ + i2c_slave_read_write_data(port); + + /* Clear the interrupt status */ + task_clear_pending_irq(i2c_slv_ctrl[port].irq); +} + +void i2c_slave_enable(int port, uint8_t slv_addr) +{ + + clock_enable_peripheral(i2c_slv_ctrl[port].clock_gate, 0, 0); + + /* I2C slave channel A FIFO mode */ + if (port < I2C_STANDARD_PORT_COUNT) { + + /* This field defines the SMCLK0/1/2 clock/data low timeout. */ + IT83XX_SMB_25MS = I2C_CLK_LOW_TIMEOUT; + + /* bit0 : Slave A FIFO Enable */ + IT83XX_SMB_SFFCTL |= IT83XX_SMB_SAFE; + + /* + * bit1 : Slave interrupt enable. + * bit2 : SMCLK/SMDAT will be released if timeout. + * bit3 : Slave detect STOP condition interrupt enable. + */ + IT83XX_SMB_SICR = 0x0E; + + /* Slave address 1 */ + IT83XX_SMB_RESLADR = slv_addr; + + /* Write clear all slave status */ + IT83XX_SMB_SLSTA = 0xE7; + + /* bit5 : Enable the SMBus slave device */ + IT83XX_SMB_HOCTL2(port) |= IT83XX_SMB_SLVEN; + } + /* Enhanced I2C slave channel D, E, F DMA mode */ + else { + int ch, idx; + + /* Get enhanced i2c channel */ + ch = i2c_slv_ctrl[port].offset / I2C_ENHANCED_CH_INTERVAL; + + idx = i2c_slv_ctrl[port].dma_index; + + switch (port) { + case IT83XX_I2C_CH_D: + /* Enable I2C D channel */ + IT83XX_GPIO_GRC2 |= (1 << 5); + break; + case IT83XX_I2C_CH_E: + /* Enable I2C E channel */ + IT83XX_GCTRL_PMER1 |= (1 << 0); + break; + case IT83XX_I2C_CH_F: + /* Enable I2C F channel */ + IT83XX_GCTRL_PMER1 |= (1 << 1); + break; + } + + /* Software reset */ + IT83XX_I2C_DHTR(ch) |= (1 << 7); + IT83XX_I2C_DHTR(ch) &= ~(1 << 7); + + /* This field defines the SMCLK3/4/5 clock/data low timeout. */ + IT83XX_I2C_TOR(ch) = I2C_CLK_LOW_TIMEOUT; + + /* Bit stretching */ + IT83XX_I2C_TOS(ch) |= IT83XX_I2C_CLK_STR; + + /* Slave address(8-bit)*/ + IT83XX_I2C_IDR(ch) = slv_addr << 1; + + /* I2C interrupt enable and set acknowledge */ + IT83XX_I2C_CTR(ch) = IT83XX_I2C_HALT | + IT83XX_I2C_INTEN | IT83XX_I2C_ACK; + + /* + * bit3 : Slave ID write flag + * bit2 : Slave ID read flag + * bit1 : Slave received data flag + * bit0 : Slave finish + */ + IT83XX_I2C_IRQ_ST(ch) = 0xFF; + + /* Clear read and write data buffer of DMA */ + memset(in_data[idx], 0, I2C_MAX_BUFFER_SIZE); + memset(out_data[idx], 0, I2C_MAX_BUFFER_SIZE); + + /* DMA write target address register */ + IT83XX_I2C_RAMHA(ch) = ((uint32_t)in_data[idx] >> 8) & 0x0F; + IT83XX_I2C_RAMLA(ch) = (uint32_t)in_data[idx] & 0xFF; + + /* DMA read target address register */ + IT83XX_I2C_RAMHA2(ch) = ((uint32_t)out_data[idx] >> 8) & 0x0F; + IT83XX_I2C_RAMLA2(ch) = (uint32_t)out_data[idx] & 0xFF; + + /* I2C module enable and command queue mode */ + IT83XX_I2C_CTR1(ch) = IT83XX_I2C_COMQ_EN | + IT83XX_I2C_MDL_EN; + } +} + +static void i2c_slave_init(void) +{ + int i, p; + + /* DLM 52k~56k size select enable */ + IT83XX_GCTRL_MCCR2 |= (1 << 4); + + /* Enable I2C Slave function */ + for (i = 0; i < i2c_slvs_used; i++) { + + /* I2c slave port mapping. */ + p = i2c_slv_ports[i].port; + + /* To enable slave ch[x] */ + i2c_slave_enable(p, i2c_slv_ports[i].slave_adr); + + /* Clear the interrupt status */ + task_clear_pending_irq(i2c_slv_ctrl[p].irq); + + /* enable i2c interrupt */ + task_enable_irq(i2c_slv_ctrl[p].irq); + } +} +DECLARE_HOOK(HOOK_INIT, i2c_slave_init, HOOK_PRIO_INIT_I2C + 1); diff --git a/chip/it83xx/intc.c b/chip/it83xx/intc.c index 79d738e93c..033a65d87b 100644 --- a/chip/it83xx/intc.c +++ b/chip/it83xx/intc.c @@ -219,9 +219,14 @@ void intc_cpu_int_group_6(void) int intc_group_6 = intc_get_ec_int(); switch (intc_group_6) { -#ifdef CONFIG_I2C +#if defined(CONFIG_I2C_MASTER) || defined(CONFIG_I2C_SLAVE) case IT83XX_IRQ_SMB_A: - i2c_interrupt(IT83XX_I2C_CH_A); +#ifdef CONFIG_I2C_SLAVE + if (IT83XX_SMB_SFFCTL & IT83XX_SMB_SAFE) + i2c_slv_interrupt(IT83XX_I2C_CH_A); + else +#endif + i2c_interrupt(IT83XX_I2C_CH_A); break; case IT83XX_IRQ_SMB_B: @@ -233,15 +238,30 @@ void intc_cpu_int_group_6(void) break; case IT83XX_IRQ_SMB_D: - i2c_interrupt(IT83XX_I2C_CH_D); +#ifdef CONFIG_I2C_SLAVE + if (!(IT83XX_I2C_CTR(3) & IT83XX_I2C_MODE)) + i2c_slv_interrupt(IT83XX_I2C_CH_D); + else +#endif + i2c_interrupt(IT83XX_I2C_CH_D); break; case IT83XX_IRQ_SMB_E: - i2c_interrupt(IT83XX_I2C_CH_E); +#ifdef CONFIG_I2C_SLAVE + if (!(IT83XX_I2C_CTR(0) & IT83XX_I2C_MODE)) + i2c_slv_interrupt(IT83XX_I2C_CH_E); + else +#endif + i2c_interrupt(IT83XX_I2C_CH_E); break; case IT83XX_IRQ_SMB_F: - i2c_interrupt(IT83XX_I2C_CH_F); +#ifdef CONFIG_I2C_SLAVE + if (!(IT83XX_I2C_CTR(1) & IT83XX_I2C_MODE)) + i2c_slv_interrupt(IT83XX_I2C_CH_F); + else +#endif + i2c_interrupt(IT83XX_I2C_CH_F); break; #endif default: diff --git a/chip/it83xx/intc.h b/chip/it83xx/intc.h index 2655f64b45..3a05e3d5a3 100644 --- a/chip/it83xx/intc.h +++ b/chip/it83xx/intc.h @@ -18,6 +18,9 @@ void lpcrst_interrupt(enum gpio_signal signal); void peci_interrupt(void); void adc_interrupt(void); void i2c_interrupt(int port); +#ifdef CONFIG_I2C_SLAVE +void i2c_slv_interrupt(int port); +#endif void clock_sleep_mode_wakeup_isr(void); int clock_ec_wake_from_sleep(void); void __enter_hibernate(uint32_t seconds, uint32_t microseconds); diff --git a/chip/it83xx/registers.h b/chip/it83xx/registers.h index 6414ec9d16..aff0b7cea0 100644 --- a/chip/it83xx/registers.h +++ b/chip/it83xx/registers.h @@ -1065,6 +1065,12 @@ REG8(IT83XX_PMC_BASE + (ch > LPC_PM2 ? 5 : 8) + (ch << 4)) #define IT83XX_PECI_AWFCSV REG8(IT83XX_PECI_BASE+0x0D) #define IT83XX_PECI_PADCTLR REG8(IT83XX_PECI_BASE+0x0E) +/* + * The count number of the counter for 25 ms register. + * The 25 ms register is calculated by (count number *1.024 kHz). + */ +#define I2C_CLK_LOW_TIMEOUT 255 /* ~=249 ms */ + /* SMBus/I2C Interface (SMB/I2C) */ #define IT83XX_SMB_BASE 0x00F01C00 @@ -1091,6 +1097,21 @@ REG8(IT83XX_PMC_BASE + (ch > LPC_PM2 ? 5 : 8) + (ch << 4)) #define IT83XX_SMB_PECERC(ch) REG8(IT83XX_SMB_BASE+0x47+(ch << 6)) #define IT83XX_SMB_SMBPCTL(ch) REG8(IT83XX_SMB_BASE+0x4A+(ch << 6)) #define IT83XX_SMB_HOCTL2(ch) REG8(IT83XX_SMB_BASE+0x50+(ch << 6)) +#define IT83XX_SMB_SLVEN (1 << 5) +#define IT83XX_SMB_RESLADR REG8(IT83XX_SMB_BASE+0x48) +#define IT83XX_SMB_SLDA REG8(IT83XX_SMB_BASE+0x49) +#define IT83XX_SMB_SLSTA REG8(IT83XX_SMB_BASE+0x4B) +#define IT83XX_SMB_SPDS (1 << 5) +#define IT83XX_SMB_RCS (1 << 3) +#define IT83XX_SMB_STS (1 << 2) +#define IT83XX_SMB_SDS (1 << 1) +#define IT83XX_SMB_SICR REG8(IT83XX_SMB_BASE+0x4C) +#define IT83XX_SMB_RESLADR2 REG8(IT83XX_SMB_BASE+0x51) +#define IT83XX_SMB_ENADDR2 (1 << 7) +#define IT83XX_SMB_SFFCTL REG8(IT83XX_SMB_BASE+0x55) +#define IT83XX_SMB_SAFE (1 << 0) +#define IT83XX_SMB_SFFSTA REG8(IT83XX_SMB_BASE+0x56) +#define IT83XX_SMB_SFFFULL (1 << 6) /* BRAM */ #define IT83XX_BRAM_BASE 0x00F02200 @@ -1159,11 +1180,36 @@ enum bram_indices { #define IT83XX_I2C_PSR(ch) REG8(IT83XX_I2C_BASE+0x01+(ch << 7)) #define IT83XX_I2C_HSPR(ch) REG8(IT83XX_I2C_BASE+0x02+(ch << 7)) #define IT83XX_I2C_STR(ch) REG8(IT83XX_I2C_BASE+0x03+(ch << 7)) +#define IT83XX_I2C_BB (1 << 5) +#define IT83XX_I2C_TIME_OUT (1 << 3) +#define IT83XX_I2C_RW (1 << 2) +#define IT83XX_I2C_INTPEND (1 << 1) #define IT83XX_I2C_DHTR(ch) REG8(IT83XX_I2C_BASE+0x04+(ch << 7)) #define IT83XX_I2C_TOR(ch) REG8(IT83XX_I2C_BASE+0x05+(ch << 7)) #define IT83XX_I2C_DTR(ch) REG8(IT83XX_I2C_BASE+0x08+(ch << 7)) #define IT83XX_I2C_CTR(ch) REG8(IT83XX_I2C_BASE+0x09+(ch << 7)) +#define IT83XX_I2C_INTEN (1 << 6) +#define IT83XX_I2C_MODE (1 << 5) +#define IT83XX_I2C_STARST (1 << 4) +#define IT83XX_I2C_ACK (1 << 3) +#define IT83XX_I2C_HALT (1 << 0) #define IT83XX_I2C_CTR1(ch) REG8(IT83XX_I2C_BASE+0x0A+(ch << 7)) +#define IT83XX_I2C_COMQ_EN (1 << 7) +#define IT83XX_I2C_MDL_EN (1 << 1) +#define IT83XX_I2C_BYTE_CNT_L(ch) REG8(IT83XX_I2C_BASE+0x0C+(ch << 7)) +#define IT83XX_I2C_IRQ_ST(ch) REG8(IT83XX_I2C_BASE+0x0D+(ch << 7)) +#define IT83XX_I2C_IDW_CLR (1 << 3) +#define IT83XX_I2C_IDR_CLR (1 << 2) +#define IT83XX_I2C_SLVDATAFLG (1 << 1) +#define IT83XX_I2C_P_CLR (1 << 0) +#define IT83XX_I2C_IDR(ch) REG8(IT83XX_I2C_BASE+0x06+(ch << 7)) +#define IT83XX_I2C_TOS(ch) REG8(IT83XX_I2C_BASE+0x07+(ch << 7)) +#define IT83XX_I2C_CLK_STR (1 << 7) +#define IT83XX_I2C_IDR2(ch) REG8(IT83XX_I2C_BASE+0x1F+(ch << 7)) +#define IT83XX_I2C_RAMHA(ch) REG8(IT83XX_I2C_BASE+0x23+(ch << 7)) +#define IT83XX_I2C_RAMLA(ch) REG8(IT83XX_I2C_BASE+0x24+(ch << 7)) +#define IT83XX_I2C_RAMHA2(ch) REG8(IT83XX_I2C_BASE+0x2B+(ch << 7)) +#define IT83XX_I2C_RAMLA2(ch) REG8(IT83XX_I2C_BASE+0x2C+(ch << 7)) enum i2c_channels { IT83XX_I2C_CH_A, /* GPIO.B3/B4 */ diff --git a/core/nds32/ec.lds.S b/core/nds32/ec.lds.S index 659270c5b4..bb115ed8df 100644 --- a/core/nds32/ec.lds.S +++ b/core/nds32/ec.lds.S @@ -21,7 +21,7 @@ MEMORY { FLASH (rx) : ORIGIN = FW_OFF(SECTION), LENGTH = FW_SIZE(SECTION) IRAM (rw) : ORIGIN = CONFIG_RAM_BASE, LENGTH = CONFIG_RAM_SIZE -#ifdef CONFIG_HOSTCMD_X86 +#if defined(CONFIG_HOSTCMD_X86) || defined(CONFIG_I2C_SLAVE) H2RAM (rw) : ORIGIN = CONFIG_H2RAM_BASE, LENGTH = CONFIG_H2RAM_SIZE #endif } @@ -237,14 +237,21 @@ SECTIONS __image_size = LOADADDR(.data) + SIZEOF(.data) - FW_OFF(SECTION); -#ifdef CONFIG_HOSTCMD_X86 +#if defined(CONFIG_HOSTCMD_X86) || defined(CONFIG_I2C_SLAVE) .h2ram (NOLOAD) : { . += CONFIG_H2RAM_HOST_LPC_IO_BASE; *(.h2ram.pool.hostcmd) . = ALIGN(256); *(.h2ram.pool.acpiec) +#ifdef CONFIG_I2C_SLAVE + . = ALIGN(256); + *(.h2ram.pool.i2cslv) +#endif + __h2ram_end = .; } > H2RAM #endif + ASSERT((__h2ram_end) <= (CONFIG_H2RAM_BASE + CONFIG_H2RAM_SIZE), + "Not enough space for h2ram section.") #if !(defined(SECTION_IS_RO) && defined(CONFIG_FLASH)) /DISCARD/ : { diff --git a/include/i2c_slave.h b/include/i2c_slave.h new file mode 100644 index 0000000000..3145d4679b --- /dev/null +++ b/include/i2c_slave.h @@ -0,0 +1,21 @@ +/* Copyright 2019 The Chromium OS Authors. All rights reserved. + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +/* I2C slave interface for Chrome EC */ + +#ifndef __CROS_EC_I2CSLV_H +#define __CROS_EC_I2CSLV_H + +/* Data structure to define I2C slave port configuration. */ +struct i2c_slv_port_t { + const char *name; /* Port name */ + int port; /* Port */ + uint8_t slave_adr; /* slave address(7-bit without R/W) */ +}; + +extern const struct i2c_slv_port_t i2c_slv_ports[]; +extern const unsigned int i2c_slvs_used; + +#endif /* __CROS_EC_I2CSLV_H */ |