linux/drivers/spi/spi-synquacer.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0
   2//
   3// Synquacer HSSPI controller driver
   4//
   5// Copyright (c) 2015-2018 Socionext Inc.
   6// Copyright (c) 2018-2019 Linaro Ltd.
   7//
   8
   9#include <linux/acpi.h>
  10#include <linux/delay.h>
  11#include <linux/interrupt.h>
  12#include <linux/io.h>
  13#include <linux/module.h>
  14#include <linux/of.h>
  15#include <linux/platform_device.h>
  16#include <linux/pm_runtime.h>
  17#include <linux/scatterlist.h>
  18#include <linux/slab.h>
  19#include <linux/spi/spi.h>
  20#include <linux/spinlock.h>
  21#include <linux/clk.h>
  22
  23/* HSSPI register address definitions */
  24#define SYNQUACER_HSSPI_REG_MCTRL       0x00
  25#define SYNQUACER_HSSPI_REG_PCC0        0x04
  26#define SYNQUACER_HSSPI_REG_PCC(n)      (SYNQUACER_HSSPI_REG_PCC0 + (n) * 4)
  27#define SYNQUACER_HSSPI_REG_TXF         0x14
  28#define SYNQUACER_HSSPI_REG_TXE         0x18
  29#define SYNQUACER_HSSPI_REG_TXC         0x1C
  30#define SYNQUACER_HSSPI_REG_RXF         0x20
  31#define SYNQUACER_HSSPI_REG_RXE         0x24
  32#define SYNQUACER_HSSPI_REG_RXC         0x28
  33#define SYNQUACER_HSSPI_REG_FAULTF      0x2C
  34#define SYNQUACER_HSSPI_REG_FAULTC      0x30
  35#define SYNQUACER_HSSPI_REG_DMCFG       0x34
  36#define SYNQUACER_HSSPI_REG_DMSTART     0x38
  37#define SYNQUACER_HSSPI_REG_DMBCC       0x3C
  38#define SYNQUACER_HSSPI_REG_DMSTATUS    0x40
  39#define SYNQUACER_HSSPI_REG_FIFOCFG     0x4C
  40#define SYNQUACER_HSSPI_REG_TX_FIFO     0x50
  41#define SYNQUACER_HSSPI_REG_RX_FIFO     0x90
  42#define SYNQUACER_HSSPI_REG_MID         0xFC
  43
  44/* HSSPI register bit definitions */
  45#define SYNQUACER_HSSPI_MCTRL_MEN                       BIT(0)
  46#define SYNQUACER_HSSPI_MCTRL_COMMAND_SEQUENCE_EN       BIT(1)
  47#define SYNQUACER_HSSPI_MCTRL_CDSS                      BIT(3)
  48#define SYNQUACER_HSSPI_MCTRL_MES                       BIT(4)
  49#define SYNQUACER_HSSPI_MCTRL_SYNCON                    BIT(5)
  50
  51#define SYNQUACER_HSSPI_PCC_CPHA                BIT(0)
  52#define SYNQUACER_HSSPI_PCC_CPOL                BIT(1)
  53#define SYNQUACER_HSSPI_PCC_ACES                BIT(2)
  54#define SYNQUACER_HSSPI_PCC_RTM                 BIT(3)
  55#define SYNQUACER_HSSPI_PCC_SSPOL               BIT(4)
  56#define SYNQUACER_HSSPI_PCC_SDIR                BIT(7)
  57#define SYNQUACER_HSSPI_PCC_SENDIAN             BIT(8)
  58#define SYNQUACER_HSSPI_PCC_SAFESYNC            BIT(16)
  59#define SYNQUACER_HSSPI_PCC_SS2CD_SHIFT         5U
  60#define SYNQUACER_HSSPI_PCC_CDRS_MASK           0x7f
  61#define SYNQUACER_HSSPI_PCC_CDRS_SHIFT          9U
  62
  63#define SYNQUACER_HSSPI_TXF_FIFO_FULL           BIT(0)
  64#define SYNQUACER_HSSPI_TXF_FIFO_EMPTY          BIT(1)
  65#define SYNQUACER_HSSPI_TXF_SLAVE_RELEASED      BIT(6)
  66
  67#define SYNQUACER_HSSPI_TXE_FIFO_FULL           BIT(0)
  68#define SYNQUACER_HSSPI_TXE_FIFO_EMPTY          BIT(1)
  69#define SYNQUACER_HSSPI_TXE_SLAVE_RELEASED      BIT(6)
  70
  71#define SYNQUACER_HSSPI_RXF_FIFO_MORE_THAN_THRESHOLD            BIT(5)
  72#define SYNQUACER_HSSPI_RXF_SLAVE_RELEASED                      BIT(6)
  73
  74#define SYNQUACER_HSSPI_RXE_FIFO_MORE_THAN_THRESHOLD            BIT(5)
  75#define SYNQUACER_HSSPI_RXE_SLAVE_RELEASED                      BIT(6)
  76
  77#define SYNQUACER_HSSPI_DMCFG_SSDC              BIT(1)
  78#define SYNQUACER_HSSPI_DMCFG_MSTARTEN          BIT(2)
  79
  80#define SYNQUACER_HSSPI_DMSTART_START           BIT(0)
  81#define SYNQUACER_HSSPI_DMSTOP_STOP             BIT(8)
  82#define SYNQUACER_HSSPI_DMPSEL_CS_MASK          0x3
  83#define SYNQUACER_HSSPI_DMPSEL_CS_SHIFT         16U
  84#define SYNQUACER_HSSPI_DMTRP_BUS_WIDTH_SHIFT   24U
  85#define SYNQUACER_HSSPI_DMTRP_DATA_MASK         0x3
  86#define SYNQUACER_HSSPI_DMTRP_DATA_SHIFT        26U
  87#define SYNQUACER_HSSPI_DMTRP_DATA_TXRX         0
  88#define SYNQUACER_HSSPI_DMTRP_DATA_RX           1
  89#define SYNQUACER_HSSPI_DMTRP_DATA_TX           2
  90
  91#define SYNQUACER_HSSPI_DMSTATUS_RX_DATA_MASK   0x1f
  92#define SYNQUACER_HSSPI_DMSTATUS_RX_DATA_SHIFT  8U
  93#define SYNQUACER_HSSPI_DMSTATUS_TX_DATA_MASK   0x1f
  94#define SYNQUACER_HSSPI_DMSTATUS_TX_DATA_SHIFT  16U
  95
  96#define SYNQUACER_HSSPI_FIFOCFG_RX_THRESHOLD_MASK       0xf
  97#define SYNQUACER_HSSPI_FIFOCFG_RX_THRESHOLD_SHIFT      0U
  98#define SYNQUACER_HSSPI_FIFOCFG_TX_THRESHOLD_MASK       0xf
  99#define SYNQUACER_HSSPI_FIFOCFG_TX_THRESHOLD_SHIFT      4U
 100#define SYNQUACER_HSSPI_FIFOCFG_FIFO_WIDTH_MASK         0x3
 101#define SYNQUACER_HSSPI_FIFOCFG_FIFO_WIDTH_SHIFT        8U
 102#define SYNQUACER_HSSPI_FIFOCFG_RX_FLUSH                BIT(11)
 103#define SYNQUACER_HSSPI_FIFOCFG_TX_FLUSH                BIT(12)
 104
 105#define SYNQUACER_HSSPI_FIFO_DEPTH              16U
 106#define SYNQUACER_HSSPI_FIFO_TX_THRESHOLD       4U
 107#define SYNQUACER_HSSPI_FIFO_RX_THRESHOLD \
 108        (SYNQUACER_HSSPI_FIFO_DEPTH - SYNQUACER_HSSPI_FIFO_TX_THRESHOLD)
 109
 110#define SYNQUACER_HSSPI_TRANSFER_MODE_TX        BIT(1)
 111#define SYNQUACER_HSSPI_TRANSFER_MODE_RX        BIT(2)
 112#define SYNQUACER_HSSPI_TRANSFER_TMOUT_MSEC     2000U
 113#define SYNQUACER_HSSPI_ENABLE_TMOUT_MSEC       1000U
 114
 115#define SYNQUACER_HSSPI_CLOCK_SRC_IHCLK         0
 116#define SYNQUACER_HSSPI_CLOCK_SRC_IPCLK         1
 117
 118#define SYNQUACER_HSSPI_NUM_CHIP_SELECT         4U
 119#define SYNQUACER_HSSPI_IRQ_NAME_MAX            32U
 120
 121struct synquacer_spi {
 122        struct device *dev;
 123        struct completion transfer_done;
 124        unsigned int cs;
 125        unsigned int bpw;
 126        unsigned int mode;
 127        unsigned int speed;
 128        bool aces, rtm;
 129        void *rx_buf;
 130        const void *tx_buf;
 131        struct clk *clk;
 132        int clk_src_type;
 133        void __iomem *regs;
 134        u32 tx_words, rx_words;
 135        unsigned int bus_width;
 136        unsigned int transfer_mode;
 137        char rx_irq_name[SYNQUACER_HSSPI_IRQ_NAME_MAX];
 138        char tx_irq_name[SYNQUACER_HSSPI_IRQ_NAME_MAX];
 139};
 140
 141static int read_fifo(struct synquacer_spi *sspi)
 142{
 143        u32 len = readl(sspi->regs + SYNQUACER_HSSPI_REG_DMSTATUS);
 144
 145        len = (len >> SYNQUACER_HSSPI_DMSTATUS_RX_DATA_SHIFT) &
 146               SYNQUACER_HSSPI_DMSTATUS_RX_DATA_MASK;
 147        len = min(len, sspi->rx_words);
 148
 149        switch (sspi->bpw) {
 150        case 8: {
 151                u8 *buf = sspi->rx_buf;
 152
 153                ioread8_rep(sspi->regs + SYNQUACER_HSSPI_REG_RX_FIFO,
 154                            buf, len);
 155                sspi->rx_buf = buf + len;
 156                break;
 157        }
 158        case 16: {
 159                u16 *buf = sspi->rx_buf;
 160
 161                ioread16_rep(sspi->regs + SYNQUACER_HSSPI_REG_RX_FIFO,
 162                             buf, len);
 163                sspi->rx_buf = buf + len;
 164                break;
 165        }
 166        case 24:
 167                /* fallthrough, should use 32-bits access */
 168        case 32: {
 169                u32 *buf = sspi->rx_buf;
 170
 171                ioread32_rep(sspi->regs + SYNQUACER_HSSPI_REG_RX_FIFO,
 172                             buf, len);
 173                sspi->rx_buf = buf + len;
 174                break;
 175        }
 176        default:
 177                return -EINVAL;
 178        }
 179
 180        sspi->rx_words -= len;
 181        return 0;
 182}
 183
 184static int write_fifo(struct synquacer_spi *sspi)
 185{
 186        u32 len = readl(sspi->regs + SYNQUACER_HSSPI_REG_DMSTATUS);
 187
 188        len = (len >> SYNQUACER_HSSPI_DMSTATUS_TX_DATA_SHIFT) &
 189               SYNQUACER_HSSPI_DMSTATUS_TX_DATA_MASK;
 190        len = min(SYNQUACER_HSSPI_FIFO_DEPTH - len,
 191                    sspi->tx_words);
 192
 193        switch (sspi->bpw) {
 194        case 8: {
 195                const u8 *buf = sspi->tx_buf;
 196
 197                iowrite8_rep(sspi->regs + SYNQUACER_HSSPI_REG_TX_FIFO,
 198                             buf, len);
 199                sspi->tx_buf = buf + len;
 200                break;
 201        }
 202        case 16: {
 203                const u16 *buf = sspi->tx_buf;
 204
 205                iowrite16_rep(sspi->regs + SYNQUACER_HSSPI_REG_TX_FIFO,
 206                              buf, len);
 207                sspi->tx_buf = buf + len;
 208                break;
 209        }
 210        case 24:
 211                /* fallthrough, should use 32-bits access */
 212        case 32: {
 213                const u32 *buf = sspi->tx_buf;
 214
 215                iowrite32_rep(sspi->regs + SYNQUACER_HSSPI_REG_TX_FIFO,
 216                              buf, len);
 217                sspi->tx_buf = buf + len;
 218                break;
 219        }
 220        default:
 221                return -EINVAL;
 222        }
 223
 224        sspi->tx_words -= len;
 225        return 0;
 226}
 227
 228static int synquacer_spi_config(struct spi_master *master,
 229                                struct spi_device *spi,
 230                                struct spi_transfer *xfer)
 231{
 232        struct synquacer_spi *sspi = spi_master_get_devdata(master);
 233        unsigned int speed, mode, bpw, cs, bus_width, transfer_mode;
 234        u32 rate, val, div;
 235
 236        /* Full Duplex only on 1-bit wide bus */
 237        if (xfer->rx_buf && xfer->tx_buf &&
 238            (xfer->rx_nbits != 1 || xfer->tx_nbits != 1)) {
 239                dev_err(sspi->dev,
 240                        "RX and TX bus widths must be 1-bit for Full-Duplex!\n");
 241                return -EINVAL;
 242        }
 243
 244        if (xfer->tx_buf) {
 245                bus_width = xfer->tx_nbits;
 246                transfer_mode = SYNQUACER_HSSPI_TRANSFER_MODE_TX;
 247        } else {
 248                bus_width = xfer->rx_nbits;
 249                transfer_mode = SYNQUACER_HSSPI_TRANSFER_MODE_RX;
 250        }
 251
 252        mode = spi->mode;
 253        cs = spi->chip_select;
 254        speed = xfer->speed_hz;
 255        bpw = xfer->bits_per_word;
 256
 257        /* return if nothing to change */
 258        if (speed == sspi->speed &&
 259                bus_width == sspi->bus_width && bpw == sspi->bpw &&
 260                mode == sspi->mode && cs == sspi->cs &&
 261                transfer_mode == sspi->transfer_mode) {
 262                return 0;
 263        }
 264
 265        sspi->transfer_mode = transfer_mode;
 266        rate = master->max_speed_hz;
 267
 268        div = DIV_ROUND_UP(rate, speed);
 269        if (div > 254) {
 270                dev_err(sspi->dev, "Requested rate too low (%u)\n",
 271                        sspi->speed);
 272                return -EINVAL;
 273        }
 274
 275        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_PCC(cs));
 276        val &= ~SYNQUACER_HSSPI_PCC_SAFESYNC;
 277        if (bpw == 8 && (mode & (SPI_TX_DUAL | SPI_RX_DUAL)) && div < 3)
 278                val |= SYNQUACER_HSSPI_PCC_SAFESYNC;
 279        if (bpw == 8 && (mode & (SPI_TX_QUAD | SPI_RX_QUAD)) && div < 6)
 280                val |= SYNQUACER_HSSPI_PCC_SAFESYNC;
 281        if (bpw == 16 && (mode & (SPI_TX_QUAD | SPI_RX_QUAD)) && div < 3)
 282                val |= SYNQUACER_HSSPI_PCC_SAFESYNC;
 283
 284        if (mode & SPI_CPHA)
 285                val |= SYNQUACER_HSSPI_PCC_CPHA;
 286        else
 287                val &= ~SYNQUACER_HSSPI_PCC_CPHA;
 288
 289        if (mode & SPI_CPOL)
 290                val |= SYNQUACER_HSSPI_PCC_CPOL;
 291        else
 292                val &= ~SYNQUACER_HSSPI_PCC_CPOL;
 293
 294        if (mode & SPI_CS_HIGH)
 295                val |= SYNQUACER_HSSPI_PCC_SSPOL;
 296        else
 297                val &= ~SYNQUACER_HSSPI_PCC_SSPOL;
 298
 299        if (mode & SPI_LSB_FIRST)
 300                val |= SYNQUACER_HSSPI_PCC_SDIR;
 301        else
 302                val &= ~SYNQUACER_HSSPI_PCC_SDIR;
 303
 304        if (sspi->aces)
 305                val |= SYNQUACER_HSSPI_PCC_ACES;
 306        else
 307                val &= ~SYNQUACER_HSSPI_PCC_ACES;
 308
 309        if (sspi->rtm)
 310                val |= SYNQUACER_HSSPI_PCC_RTM;
 311        else
 312                val &= ~SYNQUACER_HSSPI_PCC_RTM;
 313
 314        val |= (3 << SYNQUACER_HSSPI_PCC_SS2CD_SHIFT);
 315        val |= SYNQUACER_HSSPI_PCC_SENDIAN;
 316
 317        val &= ~(SYNQUACER_HSSPI_PCC_CDRS_MASK <<
 318                 SYNQUACER_HSSPI_PCC_CDRS_SHIFT);
 319        val |= ((div >> 1) << SYNQUACER_HSSPI_PCC_CDRS_SHIFT);
 320
 321        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_PCC(cs));
 322
 323        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_FIFOCFG);
 324        val &= ~(SYNQUACER_HSSPI_FIFOCFG_FIFO_WIDTH_MASK <<
 325                 SYNQUACER_HSSPI_FIFOCFG_FIFO_WIDTH_SHIFT);
 326        val |= ((bpw / 8 - 1) << SYNQUACER_HSSPI_FIFOCFG_FIFO_WIDTH_SHIFT);
 327        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_FIFOCFG);
 328
 329        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 330        val &= ~(SYNQUACER_HSSPI_DMTRP_DATA_MASK <<
 331                 SYNQUACER_HSSPI_DMTRP_DATA_SHIFT);
 332
 333        if (xfer->rx_buf)
 334                val |= (SYNQUACER_HSSPI_DMTRP_DATA_RX <<
 335                        SYNQUACER_HSSPI_DMTRP_DATA_SHIFT);
 336        else
 337                val |= (SYNQUACER_HSSPI_DMTRP_DATA_TX <<
 338                        SYNQUACER_HSSPI_DMTRP_DATA_SHIFT);
 339
 340        val &= ~(3 << SYNQUACER_HSSPI_DMTRP_BUS_WIDTH_SHIFT);
 341        val |= ((bus_width >> 1) << SYNQUACER_HSSPI_DMTRP_BUS_WIDTH_SHIFT);
 342        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 343
 344        sspi->bpw = bpw;
 345        sspi->mode = mode;
 346        sspi->speed = speed;
 347        sspi->cs = spi->chip_select;
 348        sspi->bus_width = bus_width;
 349
 350        return 0;
 351}
 352
 353static int synquacer_spi_transfer_one(struct spi_master *master,
 354                                      struct spi_device *spi,
 355                                      struct spi_transfer *xfer)
 356{
 357        struct synquacer_spi *sspi = spi_master_get_devdata(master);
 358        int ret;
 359        int status = 0;
 360        u32 words;
 361        u8 bpw;
 362        u32 val;
 363
 364        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 365        val &= ~SYNQUACER_HSSPI_DMSTOP_STOP;
 366        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 367
 368        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_FIFOCFG);
 369        val |= SYNQUACER_HSSPI_FIFOCFG_RX_FLUSH;
 370        val |= SYNQUACER_HSSPI_FIFOCFG_TX_FLUSH;
 371        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_FIFOCFG);
 372
 373        /*
 374         * See if we can transfer 4-bytes as 1 word
 375         * to maximize the FIFO buffer efficiency.
 376         */
 377        bpw = xfer->bits_per_word;
 378        if (bpw == 8 && !(xfer->len % 4) && !(spi->mode & SPI_LSB_FIRST))
 379                xfer->bits_per_word = 32;
 380
 381        ret = synquacer_spi_config(master, spi, xfer);
 382
 383        /* restore */
 384        xfer->bits_per_word = bpw;
 385
 386        if (ret)
 387                return ret;
 388
 389        reinit_completion(&sspi->transfer_done);
 390
 391        sspi->tx_buf = xfer->tx_buf;
 392        sspi->rx_buf = xfer->rx_buf;
 393
 394        switch (sspi->bpw) {
 395        case 8:
 396                words = xfer->len;
 397                break;
 398        case 16:
 399                words = xfer->len / 2;
 400                break;
 401        case 24:
 402                /* fallthrough, should use 32-bits access */
 403        case 32:
 404                words = xfer->len / 4;
 405                break;
 406        default:
 407                dev_err(sspi->dev, "unsupported bpw: %d\n", sspi->bpw);
 408                return -EINVAL;
 409        }
 410
 411        if (xfer->tx_buf)
 412                sspi->tx_words = words;
 413        else
 414                sspi->tx_words = 0;
 415
 416        if (xfer->rx_buf)
 417                sspi->rx_words = words;
 418        else
 419                sspi->rx_words = 0;
 420
 421        if (xfer->tx_buf) {
 422                status = write_fifo(sspi);
 423                if (status < 0) {
 424                        dev_err(sspi->dev, "failed write_fifo. status: 0x%x\n",
 425                                status);
 426                        return status;
 427                }
 428        }
 429
 430        if (xfer->rx_buf) {
 431                val = readl(sspi->regs + SYNQUACER_HSSPI_REG_FIFOCFG);
 432                val &= ~(SYNQUACER_HSSPI_FIFOCFG_RX_THRESHOLD_MASK <<
 433                         SYNQUACER_HSSPI_FIFOCFG_RX_THRESHOLD_SHIFT);
 434                val |= ((sspi->rx_words > SYNQUACER_HSSPI_FIFO_DEPTH ?
 435                        SYNQUACER_HSSPI_FIFO_RX_THRESHOLD : sspi->rx_words) <<
 436                        SYNQUACER_HSSPI_FIFOCFG_RX_THRESHOLD_SHIFT);
 437                writel(val, sspi->regs + SYNQUACER_HSSPI_REG_FIFOCFG);
 438        }
 439
 440        writel(~0, sspi->regs + SYNQUACER_HSSPI_REG_TXC);
 441        writel(~0, sspi->regs + SYNQUACER_HSSPI_REG_RXC);
 442
 443        /* Trigger */
 444        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 445        val |= SYNQUACER_HSSPI_DMSTART_START;
 446        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 447
 448        if (xfer->tx_buf) {
 449                val = SYNQUACER_HSSPI_TXE_FIFO_EMPTY;
 450                writel(val, sspi->regs + SYNQUACER_HSSPI_REG_TXE);
 451                status = wait_for_completion_timeout(&sspi->transfer_done,
 452                        msecs_to_jiffies(SYNQUACER_HSSPI_TRANSFER_TMOUT_MSEC));
 453                writel(0, sspi->regs + SYNQUACER_HSSPI_REG_TXE);
 454        }
 455
 456        if (xfer->rx_buf) {
 457                u32 buf[SYNQUACER_HSSPI_FIFO_DEPTH];
 458
 459                val = SYNQUACER_HSSPI_RXE_FIFO_MORE_THAN_THRESHOLD |
 460                      SYNQUACER_HSSPI_RXE_SLAVE_RELEASED;
 461                writel(val, sspi->regs + SYNQUACER_HSSPI_REG_RXE);
 462                status = wait_for_completion_timeout(&sspi->transfer_done,
 463                        msecs_to_jiffies(SYNQUACER_HSSPI_TRANSFER_TMOUT_MSEC));
 464                writel(0, sspi->regs + SYNQUACER_HSSPI_REG_RXE);
 465
 466                /* stop RX and clean RXFIFO */
 467                val = readl(sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 468                val |= SYNQUACER_HSSPI_DMSTOP_STOP;
 469                writel(val, sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 470                sspi->rx_buf = buf;
 471                sspi->rx_words = SYNQUACER_HSSPI_FIFO_DEPTH;
 472                read_fifo(sspi);
 473        }
 474
 475        if (status < 0) {
 476                dev_err(sspi->dev, "failed to transfer. status: 0x%x\n",
 477                        status);
 478                return status;
 479        }
 480
 481        return 0;
 482}
 483
 484static void synquacer_spi_set_cs(struct spi_device *spi, bool enable)
 485{
 486        struct synquacer_spi *sspi = spi_master_get_devdata(spi->master);
 487        u32 val;
 488
 489        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 490        val &= ~(SYNQUACER_HSSPI_DMPSEL_CS_MASK <<
 491                 SYNQUACER_HSSPI_DMPSEL_CS_SHIFT);
 492        val |= spi->chip_select << SYNQUACER_HSSPI_DMPSEL_CS_SHIFT;
 493
 494        if (!enable)
 495                val |= SYNQUACER_HSSPI_DMSTOP_STOP;
 496
 497        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_DMSTART);
 498}
 499
 500static int synquacer_spi_wait_status_update(struct synquacer_spi *sspi,
 501                                            bool enable)
 502{
 503        u32 val;
 504        unsigned long timeout = jiffies +
 505                msecs_to_jiffies(SYNQUACER_HSSPI_ENABLE_TMOUT_MSEC);
 506
 507        /* wait MES(Module Enable Status) is updated */
 508        do {
 509                val = readl(sspi->regs + SYNQUACER_HSSPI_REG_MCTRL) &
 510                      SYNQUACER_HSSPI_MCTRL_MES;
 511                if (enable && val)
 512                        return 0;
 513                if (!enable && !val)
 514                        return 0;
 515        } while (time_before(jiffies, timeout));
 516
 517        dev_err(sspi->dev, "timeout occurs in updating Module Enable Status\n");
 518        return -EBUSY;
 519}
 520
 521static int synquacer_spi_enable(struct spi_master *master)
 522{
 523        u32 val;
 524        int status;
 525        struct synquacer_spi *sspi = spi_master_get_devdata(master);
 526
 527        /* Disable module */
 528        writel(0, sspi->regs + SYNQUACER_HSSPI_REG_MCTRL);
 529        status = synquacer_spi_wait_status_update(sspi, false);
 530        if (status < 0)
 531                return status;
 532
 533        writel(0, sspi->regs + SYNQUACER_HSSPI_REG_TXE);
 534        writel(0, sspi->regs + SYNQUACER_HSSPI_REG_RXE);
 535        writel(~0, sspi->regs + SYNQUACER_HSSPI_REG_TXC);
 536        writel(~0, sspi->regs + SYNQUACER_HSSPI_REG_RXC);
 537        writel(~0, sspi->regs + SYNQUACER_HSSPI_REG_FAULTC);
 538
 539        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_DMCFG);
 540        val &= ~SYNQUACER_HSSPI_DMCFG_SSDC;
 541        val &= ~SYNQUACER_HSSPI_DMCFG_MSTARTEN;
 542        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_DMCFG);
 543
 544        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_MCTRL);
 545        if (sspi->clk_src_type == SYNQUACER_HSSPI_CLOCK_SRC_IPCLK)
 546                val |= SYNQUACER_HSSPI_MCTRL_CDSS;
 547        else
 548                val &= ~SYNQUACER_HSSPI_MCTRL_CDSS;
 549
 550        val &= ~SYNQUACER_HSSPI_MCTRL_COMMAND_SEQUENCE_EN;
 551        val |= SYNQUACER_HSSPI_MCTRL_MEN;
 552        val |= SYNQUACER_HSSPI_MCTRL_SYNCON;
 553
 554        /* Enable module */
 555        writel(val, sspi->regs + SYNQUACER_HSSPI_REG_MCTRL);
 556        status = synquacer_spi_wait_status_update(sspi, true);
 557        if (status < 0)
 558                return status;
 559
 560        return 0;
 561}
 562
 563static irqreturn_t sq_spi_rx_handler(int irq, void *priv)
 564{
 565        uint32_t val;
 566        struct synquacer_spi *sspi = priv;
 567
 568        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_RXF);
 569        if ((val & SYNQUACER_HSSPI_RXF_SLAVE_RELEASED) ||
 570            (val & SYNQUACER_HSSPI_RXF_FIFO_MORE_THAN_THRESHOLD)) {
 571                read_fifo(sspi);
 572
 573                if (sspi->rx_words == 0) {
 574                        writel(0, sspi->regs + SYNQUACER_HSSPI_REG_RXE);
 575                        complete(&sspi->transfer_done);
 576                }
 577                return IRQ_HANDLED;
 578        }
 579
 580        return IRQ_NONE;
 581}
 582
 583static irqreturn_t sq_spi_tx_handler(int irq, void *priv)
 584{
 585        uint32_t val;
 586        struct synquacer_spi *sspi = priv;
 587
 588        val = readl(sspi->regs + SYNQUACER_HSSPI_REG_TXF);
 589        if (val & SYNQUACER_HSSPI_TXF_FIFO_EMPTY) {
 590                if (sspi->tx_words == 0) {
 591                        writel(0, sspi->regs + SYNQUACER_HSSPI_REG_TXE);
 592                        complete(&sspi->transfer_done);
 593                } else {
 594                        write_fifo(sspi);
 595                }
 596                return IRQ_HANDLED;
 597        }
 598
 599        return IRQ_NONE;
 600}
 601
 602static int synquacer_spi_probe(struct platform_device *pdev)
 603{
 604        struct device_node *np = pdev->dev.of_node;
 605        struct spi_master *master;
 606        struct synquacer_spi *sspi;
 607        int ret;
 608        int rx_irq, tx_irq;
 609
 610        master = spi_alloc_master(&pdev->dev, sizeof(*sspi));
 611        if (!master)
 612                return -ENOMEM;
 613
 614        platform_set_drvdata(pdev, master);
 615
 616        sspi = spi_master_get_devdata(master);
 617        sspi->dev = &pdev->dev;
 618
 619        init_completion(&sspi->transfer_done);
 620
 621        sspi->regs = devm_platform_ioremap_resource(pdev, 0);
 622        if (IS_ERR(sspi->regs)) {
 623                ret = PTR_ERR(sspi->regs);
 624                goto put_spi;
 625        }
 626
 627        sspi->clk_src_type = SYNQUACER_HSSPI_CLOCK_SRC_IHCLK; /* Default */
 628        device_property_read_u32(&pdev->dev, "socionext,ihclk-rate",
 629                                 &master->max_speed_hz); /* for ACPI */
 630
 631        if (dev_of_node(&pdev->dev)) {
 632                if (device_property_match_string(&pdev->dev,
 633                                         "clock-names", "iHCLK") >= 0) {
 634                        sspi->clk_src_type = SYNQUACER_HSSPI_CLOCK_SRC_IHCLK;
 635                        sspi->clk = devm_clk_get(sspi->dev, "iHCLK");
 636                } else if (device_property_match_string(&pdev->dev,
 637                                                "clock-names", "iPCLK") >= 0) {
 638                        sspi->clk_src_type = SYNQUACER_HSSPI_CLOCK_SRC_IPCLK;
 639                        sspi->clk = devm_clk_get(sspi->dev, "iPCLK");
 640                } else {
 641                        dev_err(&pdev->dev, "specified wrong clock source\n");
 642                        ret = -EINVAL;
 643                        goto put_spi;
 644                }
 645
 646                if (IS_ERR(sspi->clk)) {
 647                        ret = dev_err_probe(&pdev->dev, PTR_ERR(sspi->clk),
 648                                            "clock not found\n");
 649                        goto put_spi;
 650                }
 651
 652                ret = clk_prepare_enable(sspi->clk);
 653                if (ret) {
 654                        dev_err(&pdev->dev, "failed to enable clock (%d)\n",
 655                                ret);
 656                        goto put_spi;
 657                }
 658
 659                master->max_speed_hz = clk_get_rate(sspi->clk);
 660        }
 661
 662        if (!master->max_speed_hz) {
 663                dev_err(&pdev->dev, "missing clock source\n");
 664                ret = -EINVAL;
 665                goto disable_clk;
 666        }
 667        master->min_speed_hz = master->max_speed_hz / 254;
 668
 669        sspi->aces = device_property_read_bool(&pdev->dev,
 670                                               "socionext,set-aces");
 671        sspi->rtm = device_property_read_bool(&pdev->dev, "socionext,use-rtm");
 672
 673        master->num_chipselect = SYNQUACER_HSSPI_NUM_CHIP_SELECT;
 674
 675        rx_irq = platform_get_irq(pdev, 0);
 676        if (rx_irq <= 0) {
 677                ret = rx_irq;
 678                goto disable_clk;
 679        }
 680        snprintf(sspi->rx_irq_name, SYNQUACER_HSSPI_IRQ_NAME_MAX, "%s-rx",
 681                 dev_name(&pdev->dev));
 682        ret = devm_request_irq(&pdev->dev, rx_irq, sq_spi_rx_handler,
 683                                0, sspi->rx_irq_name, sspi);
 684        if (ret) {
 685                dev_err(&pdev->dev, "request rx_irq failed (%d)\n", ret);
 686                goto disable_clk;
 687        }
 688
 689        tx_irq = platform_get_irq(pdev, 1);
 690        if (tx_irq <= 0) {
 691                ret = tx_irq;
 692                goto disable_clk;
 693        }
 694        snprintf(sspi->tx_irq_name, SYNQUACER_HSSPI_IRQ_NAME_MAX, "%s-tx",
 695                 dev_name(&pdev->dev));
 696        ret = devm_request_irq(&pdev->dev, tx_irq, sq_spi_tx_handler,
 697                                0, sspi->tx_irq_name, sspi);
 698        if (ret) {
 699                dev_err(&pdev->dev, "request tx_irq failed (%d)\n", ret);
 700                goto disable_clk;
 701        }
 702
 703        master->dev.of_node = np;
 704        master->dev.fwnode = pdev->dev.fwnode;
 705        master->auto_runtime_pm = true;
 706        master->bus_num = pdev->id;
 707
 708        master->mode_bits = SPI_CPOL | SPI_CPHA | SPI_TX_DUAL | SPI_RX_DUAL |
 709                            SPI_TX_QUAD | SPI_RX_QUAD;
 710        master->bits_per_word_mask = SPI_BPW_MASK(32) | SPI_BPW_MASK(24) |
 711                                     SPI_BPW_MASK(16) | SPI_BPW_MASK(8);
 712
 713        master->set_cs = synquacer_spi_set_cs;
 714        master->transfer_one = synquacer_spi_transfer_one;
 715
 716        ret = synquacer_spi_enable(master);
 717        if (ret)
 718                goto disable_clk;
 719
 720        pm_runtime_set_active(sspi->dev);
 721        pm_runtime_enable(sspi->dev);
 722
 723        ret = devm_spi_register_master(sspi->dev, master);
 724        if (ret)
 725                goto disable_pm;
 726
 727        return 0;
 728
 729disable_pm:
 730        pm_runtime_disable(sspi->dev);
 731disable_clk:
 732        clk_disable_unprepare(sspi->clk);
 733put_spi:
 734        spi_master_put(master);
 735
 736        return ret;
 737}
 738
 739static int synquacer_spi_remove(struct platform_device *pdev)
 740{
 741        struct spi_master *master = platform_get_drvdata(pdev);
 742        struct synquacer_spi *sspi = spi_master_get_devdata(master);
 743
 744        pm_runtime_disable(sspi->dev);
 745
 746        clk_disable_unprepare(sspi->clk);
 747
 748        return 0;
 749}
 750
 751static int __maybe_unused synquacer_spi_suspend(struct device *dev)
 752{
 753        struct spi_master *master = dev_get_drvdata(dev);
 754        struct synquacer_spi *sspi = spi_master_get_devdata(master);
 755        int ret;
 756
 757        ret = spi_master_suspend(master);
 758        if (ret)
 759                return ret;
 760
 761        if (!pm_runtime_suspended(dev))
 762                clk_disable_unprepare(sspi->clk);
 763
 764        return ret;
 765}
 766
 767static int __maybe_unused synquacer_spi_resume(struct device *dev)
 768{
 769        struct spi_master *master = dev_get_drvdata(dev);
 770        struct synquacer_spi *sspi = spi_master_get_devdata(master);
 771        int ret;
 772
 773        if (!pm_runtime_suspended(dev)) {
 774                /* Ensure reconfigure during next xfer */
 775                sspi->speed = 0;
 776
 777                ret = clk_prepare_enable(sspi->clk);
 778                if (ret < 0) {
 779                        dev_err(dev, "failed to enable clk (%d)\n",
 780                                ret);
 781                        return ret;
 782                }
 783
 784                ret = synquacer_spi_enable(master);
 785                if (ret) {
 786                        dev_err(dev, "failed to enable spi (%d)\n", ret);
 787                        return ret;
 788                }
 789        }
 790
 791        ret = spi_master_resume(master);
 792        if (ret < 0)
 793                clk_disable_unprepare(sspi->clk);
 794
 795        return ret;
 796}
 797
 798static SIMPLE_DEV_PM_OPS(synquacer_spi_pm_ops, synquacer_spi_suspend,
 799                         synquacer_spi_resume);
 800
 801static const struct of_device_id synquacer_spi_of_match[] = {
 802        {.compatible = "socionext,synquacer-spi"},
 803        {}
 804};
 805MODULE_DEVICE_TABLE(of, synquacer_spi_of_match);
 806
 807#ifdef CONFIG_ACPI
 808static const struct acpi_device_id synquacer_hsspi_acpi_ids[] = {
 809        { "SCX0004" },
 810        { /* sentinel */ }
 811};
 812MODULE_DEVICE_TABLE(acpi, synquacer_hsspi_acpi_ids);
 813#endif
 814
 815static struct platform_driver synquacer_spi_driver = {
 816        .driver = {
 817                .name = "synquacer-spi",
 818                .pm = &synquacer_spi_pm_ops,
 819                .of_match_table = synquacer_spi_of_match,
 820                .acpi_match_table = ACPI_PTR(synquacer_hsspi_acpi_ids),
 821        },
 822        .probe = synquacer_spi_probe,
 823        .remove = synquacer_spi_remove,
 824};
 825module_platform_driver(synquacer_spi_driver);
 826
 827MODULE_DESCRIPTION("Socionext Synquacer HS-SPI controller driver");
 828MODULE_AUTHOR("Masahisa Kojima <masahisa.kojima@linaro.org>");
 829MODULE_AUTHOR("Jassi Brar <jaswinder.singh@linaro.org>");
 830MODULE_LICENSE("GPL v2");
 831