Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
Tony Lindgren wrote: > * Venkatraman S [100311 07:04]: >> Tony Lindgren wrote: >> > >> > Does the driver still work in PIO mode? >> > >> > We need to have the drivers capable to fail over to PIO mode >> > as the DMA channels can run out. >> > >> >> The driver doesn't have an automatic fallback to PIO, >> even without my patch. A error return from omap_request_dma is >> propogated all the way back to the transfer request. >> The decision to use_dma (the variable) is unaltered. > > OK, that might explain some nasty surprises then.. > > With these patches, does the driver still work in PIO mode though? No. The workhorse code to actually push the data byte by byte is not present in the hsmmc driver. -- To unsubscribe from this list: send the line "unsubscribe linux-omap" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
Madhusudhan wrote: > > >> -Original Message- >> From: svenk...@gmail.com [mailto:svenk...@gmail.com] On Behalf Of >> Venkatraman S >> Sent: Thursday, March 11, 2010 11:43 AM >> To: Madhusudhan >> Cc: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; >> linux-omap@vger.kernel.org >> Subject: Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor >> autoloading feature >> >> Madhusudhan wrote: >> >> -Original Message- >> >> From: svenk...@gmail.com [mailto:svenk...@gmail.com] On Behalf Of >> >> Venkatraman S >> >> Sent: Thursday, March 11, 2010 4:52 AM >> >> To: Madhusudhan >> >> Cc: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; >> >> linux-omap@vger.kernel.org >> >> Subject: Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor >> >> autoloading feature >> >> >> >> Madhusudhan wrote: >> >> >> -Original Message- >> >> >> From: linux-mmc-ow...@vger.kernel.org [mailto:linux-mmc- >> >> >> ow...@vger.kernel.org] On Behalf Of Venkatraman S >> >> >> Sent: Monday, March 01, 2010 5:27 AM >> >> >> To: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; >> >> >> linux-omap@vger.kernel.org >> >> >> Subject: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor >> >> >> autoloading feature >> >> >> >> >> >> Start to use the sDMA descriptor autoloading feature. >> >> >> For large datablocks, the MMC driver has to repeatedly setup, >> program >> >> >> and teardown the >> >> >> dma channel for each element of the sglist received in >> >> omap_hsmmc_request. >> >> >> >> >> >> By using descriptor autoloading, transfers from / to each element of >> >> >> the sglist is pre programmed >> >> >> into a linked list. The sDMA driver completes the entire transaction >> >> >> and provides a single interrupt. >> >> >> >> >> >> Due to this, number of dma interrupts for a typical 100MB transfer >> on >> >> the >> >> >> MMC is >> >> >> reduced from 25000 to about 400 (approximate). Transfer speeds are >> >> >> improved by ~5% >> >> >> (Though it varies on the size of read / write & improves on huge >> >> >> transfers) >> >> >> >> >> >> Descriptor autoloading is available only in 3630 and 4430 (as of >> now). >> >> >> Hence normal DMA >> >> >> mode is also retained. >> >> >> >> >> >> Tested on omap4430 sdp. >> >> >> >> >> >> Signed-off-by: Venkatraman S >> >> > >> >> > I don't see any issues with this patch except the concern I had on >> the >> >> first >> >> > patch in the series. Why is that change linked to this series? >> >> > >> >> Thanks. The problem was seen only in the context of using descriptor >> >> load. Would >> >> you prefer that I post it as a separate patch ? >> > >> > My point is why that change is needed for this feature to work? >> > >> > When DMA is completed and a callback is received the ch can be freed. >> Once >> > TC is received the core is notified of the same. >> > >> > Can the first patch be dropped? Or do you see issues? >> Yes there are issues without this patch when the scatterlist is large >> (300+ blocks), where the dma completion interrupt is received but the >> mmc driver hangs waiting for TC. I don't see the issue if I delay the >> execution of omap_free_dma inside the dma callback. > > This is strange. Ideally after the dma cb is received the transfer complete > interrupt should fire. > > Your first patch would break a corner erroneous case the driver is already > handling. A scenario where TC was received before DMA cb came. There is > timeout logic in the driver which handles this case to let the request > succeed if a dma cb was received after a while otherwise err out. See the > function omap_hsmmc_start_dma_transfer. > > Is there a way to keep both the cases handled? If not we have to make > changes based on which of these scenario is very odd. I think these cases are already handled properly. All actions are taken if, and only if, TC is received. Once TC is received, the sequence of execution is unaltered by DMA callback. Dma callback is effectively a no-op after the final block is transmitted. We can in fact get rid of the timeout logic. Of course, the DMA channel is cleared once the TC is received, hence there would be no spurious DMA callbacks during the start of next transaction. [The only hanging case is when the TC is never triggerred, even after a successful transfer, but that's another issue altogether] Regards, Venkat. -- To unsubscribe from this list: send the line "unsubscribe linux-omap" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
> -Original Message- > From: svenk...@gmail.com [mailto:svenk...@gmail.com] On Behalf Of > Venkatraman S > Sent: Thursday, March 11, 2010 11:43 AM > To: Madhusudhan > Cc: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; > linux-omap@vger.kernel.org > Subject: Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor > autoloading feature > > Madhusudhan wrote: > >> -Original Message- > >> From: svenk...@gmail.com [mailto:svenk...@gmail.com] On Behalf Of > >> Venkatraman S > >> Sent: Thursday, March 11, 2010 4:52 AM > >> To: Madhusudhan > >> Cc: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; > >> linux-omap@vger.kernel.org > >> Subject: Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor > >> autoloading feature > >> > >> Madhusudhan wrote: > >> >> -Original Message- > >> >> From: linux-mmc-ow...@vger.kernel.org [mailto:linux-mmc- > >> >> ow...@vger.kernel.org] On Behalf Of Venkatraman S > >> >> Sent: Monday, March 01, 2010 5:27 AM > >> >> To: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; > >> >> linux-omap@vger.kernel.org > >> >> Subject: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor > >> >> autoloading feature > >> >> > >> >> Start to use the sDMA descriptor autoloading feature. > >> >> For large datablocks, the MMC driver has to repeatedly setup, > program > >> >> and teardown the > >> >> dma channel for each element of the sglist received in > >> omap_hsmmc_request. > >> >> > >> >> By using descriptor autoloading, transfers from / to each element of > >> >> the sglist is pre programmed > >> >> into a linked list. The sDMA driver completes the entire transaction > >> >> and provides a single interrupt. > >> >> > >> >> Due to this, number of dma interrupts for a typical 100MB transfer > on > >> the > >> >> MMC is > >> >> reduced from 25000 to about 400 (approximate). Transfer speeds are > >> >> improved by ~5% > >> >> (Though it varies on the size of read / write & improves on huge > >> >> transfers) > >> >> > >> >> Descriptor autoloading is available only in 3630 and 4430 (as of > now). > >> >> Hence normal DMA > >> >> mode is also retained. > >> >> > >> >> Tested on omap4430 sdp. > >> >> > >> >> Signed-off-by: Venkatraman S > >> > > >> > I don't see any issues with this patch except the concern I had on > the > >> first > >> > patch in the series. Why is that change linked to this series? > >> > > >> Thanks. The problem was seen only in the context of using descriptor > >> load. Would > >> you prefer that I post it as a separate patch ? > > > > My point is why that change is needed for this feature to work? > > > > When DMA is completed and a callback is received the ch can be freed. > Once > > TC is received the core is notified of the same. > > > > Can the first patch be dropped? Or do you see issues? > Yes there are issues without this patch when the scatterlist is large > (300+ blocks), where the dma completion interrupt is received but the > mmc driver hangs waiting for TC. I don't see the issue if I delay the > execution of omap_free_dma inside the dma callback. This is strange. Ideally after the dma cb is received the transfer complete interrupt should fire. Your first patch would break a corner erroneous case the driver is already handling. A scenario where TC was received before DMA cb came. There is timeout logic in the driver which handles this case to let the request succeed if a dma cb was received after a while otherwise err out. See the function omap_hsmmc_start_dma_transfer. Is there a way to keep both the cases handled? If not we have to make changes based on which of these scenario is very odd. Regards, Madhu -- To unsubscribe from this list: send the line "unsubscribe linux-mmc" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
* Venkatraman S [100311 07:04]: > Tony Lindgren wrote: > > > > Does the driver still work in PIO mode? > > > > We need to have the drivers capable to fail over to PIO mode > > as the DMA channels can run out. > > > >The driver doesn't have an automatic fallback to PIO, > even without my patch. A error return from omap_request_dma is > propogated all the way back to the transfer request. > The decision to use_dma (the variable) is unaltered. OK, that might explain some nasty surprises then.. With these patches, does the driver still work in PIO mode though? >Infact, it would be easier to implement a runtime fallback after > this patch is > merged as I have separated out the capability and runtime selection. > (dma_caps and dma_in_use). Sounds good to me, thanks for looking into it. Regards, Tony -- To unsubscribe from this list: send the line "unsubscribe linux-mmc" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
Madhusudhan wrote: >> -Original Message- >> From: svenk...@gmail.com [mailto:svenk...@gmail.com] On Behalf Of >> Venkatraman S >> Sent: Thursday, March 11, 2010 4:52 AM >> To: Madhusudhan >> Cc: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; >> linux-omap@vger.kernel.org >> Subject: Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor >> autoloading feature >> >> Madhusudhan wrote: >> >> -Original Message- >> >> From: linux-mmc-ow...@vger.kernel.org [mailto:linux-mmc- >> >> ow...@vger.kernel.org] On Behalf Of Venkatraman S >> >> Sent: Monday, March 01, 2010 5:27 AM >> >> To: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; >> >> linux-omap@vger.kernel.org >> >> Subject: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor >> >> autoloading feature >> >> >> >> Start to use the sDMA descriptor autoloading feature. >> >> For large datablocks, the MMC driver has to repeatedly setup, program >> >> and teardown the >> >> dma channel for each element of the sglist received in >> omap_hsmmc_request. >> >> >> >> By using descriptor autoloading, transfers from / to each element of >> >> the sglist is pre programmed >> >> into a linked list. The sDMA driver completes the entire transaction >> >> and provides a single interrupt. >> >> >> >> Due to this, number of dma interrupts for a typical 100MB transfer on >> the >> >> MMC is >> >> reduced from 25000 to about 400 (approximate). Transfer speeds are >> >> improved by ~5% >> >> (Though it varies on the size of read / write & improves on huge >> >> transfers) >> >> >> >> Descriptor autoloading is available only in 3630 and 4430 (as of now). >> >> Hence normal DMA >> >> mode is also retained. >> >> >> >> Tested on omap4430 sdp. >> >> >> >> Signed-off-by: Venkatraman S >> > >> > I don't see any issues with this patch except the concern I had on the >> first >> > patch in the series. Why is that change linked to this series? >> > >> Thanks. The problem was seen only in the context of using descriptor >> load. Would >> you prefer that I post it as a separate patch ? > > My point is why that change is needed for this feature to work? > > When DMA is completed and a callback is received the ch can be freed. Once > TC is received the core is notified of the same. > > Can the first patch be dropped? Or do you see issues? Yes there are issues without this patch when the scatterlist is large (300+ blocks), where the dma completion interrupt is received but the mmc driver hangs waiting for TC. I don't see the issue if I delay the execution of omap_free_dma inside the dma callback. -- To unsubscribe from this list: send the line "unsubscribe linux-omap" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
> -Original Message- > From: svenk...@gmail.com [mailto:svenk...@gmail.com] On Behalf Of > Venkatraman S > Sent: Thursday, March 11, 2010 4:52 AM > To: Madhusudhan > Cc: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; > linux-omap@vger.kernel.org > Subject: Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor > autoloading feature > > Madhusudhan wrote: > >> -Original Message- > >> From: linux-mmc-ow...@vger.kernel.org [mailto:linux-mmc- > >> ow...@vger.kernel.org] On Behalf Of Venkatraman S > >> Sent: Monday, March 01, 2010 5:27 AM > >> To: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; > >> linux-omap@vger.kernel.org > >> Subject: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor > >> autoloading feature > >> > >> Start to use the sDMA descriptor autoloading feature. > >> For large datablocks, the MMC driver has to repeatedly setup, program > >> and teardown the > >> dma channel for each element of the sglist received in > omap_hsmmc_request. > >> > >> By using descriptor autoloading, transfers from / to each element of > >> the sglist is pre programmed > >> into a linked list. The sDMA driver completes the entire transaction > >> and provides a single interrupt. > >> > >> Due to this, number of dma interrupts for a typical 100MB transfer on > the > >> MMC is > >> reduced from 25000 to about 400 (approximate). Transfer speeds are > >> improved by ~5% > >> (Though it varies on the size of read / write & improves on huge > >> transfers) > >> > >> Descriptor autoloading is available only in 3630 and 4430 (as of now). > >> Hence normal DMA > >> mode is also retained. > >> > >> Tested on omap4430 sdp. > >> > >> Signed-off-by: Venkatraman S > > > > I don't see any issues with this patch except the concern I had on the > first > > patch in the series. Why is that change linked to this series? > > > Thanks. The problem was seen only in the context of using descriptor > load. Would > you prefer that I post it as a separate patch ? My point is why that change is needed for this feature to work? When DMA is completed and a callback is received the ch can be freed. Once TC is received the core is notified of the same. Can the first patch be dropped? Or do you see issues? > Regards, > Venkat. -- To unsubscribe from this list: send the line "unsubscribe linux-omap" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
Tony Lindgren wrote: > * Venkatraman S [100310 06:08]: >> @@ -1400,14 +1471,23 @@ omap_hsmmc_prepare_data(struct omap_hsmmc_host >> *host, struct mmc_request *req) >> | (req->data->blocks << 16)); >> set_data_timeout(host, req->data->timeout_ns, req->data->timeout_clks); >> >> - if (host->use_dma) { >> - ret = omap_hsmmc_start_dma_transfer(host, req); >> - if (ret != 0) { >> - dev_dbg(mmc_dev(host->mmc), "MMC start dma failure\n"); >> + if (host->dma_caps & DMA_TYPE_SDMA) { >> + ret = omap_hsmmc_configure_sdma(host, req); >> + if (ret) >> return ret; >> - } >> + host->dma_in_use = DMA_TYPE_SDMA; >> } >> - return 0; >> + if ((host->dma_caps & DMA_TYPE_SDMA_DLOAD) && >> + host->data->sg_len > 4) { >> + ret = omap_hsmmc_configure_sdma_sglist(host, req); >> + if (ret) >> + return ret; >> + host->dma_in_use = DMA_TYPE_SDMA_DLOAD; >> + >> + } >> + ret = omap_hsmmc_start_dma_transfer(host); >> + return ret; >> + >> } > > Does the driver still work in PIO mode? > > We need to have the drivers capable to fail over to PIO mode > as the DMA channels can run out. > The driver doesn't have an automatic fallback to PIO, even without my patch. A error return from omap_request_dma is propogated all the way back to the transfer request. The decision to use_dma (the variable) is unaltered. Infact, it would be easier to implement a runtime fallback after this patch is merged as I have separated out the capability and runtime selection. (dma_caps and dma_in_use). Regards, Venkat. -- To unsubscribe from this list: send the line "unsubscribe linux-omap" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
Madhusudhan wrote: >> -Original Message- >> From: linux-mmc-ow...@vger.kernel.org [mailto:linux-mmc- >> ow...@vger.kernel.org] On Behalf Of Venkatraman S >> Sent: Monday, March 01, 2010 5:27 AM >> To: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; >> linux-omap@vger.kernel.org >> Subject: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor >> autoloading feature >> >> Start to use the sDMA descriptor autoloading feature. >> For large datablocks, the MMC driver has to repeatedly setup, program >> and teardown the >> dma channel for each element of the sglist received in omap_hsmmc_request. >> >> By using descriptor autoloading, transfers from / to each element of >> the sglist is pre programmed >> into a linked list. The sDMA driver completes the entire transaction >> and provides a single interrupt. >> >> Due to this, number of dma interrupts for a typical 100MB transfer on the >> MMC is >> reduced from 25000 to about 400 (approximate). Transfer speeds are >> improved by ~5% >> (Though it varies on the size of read / write & improves on huge >> transfers) >> >> Descriptor autoloading is available only in 3630 and 4430 (as of now). >> Hence normal DMA >> mode is also retained. >> >> Tested on omap4430 sdp. >> >> Signed-off-by: Venkatraman S > > I don't see any issues with this patch except the concern I had on the first > patch in the series. Why is that change linked to this series? > Thanks. The problem was seen only in the context of using descriptor load. Would you prefer that I post it as a separate patch ? Regards, Venkat. -- To unsubscribe from this list: send the line "unsubscribe linux-mmc" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
RE: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
> -Original Message- > From: linux-mmc-ow...@vger.kernel.org [mailto:linux-mmc- > ow...@vger.kernel.org] On Behalf Of Venkatraman S > Sent: Monday, March 01, 2010 5:27 AM > To: linux-...@vger.kernel.org; linux-arm-ker...@lists.infradead.org; > linux-omap@vger.kernel.org > Subject: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor > autoloading feature > > Start to use the sDMA descriptor autoloading feature. > For large datablocks, the MMC driver has to repeatedly setup, program > and teardown the > dma channel for each element of the sglist received in omap_hsmmc_request. > > By using descriptor autoloading, transfers from / to each element of > the sglist is pre programmed > into a linked list. The sDMA driver completes the entire transaction > and provides a single interrupt. > > Due to this, number of dma interrupts for a typical 100MB transfer on the > MMC is > reduced from 25000 to about 400 (approximate). Transfer speeds are > improved by ~5% > (Though it varies on the size of read / write & improves on huge > transfers) > > Descriptor autoloading is available only in 3630 and 4430 (as of now). > Hence normal DMA > mode is also retained. > > Tested on omap4430 sdp. > > Signed-off-by: Venkatraman S I don't see any issues with this patch except the concern I had on the first patch in the series. Why is that change linked to this series? > --- > drivers/mmc/host/omap_hsmmc.c | 143 +++- > - > 1 files changed, 122 insertions(+), 21 deletions(-) > > diff --git a/drivers/mmc/host/omap_hsmmc.c b/drivers/mmc/host/omap_hsmmc.c > index 06337f6..425129b 100644 > --- a/drivers/mmc/host/omap_hsmmc.c > +++ b/drivers/mmc/host/omap_hsmmc.c > @@ -102,6 +102,7 @@ > #define SRD (1 << 26) > #define SOFTRESET(1 << 1) > #define RESETDONE(1 << 0) > +#define DMA_ICR_QUIET0xD00 > > /* > * FIXME: Most likely all the data using these _DEVID defines should come > @@ -118,6 +119,12 @@ > #define OMAP_MMC_MASTER_CLOCK9600 > #define DRIVER_NAME "mmci-omap-hs" > > +#define DMA_TYPE_NODMA 0 > +#define DMA_TYPE_SDMA1 > +#define DMA_TYPE_SDMA_DLOAD 2 > + > +#define DMA_CTRL_BUF_SIZE(PAGE_SIZE * 3) > + > /* Timeouts for entering power saving states on inactivity, msec */ > #define OMAP_MMC_DISABLED_TIMEOUT100 > #define OMAP_MMC_SLEEP_TIMEOUT 1000 > @@ -172,7 +179,11 @@ struct omap_hsmmc_host { > u32 bytesleft; > int suspended; > int irq; > - int use_dma, dma_ch; > + int dma_caps; > + int dma_in_use; > + int dma_ch; > + void*dma_ctrl_buf; > + dma_addr_t dma_ctrl_buf_phy; > int dma_line_tx, dma_line_rx; > int slot_id; > int got_dbclk; > @@ -768,7 +779,7 @@ omap_hsmmc_start_command(struct omap_hsmmc_host > *host, struct mmc_command *cmd, > OMAP_HSMMC_WRITE(host->base, STAT, STAT_CLEAR); > OMAP_HSMMC_WRITE(host->base, ISE, INT_EN_MASK); > > - if (host->use_dma) > + if (host->dma_in_use) > OMAP_HSMMC_WRITE(host->base, IE, >INT_EN_MASK & ~(BRR_ENABLE | BWR_ENABLE)); > else > @@ -803,7 +814,7 @@ omap_hsmmc_start_command(struct omap_hsmmc_host > *host, struct mmc_command *cmd, > cmdreg &= ~(DDIR); > } > > - if (host->use_dma) > + if (host->dma_in_use) > cmdreg |= DMA_EN; > > /* > @@ -850,7 +861,7 @@ omap_hsmmc_xfer_done(struct omap_hsmmc_host *host, > struct mmc_data *data) > > host->data = NULL; > > - if (host->use_dma && host->dma_ch != -1) > + if (host->dma_in_use && host->dma_ch != -1) > dma_unmap_sg(mmc_dev(host->mmc), data->sg, host->dma_len, > omap_hsmmc_get_dma_dir(host, data)); > > @@ -900,7 +911,7 @@ static void omap_hsmmc_dma_cleanup(struct > omap_hsmmc_host *host, int errno) > { > host->data->error = errno; > > - if (host->use_dma && host->dma_ch != -1) { > + if (host->dma_in_use && host->dma_ch != -1) { > dma_unmap_sg(mmc_dev(host->mmc), host->data->sg, host- > >dma_len, > omap_hsmmc_get_dma_dir(host, host->data)); > omap_free_
Re: [PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
* Venkatraman S [100310 06:08]: > @@ -1400,14 +1471,23 @@ omap_hsmmc_prepare_data(struct omap_hsmmc_host > *host, struct mmc_request *req) > | (req->data->blocks << 16)); > set_data_timeout(host, req->data->timeout_ns, req->data->timeout_clks); > > - if (host->use_dma) { > - ret = omap_hsmmc_start_dma_transfer(host, req); > - if (ret != 0) { > - dev_dbg(mmc_dev(host->mmc), "MMC start dma failure\n"); > + if (host->dma_caps & DMA_TYPE_SDMA) { > + ret = omap_hsmmc_configure_sdma(host, req); > + if (ret) > return ret; > - } > + host->dma_in_use = DMA_TYPE_SDMA; > } > - return 0; > + if ((host->dma_caps & DMA_TYPE_SDMA_DLOAD) && > + host->data->sg_len > 4) { > + ret = omap_hsmmc_configure_sdma_sglist(host, req); > + if (ret) > + return ret; > + host->dma_in_use = DMA_TYPE_SDMA_DLOAD; > + > + } > + ret = omap_hsmmc_start_dma_transfer(host); > + return ret; > + > } Does the driver still work in PIO mode? We need to have the drivers capable to fail over to PIO mode as the DMA channels can run out. Regards, Tony -- To unsubscribe from this list: send the line "unsubscribe linux-omap" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
[PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
See previous post http://patchwork.kernel.org/patch/82909/. Rebased to 2.6.34-rc1 CC: Adrian Hunter CC: Madhusudhan C CC: Tony Lindgren Signed-off-by: Venkatraman S --- drivers/mmc/host/omap_hsmmc.c | 143 +++-- 1 files changed, 122 insertions(+), 21 deletions(-) diff --git a/drivers/mmc/host/omap_hsmmc.c b/drivers/mmc/host/omap_hsmmc.c index ea2a082..131d889 100644 --- a/drivers/mmc/host/omap_hsmmc.c +++ b/drivers/mmc/host/omap_hsmmc.c @@ -102,6 +102,7 @@ #define SRD(1 << 26) #define SOFTRESET (1 << 1) #define RESETDONE (1 << 0) +#define DMA_ICR_QUIET 0xD00 /* * FIXME: Most likely all the data using these _DEVID defines should come @@ -118,6 +119,12 @@ #define OMAP_MMC_MASTER_CLOCK 9600 #define DRIVER_NAME"mmci-omap-hs" +#define DMA_TYPE_NODMA 0 +#define DMA_TYPE_SDMA 1 +#define DMA_TYPE_SDMA_DLOAD 2 + +#define DMA_CTRL_BUF_SIZE (PAGE_SIZE * 3) + /* Timeouts for entering power saving states on inactivity, msec */ #define OMAP_MMC_DISABLED_TIMEOUT 100 #define OMAP_MMC_SLEEP_TIMEOUT 1000 @@ -172,7 +179,11 @@ struct omap_hsmmc_host { u32 bytesleft; int suspended; int irq; - int use_dma, dma_ch; + int dma_caps; + int dma_in_use; + int dma_ch; + void*dma_ctrl_buf; + dma_addr_t dma_ctrl_buf_phy; int dma_line_tx, dma_line_rx; int slot_id; int got_dbclk; @@ -768,7 +779,7 @@ omap_hsmmc_start_command(struct omap_hsmmc_host *host, struct mmc_command *cmd, OMAP_HSMMC_WRITE(host->base, STAT, STAT_CLEAR); OMAP_HSMMC_WRITE(host->base, ISE, INT_EN_MASK); - if (host->use_dma) + if (host->dma_in_use) OMAP_HSMMC_WRITE(host->base, IE, INT_EN_MASK & ~(BRR_ENABLE | BWR_ENABLE)); else @@ -803,7 +814,7 @@ omap_hsmmc_start_command(struct omap_hsmmc_host *host, struct mmc_command *cmd, cmdreg &= ~(DDIR); } - if (host->use_dma) + if (host->dma_in_use) cmdreg |= DMA_EN; /* @@ -850,7 +861,7 @@ omap_hsmmc_xfer_done(struct omap_hsmmc_host *host, struct mmc_data *data) host->data = NULL; - if (host->use_dma && host->dma_ch != -1) + if (host->dma_in_use && host->dma_ch != -1) dma_unmap_sg(mmc_dev(host->mmc), data->sg, host->dma_len, omap_hsmmc_get_dma_dir(host, data)); @@ -900,7 +911,7 @@ static void omap_hsmmc_dma_cleanup(struct omap_hsmmc_host *host, int errno) { host->data->error = errno; - if (host->use_dma && host->dma_ch != -1) { + if (host->dma_in_use && host->dma_ch != -1) { dma_unmap_sg(mmc_dev(host->mmc), host->data->sg, host->dma_len, omap_hsmmc_get_dma_dir(host, host->data)); omap_free_dma(host->dma_ch); @@ -1253,7 +1264,6 @@ static void omap_hsmmc_config_dma_params(struct omap_hsmmc_host *host, omap_hsmmc_get_dma_sync_dev(host, data), !(data->flags & MMC_DATA_WRITE)); - omap_start_dma(dma_ch); } /* @@ -1268,21 +1278,32 @@ static void omap_hsmmc_dma_cb(int lch, u16 ch_status, void *data) if (host->dma_ch < 0) return; - - host->dma_sg_idx++; - if (host->dma_sg_idx < host->dma_len) { - /* Fire up the next transfer. */ - omap_hsmmc_config_dma_params(host, host->data, + if (host->dma_in_use == DMA_TYPE_SDMA) { + host->dma_sg_idx++; + if (host->dma_sg_idx < host->dma_len) { + /* Fire up the next transfer. */ + omap_hsmmc_config_dma_params(host, host->data, host->data->sg + host->dma_sg_idx); - return; + omap_start_dma(host->dma_ch); + return; + } } } +static int omap_hsmmc_start_dma_transfer(struct omap_hsmmc_host *host) +{ + if (host->dma_in_use == DMA_TYPE_SDMA) + omap_start_dma(host->dma_ch); + else if (host->dma_in_use == DMA_TYPE_SDMA_DLOAD) + return omap_start_dma_sglist_transfers(host->dma_ch, -1); + + return 0; +} /* - * Routine to configure and start DMA for the MMC card + * Routine to configure DMA for the MMC card */ -static int omap_hsmmc_start_dma_transfer(struct omap_hsmmc_host *host, +static int omap_hsmmc_configure_sdma(struct omap_hsmmc_host *host, struct mmc_request *req) { int dma_ch = 0, ret = 0, err = 1, i; @@ -1339,6 +1360,56 @@ static int omap_
[PATCH 03/03] omap hsmmc: adaptation of sdma descriptor autoloading feature
Start to use the sDMA descriptor autoloading feature. For large datablocks, the MMC driver has to repeatedly setup, program and teardown the dma channel for each element of the sglist received in omap_hsmmc_request. By using descriptor autoloading, transfers from / to each element of the sglist is pre programmed into a linked list. The sDMA driver completes the entire transaction and provides a single interrupt. Due to this, number of dma interrupts for a typical 100MB transfer on the MMC is reduced from 25000 to about 400 (approximate). Transfer speeds are improved by ~5% (Though it varies on the size of read / write & improves on huge transfers) Descriptor autoloading is available only in 3630 and 4430 (as of now). Hence normal DMA mode is also retained. Tested on omap4430 sdp. Signed-off-by: Venkatraman S --- drivers/mmc/host/omap_hsmmc.c | 143 +++-- 1 files changed, 122 insertions(+), 21 deletions(-) diff --git a/drivers/mmc/host/omap_hsmmc.c b/drivers/mmc/host/omap_hsmmc.c index 06337f6..425129b 100644 --- a/drivers/mmc/host/omap_hsmmc.c +++ b/drivers/mmc/host/omap_hsmmc.c @@ -102,6 +102,7 @@ #define SRD(1 << 26) #define SOFTRESET (1 << 1) #define RESETDONE (1 << 0) +#define DMA_ICR_QUIET 0xD00 /* * FIXME: Most likely all the data using these _DEVID defines should come @@ -118,6 +119,12 @@ #define OMAP_MMC_MASTER_CLOCK 9600 #define DRIVER_NAME"mmci-omap-hs" +#define DMA_TYPE_NODMA 0 +#define DMA_TYPE_SDMA 1 +#define DMA_TYPE_SDMA_DLOAD 2 + +#define DMA_CTRL_BUF_SIZE (PAGE_SIZE * 3) + /* Timeouts for entering power saving states on inactivity, msec */ #define OMAP_MMC_DISABLED_TIMEOUT 100 #define OMAP_MMC_SLEEP_TIMEOUT 1000 @@ -172,7 +179,11 @@ struct omap_hsmmc_host { u32 bytesleft; int suspended; int irq; - int use_dma, dma_ch; + int dma_caps; + int dma_in_use; + int dma_ch; + void*dma_ctrl_buf; + dma_addr_t dma_ctrl_buf_phy; int dma_line_tx, dma_line_rx; int slot_id; int got_dbclk; @@ -768,7 +779,7 @@ omap_hsmmc_start_command(struct omap_hsmmc_host *host, struct mmc_command *cmd, OMAP_HSMMC_WRITE(host->base, STAT, STAT_CLEAR); OMAP_HSMMC_WRITE(host->base, ISE, INT_EN_MASK); - if (host->use_dma) + if (host->dma_in_use) OMAP_HSMMC_WRITE(host->base, IE, INT_EN_MASK & ~(BRR_ENABLE | BWR_ENABLE)); else @@ -803,7 +814,7 @@ omap_hsmmc_start_command(struct omap_hsmmc_host *host, struct mmc_command *cmd, cmdreg &= ~(DDIR); } - if (host->use_dma) + if (host->dma_in_use) cmdreg |= DMA_EN; /* @@ -850,7 +861,7 @@ omap_hsmmc_xfer_done(struct omap_hsmmc_host *host, struct mmc_data *data) host->data = NULL; - if (host->use_dma && host->dma_ch != -1) + if (host->dma_in_use && host->dma_ch != -1) dma_unmap_sg(mmc_dev(host->mmc), data->sg, host->dma_len, omap_hsmmc_get_dma_dir(host, data)); @@ -900,7 +911,7 @@ static void omap_hsmmc_dma_cleanup(struct omap_hsmmc_host *host, int errno) { host->data->error = errno; - if (host->use_dma && host->dma_ch != -1) { + if (host->dma_in_use && host->dma_ch != -1) { dma_unmap_sg(mmc_dev(host->mmc), host->data->sg, host->dma_len, omap_hsmmc_get_dma_dir(host, host->data)); omap_free_dma(host->dma_ch); @@ -1253,7 +1264,6 @@ static void omap_hsmmc_config_dma_params(struct omap_hsmmc_host *host, omap_hsmmc_get_dma_sync_dev(host, data), !(data->flags & MMC_DATA_WRITE)); - omap_start_dma(dma_ch); } /* @@ -1268,21 +1278,32 @@ static void omap_hsmmc_dma_cb(int lch, u16 ch_status, void *data) if (host->dma_ch < 0) return; - - host->dma_sg_idx++; - if (host->dma_sg_idx < host->dma_len) { - /* Fire up the next transfer. */ - omap_hsmmc_config_dma_params(host, host->data, + if (host->dma_in_use == DMA_TYPE_SDMA) { + host->dma_sg_idx++; + if (host->dma_sg_idx < host->dma_len) { + /* Fire up the next transfer. */ + omap_hsmmc_config_dma_params(host, host->data, host->data->sg + host->dma_sg_idx); - return; + omap_start_dma(host->dma_ch); + return; + } } } +static int omap_hsmmc_start_dma_transfer(struct omap_hsmmc_host *host) +{ + if