diff options
author | Leif Middelschulte <leif.middelschulte@gmail.com> | 2017-04-23 15:19:58 -0400 |
---|---|---|
committer | Mark Brown <broonie@kernel.org> | 2017-04-25 11:37:53 -0400 |
commit | f72efa7e690ab5c4068ccba31c4da032bc45c29c (patch) | |
tree | 2ff01c9757a2151e4a5d655889053c854a818cf4 | |
parent | c1ae3cfa0e89fa1a7ecc4c99031f5e9ae99d9201 (diff) |
spi-imx: Implements handling of the SPI_READY mode flag.
This patch implements consideration of the SPI_READY mode flag as
defined in spi.h. It extends the device tree bindings to support
the values defined by the reference manual for the DRCTL field.
Thus supporting edge-triggered and level-triggered bursts.
Signed-off-by: Leif Middelschulte <Leif.Middelschulte@gmail.com>
Signed-off-by: Mark Brown <broonie@kernel.org>
-rw-r--r-- | Documentation/devicetree/bindings/spi/fsl-imx-cspi.txt | 7 | ||||
-rw-r--r-- | drivers/spi/spi-imx.c | 20 |
2 files changed, 25 insertions, 2 deletions
diff --git a/Documentation/devicetree/bindings/spi/fsl-imx-cspi.txt b/Documentation/devicetree/bindings/spi/fsl-imx-cspi.txt index 8bc95e2fc47f..31b5b21598ff 100644 --- a/Documentation/devicetree/bindings/spi/fsl-imx-cspi.txt +++ b/Documentation/devicetree/bindings/spi/fsl-imx-cspi.txt | |||
@@ -23,6 +23,12 @@ See the clock consumer binding, | |||
23 | Obsolete properties: | 23 | Obsolete properties: |
24 | - fsl,spi-num-chipselects : Contains the number of the chipselect | 24 | - fsl,spi-num-chipselects : Contains the number of the chipselect |
25 | 25 | ||
26 | Optional properties: | ||
27 | - fsl,spi-rdy-drctl: Integer, representing the value of DRCTL, the register | ||
28 | controlling the SPI_READY handling. Note that to enable the DRCTL consideration, | ||
29 | the SPI_READY mode-flag needs to be set too. | ||
30 | Valid values are: 0 (disabled), 1 (edge-triggered burst) and 2 (level-triggered burst). | ||
31 | |||
26 | Example: | 32 | Example: |
27 | 33 | ||
28 | ecspi@70010000 { | 34 | ecspi@70010000 { |
@@ -35,4 +41,5 @@ ecspi@70010000 { | |||
35 | <&gpio3 25 0>; /* GPIO3_25 */ | 41 | <&gpio3 25 0>; /* GPIO3_25 */ |
36 | dmas = <&sdma 3 7 1>, <&sdma 4 7 2>; | 42 | dmas = <&sdma 3 7 1>, <&sdma 4 7 2>; |
37 | dma-names = "rx", "tx"; | 43 | dma-names = "rx", "tx"; |
44 | fsl,spi-rdy-drctl = <1>; | ||
38 | }; | 45 | }; |
diff --git a/drivers/spi/spi-imx.c b/drivers/spi/spi-imx.c index 9a7c62f471dc..b402530a7a9a 100644 --- a/drivers/spi/spi-imx.c +++ b/drivers/spi/spi-imx.c | |||
@@ -95,6 +95,7 @@ struct spi_imx_data { | |||
95 | unsigned int spi_bus_clk; | 95 | unsigned int spi_bus_clk; |
96 | 96 | ||
97 | unsigned int bytes_per_word; | 97 | unsigned int bytes_per_word; |
98 | unsigned int spi_drctl; | ||
98 | 99 | ||
99 | unsigned int count; | 100 | unsigned int count; |
100 | void (*tx)(struct spi_imx_data *); | 101 | void (*tx)(struct spi_imx_data *); |
@@ -246,6 +247,7 @@ static bool spi_imx_can_dma(struct spi_master *master, struct spi_device *spi, | |||
246 | #define MX51_ECSPI_CTRL_XCH (1 << 2) | 247 | #define MX51_ECSPI_CTRL_XCH (1 << 2) |
247 | #define MX51_ECSPI_CTRL_SMC (1 << 3) | 248 | #define MX51_ECSPI_CTRL_SMC (1 << 3) |
248 | #define MX51_ECSPI_CTRL_MODE_MASK (0xf << 4) | 249 | #define MX51_ECSPI_CTRL_MODE_MASK (0xf << 4) |
250 | #define MX51_ECSPI_CTRL_DRCTL(drctl) ((drctl) << 16) | ||
249 | #define MX51_ECSPI_CTRL_POSTDIV_OFFSET 8 | 251 | #define MX51_ECSPI_CTRL_POSTDIV_OFFSET 8 |
250 | #define MX51_ECSPI_CTRL_PREDIV_OFFSET 12 | 252 | #define MX51_ECSPI_CTRL_PREDIV_OFFSET 12 |
251 | #define MX51_ECSPI_CTRL_CS(cs) ((cs) << 18) | 253 | #define MX51_ECSPI_CTRL_CS(cs) ((cs) << 18) |
@@ -355,6 +357,12 @@ static int mx51_ecspi_config(struct spi_device *spi, | |||
355 | */ | 357 | */ |
356 | ctrl |= MX51_ECSPI_CTRL_MODE_MASK; | 358 | ctrl |= MX51_ECSPI_CTRL_MODE_MASK; |
357 | 359 | ||
360 | /* | ||
361 | * Enable SPI_RDY handling (falling edge/level triggered). | ||
362 | */ | ||
363 | if (spi->mode & SPI_READY) | ||
364 | ctrl |= MX51_ECSPI_CTRL_DRCTL(spi_imx->spi_drctl); | ||
365 | |||
358 | /* set clock speed */ | 366 | /* set clock speed */ |
359 | ctrl |= mx51_ecspi_clkdiv(spi_imx, config->speed_hz, &clk); | 367 | ctrl |= mx51_ecspi_clkdiv(spi_imx, config->speed_hz, &clk); |
360 | spi_imx->spi_bus_clk = clk; | 368 | spi_imx->spi_bus_clk = clk; |
@@ -1173,7 +1181,7 @@ static int spi_imx_probe(struct platform_device *pdev) | |||
1173 | struct spi_master *master; | 1181 | struct spi_master *master; |
1174 | struct spi_imx_data *spi_imx; | 1182 | struct spi_imx_data *spi_imx; |
1175 | struct resource *res; | 1183 | struct resource *res; |
1176 | int i, ret, irq; | 1184 | int i, ret, irq, spi_drctl; |
1177 | 1185 | ||
1178 | if (!np && !mxc_platform_info) { | 1186 | if (!np && !mxc_platform_info) { |
1179 | dev_err(&pdev->dev, "can't get the platform data\n"); | 1187 | dev_err(&pdev->dev, "can't get the platform data\n"); |
@@ -1181,6 +1189,12 @@ static int spi_imx_probe(struct platform_device *pdev) | |||
1181 | } | 1189 | } |
1182 | 1190 | ||
1183 | master = spi_alloc_master(&pdev->dev, sizeof(struct spi_imx_data)); | 1191 | master = spi_alloc_master(&pdev->dev, sizeof(struct spi_imx_data)); |
1192 | ret = of_property_read_u32(np, "fsl,spi-rdy-drctl", &spi_drctl); | ||
1193 | if ((ret < 0) || (spi_drctl >= 0x3)) { | ||
1194 | /* '11' is reserved */ | ||
1195 | spi_drctl = 0; | ||
1196 | } | ||
1197 | |||
1184 | if (!master) | 1198 | if (!master) |
1185 | return -ENOMEM; | 1199 | return -ENOMEM; |
1186 | 1200 | ||
@@ -1216,7 +1230,9 @@ static int spi_imx_probe(struct platform_device *pdev) | |||
1216 | spi_imx->bitbang.master->unprepare_message = spi_imx_unprepare_message; | 1230 | spi_imx->bitbang.master->unprepare_message = spi_imx_unprepare_message; |
1217 | spi_imx->bitbang.master->mode_bits = SPI_CPOL | SPI_CPHA | SPI_CS_HIGH; | 1231 | spi_imx->bitbang.master->mode_bits = SPI_CPOL | SPI_CPHA | SPI_CS_HIGH; |
1218 | if (is_imx35_cspi(spi_imx) || is_imx51_ecspi(spi_imx)) | 1232 | if (is_imx35_cspi(spi_imx) || is_imx51_ecspi(spi_imx)) |
1219 | spi_imx->bitbang.master->mode_bits |= SPI_LOOP; | 1233 | spi_imx->bitbang.master->mode_bits |= SPI_LOOP | SPI_READY; |
1234 | |||
1235 | spi_imx->spi_drctl = spi_drctl; | ||
1220 | 1236 | ||
1221 | init_completion(&spi_imx->xfer_done); | 1237 | init_completion(&spi_imx->xfer_done); |
1222 | 1238 | ||