diff --git a/src/board/system76/darp5/board.mk b/src/board/system76/darp5/board.mk index 4d1d49b..a2c5fcd 100644 --- a/src/board/system76/darp5/board.mk +++ b/src/board/system76/darp5/board.mk @@ -19,6 +19,9 @@ CFLAGS+=-DLEVEL=4 # Set battery I2C bus CFLAGS+=-DI2C_SMBUS=I2C_0 +# Set keyboard LED I2C bus +CFLAGS+=-DI2C_KBLED=I2C_1 + # Set scratch ROM parameters SCRATCH_OFFSET=1024 SCRATCH_SIZE=1024 diff --git a/src/board/system76/darp5/gpio.c b/src/board/system76/darp5/gpio.c index d40203c..ec639cf 100644 --- a/src/board/system76/darp5/gpio.c +++ b/src/board/system76/darp5/gpio.c @@ -94,9 +94,9 @@ void gpio_init() { // ALL_SYS_PWRGD GPCRC0 = GPIO_IN; // SMC_VGA_THERM - GPCRC1 = GPIO_IN | GPIO_UP; + GPCRC1 = GPIO_ALT; // SMD_VGA_THERM - GPCRC2 = GPIO_IN | GPIO_UP; + GPCRC2 = GPIO_ALT; // KSO16 (Darter) GPCRC3 = GPIO_IN; // CNVI_DET# diff --git a/src/board/system76/darp5/include/board/kbled.h b/src/board/system76/darp5/include/board/kbled.h new file mode 100644 index 0000000..373ff89 --- /dev/null +++ b/src/board/system76/darp5/include/board/kbled.h @@ -0,0 +1,11 @@ +#ifndef _BOARD_KBLED_H +#define _BOARD_KBLED_H + +#include + +void kbled_init(void); +uint8_t kbled_get(void); +void kbled_set(uint8_t level); +void kbled_set_color(uint32_t color); + +#endif // _BOARD_KBLED_H diff --git a/src/board/system76/darp5/kbled.c b/src/board/system76/darp5/kbled.c new file mode 100644 index 0000000..530392c --- /dev/null +++ b/src/board/system76/darp5/kbled.c @@ -0,0 +1,58 @@ +#include +#include +#include + +#define kbled_i2c_get(A, D, L) i2c_get(&I2C_KBLED, 0x68, A, D, L) +#define kbled_i2c_set(A, D, L) i2c_set(&I2C_KBLED, 0x68, A, D, L) + +static uint8_t __code levels[] = { + 0x00, + 0x80, + 0x90, + 0xA8, + 0xC0, + 0xFF +}; + +void kbled_init(void) { + i2c_reset(&I2C_KBLED, true); + kbled_set(0xFF); + kbled_set_color(0xFFFFFF); +} + +uint8_t kbled_get(void) { + uint8_t level; + uint8_t raw = 0; + kbled_i2c_get(0x12, &raw, 1); + for (level = 0; level < ARRAY_SIZE(levels); level++) { + if (raw <= levels[level]) { + return level; + } + } + return 0; +} + +void kbled_set(uint8_t level) { + uint8_t raw = 0; + if (level < ARRAY_SIZE(levels)) { + raw = levels[level]; + } + kbled_i2c_set(0x12, &raw, 1); +} + +void kbled_set_color(uint32_t color) { + uint8_t b = (uint8_t)(color); + kbled_i2c_set(0x02, &b, 1); + kbled_i2c_set(0x03, &b, 1); + kbled_i2c_set(0x04, &b, 1); + + uint8_t g = (uint8_t)(color >> 8); + kbled_i2c_set(0x05, &g, 1); + kbled_i2c_set(0x06, &g, 1); + kbled_i2c_set(0x07, &g, 1); + + uint8_t r = (uint8_t)(color >> 16); + kbled_i2c_set(0x08, &r, 1); + kbled_i2c_set(0x09, &r, 1); + kbled_i2c_set(0x0A, &r, 1); +} diff --git a/src/board/system76/darp5/main.c b/src/board/system76/darp5/main.c index d4b8a0b..ab3aaf7 100644 --- a/src/board/system76/darp5/main.c +++ b/src/board/system76/darp5/main.c @@ -9,6 +9,7 @@ #include #include #include +#include #include #include #include @@ -41,6 +42,7 @@ void init(void) { // Can happen in any order ecpm_init(); kbc_init(); + kbled_init(); kbscan_init(); peci_init(); pmc_init(); diff --git a/src/ec/it5570e/i2c.c b/src/ec/it5570e/i2c.c index 17dcbfa..8733010 100644 --- a/src/ec/it5570e/i2c.c +++ b/src/ec/it5570e/i2c.c @@ -14,6 +14,14 @@ struct I2C { volatile uint8_t * trasla; }; +struct I2C __code I2C_0 = { + .hosta = HOSTAA, + .hoctl = HOCTLA, + .hoctl2 = HOCTL2A, + .hobdb = HOBDBA, + .trasla = TRASLAA, +}; + struct I2C __code I2C_1 = { .hosta = HOSTAB, .hoctl = HOCTLB, diff --git a/src/ec/it8587e/i2c.c b/src/ec/it8587e/i2c.c index 9b86eec..cfbbdce 100644 --- a/src/ec/it8587e/i2c.c +++ b/src/ec/it8587e/i2c.c @@ -22,6 +22,14 @@ struct I2C __code I2C_0 = { .trasla = TRASLAA, }; +struct I2C __code I2C_1 = { + .hosta = HOSTAB, + .hoctl = HOCTLB, + .hoctl2 = HOCTL2B, + .hobdb = HOBDBB, + .trasla = TRASLAB, +}; + void i2c_reset(struct I2C * i2c, bool kill) { if (*(i2c->hosta) & HOSTA_BUSY) { // Set kill bit diff --git a/src/ec/it8587e/include/ec/i2c.h b/src/ec/it8587e/include/ec/i2c.h index 9cd9e19..ee513bc 100644 --- a/src/ec/it8587e/include/ec/i2c.h +++ b/src/ec/it8587e/include/ec/i2c.h @@ -4,6 +4,7 @@ #include extern struct I2C __code I2C_0; +extern struct I2C __code I2C_1; void i2c_reset(struct I2C * i2c, bool kill); diff --git a/src/ec/it8587e/include/ec/smbus.h b/src/ec/it8587e/include/ec/smbus.h index c1d7ffc..b47cd1c 100644 --- a/src/ec/it8587e/include/ec/smbus.h +++ b/src/ec/it8587e/include/ec/smbus.h @@ -52,6 +52,45 @@ volatile uint8_t __xdata __at(0x1C3F) RESLADR2A; // SMCLK timing setting for channel A volatile uint8_t __xdata __at(0x1C40) SCLKTSA; +// Host status for channel B +volatile uint8_t __xdata __at(0x1C11) HOSTAB; +// Host control for channel B +volatile uint8_t __xdata __at(0x1C12) HOCTLB; +// Host command for channel B +volatile uint8_t __xdata __at(0x1C13) HOCMDB; +// Transmit slave address for channel B +volatile uint8_t __xdata __at(0x1C14) TRASLAB; +// Host data 0 for channel B +volatile uint8_t __xdata __at(0x1C15) D0REGB; +// Host data 1 for channel B +volatile uint8_t __xdata __at(0x1C16) D1REGB; +// Host block data byte for channel B +volatile uint8_t __xdata __at(0x1C17) HOBDBB; +// Packet error check for channel B +volatile uint8_t __xdata __at(0x1C18) PECERCB; +// Receive slave address for channel B +volatile uint8_t __xdata __at(0x1C19) RESLADRB; +// Slave data for channel B +volatile uint8_t __xdata __at(0x1C1A) SLDAB; +// SMBus pin control for channel B +volatile uint8_t __xdata __at(0x1C1B) SMBPCTLB; +// Slave status for channel B +volatile uint8_t __xdata __at(0x1C1C) SLSTAB; +// Slave interrupt control for channel B +volatile uint8_t __xdata __at(0x1C1D) SICRB; +// Notify device address for channel B +volatile uint8_t __xdata __at(0x1C1E) NDADRB; +// Notify data low byte for channel A +volatile uint8_t __xdata __at(0x1C1F) NDLBB; +// Notify data high byte for channel B +volatile uint8_t __xdata __at(0x1C20) NDHBB; +// Host control 2 for channel B +volatile uint8_t __xdata __at(0x1C21) HOCTL2B; +// Receive slave address 2 for channel B +volatile uint8_t __xdata __at(0x1C44) RESLADR2B; +// SMCLK timing setting for channel B +volatile uint8_t __xdata __at(0x1C41) SCLKTSB; + // Timing registers volatile uint8_t __xdata __at(0x1C22) SMB4P7USL; volatile uint8_t __xdata __at(0x1C23) SMB4P0USL;