help
Support for console on SCCNXP serial ports.
+config SERIAL_SC16IS7XX_CORE
+ tristate
+
config SERIAL_SC16IS7XX
- tristate "SC16IS7xx serial support"
- depends on I2C
- select SERIAL_CORE
- select REGMAP_I2C if I2C
- help
- This selects support for SC16IS7xx serial ports.
- Supported ICs are SC16IS740, SC16IS741, SC16IS750, SC16IS752,
- SC16IS760 and SC16IS762.
+ tristate "SC16IS7xx serial support"
+ select SERIAL_CORE
+ depends on I2C || SPI_MASTER
+ help
+ This selects support for SC16IS7xx serial ports.
+ Supported ICs are SC16IS740, SC16IS741, SC16IS750, SC16IS752,
+ SC16IS760 and SC16IS762. Select supported buses using options below.
+
+config SERIAL_SC16IS7XX_I2C
+ bool "SC16IS7xx for I2C interface"
+ depends on SERIAL_SC16IS7XX
+ depends on I2C
+ select SERIAL_SC16IS7XX_CORE if SERIAL_SC16IS7XX
+ select REGMAP_I2C if I2C
+ default y
+ help
+ Enable SC16IS7xx driver on I2C bus,
+ If required say y, and say n to i2c if not required,
+ Enabled by default to support oldconfig.
+ You must select at least one bus for the driver to be built.
+
+config SERIAL_SC16IS7XX_SPI
+ bool "SC16IS7xx for spi interface"
+ depends on SERIAL_SC16IS7XX
+ depends on SPI_MASTER
+ select SERIAL_SC16IS7XX_CORE if SERIAL_SC16IS7XX
+ select REGMAP_SPI if SPI_MASTER
+ help
+ Enable SC16IS7xx driver on SPI bus,
+ If required say y, and say n to spi if not required,
+ This is additional support to exsisting driver.
+ You must select at least one bus for the driver to be built.
config SERIAL_BFIN_SPORT
tristate "Blackfin SPORT emulate UART"
#include <linux/serial.h>
#include <linux/tty.h>
#include <linux/tty_flip.h>
+#include <linux/spi/spi.h>
#include <linux/uaccess.h>
#define SC16IS7XX_NAME "sc16is7xx"
.precious_reg = sc16is7xx_regmap_precious,
};
+#ifdef CONFIG_SERIAL_SC16IS7XX_SPI
+static int sc16is7xx_spi_probe(struct spi_device *spi)
+{
+ struct sc16is7xx_devtype *devtype;
+ unsigned long flags = 0;
+ struct regmap *regmap;
+ int ret;
+
+ /* Setup SPI bus */
+ spi->bits_per_word = 8;
+ /* only supports mode 0 on SC16IS762 */
+ spi->mode = spi->mode ? : SPI_MODE_0;
+ spi->max_speed_hz = spi->max_speed_hz ? : 15000000;
+ ret = spi_setup(spi);
+ if (ret)
+ return ret;
+
+ if (spi->dev.of_node) {
+ const struct of_device_id *of_id =
+ of_match_device(sc16is7xx_dt_ids, &spi->dev);
+
+ devtype = (struct sc16is7xx_devtype *)of_id->data;
+ } else {
+ const struct spi_device_id *id_entry = spi_get_device_id(spi);
+
+ devtype = (struct sc16is7xx_devtype *)id_entry->driver_data;
+ flags = IRQF_TRIGGER_FALLING;
+ }
+
+ regcfg.max_register = (0xf << SC16IS7XX_REG_SHIFT) |
+ (devtype->nr_uart - 1);
+ regmap = devm_regmap_init_spi(spi, ®cfg);
+
+ return sc16is7xx_probe(&spi->dev, devtype, regmap, spi->irq, flags);
+}
+
+static int sc16is7xx_spi_remove(struct spi_device *spi)
+{
+ return sc16is7xx_remove(&spi->dev);
+}
+
+static const struct spi_device_id sc16is7xx_spi_id_table[] = {
+ { "sc16is74x", (kernel_ulong_t)&sc16is74x_devtype, },
+ { "sc16is750", (kernel_ulong_t)&sc16is750_devtype, },
+ { "sc16is752", (kernel_ulong_t)&sc16is752_devtype, },
+ { "sc16is760", (kernel_ulong_t)&sc16is760_devtype, },
+ { "sc16is762", (kernel_ulong_t)&sc16is762_devtype, },
+ { }
+};
+
+MODULE_DEVICE_TABLE(spi, sc16is7xx_spi_id_table);
+
+static struct spi_driver sc16is7xx_spi_uart_driver = {
+ .driver = {
+ .name = SC16IS7XX_NAME,
+ .owner = THIS_MODULE,
+ .of_match_table = of_match_ptr(sc16is7xx_dt_ids),
+ },
+ .probe = sc16is7xx_spi_probe,
+ .remove = sc16is7xx_spi_remove,
+ .id_table = sc16is7xx_spi_id_table,
+};
+
+MODULE_ALIAS("spi:sc16is7xx");
+#endif
+
+#ifdef CONFIG_SERIAL_SC16IS7XX_I2C
static int sc16is7xx_i2c_probe(struct i2c_client *i2c,
const struct i2c_device_id *id)
{
.remove = sc16is7xx_i2c_remove,
.id_table = sc16is7xx_i2c_id_table,
};
-module_i2c_driver(sc16is7xx_i2c_uart_driver);
+
MODULE_ALIAS("i2c:sc16is7xx");
+#endif
+
+static int __init sc16is7xx_init(void)
+{
+ int ret = 0;
+#ifdef CONFIG_SERIAL_SC16IS7XX_I2C
+ ret = i2c_add_driver(&sc16is7xx_i2c_uart_driver);
+ if (ret < 0) {
+ pr_err("failed to init sc16is7xx i2c --> %d\n", ret);
+ return ret;
+ }
+#endif
+
+#ifdef CONFIG_SERIAL_SC16IS7XX_SPI
+ ret = spi_register_driver(&sc16is7xx_spi_uart_driver);
+ if (ret < 0) {
+ pr_err("failed to init sc16is7xx spi --> %d\n", ret);
+ return ret;
+ }
+#endif
+ return ret;
+}
+module_init(sc16is7xx_init);
+
+static void __exit sc16is7xx_exit(void)
+{
+#ifdef CONFIG_SERIAL_SC16IS7XX_I2C
+ i2c_del_driver(&sc16is7xx_i2c_uart_driver);
+#endif
+
+#ifdef CONFIG_SERIAL_SC16IS7XX_SPI
+ spi_unregister_driver(&sc16is7xx_spi_uart_driver);
+#endif
+}
+module_exit(sc16is7xx_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("Jon Ringle <jringle@gridpoint.com>");