linux-spi.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework.
@ 2012-05-10 16:26 Steven King
  2012-05-11  6:28 ` Greg Ungerer
       [not found] ` <201205100926.55444.sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
  0 siblings, 2 replies; 7+ messages in thread
From: Steven King @ 2012-05-10 16:26 UTC (permalink / raw)
  To: spi-devel-general; +Cc: Grant Likely, uClinux development list, gerg

Use the new SPI queue framework; remove use of workqueue, replace
mcfqspi_transfer with mcfqspi_transfer_one_message, add
mcfqspi_prepare_transfer_hw and mcfqspi_unprepare_transfer_hw, update power
management routines.

Signed-off-by: Steven King <sfking@fdwdc.com>
---
 drivers/spi/spi-coldfire-qspi.c |  255 +++++++++++++++++---------------------
 1 files changed, 114 insertions(+), 141 deletions(-)

diff --git a/drivers/spi/spi-coldfire-qspi.c b/drivers/spi/spi-coldfire-qspi.c
index 6eee64a..b2d4b9e 100644
--- a/drivers/spi/spi-coldfire-qspi.c
+++ b/drivers/spi/spi-coldfire-qspi.c
@@ -25,12 +25,12 @@
 #include <linux/errno.h>
 #include <linux/platform_device.h>
 #include <linux/sched.h>
-#include <linux/workqueue.h>
 #include <linux/delay.h>
 #include <linux/io.h>
 #include <linux/clk.h>
 #include <linux/err.h>
 #include <linux/spi/spi.h>
+#include <linux/pm_runtime.h>
 
 #include <asm/coldfire.h>
 #include <asm/mcfsim.h>
@@ -78,10 +78,7 @@ struct mcfqspi {
 
 	wait_queue_head_t waitq;
 
-	struct work_struct work;
-	struct workqueue_struct *workq;
-	spinlock_t lock;
-	struct list_head msgq;
+	struct device *dev;
 };
 
 static void mcfqspi_wr_qmr(struct mcfqspi *mcfqspi, u16 val)
@@ -303,120 +300,80 @@ static void mcfqspi_transfer_msg16(struct mcfqspi *mcfqspi, unsigned count,
 	}
 }
 
-static void mcfqspi_work(struct work_struct *work)
+static int mcfqspi_transfer_one_message(struct spi_master *master,
+					 struct spi_message *msg)
 {
-	struct mcfqspi *mcfqspi = container_of(work, struct mcfqspi, work);
-	unsigned long flags;
-
-	spin_lock_irqsave(&mcfqspi->lock, flags);
-	while (!list_empty(&mcfqspi->msgq)) {
-		struct spi_message *msg;
-		struct spi_device *spi;
-		struct spi_transfer *xfer;
-		int status = 0;
-
-		msg = container_of(mcfqspi->msgq.next, struct spi_message,
-				   queue);
-
-		list_del_init(&msg->queue);
-		spin_unlock_irqrestore(&mcfqspi->lock, flags);
-
-		spi = msg->spi;
-
-		list_for_each_entry(xfer, &msg->transfers, transfer_list) {
-			bool cs_high = spi->mode & SPI_CS_HIGH;
-			u16 qmr = MCFQSPI_QMR_MSTR;
-
-			if (xfer->bits_per_word)
-				qmr |= xfer->bits_per_word << 10;
-			else
-				qmr |= spi->bits_per_word << 10;
-			if (spi->mode & SPI_CPHA)
-				qmr |= MCFQSPI_QMR_CPHA;
-			if (spi->mode & SPI_CPOL)
-				qmr |= MCFQSPI_QMR_CPOL;
-			if (xfer->speed_hz)
-				qmr |= mcfqspi_qmr_baud(xfer->speed_hz);
-			else
-				qmr |= mcfqspi_qmr_baud(spi->max_speed_hz);
-			mcfqspi_wr_qmr(mcfqspi, qmr);
-
-			mcfqspi_cs_select(mcfqspi, spi->chip_select, cs_high);
-
-			mcfqspi_wr_qir(mcfqspi, MCFQSPI_QIR_SPIFE);
-			if ((xfer->bits_per_word ? xfer->bits_per_word :
-						spi->bits_per_word) == 8)
-				mcfqspi_transfer_msg8(mcfqspi, xfer->len,
-						      xfer->tx_buf,
-						      xfer->rx_buf);
-			else
-				mcfqspi_transfer_msg16(mcfqspi, xfer->len / 2,
-						       xfer->tx_buf,
-						       xfer->rx_buf);
-			mcfqspi_wr_qir(mcfqspi, 0);
-
-			if (xfer->delay_usecs)
-				udelay(xfer->delay_usecs);
-			if (xfer->cs_change) {
-				if (!list_is_last(&xfer->transfer_list,
-						  &msg->transfers))
-					mcfqspi_cs_deselect(mcfqspi,
-							    spi->chip_select,
-							    cs_high);
-			} else {
-				if (list_is_last(&xfer->transfer_list,
-						 &msg->transfers))
-					mcfqspi_cs_deselect(mcfqspi,
-							    spi->chip_select,
-							    cs_high);
-			}
-			msg->actual_length += xfer->len;
+	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
+	struct spi_device *spi = msg->spi;
+	struct spi_transfer *t;
+	int status = 0;
+
+	list_for_each_entry(t, &msg->transfers, transfer_list) {
+		bool cs_high = spi->mode & SPI_CS_HIGH;
+		u16 qmr = MCFQSPI_QMR_MSTR;
+
+		if (t->bits_per_word)
+			qmr |= t->bits_per_word << 10;
+		else
+			qmr |= spi->bits_per_word << 10;
+		if (spi->mode & SPI_CPHA)
+			qmr |= MCFQSPI_QMR_CPHA;
+		if (spi->mode & SPI_CPOL)
+			qmr |= MCFQSPI_QMR_CPOL;
+		if (t->speed_hz)
+			qmr |= mcfqspi_qmr_baud(t->speed_hz);
+		else
+			qmr |= mcfqspi_qmr_baud(spi->max_speed_hz);
+		mcfqspi_wr_qmr(mcfqspi, qmr);
+
+		mcfqspi_cs_select(mcfqspi, spi->chip_select, cs_high);
+
+		mcfqspi_wr_qir(mcfqspi, MCFQSPI_QIR_SPIFE);
+		if ((t->bits_per_word ? t->bits_per_word :
+					spi->bits_per_word) == 8)
+			mcfqspi_transfer_msg8(mcfqspi, t->len, t->tx_buf,
+					t->rx_buf);
+		else
+			mcfqspi_transfer_msg16(mcfqspi, t->len / 2, t->tx_buf,
+					t->rx_buf);
+		mcfqspi_wr_qir(mcfqspi, 0);
+
+		if (t->delay_usecs)
+			udelay(t->delay_usecs);
+		if (t->cs_change) {
+			if (!list_is_last(&t->transfer_list, &msg->transfers))
+				mcfqspi_cs_deselect(mcfqspi, spi->chip_select,
+						cs_high);
+		} else {
+			if (list_is_last(&t->transfer_list, &msg->transfers))
+				mcfqspi_cs_deselect(mcfqspi, spi->chip_select,
+						cs_high);
 		}
-		msg->status = status;
-		msg->complete(msg->context);
-
-		spin_lock_irqsave(&mcfqspi->lock, flags);
+		msg->actual_length += t->len;
 	}
-	spin_unlock_irqrestore(&mcfqspi->lock, flags);
+	msg->status = status;
+	spi_finalize_current_message(master);
+
+	return status;
+
 }
 
-static int mcfqspi_transfer(struct spi_device *spi, struct spi_message *msg)
+static int mcfqspi_prepare_transfer_hw(struct spi_master *master)
 {
-	struct mcfqspi *mcfqspi;
-	struct spi_transfer *xfer;
-	unsigned long flags;
-
-	mcfqspi = spi_master_get_devdata(spi->master);
-
-	list_for_each_entry(xfer, &msg->transfers, transfer_list) {
-		if (xfer->bits_per_word && ((xfer->bits_per_word < 8)
-					|| (xfer->bits_per_word > 16))) {
-			dev_dbg(&spi->dev,
-				"%d bits per word is not supported\n",
-				xfer->bits_per_word);
-			goto fail;
-		}
-		if (xfer->speed_hz) {
-			u32 real_speed = MCFQSPI_BUSCLK /
-				mcfqspi_qmr_baud(xfer->speed_hz);
-			if (real_speed != xfer->speed_hz)
-				dev_dbg(&spi->dev,
-					"using speed %d instead of %d\n",
-					real_speed, xfer->speed_hz);
-		}
-	}
-	msg->status = -EINPROGRESS;
-	msg->actual_length = 0;
+	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
 
-	spin_lock_irqsave(&mcfqspi->lock, flags);
-	list_add_tail(&msg->queue, &mcfqspi->msgq);
-	queue_work(mcfqspi->workq, &mcfqspi->work);
-	spin_unlock_irqrestore(&mcfqspi->lock, flags);
+	pm_runtime_get_sync(mcfqspi->dev);
+
+	return 0;
+}
+
+static int mcfqspi_unprepare_transfer_hw(struct spi_master *master)
+{
+	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
+
+	pm_runtime_put_sync(mcfqspi->dev);
 
 	return 0;
-fail:
-	msg->status = -EINVAL;
-	return -EINVAL;
 }
 
 static int mcfqspi_setup(struct spi_device *spi)
@@ -502,21 +459,10 @@ static int __devinit mcfqspi_probe(struct platform_device *pdev)
 	}
 	clk_enable(mcfqspi->clk);
 
-	mcfqspi->workq = create_singlethread_workqueue(dev_name(master->dev.parent));
-	if (!mcfqspi->workq) {
-		dev_dbg(&pdev->dev, "create_workqueue failed\n");
-		status = -ENOMEM;
-		goto fail4;
-	}
-	INIT_WORK(&mcfqspi->work, mcfqspi_work);
-	spin_lock_init(&mcfqspi->lock);
-	INIT_LIST_HEAD(&mcfqspi->msgq);
-	init_waitqueue_head(&mcfqspi->waitq);
-
 	pdata = pdev->dev.platform_data;
 	if (!pdata) {
 		dev_dbg(&pdev->dev, "platform data is missing\n");
-		goto fail5;
+		goto fail4;
 	}
 	master->bus_num = pdata->bus_num;
 	master->num_chipselect = pdata->num_chipselect;
@@ -525,28 +471,33 @@ static int __devinit mcfqspi_probe(struct platform_device *pdev)
 	status = mcfqspi_cs_setup(mcfqspi);
 	if (status) {
 		dev_dbg(&pdev->dev, "error initializing cs_control\n");
-		goto fail5;
+		goto fail4;
 	}
 
+	init_waitqueue_head(&mcfqspi->waitq);
+	mcfqspi->dev = &pdev->dev;
+
 	master->mode_bits = SPI_CS_HIGH | SPI_CPOL | SPI_CPHA;
 	master->setup = mcfqspi_setup;
-	master->transfer = mcfqspi_transfer;
+	master->transfer_one_message = mcfqspi_transfer_one_message;
+	master->prepare_transfer_hardware = mcfqspi_prepare_transfer_hw;
+	master->unprepare_transfer_hardware = mcfqspi_unprepare_transfer_hw;
 
 	platform_set_drvdata(pdev, master);
 
 	status = spi_register_master(master);
 	if (status) {
 		dev_dbg(&pdev->dev, "spi_register_master failed\n");
-		goto fail6;
+		goto fail5;
 	}
+	pm_runtime_enable(mcfqspi->dev);
+
 	dev_info(&pdev->dev, "Coldfire QSPI bus driver\n");
 
 	return 0;
 
-fail6:
-	mcfqspi_cs_teardown(mcfqspi);
 fail5:
-	destroy_workqueue(mcfqspi->workq);
+	mcfqspi_cs_teardown(mcfqspi);
 fail4:
 	clk_disable(mcfqspi->clk);
 	clk_put(mcfqspi->clk);
@@ -570,12 +521,12 @@ static int __devexit mcfqspi_remove(struct platform_device *pdev)
 	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
 	struct resource *res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
 
+	pm_runtime_disable(mcfqspi->dev);
 	/* disable the hardware (set the baud rate to 0) */
 	mcfqspi_wr_qmr(mcfqspi, MCFQSPI_QMR_MSTR);
 
 	platform_set_drvdata(pdev, NULL);
 	mcfqspi_cs_teardown(mcfqspi);
-	destroy_workqueue(mcfqspi->workq);
 	clk_disable(mcfqspi->clk);
 	clk_put(mcfqspi->clk);
 	free_irq(mcfqspi->irq, mcfqspi);
@@ -587,11 +538,13 @@ static int __devexit mcfqspi_remove(struct platform_device *pdev)
 	return 0;
 }
 
-#ifdef CONFIG_PM
-
+#ifdef CONFIG_PM_SLEEP
 static int mcfqspi_suspend(struct device *dev)
 {
-	struct mcfqspi *mcfqspi = platform_get_drvdata(to_platform_device(dev));
+	struct spi_master *master = spi_master_get(dev_get_drvdata(dev));
+	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
+
+	spi_master_suspend(master);
 
 	clk_disable(mcfqspi->clk);
 
@@ -600,27 +553,47 @@ static int mcfqspi_suspend(struct device *dev)
 
 static int mcfqspi_resume(struct device *dev)
 {
-	struct mcfqspi *mcfqspi = platform_get_drvdata(to_platform_device(dev));
+	struct spi_master *master = spi_master_get(dev_get_drvdata(dev));
+	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
+
+	spi_master_resume(master);
 
 	clk_enable(mcfqspi->clk);
 
 	return 0;
 }
+#endif
 
-static struct dev_pm_ops mcfqspi_dev_pm_ops = {
-	.suspend	= mcfqspi_suspend,
-	.resume		= mcfqspi_resume,
-};
+#ifdef CONFIG_PM_RUNTIME
+static int mcfqspi_runtime_suspend(struct device *dev)
+{
+	struct mcfqspi *mcfqspi = platform_get_drvdata(to_platform_device(dev));
 
-#define	MCFQSPI_DEV_PM_OPS	(&mcfqspi_dev_pm_ops)
-#else
-#define	MCFQSPI_DEV_PM_OPS	NULL
+	clk_disable(mcfqspi->clk);
+
+	return 0;
+}
+
+static int mcfqspi_runtime_resume(struct device *dev)
+{
+	struct mcfqspi *mcfqspi = platform_get_drvdata(to_platform_device(dev));
+
+	clk_enable(mcfqspi->clk);
+
+	return 0;
+}
 #endif
 
+static const struct dev_pm_ops mcfqspi_pm = {
+	SET_SYSTEM_SLEEP_PM_OPS(mcfqspi_suspend, mcfqspi_resume)
+	SET_RUNTIME_PM_OPS(mcfqspi_runtime_suspend, mcfqspi_runtime_resume,
+			NULL)
+};
+
 static struct platform_driver mcfqspi_driver = {
 	.driver.name	= DRIVER_NAME,
 	.driver.owner	= THIS_MODULE,
-	.driver.pm	= MCFQSPI_DEV_PM_OPS,
+	.driver.pm	= &mcfqspi_pm,
 	.probe		= mcfqspi_probe,
 	.remove		= __devexit_p(mcfqspi_remove),
 };
_______________________________________________
uClinux-dev mailing list
uClinux-dev@uclinux.org
http://mailman.uclinux.org/mailman/listinfo/uclinux-dev
This message was resent by uclinux-dev@uclinux.org
To unsubscribe see:
http://mailman.uclinux.org/mailman/options/uclinux-dev

^ permalink raw reply related	[flat|nested] 7+ messages in thread

* Re: [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework.
  2012-05-10 16:26 [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework Steven King
@ 2012-05-11  6:28 ` Greg Ungerer
       [not found]   ` <4FACB1A9.3060800-XXXsiaCtIV5Wk0Htik3J/w@public.gmane.org>
       [not found] ` <201205100926.55444.sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
  1 sibling, 1 reply; 7+ messages in thread
From: Greg Ungerer @ 2012-05-11  6:28 UTC (permalink / raw)
  To: Steven King
  Cc: Grant Likely, spi-devel-general, uClinux development list, gerg

On 11/05/12 02:26, Steven King wrote:
> Use the new SPI queue framework; remove use of workqueue, replace
> mcfqspi_transfer with mcfqspi_transfer_one_message, add
> mcfqspi_prepare_transfer_hw and mcfqspi_unprepare_transfer_hw, update power
> management routines.
>
> Signed-off-by: Steven King<sfking@fdwdc.com>

I can't add much value reviewing this one, style wise it looks good.

Grant: if you don't want to take this through one of your trees
I can add it to the m68knommu git tree.

Regards
Greg


>   drivers/spi/spi-coldfire-qspi.c |  255 +++++++++++++++++---------------------
>   1 files changed, 114 insertions(+), 141 deletions(-)
>
> diff --git a/drivers/spi/spi-coldfire-qspi.c b/drivers/spi/spi-coldfire-qspi.c
> index 6eee64a..b2d4b9e 100644
> --- a/drivers/spi/spi-coldfire-qspi.c
> +++ b/drivers/spi/spi-coldfire-qspi.c
> @@ -25,12 +25,12 @@
>   #include<linux/errno.h>
>   #include<linux/platform_device.h>
>   #include<linux/sched.h>
> -#include<linux/workqueue.h>
>   #include<linux/delay.h>
>   #include<linux/io.h>
>   #include<linux/clk.h>
>   #include<linux/err.h>
>   #include<linux/spi/spi.h>
> +#include<linux/pm_runtime.h>
>
>   #include<asm/coldfire.h>
>   #include<asm/mcfsim.h>
> @@ -78,10 +78,7 @@ struct mcfqspi {
>
>   	wait_queue_head_t waitq;
>
> -	struct work_struct work;
> -	struct workqueue_struct *workq;
> -	spinlock_t lock;
> -	struct list_head msgq;
> +	struct device *dev;
>   };
>
>   static void mcfqspi_wr_qmr(struct mcfqspi *mcfqspi, u16 val)
> @@ -303,120 +300,80 @@ static void mcfqspi_transfer_msg16(struct mcfqspi *mcfqspi, unsigned count,
>   	}
>   }
>
> -static void mcfqspi_work(struct work_struct *work)
> +static int mcfqspi_transfer_one_message(struct spi_master *master,
> +					 struct spi_message *msg)
>   {
> -	struct mcfqspi *mcfqspi = container_of(work, struct mcfqspi, work);
> -	unsigned long flags;
> -
> -	spin_lock_irqsave(&mcfqspi->lock, flags);
> -	while (!list_empty(&mcfqspi->msgq)) {
> -		struct spi_message *msg;
> -		struct spi_device *spi;
> -		struct spi_transfer *xfer;
> -		int status = 0;
> -
> -		msg = container_of(mcfqspi->msgq.next, struct spi_message,
> -				   queue);
> -
> -		list_del_init(&msg->queue);
> -		spin_unlock_irqrestore(&mcfqspi->lock, flags);
> -
> -		spi = msg->spi;
> -
> -		list_for_each_entry(xfer,&msg->transfers, transfer_list) {
> -			bool cs_high = spi->mode&  SPI_CS_HIGH;
> -			u16 qmr = MCFQSPI_QMR_MSTR;
> -
> -			if (xfer->bits_per_word)
> -				qmr |= xfer->bits_per_word<<  10;
> -			else
> -				qmr |= spi->bits_per_word<<  10;
> -			if (spi->mode&  SPI_CPHA)
> -				qmr |= MCFQSPI_QMR_CPHA;
> -			if (spi->mode&  SPI_CPOL)
> -				qmr |= MCFQSPI_QMR_CPOL;
> -			if (xfer->speed_hz)
> -				qmr |= mcfqspi_qmr_baud(xfer->speed_hz);
> -			else
> -				qmr |= mcfqspi_qmr_baud(spi->max_speed_hz);
> -			mcfqspi_wr_qmr(mcfqspi, qmr);
> -
> -			mcfqspi_cs_select(mcfqspi, spi->chip_select, cs_high);
> -
> -			mcfqspi_wr_qir(mcfqspi, MCFQSPI_QIR_SPIFE);
> -			if ((xfer->bits_per_word ? xfer->bits_per_word :
> -						spi->bits_per_word) == 8)
> -				mcfqspi_transfer_msg8(mcfqspi, xfer->len,
> -						      xfer->tx_buf,
> -						      xfer->rx_buf);
> -			else
> -				mcfqspi_transfer_msg16(mcfqspi, xfer->len / 2,
> -						       xfer->tx_buf,
> -						       xfer->rx_buf);
> -			mcfqspi_wr_qir(mcfqspi, 0);
> -
> -			if (xfer->delay_usecs)
> -				udelay(xfer->delay_usecs);
> -			if (xfer->cs_change) {
> -				if (!list_is_last(&xfer->transfer_list,
> -						&msg->transfers))
> -					mcfqspi_cs_deselect(mcfqspi,
> -							    spi->chip_select,
> -							    cs_high);
> -			} else {
> -				if (list_is_last(&xfer->transfer_list,
> -						&msg->transfers))
> -					mcfqspi_cs_deselect(mcfqspi,
> -							    spi->chip_select,
> -							    cs_high);
> -			}
> -			msg->actual_length += xfer->len;
> +	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
> +	struct spi_device *spi = msg->spi;
> +	struct spi_transfer *t;
> +	int status = 0;
> +
> +	list_for_each_entry(t,&msg->transfers, transfer_list) {
> +		bool cs_high = spi->mode&  SPI_CS_HIGH;
> +		u16 qmr = MCFQSPI_QMR_MSTR;
> +
> +		if (t->bits_per_word)
> +			qmr |= t->bits_per_word<<  10;
> +		else
> +			qmr |= spi->bits_per_word<<  10;
> +		if (spi->mode&  SPI_CPHA)
> +			qmr |= MCFQSPI_QMR_CPHA;
> +		if (spi->mode&  SPI_CPOL)
> +			qmr |= MCFQSPI_QMR_CPOL;
> +		if (t->speed_hz)
> +			qmr |= mcfqspi_qmr_baud(t->speed_hz);
> +		else
> +			qmr |= mcfqspi_qmr_baud(spi->max_speed_hz);
> +		mcfqspi_wr_qmr(mcfqspi, qmr);
> +
> +		mcfqspi_cs_select(mcfqspi, spi->chip_select, cs_high);
> +
> +		mcfqspi_wr_qir(mcfqspi, MCFQSPI_QIR_SPIFE);
> +		if ((t->bits_per_word ? t->bits_per_word :
> +					spi->bits_per_word) == 8)
> +			mcfqspi_transfer_msg8(mcfqspi, t->len, t->tx_buf,
> +					t->rx_buf);
> +		else
> +			mcfqspi_transfer_msg16(mcfqspi, t->len / 2, t->tx_buf,
> +					t->rx_buf);
> +		mcfqspi_wr_qir(mcfqspi, 0);
> +
> +		if (t->delay_usecs)
> +			udelay(t->delay_usecs);
> +		if (t->cs_change) {
> +			if (!list_is_last(&t->transfer_list,&msg->transfers))
> +				mcfqspi_cs_deselect(mcfqspi, spi->chip_select,
> +						cs_high);
> +		} else {
> +			if (list_is_last(&t->transfer_list,&msg->transfers))
> +				mcfqspi_cs_deselect(mcfqspi, spi->chip_select,
> +						cs_high);
>   		}
> -		msg->status = status;
> -		msg->complete(msg->context);
> -
> -		spin_lock_irqsave(&mcfqspi->lock, flags);
> +		msg->actual_length += t->len;
>   	}
> -	spin_unlock_irqrestore(&mcfqspi->lock, flags);
> +	msg->status = status;
> +	spi_finalize_current_message(master);
> +
> +	return status;
> +
>   }
>
> -static int mcfqspi_transfer(struct spi_device *spi, struct spi_message *msg)
> +static int mcfqspi_prepare_transfer_hw(struct spi_master *master)
>   {
> -	struct mcfqspi *mcfqspi;
> -	struct spi_transfer *xfer;
> -	unsigned long flags;
> -
> -	mcfqspi = spi_master_get_devdata(spi->master);
> -
> -	list_for_each_entry(xfer,&msg->transfers, transfer_list) {
> -		if (xfer->bits_per_word&&  ((xfer->bits_per_word<  8)
> -					|| (xfer->bits_per_word>  16))) {
> -			dev_dbg(&spi->dev,
> -				"%d bits per word is not supported\n",
> -				xfer->bits_per_word);
> -			goto fail;
> -		}
> -		if (xfer->speed_hz) {
> -			u32 real_speed = MCFQSPI_BUSCLK /
> -				mcfqspi_qmr_baud(xfer->speed_hz);
> -			if (real_speed != xfer->speed_hz)
> -				dev_dbg(&spi->dev,
> -					"using speed %d instead of %d\n",
> -					real_speed, xfer->speed_hz);
> -		}
> -	}
> -	msg->status = -EINPROGRESS;
> -	msg->actual_length = 0;
> +	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
>
> -	spin_lock_irqsave(&mcfqspi->lock, flags);
> -	list_add_tail(&msg->queue,&mcfqspi->msgq);
> -	queue_work(mcfqspi->workq,&mcfqspi->work);
> -	spin_unlock_irqrestore(&mcfqspi->lock, flags);
> +	pm_runtime_get_sync(mcfqspi->dev);
> +
> +	return 0;
> +}
> +
> +static int mcfqspi_unprepare_transfer_hw(struct spi_master *master)
> +{
> +	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
> +
> +	pm_runtime_put_sync(mcfqspi->dev);
>
>   	return 0;
> -fail:
> -	msg->status = -EINVAL;
> -	return -EINVAL;
>   }
>
>   static int mcfqspi_setup(struct spi_device *spi)
> @@ -502,21 +459,10 @@ static int __devinit mcfqspi_probe(struct platform_device *pdev)
>   	}
>   	clk_enable(mcfqspi->clk);
>
> -	mcfqspi->workq = create_singlethread_workqueue(dev_name(master->dev.parent));
> -	if (!mcfqspi->workq) {
> -		dev_dbg(&pdev->dev, "create_workqueue failed\n");
> -		status = -ENOMEM;
> -		goto fail4;
> -	}
> -	INIT_WORK(&mcfqspi->work, mcfqspi_work);
> -	spin_lock_init(&mcfqspi->lock);
> -	INIT_LIST_HEAD(&mcfqspi->msgq);
> -	init_waitqueue_head(&mcfqspi->waitq);
> -
>   	pdata = pdev->dev.platform_data;
>   	if (!pdata) {
>   		dev_dbg(&pdev->dev, "platform data is missing\n");
> -		goto fail5;
> +		goto fail4;
>   	}
>   	master->bus_num = pdata->bus_num;
>   	master->num_chipselect = pdata->num_chipselect;
> @@ -525,28 +471,33 @@ static int __devinit mcfqspi_probe(struct platform_device *pdev)
>   	status = mcfqspi_cs_setup(mcfqspi);
>   	if (status) {
>   		dev_dbg(&pdev->dev, "error initializing cs_control\n");
> -		goto fail5;
> +		goto fail4;
>   	}
>
> +	init_waitqueue_head(&mcfqspi->waitq);
> +	mcfqspi->dev =&pdev->dev;
> +
>   	master->mode_bits = SPI_CS_HIGH | SPI_CPOL | SPI_CPHA;
>   	master->setup = mcfqspi_setup;
> -	master->transfer = mcfqspi_transfer;
> +	master->transfer_one_message = mcfqspi_transfer_one_message;
> +	master->prepare_transfer_hardware = mcfqspi_prepare_transfer_hw;
> +	master->unprepare_transfer_hardware = mcfqspi_unprepare_transfer_hw;
>
>   	platform_set_drvdata(pdev, master);
>
>   	status = spi_register_master(master);
>   	if (status) {
>   		dev_dbg(&pdev->dev, "spi_register_master failed\n");
> -		goto fail6;
> +		goto fail5;
>   	}
> +	pm_runtime_enable(mcfqspi->dev);
> +
>   	dev_info(&pdev->dev, "Coldfire QSPI bus driver\n");
>
>   	return 0;
>
> -fail6:
> -	mcfqspi_cs_teardown(mcfqspi);
>   fail5:
> -	destroy_workqueue(mcfqspi->workq);
> +	mcfqspi_cs_teardown(mcfqspi);
>   fail4:
>   	clk_disable(mcfqspi->clk);
>   	clk_put(mcfqspi->clk);
> @@ -570,12 +521,12 @@ static int __devexit mcfqspi_remove(struct platform_device *pdev)
>   	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
>   	struct resource *res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
>
> +	pm_runtime_disable(mcfqspi->dev);
>   	/* disable the hardware (set the baud rate to 0) */
>   	mcfqspi_wr_qmr(mcfqspi, MCFQSPI_QMR_MSTR);
>
>   	platform_set_drvdata(pdev, NULL);
>   	mcfqspi_cs_teardown(mcfqspi);
> -	destroy_workqueue(mcfqspi->workq);
>   	clk_disable(mcfqspi->clk);
>   	clk_put(mcfqspi->clk);
>   	free_irq(mcfqspi->irq, mcfqspi);
> @@ -587,11 +538,13 @@ static int __devexit mcfqspi_remove(struct platform_device *pdev)
>   	return 0;
>   }
>
> -#ifdef CONFIG_PM
> -
> +#ifdef CONFIG_PM_SLEEP
>   static int mcfqspi_suspend(struct device *dev)
>   {
> -	struct mcfqspi *mcfqspi = platform_get_drvdata(to_platform_device(dev));
> +	struct spi_master *master = spi_master_get(dev_get_drvdata(dev));
> +	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
> +
> +	spi_master_suspend(master);
>
>   	clk_disable(mcfqspi->clk);
>
> @@ -600,27 +553,47 @@ static int mcfqspi_suspend(struct device *dev)
>
>   static int mcfqspi_resume(struct device *dev)
>   {
> -	struct mcfqspi *mcfqspi = platform_get_drvdata(to_platform_device(dev));
> +	struct spi_master *master = spi_master_get(dev_get_drvdata(dev));
> +	struct mcfqspi *mcfqspi = spi_master_get_devdata(master);
> +
> +	spi_master_resume(master);
>
>   	clk_enable(mcfqspi->clk);
>
>   	return 0;
>   }
> +#endif
>
> -static struct dev_pm_ops mcfqspi_dev_pm_ops = {
> -	.suspend	= mcfqspi_suspend,
> -	.resume		= mcfqspi_resume,
> -};
> +#ifdef CONFIG_PM_RUNTIME
> +static int mcfqspi_runtime_suspend(struct device *dev)
> +{
> +	struct mcfqspi *mcfqspi = platform_get_drvdata(to_platform_device(dev));
>
> -#define	MCFQSPI_DEV_PM_OPS	(&mcfqspi_dev_pm_ops)
> -#else
> -#define	MCFQSPI_DEV_PM_OPS	NULL
> +	clk_disable(mcfqspi->clk);
> +
> +	return 0;
> +}
> +
> +static int mcfqspi_runtime_resume(struct device *dev)
> +{
> +	struct mcfqspi *mcfqspi = platform_get_drvdata(to_platform_device(dev));
> +
> +	clk_enable(mcfqspi->clk);
> +
> +	return 0;
> +}
>   #endif
>
> +static const struct dev_pm_ops mcfqspi_pm = {
> +	SET_SYSTEM_SLEEP_PM_OPS(mcfqspi_suspend, mcfqspi_resume)
> +	SET_RUNTIME_PM_OPS(mcfqspi_runtime_suspend, mcfqspi_runtime_resume,
> +			NULL)
> +};
> +
>   static struct platform_driver mcfqspi_driver = {
>   	.driver.name	= DRIVER_NAME,
>   	.driver.owner	= THIS_MODULE,
> -	.driver.pm	= MCFQSPI_DEV_PM_OPS,
> +	.driver.pm	=&mcfqspi_pm,
>   	.probe		= mcfqspi_probe,
>   	.remove		= __devexit_p(mcfqspi_remove),
>   };
>
>
>


-- 
------------------------------------------------------------------------
Greg Ungerer  --  Principal Engineer        EMAIL:     gerg@snapgear.com
SnapGear Group, McAfee                      PHONE:       +61 7 3435 2888
8 Gardner Close                             FAX:         +61 7 3217 5323
Milton, QLD, 4064, Australia                WEB: http://www.SnapGear.com
_______________________________________________
uClinux-dev mailing list
uClinux-dev@uclinux.org
http://mailman.uclinux.org/mailman/listinfo/uclinux-dev
This message was resent by uclinux-dev@uclinux.org
To unsubscribe see:
http://mailman.uclinux.org/mailman/options/uclinux-dev

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework.
       [not found] ` <201205100926.55444.sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
@ 2012-05-11  8:33   ` Shubhrajyoti Datta
  2012-05-11 10:33     ` Steven King
  2012-05-14 19:50   ` Linus Walleij
  1 sibling, 1 reply; 7+ messages in thread
From: Shubhrajyoti Datta @ 2012-05-11  8:33 UTC (permalink / raw)
  To: Steven King
  Cc: spi-devel-general-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f,
	uClinux development list, gerg-JBU5SbJe1FlAfugRpC6u6w

Hi Steven,

On Thu, May 10, 2012 at 9:56 PM, Steven King <sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org> wrote:
> Use the new SPI queue framework; remove use of workqueue, replace
> mcfqspi_transfer with mcfqspi_transfer_one_message, add
> mcfqspi_prepare_transfer_hw and mcfqspi_unprepare_transfer_hw, update power
> management routines.

By update are you attempting to convert to runtime framework also?

>

------------------------------------------------------------------------------
Live Security Virtual Conference
Exclusive live event will cover all the ways today's security and 
threat landscape has changed and how IT managers can respond. Discussions 
will include endpoint security, mobile security and the latest in malware 
threats. http://www.accelacomm.com/jaw/sfrnl04242012/114/50122263/

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework.
  2012-05-11  8:33   ` Shubhrajyoti Datta
@ 2012-05-11 10:33     ` Steven King
       [not found]       ` <201205110333.22096.sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
  0 siblings, 1 reply; 7+ messages in thread
From: Steven King @ 2012-05-11 10:33 UTC (permalink / raw)
  To: Shubhrajyoti Datta; +Cc: spi-devel-general, uClinux development list, gerg

On Friday 11 May 2012 1:33:25 am Shubhrajyoti Datta wrote:
> Hi Steven,
>
> On Thu, May 10, 2012 at 9:56 PM, Steven King <sfking@fdwdc.com> wrote:
> > Use the new SPI queue framework; remove use of workqueue, replace
> > mcfqspi_transfer with mcfqspi_transfer_one_message, add
> > mcfqspi_prepare_transfer_hw and mcfqspi_unprepare_transfer_hw, update
> > power management routines.
>
> By update are you attempting to convert to runtime framework also?

laying the ground work for it; right now its mostly just a big nop as 
currently on Coldfire there isnt any PM support.  I suppose it would have 
been better to have that as a separate patch, i can resubmit with that broken 
out if people would prefer.
_______________________________________________
uClinux-dev mailing list
uClinux-dev@uclinux.org
http://mailman.uclinux.org/mailman/listinfo/uclinux-dev
This message was resent by uclinux-dev@uclinux.org
To unsubscribe see:
http://mailman.uclinux.org/mailman/options/uclinux-dev

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework.
       [not found]       ` <201205110333.22096.sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
@ 2012-05-11 13:21         ` Shubhrajyoti Datta
  0 siblings, 0 replies; 7+ messages in thread
From: Shubhrajyoti Datta @ 2012-05-11 13:21 UTC (permalink / raw)
  To: Steven King
  Cc: spi-devel-general-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f,
	uClinux development list, gerg-JBU5SbJe1FlAfugRpC6u6w

On Fri, May 11, 2012 at 4:03 PM, Steven King <sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org> wrote:
> On Friday 11 May 2012 1:33:25 am Shubhrajyoti Datta wrote:
>> Hi Steven,
>>
>> On Thu, May 10, 2012 at 9:56 PM, Steven King <sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org> wrote:
>> > Use the new SPI queue framework; remove use of workqueue, replace
>> > mcfqspi_transfer with mcfqspi_transfer_one_message, add
>> > mcfqspi_prepare_transfer_hw and mcfqspi_unprepare_transfer_hw, update
>> > power management routines.
>>
>> By update are you attempting to convert to runtime framework also?
>
> laying the ground work for it; right now its mostly just a big nop as
> currently on Coldfire there isnt any PM support.

OK , BTW my concern was partly clock apis and partly runtime.
Anyways dont have any strong opinions.

>  I suppose it would have
> been better to have that as a separate patch, i can resubmit with that broken
> out if people would prefer.

------------------------------------------------------------------------------
Live Security Virtual Conference
Exclusive live event will cover all the ways today's security and 
threat landscape has changed and how IT managers can respond. Discussions 
will include endpoint security, mobile security and the latest in malware 
threats. http://www.accelacomm.com/jaw/sfrnl04242012/114/50122263/

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework.
       [not found] ` <201205100926.55444.sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
  2012-05-11  8:33   ` Shubhrajyoti Datta
@ 2012-05-14 19:50   ` Linus Walleij
  1 sibling, 0 replies; 7+ messages in thread
From: Linus Walleij @ 2012-05-14 19:50 UTC (permalink / raw)
  To: Steven King
  Cc: spi-devel-general-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f,
	uClinux development list, gerg-JBU5SbJe1FlAfugRpC6u6w

On Thu, May 10, 2012 at 6:26 PM, Steven King <sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org> wrote:

> Use the new SPI queue framework; remove use of workqueue, replace
> mcfqspi_transfer with mcfqspi_transfer_one_message, add
> mcfqspi_prepare_transfer_hw and mcfqspi_unprepare_transfer_hw, update power
> management routines.
>
> Signed-off-by: Steven King <sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>

Looks good to me, the PM runtime stuff could have been in a separate patch
but that's no big deal to me.
Acked-by: Linus Walleij <linus.walleij-QSEj5FYQhm4dnm+yROfE0A@public.gmane.org>

Yours,
Linus Walleij

------------------------------------------------------------------------------
Live Security Virtual Conference
Exclusive live event will cover all the ways today's security and 
threat landscape has changed and how IT managers can respond. Discussions 
will include endpoint security, mobile security and the latest in malware 
threats. http://www.accelacomm.com/jaw/sfrnl04242012/114/50122263/

^ permalink raw reply	[flat|nested] 7+ messages in thread

* Re: [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework.
       [not found]   ` <4FACB1A9.3060800-XXXsiaCtIV5Wk0Htik3J/w@public.gmane.org>
@ 2012-05-20  4:57     ` Grant Likely
  0 siblings, 0 replies; 7+ messages in thread
From: Grant Likely @ 2012-05-20  4:57 UTC (permalink / raw)
  To: Greg Ungerer, Steven King
  Cc: spi-devel-general-5NWGOfrQmneRv+LV9MX5uipxlwaOVQ5f,
	uClinux development list, gerg-JBU5SbJe1FlAfugRpC6u6w

On Fri, 11 May 2012 16:28:57 +1000, Greg Ungerer <gerg-XXXsiaCtIV5Wk0Htik3J/w@public.gmane.org> wrote:
> On 11/05/12 02:26, Steven King wrote:
> > Use the new SPI queue framework; remove use of workqueue, replace
> > mcfqspi_transfer with mcfqspi_transfer_one_message, add
> > mcfqspi_prepare_transfer_hw and mcfqspi_unprepare_transfer_hw, update power
> > management routines.
> >
> > Signed-off-by: Steven King<sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
> 
> I can't add much value reviewing this one, style wise it looks good.

I'll take that as an ack.

> 
> Grant: if you don't want to take this through one of your trees
> I can add it to the m68knommu git tree.

Merged, thanks.

g.


------------------------------------------------------------------------------
Live Security Virtual Conference
Exclusive live event will cover all the ways today's security and 
threat landscape has changed and how IT managers can respond. Discussions 
will include endpoint security, mobile security and the latest in malware 
threats. http://www.accelacomm.com/jaw/sfrnl04242012/114/50122263/

^ permalink raw reply	[flat|nested] 7+ messages in thread

end of thread, other threads:[~2012-05-20  4:57 UTC | newest]

Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2012-05-10 16:26 [PATCH] spi: refactor spi-coldfire-qspi to use SPI queue framework Steven King
2012-05-11  6:28 ` Greg Ungerer
     [not found]   ` <4FACB1A9.3060800-XXXsiaCtIV5Wk0Htik3J/w@public.gmane.org>
2012-05-20  4:57     ` Grant Likely
     [not found] ` <201205100926.55444.sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
2012-05-11  8:33   ` Shubhrajyoti Datta
2012-05-11 10:33     ` Steven King
     [not found]       ` <201205110333.22096.sfking-xS0NTnu2YfYAvxtiuMwx3w@public.gmane.org>
2012-05-11 13:21         ` Shubhrajyoti Datta
2012-05-14 19:50   ` Linus Walleij

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).