19e862375SLee Jones /* 29e862375SLee Jones * Copyright (c) 2008-2014 STMicroelectronics Limited 39e862375SLee Jones * 49e862375SLee Jones * Author: Angus Clark <Angus.Clark@st.com> 59e862375SLee Jones * Patrice Chotard <patrice.chotard@st.com> 69e862375SLee Jones * Lee Jones <lee.jones@linaro.org> 79e862375SLee Jones * 89e862375SLee Jones * SPI master mode controller driver, used in STMicroelectronics devices. 99e862375SLee Jones * 109e862375SLee Jones * May be copied or modified under the terms of the GNU General Public 119e862375SLee Jones * License Version 2.0 only. See linux/COPYING for more information. 129e862375SLee Jones */ 139e862375SLee Jones 149e862375SLee Jones #include <linux/clk.h> 159e862375SLee Jones #include <linux/delay.h> 169e862375SLee Jones #include <linux/interrupt.h> 179e862375SLee Jones #include <linux/io.h> 189e862375SLee Jones #include <linux/module.h> 199e862375SLee Jones #include <linux/pinctrl/consumer.h> 209e862375SLee Jones #include <linux/platform_device.h> 219e862375SLee Jones #include <linux/of.h> 229e862375SLee Jones #include <linux/of_gpio.h> 239e862375SLee Jones #include <linux/of_irq.h> 249e862375SLee Jones #include <linux/pm_runtime.h> 259e862375SLee Jones #include <linux/spi/spi.h> 269e862375SLee Jones #include <linux/spi/spi_bitbang.h> 279e862375SLee Jones 289e862375SLee Jones /* SSC registers */ 299e862375SLee Jones #define SSC_BRG 0x000 309e862375SLee Jones #define SSC_TBUF 0x004 319e862375SLee Jones #define SSC_RBUF 0x008 329e862375SLee Jones #define SSC_CTL 0x00C 339e862375SLee Jones #define SSC_IEN 0x010 349e862375SLee Jones #define SSC_I2C 0x018 359e862375SLee Jones 369e862375SLee Jones /* SSC Control */ 379e862375SLee Jones #define SSC_CTL_DATA_WIDTH_9 0x8 389e862375SLee Jones #define SSC_CTL_DATA_WIDTH_MSK 0xf 399e862375SLee Jones #define SSC_CTL_BM 0xf 409e862375SLee Jones #define SSC_CTL_HB BIT(4) 419e862375SLee Jones #define SSC_CTL_PH BIT(5) 429e862375SLee Jones #define SSC_CTL_PO BIT(6) 439e862375SLee Jones #define SSC_CTL_SR BIT(7) 449e862375SLee Jones #define SSC_CTL_MS BIT(8) 459e862375SLee Jones #define SSC_CTL_EN BIT(9) 469e862375SLee Jones #define SSC_CTL_LPB BIT(10) 479e862375SLee Jones #define SSC_CTL_EN_TX_FIFO BIT(11) 489e862375SLee Jones #define SSC_CTL_EN_RX_FIFO BIT(12) 499e862375SLee Jones #define SSC_CTL_EN_CLST_RX BIT(13) 509e862375SLee Jones 519e862375SLee Jones /* SSC Interrupt Enable */ 529e862375SLee Jones #define SSC_IEN_TEEN BIT(2) 539e862375SLee Jones 549e862375SLee Jones #define FIFO_SIZE 8 559e862375SLee Jones 569e862375SLee Jones struct spi_st { 579e862375SLee Jones /* SSC SPI Controller */ 589e862375SLee Jones void __iomem *base; 599e862375SLee Jones struct clk *clk; 609e862375SLee Jones struct device *dev; 619e862375SLee Jones 629e862375SLee Jones /* SSC SPI current transaction */ 639e862375SLee Jones const u8 *tx_ptr; 649e862375SLee Jones u8 *rx_ptr; 659e862375SLee Jones u16 bytes_per_word; 669e862375SLee Jones unsigned int words_remaining; 679e862375SLee Jones unsigned int baud; 689e862375SLee Jones struct completion done; 699e862375SLee Jones }; 709e862375SLee Jones 719e862375SLee Jones static int spi_st_clk_enable(struct spi_st *spi_st) 729e862375SLee Jones { 739e862375SLee Jones /* 749e862375SLee Jones * Current platforms use one of the core clocks for SPI and I2C. 759e862375SLee Jones * If we attempt to disable the clock, the system will hang. 769e862375SLee Jones * 779e862375SLee Jones * TODO: Remove this when platform supports power domains. 789e862375SLee Jones */ 799e862375SLee Jones return 0; 809e862375SLee Jones 819e862375SLee Jones return clk_prepare_enable(spi_st->clk); 829e862375SLee Jones } 839e862375SLee Jones 849e862375SLee Jones static void spi_st_clk_disable(struct spi_st *spi_st) 859e862375SLee Jones { 869e862375SLee Jones /* 879e862375SLee Jones * Current platforms use one of the core clocks for SPI and I2C. 889e862375SLee Jones * If we attempt to disable the clock, the system will hang. 899e862375SLee Jones * 909e862375SLee Jones * TODO: Remove this when platform supports power domains. 919e862375SLee Jones */ 929e862375SLee Jones return; 939e862375SLee Jones 949e862375SLee Jones clk_disable_unprepare(spi_st->clk); 959e862375SLee Jones } 969e862375SLee Jones 979e862375SLee Jones /* Load the TX FIFO */ 989e862375SLee Jones static void ssc_write_tx_fifo(struct spi_st *spi_st) 999e862375SLee Jones { 1009e862375SLee Jones unsigned int count, i; 1019e862375SLee Jones uint32_t word = 0; 1029e862375SLee Jones 1039e862375SLee Jones if (spi_st->words_remaining > FIFO_SIZE) 1049e862375SLee Jones count = FIFO_SIZE; 1059e862375SLee Jones else 1069e862375SLee Jones count = spi_st->words_remaining; 1079e862375SLee Jones 1089e862375SLee Jones for (i = 0; i < count; i++) { 1099e862375SLee Jones if (spi_st->tx_ptr) { 1109e862375SLee Jones if (spi_st->bytes_per_word == 1) { 1119e862375SLee Jones word = *spi_st->tx_ptr++; 1129e862375SLee Jones } else { 1139e862375SLee Jones word = *spi_st->tx_ptr++; 1149e862375SLee Jones word = *spi_st->tx_ptr++ | (word << 8); 1159e862375SLee Jones } 1169e862375SLee Jones } 1179e862375SLee Jones writel_relaxed(word, spi_st->base + SSC_TBUF); 1189e862375SLee Jones } 1199e862375SLee Jones } 1209e862375SLee Jones 1219e862375SLee Jones /* Read the RX FIFO */ 1229e862375SLee Jones static void ssc_read_rx_fifo(struct spi_st *spi_st) 1239e862375SLee Jones { 1249e862375SLee Jones unsigned int count, i; 1259e862375SLee Jones uint32_t word = 0; 1269e862375SLee Jones 1279e862375SLee Jones if (spi_st->words_remaining > FIFO_SIZE) 1289e862375SLee Jones count = FIFO_SIZE; 1299e862375SLee Jones else 1309e862375SLee Jones count = spi_st->words_remaining; 1319e862375SLee Jones 1329e862375SLee Jones for (i = 0; i < count; i++) { 1339e862375SLee Jones word = readl_relaxed(spi_st->base + SSC_RBUF); 1349e862375SLee Jones 1359e862375SLee Jones if (spi_st->rx_ptr) { 1369e862375SLee Jones if (spi_st->bytes_per_word == 1) { 1379e862375SLee Jones *spi_st->rx_ptr++ = (uint8_t)word; 1389e862375SLee Jones } else { 1399e862375SLee Jones *spi_st->rx_ptr++ = (word >> 8); 1409e862375SLee Jones *spi_st->rx_ptr++ = word & 0xff; 1419e862375SLee Jones } 1429e862375SLee Jones } 1439e862375SLee Jones } 1449e862375SLee Jones spi_st->words_remaining -= count; 1459e862375SLee Jones } 1469e862375SLee Jones 1479e862375SLee Jones static int spi_st_transfer_one(struct spi_master *master, 1489e862375SLee Jones struct spi_device *spi, struct spi_transfer *t) 1499e862375SLee Jones { 1509e862375SLee Jones struct spi_st *spi_st = spi_master_get_devdata(master); 1519e862375SLee Jones uint32_t ctl = 0; 1529e862375SLee Jones 1539e862375SLee Jones /* Setup transfer */ 1549e862375SLee Jones spi_st->tx_ptr = t->tx_buf; 1559e862375SLee Jones spi_st->rx_ptr = t->rx_buf; 1569e862375SLee Jones 1579e862375SLee Jones if (spi->bits_per_word > 8) { 1589e862375SLee Jones /* 1599e862375SLee Jones * Anything greater than 8 bits-per-word requires 2 1609e862375SLee Jones * bytes-per-word in the RX/TX buffers 1619e862375SLee Jones */ 1629e862375SLee Jones spi_st->bytes_per_word = 2; 1639e862375SLee Jones spi_st->words_remaining = t->len / 2; 1649e862375SLee Jones 1659e862375SLee Jones } else if (spi->bits_per_word == 8 && !(t->len & 0x1)) { 1669e862375SLee Jones /* 1679e862375SLee Jones * If transfer is even-length, and 8 bits-per-word, then 1689e862375SLee Jones * implement as half-length 16 bits-per-word transfer 1699e862375SLee Jones */ 1709e862375SLee Jones spi_st->bytes_per_word = 2; 1719e862375SLee Jones spi_st->words_remaining = t->len / 2; 1729e862375SLee Jones 1739e862375SLee Jones /* Set SSC_CTL to 16 bits-per-word */ 1749e862375SLee Jones ctl = readl_relaxed(spi_st->base + SSC_CTL); 1759e862375SLee Jones writel_relaxed((ctl | 0xf), spi_st->base + SSC_CTL); 1769e862375SLee Jones 1779e862375SLee Jones readl_relaxed(spi_st->base + SSC_RBUF); 1789e862375SLee Jones 1799e862375SLee Jones } else { 1809e862375SLee Jones spi_st->bytes_per_word = 1; 1819e862375SLee Jones spi_st->words_remaining = t->len; 1829e862375SLee Jones } 1839e862375SLee Jones 1849e862375SLee Jones reinit_completion(&spi_st->done); 1859e862375SLee Jones 1869e862375SLee Jones /* Start transfer by writing to the TX FIFO */ 1879e862375SLee Jones ssc_write_tx_fifo(spi_st); 1889e862375SLee Jones writel_relaxed(SSC_IEN_TEEN, spi_st->base + SSC_IEN); 1899e862375SLee Jones 1909e862375SLee Jones /* Wait for transfer to complete */ 1919e862375SLee Jones wait_for_completion(&spi_st->done); 1929e862375SLee Jones 1939e862375SLee Jones /* Restore SSC_CTL if necessary */ 1949e862375SLee Jones if (ctl) 1959e862375SLee Jones writel_relaxed(ctl, spi_st->base + SSC_CTL); 1969e862375SLee Jones 1979e862375SLee Jones spi_finalize_current_transfer(spi->master); 1989e862375SLee Jones 1999e862375SLee Jones return t->len; 2009e862375SLee Jones } 2019e862375SLee Jones 2029e862375SLee Jones static void spi_st_cleanup(struct spi_device *spi) 2039e862375SLee Jones { 2049e862375SLee Jones int cs = spi->cs_gpio; 2059e862375SLee Jones 2069e862375SLee Jones if (gpio_is_valid(cs)) 2079e862375SLee Jones devm_gpio_free(&spi->dev, cs); 2089e862375SLee Jones } 2099e862375SLee Jones 2109e862375SLee Jones /* the spi->mode bits understood by this driver: */ 2119e862375SLee Jones #define MODEBITS (SPI_CPOL | SPI_CPHA | SPI_LSB_FIRST | SPI_LOOP | SPI_CS_HIGH) 2129e862375SLee Jones static int spi_st_setup(struct spi_device *spi) 2139e862375SLee Jones { 2149e862375SLee Jones struct spi_st *spi_st = spi_master_get_devdata(spi->master); 2159e862375SLee Jones u32 spi_st_clk, sscbrg, var; 2169e862375SLee Jones u32 hz = spi->max_speed_hz; 2179e862375SLee Jones int cs = spi->cs_gpio; 2189e862375SLee Jones int ret; 2199e862375SLee Jones 2209e862375SLee Jones if (!hz) { 2219e862375SLee Jones dev_err(&spi->dev, "max_speed_hz unspecified\n"); 2229e862375SLee Jones return -EINVAL; 2239e862375SLee Jones } 2249e862375SLee Jones 2259e862375SLee Jones if (!gpio_is_valid(cs)) { 2269e862375SLee Jones dev_err(&spi->dev, "%d is not a valid gpio\n", cs); 2279e862375SLee Jones return -EINVAL; 2289e862375SLee Jones } 2299e862375SLee Jones 2309e862375SLee Jones if (devm_gpio_request(&spi->dev, cs, dev_name(&spi->dev))) { 2319e862375SLee Jones dev_err(&spi->dev, "could not request gpio:%d\n", cs); 2329e862375SLee Jones return -EINVAL; 2339e862375SLee Jones } 2349e862375SLee Jones 2359e862375SLee Jones ret = gpio_direction_output(cs, spi->mode & SPI_CS_HIGH); 2369e862375SLee Jones if (ret) 2379e862375SLee Jones return ret; 2389e862375SLee Jones 2399e862375SLee Jones spi_st_clk = clk_get_rate(spi_st->clk); 2409e862375SLee Jones 2419e862375SLee Jones /* Set SSC_BRF */ 2429e862375SLee Jones sscbrg = spi_st_clk / (2 * hz); 2439e862375SLee Jones if (sscbrg < 0x07 || sscbrg > BIT(16)) { 2449e862375SLee Jones dev_err(&spi->dev, 2459e862375SLee Jones "baudrate %d outside valid range %d\n", sscbrg, hz); 2469e862375SLee Jones return -EINVAL; 2479e862375SLee Jones } 2489e862375SLee Jones 2499e862375SLee Jones spi_st->baud = spi_st_clk / (2 * sscbrg); 2509e862375SLee Jones if (sscbrg == BIT(16)) /* 16-bit counter wraps */ 2519e862375SLee Jones sscbrg = 0x0; 2529e862375SLee Jones 2539e862375SLee Jones writel_relaxed(sscbrg, spi_st->base + SSC_BRG); 2549e862375SLee Jones 2559e862375SLee Jones dev_dbg(&spi->dev, 2569e862375SLee Jones "setting baudrate:target= %u hz, actual= %u hz, sscbrg= %u\n", 2579e862375SLee Jones hz, spi_st->baud, sscbrg); 2589e862375SLee Jones 2599e862375SLee Jones /* Set SSC_CTL and enable SSC */ 2609e862375SLee Jones var = readl_relaxed(spi_st->base + SSC_CTL); 2619e862375SLee Jones var |= SSC_CTL_MS; 2629e862375SLee Jones 2639e862375SLee Jones if (spi->mode & SPI_CPOL) 2649e862375SLee Jones var |= SSC_CTL_PO; 2659e862375SLee Jones else 2669e862375SLee Jones var &= ~SSC_CTL_PO; 2679e862375SLee Jones 2689e862375SLee Jones if (spi->mode & SPI_CPHA) 2699e862375SLee Jones var |= SSC_CTL_PH; 2709e862375SLee Jones else 2719e862375SLee Jones var &= ~SSC_CTL_PH; 2729e862375SLee Jones 2739e862375SLee Jones if ((spi->mode & SPI_LSB_FIRST) == 0) 2749e862375SLee Jones var |= SSC_CTL_HB; 2759e862375SLee Jones else 2769e862375SLee Jones var &= ~SSC_CTL_HB; 2779e862375SLee Jones 2789e862375SLee Jones if (spi->mode & SPI_LOOP) 2799e862375SLee Jones var |= SSC_CTL_LPB; 2809e862375SLee Jones else 2819e862375SLee Jones var &= ~SSC_CTL_LPB; 2829e862375SLee Jones 2839e862375SLee Jones var &= ~SSC_CTL_DATA_WIDTH_MSK; 2849e862375SLee Jones var |= (spi->bits_per_word - 1); 2859e862375SLee Jones 2869e862375SLee Jones var |= SSC_CTL_EN_TX_FIFO | SSC_CTL_EN_RX_FIFO; 2879e862375SLee Jones var |= SSC_CTL_EN; 2889e862375SLee Jones 2899e862375SLee Jones writel_relaxed(var, spi_st->base + SSC_CTL); 2909e862375SLee Jones 2919e862375SLee Jones /* Clear the status register */ 2929e862375SLee Jones readl_relaxed(spi_st->base + SSC_RBUF); 2939e862375SLee Jones 2949e862375SLee Jones return 0; 2959e862375SLee Jones } 2969e862375SLee Jones 2979e862375SLee Jones /* Interrupt fired when TX shift register becomes empty */ 2989e862375SLee Jones static irqreturn_t spi_st_irq(int irq, void *dev_id) 2999e862375SLee Jones { 3009e862375SLee Jones struct spi_st *spi_st = (struct spi_st *)dev_id; 3019e862375SLee Jones 3029e862375SLee Jones /* Read RX FIFO */ 3039e862375SLee Jones ssc_read_rx_fifo(spi_st); 3049e862375SLee Jones 3059e862375SLee Jones /* Fill TX FIFO */ 3069e862375SLee Jones if (spi_st->words_remaining) { 3079e862375SLee Jones ssc_write_tx_fifo(spi_st); 3089e862375SLee Jones } else { 3099e862375SLee Jones /* TX/RX complete */ 3109e862375SLee Jones writel_relaxed(0x0, spi_st->base + SSC_IEN); 3119e862375SLee Jones /* 3129e862375SLee Jones * read SSC_IEN to ensure that this bit is set 3139e862375SLee Jones * before re-enabling interrupt 3149e862375SLee Jones */ 3159e862375SLee Jones readl(spi_st->base + SSC_IEN); 3169e862375SLee Jones complete(&spi_st->done); 3179e862375SLee Jones } 3189e862375SLee Jones 3199e862375SLee Jones return IRQ_HANDLED; 3209e862375SLee Jones } 3219e862375SLee Jones 3229e862375SLee Jones static int spi_st_probe(struct platform_device *pdev) 3239e862375SLee Jones { 3249e862375SLee Jones struct device_node *np = pdev->dev.of_node; 3259e862375SLee Jones struct spi_master *master; 3269e862375SLee Jones struct resource *res; 3279e862375SLee Jones struct spi_st *spi_st; 3289e862375SLee Jones int irq, ret = 0; 3299e862375SLee Jones u32 var; 3309e862375SLee Jones 3319e862375SLee Jones master = spi_alloc_master(&pdev->dev, sizeof(*spi_st)); 3329e862375SLee Jones if (!master) 3339e862375SLee Jones return -ENOMEM; 3349e862375SLee Jones 3359e862375SLee Jones master->dev.of_node = np; 3369e862375SLee Jones master->mode_bits = MODEBITS; 3379e862375SLee Jones master->setup = spi_st_setup; 3389e862375SLee Jones master->cleanup = spi_st_cleanup; 3399e862375SLee Jones master->transfer_one = spi_st_transfer_one; 3409e862375SLee Jones master->bits_per_word_mask = SPI_BPW_MASK(8) | SPI_BPW_MASK(16); 3419e862375SLee Jones master->auto_runtime_pm = true; 3429e862375SLee Jones master->bus_num = pdev->id; 3439e862375SLee Jones spi_st = spi_master_get_devdata(master); 3449e862375SLee Jones 3459e862375SLee Jones spi_st->clk = devm_clk_get(&pdev->dev, "ssc"); 3469e862375SLee Jones if (IS_ERR(spi_st->clk)) { 3479e862375SLee Jones dev_err(&pdev->dev, "Unable to request clock\n"); 3489e862375SLee Jones return PTR_ERR(spi_st->clk); 3499e862375SLee Jones } 3509e862375SLee Jones 3519e862375SLee Jones ret = spi_st_clk_enable(spi_st); 3529e862375SLee Jones if (ret) 3539e862375SLee Jones return ret; 3549e862375SLee Jones 3559e862375SLee Jones init_completion(&spi_st->done); 3569e862375SLee Jones 3579e862375SLee Jones /* Get resources */ 3589e862375SLee Jones res = platform_get_resource(pdev, IORESOURCE_MEM, 0); 3599e862375SLee Jones spi_st->base = devm_ioremap_resource(&pdev->dev, res); 3609e862375SLee Jones if (IS_ERR(spi_st->base)) { 3619e862375SLee Jones ret = PTR_ERR(spi_st->base); 3629e862375SLee Jones goto clk_disable; 3639e862375SLee Jones } 3649e862375SLee Jones 3659e862375SLee Jones /* Disable I2C and Reset SSC */ 3669e862375SLee Jones writel_relaxed(0x0, spi_st->base + SSC_I2C); 3679e862375SLee Jones var = readw_relaxed(spi_st->base + SSC_CTL); 3689e862375SLee Jones var |= SSC_CTL_SR; 3699e862375SLee Jones writel_relaxed(var, spi_st->base + SSC_CTL); 3709e862375SLee Jones 3719e862375SLee Jones udelay(1); 3729e862375SLee Jones var = readl_relaxed(spi_st->base + SSC_CTL); 3739e862375SLee Jones var &= ~SSC_CTL_SR; 3749e862375SLee Jones writel_relaxed(var, spi_st->base + SSC_CTL); 3759e862375SLee Jones 3769e862375SLee Jones /* Set SSC into slave mode before reconfiguring PIO pins */ 3779e862375SLee Jones var = readl_relaxed(spi_st->base + SSC_CTL); 3789e862375SLee Jones var &= ~SSC_CTL_MS; 3799e862375SLee Jones writel_relaxed(var, spi_st->base + SSC_CTL); 3809e862375SLee Jones 3819e862375SLee Jones irq = irq_of_parse_and_map(np, 0); 3829e862375SLee Jones if (!irq) { 3839e862375SLee Jones dev_err(&pdev->dev, "IRQ missing or invalid\n"); 3849e862375SLee Jones ret = -EINVAL; 3859e862375SLee Jones goto clk_disable; 3869e862375SLee Jones } 3879e862375SLee Jones 3889e862375SLee Jones ret = devm_request_irq(&pdev->dev, irq, spi_st_irq, 0, 3899e862375SLee Jones pdev->name, spi_st); 3909e862375SLee Jones if (ret) { 3919e862375SLee Jones dev_err(&pdev->dev, "Failed to request irq %d\n", irq); 3929e862375SLee Jones goto clk_disable; 3939e862375SLee Jones } 3949e862375SLee Jones 3959e862375SLee Jones /* by default the device is on */ 3969e862375SLee Jones pm_runtime_set_active(&pdev->dev); 3979e862375SLee Jones pm_runtime_enable(&pdev->dev); 3989e862375SLee Jones 3999e862375SLee Jones platform_set_drvdata(pdev, master); 4009e862375SLee Jones 4019e862375SLee Jones ret = devm_spi_register_master(&pdev->dev, master); 4029e862375SLee Jones if (ret) { 4039e862375SLee Jones dev_err(&pdev->dev, "Failed to register master\n"); 4049e862375SLee Jones goto clk_disable; 4059e862375SLee Jones } 4069e862375SLee Jones 4079e862375SLee Jones return 0; 4089e862375SLee Jones 4099e862375SLee Jones clk_disable: 4109e862375SLee Jones spi_st_clk_disable(spi_st); 4119e862375SLee Jones 4129e862375SLee Jones return ret; 4139e862375SLee Jones } 4149e862375SLee Jones 4159e862375SLee Jones static int spi_st_remove(struct platform_device *pdev) 4169e862375SLee Jones { 4179e862375SLee Jones struct spi_master *master = platform_get_drvdata(pdev); 4189e862375SLee Jones struct spi_st *spi_st = spi_master_get_devdata(master); 4199e862375SLee Jones 4209e862375SLee Jones spi_st_clk_disable(spi_st); 4219e862375SLee Jones 4229e862375SLee Jones pinctrl_pm_select_sleep_state(&pdev->dev); 4239e862375SLee Jones 4249e862375SLee Jones return 0; 4259e862375SLee Jones } 4269e862375SLee Jones 4279e862375SLee Jones #ifdef CONFIG_PM 4289e862375SLee Jones static int spi_st_runtime_suspend(struct device *dev) 4299e862375SLee Jones { 4309e862375SLee Jones struct spi_master *master = dev_get_drvdata(dev); 4319e862375SLee Jones struct spi_st *spi_st = spi_master_get_devdata(master); 4329e862375SLee Jones 4339e862375SLee Jones writel_relaxed(0, spi_st->base + SSC_IEN); 4349e862375SLee Jones pinctrl_pm_select_sleep_state(dev); 4359e862375SLee Jones 4369e862375SLee Jones spi_st_clk_disable(spi_st); 4379e862375SLee Jones 4389e862375SLee Jones return 0; 4399e862375SLee Jones } 4409e862375SLee Jones 4419e862375SLee Jones static int spi_st_runtime_resume(struct device *dev) 4429e862375SLee Jones { 4439e862375SLee Jones struct spi_master *master = dev_get_drvdata(dev); 4449e862375SLee Jones struct spi_st *spi_st = spi_master_get_devdata(master); 4459e862375SLee Jones int ret; 4469e862375SLee Jones 4479e862375SLee Jones ret = spi_st_clk_enable(spi_st); 4489e862375SLee Jones pinctrl_pm_select_default_state(dev); 4499e862375SLee Jones 4509e862375SLee Jones return ret; 4519e862375SLee Jones } 4529e862375SLee Jones #endif 4539e862375SLee Jones 4549e862375SLee Jones #ifdef CONFIG_PM_SLEEP 4559e862375SLee Jones static int spi_st_suspend(struct device *dev) 4569e862375SLee Jones { 4579e862375SLee Jones struct spi_master *master = dev_get_drvdata(dev); 4589e862375SLee Jones int ret; 4599e862375SLee Jones 4609e862375SLee Jones ret = spi_master_suspend(master); 4619e862375SLee Jones if (ret) 4629e862375SLee Jones return ret; 4639e862375SLee Jones 4649e862375SLee Jones return pm_runtime_force_suspend(dev); 4659e862375SLee Jones } 4669e862375SLee Jones 4679e862375SLee Jones static int spi_st_resume(struct device *dev) 4689e862375SLee Jones { 4699e862375SLee Jones struct spi_master *master = dev_get_drvdata(dev); 4709e862375SLee Jones int ret; 4719e862375SLee Jones 4729e862375SLee Jones ret = spi_master_resume(master); 4739e862375SLee Jones if (ret) 4749e862375SLee Jones return ret; 4759e862375SLee Jones 4769e862375SLee Jones return pm_runtime_force_resume(dev); 4779e862375SLee Jones } 4789e862375SLee Jones #endif 4799e862375SLee Jones 4809e862375SLee Jones static const struct dev_pm_ops spi_st_pm = { 4819e862375SLee Jones SET_SYSTEM_SLEEP_PM_OPS(spi_st_suspend, spi_st_resume) 4829e862375SLee Jones SET_RUNTIME_PM_OPS(spi_st_runtime_suspend, spi_st_runtime_resume, NULL) 4839e862375SLee Jones }; 4849e862375SLee Jones 485*09355402SFabian Frederick static const struct of_device_id stm_spi_match[] = { 4869e862375SLee Jones { .compatible = "st,comms-ssc4-spi", }, 4879e862375SLee Jones {}, 4889e862375SLee Jones }; 4899e862375SLee Jones MODULE_DEVICE_TABLE(of, stm_spi_match); 4909e862375SLee Jones 4919e862375SLee Jones static struct platform_driver spi_st_driver = { 4929e862375SLee Jones .driver = { 4939e862375SLee Jones .name = "spi-st", 4949e862375SLee Jones .pm = &spi_st_pm, 4959e862375SLee Jones .of_match_table = of_match_ptr(stm_spi_match), 4969e862375SLee Jones }, 4979e862375SLee Jones .probe = spi_st_probe, 4989e862375SLee Jones .remove = spi_st_remove, 4999e862375SLee Jones }; 5009e862375SLee Jones module_platform_driver(spi_st_driver); 5019e862375SLee Jones 5029e862375SLee Jones MODULE_AUTHOR("Patrice Chotard <patrice.chotard@st.com>"); 5039e862375SLee Jones MODULE_DESCRIPTION("STM SSC SPI driver"); 5049e862375SLee Jones MODULE_LICENSE("GPL v2"); 505