aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/mmc/core/sdio_io.c
diff options
context:
space:
mode:
authorStefan Nilsson XK <stefan.xk.nilsson@stericsson.com>2011-10-26 04:52:17 -0400
committerChris Ball <cjb@laptop.org>2012-01-11 23:58:40 -0500
commit052d81da6e6f0f8839ef6d5a46f215fc8cd99d5a (patch)
tree39e77d55630168ae27eb5d63c58ae505875a31e3 /drivers/mmc/core/sdio_io.c
parentfffe5d5aa05b4e69f79bc75a51c5ee0fc6203fa5 (diff)
mmc: sdio: Fix to support any block size optimally
This patch allows any block size to be set on the SDIO link, and still have an arbitrary sized packet (adjusted in size by using sdio_align_size) transferred in an optimal way (preferably one transfer). Previously if the block size was larger than the default of 512 bytes and the transfer size was exactly one block size (possibly thanks to using sdio_align_size to get an optimal transfer size), it was sent as a number of byte transfers instead of one block transfer. Also if the number of blocks was (max_blocks * N) + 1, the tranfer would be conducted with a number of blocks and finished off with a number of byte transfers. When doing this change it was also possible to break out the quirk for broken byte mode in a much cleaner way, and collect the logic of when to do byte or block transfer in one function instead of two. Signed-off-by: Stefan Nilsson XK <stefan.xk.nilsson@stericsson.com> Signed-off-by: Ulf Hansson <ulf.hansson@stericsson.com> Acked-by: Linus Walleij <linus.walleij@linaro.org> Signed-off-by: Chris Ball <cjb@laptop.org>
Diffstat (limited to 'drivers/mmc/core/sdio_io.c')
-rw-r--r--drivers/mmc/core/sdio_io.c8
1 files changed, 6 insertions, 2 deletions
diff --git a/drivers/mmc/core/sdio_io.c b/drivers/mmc/core/sdio_io.c
index b1f3168f791b..8f6f5ac131fc 100644
--- a/drivers/mmc/core/sdio_io.c
+++ b/drivers/mmc/core/sdio_io.c
@@ -196,6 +196,9 @@ static inline unsigned int sdio_max_byte_size(struct sdio_func *func)
196 else 196 else
197 mval = min(mval, func->max_blksize); 197 mval = min(mval, func->max_blksize);
198 198
199 if (mmc_card_broken_byte_mode_512(func->card))
200 return min(mval, 511u);
201
199 return min(mval, 512u); /* maximum size for byte mode */ 202 return min(mval, 512u); /* maximum size for byte mode */
200} 203}
201 204
@@ -314,7 +317,7 @@ static int sdio_io_rw_ext_helper(struct sdio_func *func, int write,
314 func->card->host->max_seg_size / func->cur_blksize); 317 func->card->host->max_seg_size / func->cur_blksize);
315 max_blocks = min(max_blocks, 511u); 318 max_blocks = min(max_blocks, 511u);
316 319
317 while (remainder > func->cur_blksize) { 320 while (remainder >= func->cur_blksize) {
318 unsigned blocks; 321 unsigned blocks;
319 322
320 blocks = remainder / func->cur_blksize; 323 blocks = remainder / func->cur_blksize;
@@ -339,8 +342,9 @@ static int sdio_io_rw_ext_helper(struct sdio_func *func, int write,
339 while (remainder > 0) { 342 while (remainder > 0) {
340 size = min(remainder, sdio_max_byte_size(func)); 343 size = min(remainder, sdio_max_byte_size(func));
341 344
345 /* Indicate byte mode by setting "blocks" = 0 */
342 ret = mmc_io_rw_extended(func->card, write, func->num, addr, 346 ret = mmc_io_rw_extended(func->card, write, func->num, addr,
343 incr_addr, buf, 1, size); 347 incr_addr, buf, 0, size);
344 if (ret) 348 if (ret)
345 return ret; 349 return ret;
346 350