1 From 7008284716403237f6bc7d7590b3ed073555bd56 Mon Sep 17 00:00:00 2001
2 From: Gabor Juhos <juhosg@openwrt.org>
3 Date: Wed, 11 Jan 2012 22:25:11 +0100
4 Subject: [PATCH 34/34] spi/ath79: make chipselect logic more flexible
6 Signed-off-by: Gabor Juhos <juhosg@openwrt.org>
8 arch/mips/ath79/mach-pb44.c | 6 ++
9 .../include/asm/mach-ath79/ath79_spi_platform.h | 8 ++-
10 drivers/spi/spi-ath79.c | 67 +++++++++++++-------
11 8 files changed, 88 insertions(+), 23 deletions(-)
13 --- a/arch/mips/ath79/mach-pb44.c
14 +++ b/arch/mips/ath79/mach-pb44.c
15 @@ -87,12 +87,18 @@ static struct gpio_keys_button pb44_gpio
19 +static struct ath79_spi_controller_data pb44_spi0_data = {
20 + .cs_type = ATH79_SPI_CS_TYPE_INTERNAL,
24 static struct spi_board_info pb44_spi_info[] = {
28 .max_speed_hz = 25000000,
30 + .controller_data = &pb44_spi0_data,
34 --- a/arch/mips/include/asm/mach-ath79/ath79_spi_platform.h
35 +++ b/arch/mips/include/asm/mach-ath79/ath79_spi_platform.h
36 @@ -16,8 +16,14 @@ struct ath79_spi_platform_data {
37 unsigned num_chipselect;
40 +enum ath79_spi_cs_type {
41 + ATH79_SPI_CS_TYPE_INTERNAL,
42 + ATH79_SPI_CS_TYPE_GPIO,
45 struct ath79_spi_controller_data {
47 + enum ath79_spi_cs_type cs_type;
51 #endif /* _ATH79_SPI_PLATFORM_H */
52 --- a/drivers/spi/spi-ath79.c
53 +++ b/drivers/spi/spi-ath79.c
55 #define ATH79_SPI_RRW_DELAY_FACTOR 12000
56 #define MHZ (1000 * 1000)
58 +#define ATH79_SPI_CS_LINE_MAX 2
61 struct spi_bitbang bitbang;
63 @@ -67,6 +69,7 @@ static void ath79_spi_chipselect(struct
65 struct ath79_spi *sp = ath79_spidev_to_sp(spi);
66 int cs_high = (spi->mode & SPI_CS_HIGH) ? is_active : !is_active;
67 + struct ath79_spi_controller_data *cdata = spi->controller_data;
70 /* set initial clock polarity */
71 @@ -78,20 +81,24 @@ static void ath79_spi_chipselect(struct
72 ath79_spi_wr(sp, AR71XX_SPI_REG_IOC, sp->ioc_base);
75 - if (spi->chip_select) {
76 - struct ath79_spi_controller_data *cdata = spi->controller_data;
78 - /* SPI is normally active-low */
79 - gpio_set_value(cdata->gpio, cs_high);
81 + switch (cdata->cs_type) {
82 + case ATH79_SPI_CS_TYPE_INTERNAL:
84 - sp->ioc_base |= AR71XX_SPI_IOC_CS0;
85 + sp->ioc_base |= AR71XX_SPI_IOC_CS(cdata->cs_line);
87 - sp->ioc_base &= ~AR71XX_SPI_IOC_CS0;
88 + sp->ioc_base &= ~AR71XX_SPI_IOC_CS(cdata->cs_line);
90 ath79_spi_wr(sp, AR71XX_SPI_REG_IOC, sp->ioc_base);
94 + case ATH79_SPI_CS_TYPE_GPIO:
95 + /* SPI is normally active-low */
96 + if (gpio_cansleep(cdata->cs_line))
97 + gpio_set_value_cansleep(cdata->cs_line, cs_high);
99 + gpio_set_value(cdata->cs_line, cs_high);
104 static void ath79_spi_enable(struct ath79_spi *sp)
105 @@ -118,24 +125,30 @@ static void ath79_spi_disable(struct ath
106 static int ath79_spi_setup_cs(struct spi_device *spi)
108 struct ath79_spi_controller_data *cdata;
109 + unsigned long flags;
112 cdata = spi->controller_data;
113 - if (spi->chip_select && !cdata)
118 - if (spi->chip_select) {
119 - unsigned long flags;
120 + switch (cdata->cs_type) {
121 + case ATH79_SPI_CS_TYPE_INTERNAL:
122 + if (cdata->cs_line > ATH79_SPI_CS_LINE_MAX)
126 + case ATH79_SPI_CS_TYPE_GPIO:
127 flags = GPIOF_DIR_OUT;
128 if (spi->mode & SPI_CS_HIGH)
129 flags |= GPIOF_INIT_LOW;
131 flags |= GPIOF_INIT_HIGH;
133 - status = gpio_request_one(cdata->gpio, flags,
134 + status = gpio_request_one(cdata->cs_line, flags,
135 dev_name(&spi->dev));
140 @@ -143,9 +156,19 @@ static int ath79_spi_setup_cs(struct spi
142 static void ath79_spi_cleanup_cs(struct spi_device *spi)
144 - if (spi->chip_select) {
145 - struct ath79_spi_controller_data *cdata = spi->controller_data;
146 - gpio_free(cdata->gpio);
147 + struct ath79_spi_controller_data *cdata;
149 + cdata = spi->controller_data;
153 + switch (cdata->cs_type) {
154 + case ATH79_SPI_CS_TYPE_INTERNAL:
155 + /* nothing to do */
157 + case ATH79_SPI_CS_TYPE_GPIO:
158 + gpio_free(cdata->cs_line);
163 @@ -210,6 +233,10 @@ static int ath79_spi_probe(struct platfo
167 + pdata = pdev->dev.platform_data;
171 master = spi_alloc_master(&pdev->dev, sizeof(*sp));
172 if (master == NULL) {
173 dev_err(&pdev->dev, "failed to allocate spi master\n");
174 @@ -219,15 +246,11 @@ static int ath79_spi_probe(struct platfo
175 sp = spi_master_get_devdata(master);
176 platform_set_drvdata(pdev, sp);
178 - pdata = dev_get_platdata(&pdev->dev);
180 master->bits_per_word_mask = SPI_BPW_RANGE_MASK(1, 32);
181 master->setup = ath79_spi_setup;
182 master->cleanup = ath79_spi_cleanup;
184 - master->bus_num = pdata->bus_num;
185 - master->num_chipselect = pdata->num_chipselect;
187 + master->bus_num = pdata->bus_num;
188 + master->num_chipselect = pdata->num_chipselect;
190 sp->bitbang.master = master;
191 sp->bitbang.chipselect = ath79_spi_chipselect;