Skip to content

Commit 5211070

Browse files
mhennerichbroonie
authored andcommitted
spi: xcomm: add gpiochip support
The hardware can expose one pin as a GPO. Hence, register a simple gpiochip to support it. Signed-off-by: Michael Hennerich <[email protected]> Co-developed-by: Nuno Sa <[email protected]> Signed-off-by: Nuno Sa <[email protected]> Link: https://patch.msgid.link/[email protected] Signed-off-by: Mark Brown <[email protected]>
1 parent 6c387fb commit 5211070

File tree

1 file changed

+41
-1
lines changed

1 file changed

+41
-1
lines changed

drivers/spi/spi-xcomm.c

Lines changed: 41 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@
1010
#include <linux/module.h>
1111
#include <linux/delay.h>
1212
#include <linux/i2c.h>
13+
#include <linux/gpio/driver.h>
1314
#include <linux/spi/spi.h>
1415
#include <asm/unaligned.h>
1516

@@ -26,12 +27,15 @@
2627

2728
#define SPI_XCOMM_CMD_UPDATE_CONFIG 0x03
2829
#define SPI_XCOMM_CMD_WRITE 0x04
30+
#define SPI_XCOMM_CMD_GPIO_SET 0x05
2931

3032
#define SPI_XCOMM_CLOCK 48000000
3133

3234
struct spi_xcomm {
3335
struct i2c_client *i2c;
3436

37+
struct gpio_chip gc;
38+
3539
uint16_t settings;
3640
uint16_t chipselect;
3741

@@ -40,6 +44,42 @@ struct spi_xcomm {
4044
uint8_t buf[63];
4145
};
4246

47+
static void spi_xcomm_gpio_set_value(struct gpio_chip *chip,
48+
unsigned int offset, int val)
49+
{
50+
struct spi_xcomm *spi_xcomm = gpiochip_get_data(chip);
51+
unsigned char buf[2];
52+
53+
buf[0] = SPI_XCOMM_CMD_GPIO_SET;
54+
buf[1] = !!val;
55+
56+
i2c_master_send(spi_xcomm->i2c, buf, 2);
57+
}
58+
59+
static int spi_xcomm_gpio_get_direction(struct gpio_chip *chip,
60+
unsigned int offset)
61+
{
62+
return GPIO_LINE_DIRECTION_OUT;
63+
}
64+
65+
static int spi_xcomm_gpio_add(struct spi_xcomm *spi_xcomm)
66+
{
67+
struct device *dev = &spi_xcomm->i2c->dev;
68+
69+
if (!IS_ENABLED(CONFIG_GPIOLIB))
70+
return 0;
71+
72+
spi_xcomm->gc.get_direction = spi_xcomm_gpio_get_direction;
73+
spi_xcomm->gc.set = spi_xcomm_gpio_set_value;
74+
spi_xcomm->gc.can_sleep = 1;
75+
spi_xcomm->gc.base = -1;
76+
spi_xcomm->gc.ngpio = 1;
77+
spi_xcomm->gc.label = spi_xcomm->i2c->name;
78+
spi_xcomm->gc.owner = THIS_MODULE;
79+
80+
return devm_gpiochip_add_data(dev, &spi_xcomm->gc, spi_xcomm);
81+
}
82+
4383
static int spi_xcomm_sync_config(struct spi_xcomm *spi_xcomm, unsigned int len)
4484
{
4585
uint16_t settings;
@@ -227,7 +267,7 @@ static int spi_xcomm_probe(struct i2c_client *i2c)
227267
if (ret < 0)
228268
spi_controller_put(host);
229269

230-
return ret;
270+
return spi_xcomm_gpio_add(spi_xcomm);
231271
}
232272

233273
static const struct i2c_device_id spi_xcomm_ids[] = {

0 commit comments

Comments
 (0)