From: David Brownell Date: Fri, 7 Apr 2006 05:25:56 +0000 (-0700) Subject: [PATCH] SPI: spi_bitbang: clocking fixes X-Git-Url: https://git.karo-electronics.de/?a=commitdiff_plain;h=1e316d7566b63767aa18902235c719e9e95465d0;p=linux-beck.git [PATCH] SPI: spi_bitbang: clocking fixes This fixes two problems triggered by the MMC stack updating clocks: - SPI masters driver should accept a max clock speed of zero; that's one convention for marking idle devices. (Presumably that helps controllers that don't autogate clocks to "off" when not in use.) - There are more than 1000 nanoseconds per millisecond; setting the clock down to 125 KHz now works properly. Showing once again that Zero (http://en.wikipedia.org/wiki/Zero) is still an inexhaustible number of bugs. Signed-off-by: David Brownell Signed-off-by: Greg Kroah-Hartman --- diff --git a/drivers/spi/spi_bitbang.c b/drivers/spi/spi_bitbang.c index 0f7f5c64391c..dd2f950b21a7 100644 --- a/drivers/spi/spi_bitbang.c +++ b/drivers/spi/spi_bitbang.c @@ -167,9 +167,11 @@ int spi_bitbang_setup_transfer(struct spi_device *spi, struct spi_transfer *t) /* nsecs = (clock period)/2 */ if (!hz) hz = spi->max_speed_hz; - cs->nsecs = (1000000000/2) / hz; - if (cs->nsecs > MAX_UDELAY_MS * 1000) - return -EINVAL; + if (hz) { + cs->nsecs = (1000000000/2) / hz; + if (cs->nsecs > (MAX_UDELAY_MS * 1000 * 1000)) + return -EINVAL; + } return 0; } @@ -184,9 +186,6 @@ int spi_bitbang_setup(struct spi_device *spi) struct spi_bitbang *bitbang; int retval; - if (!spi->max_speed_hz) - return -EINVAL; - bitbang = spi_master_get_devdata(spi->master); /* REVISIT: some systems will want to support devices using lsb-first @@ -216,7 +215,7 @@ int spi_bitbang_setup(struct spi_device *spi) if (retval < 0) return retval; - dev_dbg(&spi->dev, "%s, mode %d, %u bits/w, %u nsec\n", + dev_dbg(&spi->dev, "%s, mode %d, %u bits/w, %u nsec/bit\n", __FUNCTION__, spi->mode & (SPI_CPOL | SPI_CPHA), spi->bits_per_word, 2 * cs->nsecs); @@ -405,6 +404,7 @@ int spi_bitbang_transfer(struct spi_device *spi, struct spi_message *m) { struct spi_bitbang *bitbang; unsigned long flags; + int status = 0; m->actual_length = 0; m->status = -EINPROGRESS; @@ -414,11 +414,15 @@ int spi_bitbang_transfer(struct spi_device *spi, struct spi_message *m) return -ESHUTDOWN; spin_lock_irqsave(&bitbang->lock, flags); - list_add_tail(&m->queue, &bitbang->queue); - queue_work(bitbang->workqueue, &bitbang->work); + if (!spi->max_speed_hz) + status = -ENETDOWN; + else { + list_add_tail(&m->queue, &bitbang->queue); + queue_work(bitbang->workqueue, &bitbang->work); + } spin_unlock_irqrestore(&bitbang->lock, flags); - return 0; + return status; } EXPORT_SYMBOL_GPL(spi_bitbang_transfer);