1 From 3c8e1a84fd6b984a7bce8816db2e3defc57bbfe4 Mon Sep 17 00:00:00 2001
2 From: Marek Szyprowski <m.szyprowski@samsung.com>
3 Date: Wed, 30 Jun 2010 14:27:37 -0600
4 Subject: [PATCH] spi/spi-gpio: add support for controllers without MISO or MOSI pin
6 There are some boards that do not strictly follow SPI standard and use
7 only 3 wires (SCLK, MOSI or MISO, SS) for connecting some simple auxiliary
8 chips and controls them with GPIO based 'spi controller'. In this
9 configuration the MISO or MOSI line is missing (it is not required if the
10 chip does not transfer any data back to host or host only reads data from
13 This patch adds support for such non-standard configuration in GPIO-based
14 SPI controller. It has been tested in configuration without MISO pin.
16 Reviewed-by: Kyungmin Park <kyungmin.park@samsung.com>
17 Signed-off-by: Marek Szyprowski <m.szyprowski@samsung.com>
18 Acked-by: David Brownell <dbrownell@users.sourceforge.net>
19 Signed-off-by: Grant Likely <grant.likely@secretlab.ca>
21 drivers/spi/spi_gpio.c | 101 ++++++++++++++++++++++++++++++++++-------
22 include/linux/spi/spi_gpio.h | 5 ++
23 2 files changed, 88 insertions(+), 18 deletions(-)
25 --- a/drivers/spi/spi_gpio.c
26 +++ b/drivers/spi/spi_gpio.c
27 @@ -178,6 +178,44 @@ static u32 spi_gpio_txrx_word_mode3(stru
28 return bitbang_txrx_be_cpha1(spi, nsecs, 1, 0, word, bits);
32 + * These functions do not call setmosi or getmiso if respective flag
33 + * (SPI_MASTER_NO_RX or SPI_MASTER_NO_TX) is set, so they are safe to
34 + * call when such pin is not present or defined in the controller.
35 + * A separate set of callbacks is defined to get highest possible
36 + * speed in the generic case (when both MISO and MOSI lines are
37 + * available), as optimiser will remove the checks when argument is
41 +static u32 spi_gpio_spec_txrx_word_mode0(struct spi_device *spi,
42 + unsigned nsecs, u32 word, u8 bits)
44 + unsigned flags = spi->master->flags;
45 + return bitbang_txrx_be_cpha0(spi, nsecs, 0, flags, word, bits);
48 +static u32 spi_gpio_spec_txrx_word_mode1(struct spi_device *spi,
49 + unsigned nsecs, u32 word, u8 bits)
51 + unsigned flags = spi->master->flags;
52 + return bitbang_txrx_be_cpha1(spi, nsecs, 0, flags, word, bits);
55 +static u32 spi_gpio_spec_txrx_word_mode2(struct spi_device *spi,
56 + unsigned nsecs, u32 word, u8 bits)
58 + unsigned flags = spi->master->flags;
59 + return bitbang_txrx_be_cpha0(spi, nsecs, 1, flags, word, bits);
62 +static u32 spi_gpio_spec_txrx_word_mode3(struct spi_device *spi,
63 + unsigned nsecs, u32 word, u8 bits)
65 + unsigned flags = spi->master->flags;
66 + return bitbang_txrx_be_cpha1(spi, nsecs, 1, flags, word, bits);
69 /*----------------------------------------------------------------------*/
71 static void spi_gpio_chipselect(struct spi_device *spi, int is_active)
72 @@ -243,19 +281,30 @@ static int __devinit spi_gpio_alloc(unsi
76 -spi_gpio_request(struct spi_gpio_platform_data *pdata, const char *label)
77 +spi_gpio_request(struct spi_gpio_platform_data *pdata, const char *label,
82 /* NOTE: SPI_*_GPIO symbols may reference "pdata" */
84 - value = spi_gpio_alloc(SPI_MOSI_GPIO, label, false);
88 - value = spi_gpio_alloc(SPI_MISO_GPIO, label, true);
91 + if (SPI_MOSI_GPIO != SPI_GPIO_NO_MOSI) {
92 + value = spi_gpio_alloc(SPI_MOSI_GPIO, label, false);
96 + /* HW configuration without MOSI pin */
97 + *res_flags |= SPI_MASTER_NO_TX;
100 + if (SPI_MISO_GPIO != SPI_GPIO_NO_MISO) {
101 + value = spi_gpio_alloc(SPI_MISO_GPIO, label, true);
105 + /* HW configuration without MISO pin */
106 + *res_flags |= SPI_MASTER_NO_RX;
109 value = spi_gpio_alloc(SPI_SCK_GPIO, label, false);
111 @@ -264,9 +313,11 @@ spi_gpio_request(struct spi_gpio_platfor
115 - gpio_free(SPI_MISO_GPIO);
116 + if (SPI_MISO_GPIO != SPI_GPIO_NO_MISO)
117 + gpio_free(SPI_MISO_GPIO);
119 - gpio_free(SPI_MOSI_GPIO);
120 + if (SPI_MOSI_GPIO != SPI_GPIO_NO_MOSI)
121 + gpio_free(SPI_MOSI_GPIO);
125 @@ -277,6 +328,7 @@ static int __devinit spi_gpio_probe(stru
126 struct spi_master *master;
127 struct spi_gpio *spi_gpio;
128 struct spi_gpio_platform_data *pdata;
129 + u16 master_flags = 0;
131 pdata = pdev->dev.platform_data;
132 #ifdef GENERIC_BITBANG
133 @@ -284,7 +336,7 @@ static int __devinit spi_gpio_probe(stru
137 - status = spi_gpio_request(pdata, dev_name(&pdev->dev));
138 + status = spi_gpio_request(pdata, dev_name(&pdev->dev), &master_flags);
142 @@ -300,6 +352,7 @@ static int __devinit spi_gpio_probe(stru
144 spi_gpio->pdata = *pdata;
146 + master->flags = master_flags;
147 master->bus_num = pdev->id;
148 master->num_chipselect = SPI_N_CHIPSEL;
149 master->setup = spi_gpio_setup;
150 @@ -307,10 +360,18 @@ static int __devinit spi_gpio_probe(stru
152 spi_gpio->bitbang.master = spi_master_get(master);
153 spi_gpio->bitbang.chipselect = spi_gpio_chipselect;
154 - spi_gpio->bitbang.txrx_word[SPI_MODE_0] = spi_gpio_txrx_word_mode0;
155 - spi_gpio->bitbang.txrx_word[SPI_MODE_1] = spi_gpio_txrx_word_mode1;
156 - spi_gpio->bitbang.txrx_word[SPI_MODE_2] = spi_gpio_txrx_word_mode2;
157 - spi_gpio->bitbang.txrx_word[SPI_MODE_3] = spi_gpio_txrx_word_mode3;
159 + if ((master_flags & (SPI_MASTER_NO_RX | SPI_MASTER_NO_RX)) == 0) {
160 + spi_gpio->bitbang.txrx_word[SPI_MODE_0] = spi_gpio_txrx_word_mode0;
161 + spi_gpio->bitbang.txrx_word[SPI_MODE_1] = spi_gpio_txrx_word_mode1;
162 + spi_gpio->bitbang.txrx_word[SPI_MODE_2] = spi_gpio_txrx_word_mode2;
163 + spi_gpio->bitbang.txrx_word[SPI_MODE_3] = spi_gpio_txrx_word_mode3;
165 + spi_gpio->bitbang.txrx_word[SPI_MODE_0] = spi_gpio_spec_txrx_word_mode0;
166 + spi_gpio->bitbang.txrx_word[SPI_MODE_1] = spi_gpio_spec_txrx_word_mode1;
167 + spi_gpio->bitbang.txrx_word[SPI_MODE_2] = spi_gpio_spec_txrx_word_mode2;
168 + spi_gpio->bitbang.txrx_word[SPI_MODE_3] = spi_gpio_spec_txrx_word_mode3;
170 spi_gpio->bitbang.setup_transfer = spi_bitbang_setup_transfer;
171 spi_gpio->bitbang.flags = SPI_CS_HIGH;
173 @@ -318,8 +379,10 @@ static int __devinit spi_gpio_probe(stru
175 spi_master_put(spi_gpio->bitbang.master);
177 - gpio_free(SPI_MISO_GPIO);
178 - gpio_free(SPI_MOSI_GPIO);
179 + if (SPI_MISO_GPIO != SPI_GPIO_NO_MISO)
180 + gpio_free(SPI_MISO_GPIO);
181 + if (SPI_MOSI_GPIO != SPI_GPIO_NO_MOSI)
182 + gpio_free(SPI_MOSI_GPIO);
183 gpio_free(SPI_SCK_GPIO);
184 spi_master_put(master);
186 @@ -342,8 +405,10 @@ static int __devexit spi_gpio_remove(str
188 platform_set_drvdata(pdev, NULL);
190 - gpio_free(SPI_MISO_GPIO);
191 - gpio_free(SPI_MOSI_GPIO);
192 + if (SPI_MISO_GPIO != SPI_GPIO_NO_MISO)
193 + gpio_free(SPI_MISO_GPIO);
194 + if (SPI_MOSI_GPIO != SPI_GPIO_NO_MOSI)
195 + gpio_free(SPI_MOSI_GPIO);
196 gpio_free(SPI_SCK_GPIO);
199 --- a/include/linux/spi/spi_gpio.h
200 +++ b/include/linux/spi/spi_gpio.h
202 * SPI_GPIO_NO_CHIPSELECT to the controller_data:
203 * .controller_data = (void *) SPI_GPIO_NO_CHIPSELECT;
205 + * If the MISO or MOSI pin is not available then it should be set to
206 + * SPI_GPIO_NO_MISO or SPI_GPIO_NO_MOSI.
208 * If the bitbanged bus is later switched to a "native" controller,
209 * that platform_device and controller_data should be removed.
212 #define SPI_GPIO_NO_CHIPSELECT ((unsigned long)-1l)
213 +#define SPI_GPIO_NO_MISO ((unsigned long)-1l)
214 +#define SPI_GPIO_NO_MOSI ((unsigned long)-1l)
217 * struct spi_gpio_platform_data - parameter for bitbanged SPI master