Skip to content

Commit

Permalink
spi: s3c64xx: add support for google,gs101-spi
Browse files Browse the repository at this point in the history
Merge series from Tudor Ambarus <tudor.ambarus@linaro.org>:

The Google GCS101 uses a variant of the Samsung SPI controller IP.
  • Loading branch information
Mark Brown committed Feb 8, 2024
2 parents 9538ede + e010c04 commit 0f02125
Show file tree
Hide file tree
Showing 2 changed files with 71 additions and 15 deletions.
1 change: 1 addition & 0 deletions Documentation/devicetree/bindings/spi/samsung,spi.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@ properties:
compatible:
oneOf:
- enum:
- google,gs101-spi
- samsung,s3c2443-spi # for S3C2443, S3C2416 and S3C2450
- samsung,s3c6410-spi
- samsung,s5pv210-spi # for S5PV210 and S5PC110
Expand Down
85 changes: 70 additions & 15 deletions drivers/spi/spi-s3c64xx.c
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@

#include <linux/platform_data/spi-s3c64xx.h>

#define MAX_SPI_PORTS 12
#define MAX_SPI_PORTS 16
#define S3C64XX_SPI_QUIRK_CS_AUTO (1 << 1)
#define AUTOSUSPEND_TIMEOUT 2000

Expand Down Expand Up @@ -142,6 +142,7 @@ struct s3c64xx_spi_dma_data {
* prescaler unit.
* @clk_ioclk: True if clock is present on this device
* @has_loopback: True if loopback mode can be supported
* @use_32bit_io: True if the SoC allows only 32-bit register accesses.
*
* The Samsung s3c64xx SPI controller are used on various Samsung SoC's but
* differ in some aspects such as the size of the fifo and spi bus clock
Expand All @@ -158,6 +159,7 @@ struct s3c64xx_spi_port_config {
bool clk_from_cmu;
bool clk_ioclk;
bool has_loopback;
bool use_32bit_io;
};

/**
Expand Down Expand Up @@ -414,6 +416,56 @@ static bool s3c64xx_spi_can_dma(struct spi_controller *host,

}

static void s3c64xx_iowrite8_32_rep(volatile void __iomem *addr,
const void *buffer, unsigned int count)
{
if (count) {
const u8 *buf = buffer;

do {
__raw_writel(*buf++, addr);
} while (--count);
}
}

static void s3c64xx_iowrite16_32_rep(volatile void __iomem *addr,
const void *buffer, unsigned int count)
{
if (count) {
const u16 *buf = buffer;

do {
__raw_writel(*buf++, addr);
} while (--count);
}
}

static void s3c64xx_iowrite_rep(const struct s3c64xx_spi_driver_data *sdd,
struct spi_transfer *xfer)
{
void __iomem *addr = sdd->regs + S3C64XX_SPI_TX_DATA;
const void *buf = xfer->tx_buf;
unsigned int len = xfer->len;

switch (sdd->cur_bpw) {
case 32:
iowrite32_rep(addr, buf, len / 4);
break;
case 16:
if (sdd->port_conf->use_32bit_io)
s3c64xx_iowrite16_32_rep(addr, buf, len / 2);
else
iowrite16_rep(addr, buf, len / 2);
break;
default:
if (sdd->port_conf->use_32bit_io)
s3c64xx_iowrite8_32_rep(addr, buf, len);
else
iowrite8_rep(addr, buf, len);
break;
}
}

static int s3c64xx_enable_datapath(struct s3c64xx_spi_driver_data *sdd,
struct spi_transfer *xfer, int dma_mode)
{
Expand Down Expand Up @@ -447,20 +499,7 @@ static int s3c64xx_enable_datapath(struct s3c64xx_spi_driver_data *sdd,
modecfg |= S3C64XX_SPI_MODE_TXDMA_ON;
ret = prepare_dma(&sdd->tx_dma, &xfer->tx_sg);
} else {
switch (sdd->cur_bpw) {
case 32:
iowrite32_rep(regs + S3C64XX_SPI_TX_DATA,
xfer->tx_buf, xfer->len / 4);
break;
case 16:
iowrite16_rep(regs + S3C64XX_SPI_TX_DATA,
xfer->tx_buf, xfer->len / 2);
break;
default:
iowrite8_rep(regs + S3C64XX_SPI_TX_DATA,
xfer->tx_buf, xfer->len);
break;
}
s3c64xx_iowrite_rep(sdd, xfer);
}
}

Expand Down Expand Up @@ -1495,6 +1534,19 @@ static const struct s3c64xx_spi_port_config fsd_spi_port_config = {
.quirks = S3C64XX_SPI_QUIRK_CS_AUTO,
};

static const struct s3c64xx_spi_port_config gs101_spi_port_config = {
.fifo_lvl_mask = { 0x7f, 0x7f, 0x7f, 0x7f, 0x7f, 0x7f, 0x7f, 0x7f,
0x7f, 0x7f, 0x7f, 0x7f, 0x7f, 0x7f, 0x7f, 0x7f},
.rx_lvl_offset = 15,
.tx_st_done = 25,
.clk_div = 4,
.high_speed = true,
.clk_from_cmu = true,
.has_loopback = true,
.use_32bit_io = true,
.quirks = S3C64XX_SPI_QUIRK_CS_AUTO,
};

static const struct platform_device_id s3c64xx_spi_driver_ids[] = {
{
.name = "s3c2443-spi",
Expand All @@ -1507,6 +1559,9 @@ static const struct platform_device_id s3c64xx_spi_driver_ids[] = {
};

static const struct of_device_id s3c64xx_spi_dt_match[] = {
{ .compatible = "google,gs101-spi",
.data = &gs101_spi_port_config,
},
{ .compatible = "samsung,s3c2443-spi",
.data = (void *)&s3c2443_spi_port_config,
},
Expand Down

0 comments on commit 0f02125

Please sign in to comment.