|
@@ -370,6 +370,17 @@ static void spi_dev_set_name(struct spi_device *spi)
|
|
|
spi->chip_select);
|
|
|
}
|
|
|
|
|
|
+static int spi_dev_check(struct device *dev, void *data)
|
|
|
+{
|
|
|
+ struct spi_device *spi = to_spi_device(dev);
|
|
|
+ struct spi_device *new_spi = data;
|
|
|
+
|
|
|
+ if (spi->master == new_spi->master &&
|
|
|
+ spi->chip_select == new_spi->chip_select)
|
|
|
+ return -EBUSY;
|
|
|
+ return 0;
|
|
|
+}
|
|
|
+
|
|
|
/**
|
|
|
* spi_add_device - Add spi_device allocated with spi_alloc_device
|
|
|
* @spi: spi_device to register
|
|
@@ -384,7 +395,6 @@ int spi_add_device(struct spi_device *spi)
|
|
|
static DEFINE_MUTEX(spi_add_lock);
|
|
|
struct spi_master *master = spi->master;
|
|
|
struct device *dev = master->dev.parent;
|
|
|
- struct device *d;
|
|
|
int status;
|
|
|
|
|
|
/* Chipselects are numbered 0..max; validate. */
|
|
@@ -404,12 +414,10 @@ int spi_add_device(struct spi_device *spi)
|
|
|
*/
|
|
|
mutex_lock(&spi_add_lock);
|
|
|
|
|
|
- d = bus_find_device_by_name(&spi_bus_type, NULL, dev_name(&spi->dev));
|
|
|
- if (d != NULL) {
|
|
|
+ status = bus_for_each_dev(&spi_bus_type, NULL, spi, spi_dev_check);
|
|
|
+ if (status) {
|
|
|
dev_err(dev, "chipselect %d already in use\n",
|
|
|
spi->chip_select);
|
|
|
- put_device(d);
|
|
|
- status = -EBUSY;
|
|
|
goto done;
|
|
|
}
|
|
|
|
|
@@ -591,8 +599,10 @@ static int spi_transfer_one_message(struct spi_master *master,
|
|
|
goto out;
|
|
|
}
|
|
|
|
|
|
- if (ret > 0)
|
|
|
+ if (ret > 0) {
|
|
|
+ ret = 0;
|
|
|
wait_for_completion(&master->xfer_completion);
|
|
|
+ }
|
|
|
|
|
|
trace_spi_transfer_stop(msg, xfer);
|
|
|
|
|
@@ -632,7 +642,7 @@ out:
|
|
|
*
|
|
|
* Called by SPI drivers using the core transfer_one_message()
|
|
|
* implementation to notify it that the current interrupt driven
|
|
|
- * transfer has finised and the next one may be scheduled.
|
|
|
+ * transfer has finished and the next one may be scheduled.
|
|
|
*/
|
|
|
void spi_finalize_current_transfer(struct spi_master *master)
|
|
|
{
|
|
@@ -735,7 +745,9 @@ static void spi_pump_messages(struct kthread_work *work)
|
|
|
ret = master->transfer_one_message(master, master->cur_msg);
|
|
|
if (ret) {
|
|
|
dev_err(&master->dev,
|
|
|
- "failed to transfer one message from queue\n");
|
|
|
+ "failed to transfer one message from queue: %d\n", ret);
|
|
|
+ master->cur_msg->status = ret;
|
|
|
+ spi_finalize_current_message(master);
|
|
|
return;
|
|
|
}
|
|
|
}
|