目录
1.1 spi_dev_set_name(设置bus id)
1. spi_add_device
int spi_add_device(struct spi_device *spi)
{
.....
/* Chipselects are numbered 0..max; validate. */
if (spi->chip_select >= ctlr->num_chipselect) {
dev_err(dev, "cs%d >= max %d\n", spi->chip_select,
ctlr->num_chipselect);
return -EINVAL;
}
/* Set the bus ID string */
spi_dev_set_name(spi);
.......
if (ctlr->cs_gpios)
spi->cs_gpio = ctlr->cs_gpios[spi->chip_select];
/* Drivers may modify this initial i/o setup, but will
* normally rely on the device being setup. Devices
* using SPI_CS_HIGH can't coexist well otherwise...
*/
status = spi_setup(spi);
......
/* Device may be bound to an active driver when this returns */
status = device_add(&spi->dev);
......
}
1.1 spi_dev_set_name(设置bus id)
static void spi_dev_set_name(struct spi_device *spi)
{
struct acpi_device *adev = ACPI_COMPANION(&spi->dev);
if (adev) {
dev_set_name(&spi->dev, "spi-%s", acpi_dev_name(adev));
return;
}
dev_set_name(&spi->dev, "%s.%u", dev_name(&spi->controller->dev),
spi->chip_select);
}
1.2 spi_setup(参数的一些默认设置和检查)
int spi_setup(struct spi_device *spi)
{
unsigned bad_bits, ugly_bits;
int status;
/* check mode to prevent that DUAL and QUAD set at the same time
*/
if (((spi->mode & SPI_TX_DUAL) && (spi->mode & SPI_TX_QUAD)) ||
((spi->mode & SPI_RX_DUAL) && (spi->mode & SPI_RX_QUAD))) {
dev_err(&spi->dev,
"setup: can not select dual and quad at the same time\n");
return -EINVAL;
}
/* if it is SPI_3WIRE mode, DUAL and QUAD should be forbidden
*/
if ((spi->mode & SPI_3WIRE) && (spi->mode &
(SPI_TX_DUAL | SPI_TX_QUAD | SPI_RX_DUAL | SPI_RX_QUAD)))
return -EINVAL;
/* help drivers fail *cleanly* when they need options
* that aren't supported with their current controller
*/
bad_bits = spi->mode & ~spi->controller->mode_bits;
ugly_bits = bad_bits &
(SPI_TX_DUAL | SPI_TX_QUAD | SPI_RX_DUAL | SPI_RX_QUAD);
if (ugly_bits) {
dev_warn(&spi->dev,
"setup: ignoring unsupported mode bits %x\n",
ugly_bits);
spi->mode &= ~ugly_bits;
bad_bits &= ~ugly_bits;
}
if (bad_bits) {
dev_err(&spi->dev, "setup: unsupported mode bits %x\n",
bad_bits);
return -EINVAL;
}
if (!spi->bits_per_word)
spi->bits_per_word = 8;
status = __spi_validate_bits_per_word(spi->controller,
spi->bits_per_word);
if (status)
return status;
if (!spi->max_speed_hz)
spi->max_speed_hz = spi->controller->max_speed_hz;
if (spi->controller->setup)
status = spi->controller->setup(spi);
spi_set_cs(spi, false);
dev_dbg(&spi->dev, "setup mode %d, %s%s%s%s%u bits/w, %u Hz max --> %d\n",
(int) (spi->mode & (SPI_CPOL | SPI_CPHA)),
(spi->mode & SPI_CS_HIGH) ? "cs_high, " : "",
(spi->mode & SPI_LSB_FIRST) ? "lsb, " : "",
(spi->mode & SPI_3WIRE) ? "3wire, " : "",
(spi->mode & SPI_LOOP) ? "loopback, " : "",
spi->bits_per_word, spi->max_speed_hz,
status);
return status;
}
(1)检查DUAL and QUAD是否同时存在
(2)如果是SPI_3WIRE,则禁止DUAL and QUAD
(3)如果spi->bits_per_word为0,默认设置为spi->bits_per_word = 8。
(4)设置默认的max_speed_hz
(5)调用spi->controller->setup
(6)片选选为非工作模式
2. spi_alloc_device
struct spi_device *spi_alloc_device(struct spi_controller *ctlr)
{
struct spi_device *spi;
if (!spi_controller_get(ctlr))
return NULL;
spi = kzalloc(sizeof(*spi), GFP_KERNEL);
if (!spi) {
spi_controller_put(ctlr);
return NULL;
}
spi->master = spi->controller = ctlr;
spi->dev.parent = &ctlr->dev;
spi->dev.bus = &spi_bus_type;
spi->dev.release = spidev_release;
spi->cs_gpio = -ENOENT;
spin_lock_init(&spi->statistics.lock);
device_initialize(&spi->dev);
return spi;
}