From: Jaehoon Chung <jh80.chung@samsung.com>
To: Avi Shchislowski <avi.shchislowski@sandisk.com>, ulf.hansson@linaro.org
Cc: 'Chris Ball' <chris@printf.net>,
linux-mmc@vger.kernel.org, Alex.Lemberg@sandisk.com,
gwendal@google.com, open list <linux-kernel@vger.kernel.org>,
CPGS <cpgs@samsung.com>
Subject: Re: [PATCH 2/3] mmc: Support FFU for eMMC v5.0
Date: Tue, 11 Nov 2014 12:30:33 +0900 [thread overview]
Message-ID: <546182D9.7040107@samsung.com> (raw)
In-Reply-To: <1415639943-12068-1-git-send-email-avi.shchislowski@sandisk.com>
Hi,
On 11/11/2014 02:18 AM, Avi Shchislowski wrote:
> eMMC5.0 FFU is using some of pre-existing mmc_test.c functionality.
> In order to prevent code duplication, some code of mmc_test.c was moved to core.c and modified.
>
> Signed-off-by: Avi Shchislowski <avi.shchislowski@sandisk.com>
> Signed-off-by: Alex Lemberg <alex.lemberg@sandisk.com>
>
> diff --git a/drivers/mmc/card/mmc_test.c b/drivers/mmc/card/mmc_test.c
> index 0c0fc52..e6ee0a8 100644
> --- a/drivers/mmc/card/mmc_test.c
> +++ b/drivers/mmc/card/mmc_test.c
> @@ -13,6 +13,7 @@
> #include <linux/mmc/card.h>
> #include <linux/mmc/host.h>
> #include <linux/mmc/mmc.h>
> +#include <linux/mmc/core.h>
> #include <linux/slab.h>
>
> #include <linux/scatterlist.h>
> @@ -189,43 +190,8 @@ static void mmc_test_prepare_mrq(struct mmc_test_card *test,
> struct mmc_request *mrq, struct scatterlist *sg, unsigned sg_len,
> unsigned dev_addr, unsigned blocks, unsigned blksz, int write)
> {
> - BUG_ON(!mrq || !mrq->cmd || !mrq->data || !mrq->stop);
> -
> - if (blocks > 1) {
> - mrq->cmd->opcode = write ?
> - MMC_WRITE_MULTIPLE_BLOCK : MMC_READ_MULTIPLE_BLOCK;
> - } else {
> - mrq->cmd->opcode = write ?
> - MMC_WRITE_BLOCK : MMC_READ_SINGLE_BLOCK;
> - }
> -
> - mrq->cmd->arg = dev_addr;
> - if (!mmc_card_blockaddr(test->card))
> - mrq->cmd->arg <<= 9;
> -
> - mrq->cmd->flags = MMC_RSP_R1 | MMC_CMD_ADTC;
> -
> - if (blocks == 1)
> - mrq->stop = NULL;
> - else {
> - mrq->stop->opcode = MMC_STOP_TRANSMISSION;
> - mrq->stop->arg = 0;
> - mrq->stop->flags = MMC_RSP_R1B | MMC_CMD_AC;
> - }
> -
> - mrq->data->blksz = blksz;
> - mrq->data->blocks = blocks;
> - mrq->data->flags = write ? MMC_DATA_WRITE : MMC_DATA_READ;
> - mrq->data->sg = sg;
> - mrq->data->sg_len = sg_len;
> -
> - mmc_set_data_timeout(mrq->data, test->card);
> -}
> -
> -static int mmc_test_busy(struct mmc_command *cmd)
> -{
> - return !(cmd->resp[0] & R1_READY_FOR_DATA) ||
> - (R1_CURRENT_STATE(cmd->resp[0]) == R1_STATE_PRG);
> + mmc_prepare_mrq(test->card, mrq, sg, sg_len,
> + dev_addr, blocks, blksz, write);
> }
>
> /*
> @@ -233,30 +199,9 @@ static int mmc_test_busy(struct mmc_command *cmd)
> */
> static int mmc_test_wait_busy(struct mmc_test_card *test)
> {
> - int ret, busy;
> - struct mmc_command cmd = {0};
> -
> - busy = 0;
> - do {
> - memset(&cmd, 0, sizeof(struct mmc_command));
> -
> - cmd.opcode = MMC_SEND_STATUS;
> - cmd.arg = test->card->rca << 16;
> - cmd.flags = MMC_RSP_R1 | MMC_CMD_AC;
> -
> - ret = mmc_wait_for_cmd(test->card->host, &cmd, 0);
> - if (ret)
> - break;
> -
> - if (!busy && mmc_test_busy(&cmd)) {
> - busy = 1;
> - if (test->card->host->caps & MMC_CAP_WAIT_WHILE_BUSY)
> - pr_info("%s: Warning: Host did not "
> - "wait for busy state to end.\n",
> - mmc_hostname(test->card->host));
> - }
> - } while (mmc_test_busy(&cmd));
> + int ret;
>
> + ret = mmc_wait_busy(test->card);
return mmc_wait_busy(test->card);
And mmc_test_wait_busy is wrapper function?
Why do you use the wrapper function?
> return ret;
> }
>
> @@ -693,19 +638,9 @@ static int mmc_test_check_result(struct mmc_test_card *test,
> {
> int ret;
>
> - BUG_ON(!mrq || !mrq->cmd || !mrq->data);
> -
> ret = 0;
>
> - if (!ret && mrq->cmd->error)
> - ret = mrq->cmd->error;
> - if (!ret && mrq->data->error)
> - ret = mrq->data->error;
> - if (!ret && mrq->stop && mrq->stop->error)
> - ret = mrq->stop->error;
> - if (!ret && mrq->data->bytes_xfered !=
> - mrq->data->blocks * mrq->data->blksz)
> - ret = RESULT_FAIL;
> + ret = mmc_check_result(mrq);
>
> if (ret == -EINVAL)
> ret = RESULT_UNSUP_HOST;
> @@ -844,23 +779,13 @@ static int mmc_test_simple_transfer(struct mmc_test_card *test,
> struct scatterlist *sg, unsigned sg_len, unsigned dev_addr,
> unsigned blocks, unsigned blksz, int write)
> {
> - struct mmc_request mrq = {0};
> - struct mmc_command cmd = {0};
> - struct mmc_command stop = {0};
> - struct mmc_data data = {0};
> -
> - mrq.cmd = &cmd;
> - mrq.data = &data;
> - mrq.stop = &stop;
> + int ret;
>
> - mmc_test_prepare_mrq(test, &mrq, sg, sg_len, dev_addr,
> + ret = mmc_simple_transfer(test->card, sg, sg_len, dev_addr,
> blocks, blksz, write);
> -
> - mmc_wait_for_req(test->card->host, &mrq);
> -
> - mmc_test_wait_busy(test);
> -
> - return mmc_test_check_result(test, &mrq);
> + if (ret == -EINVAL)
> + ret = RESULT_UNSUP_HOST;
> + return ret;
> }
>
> /*
> diff --git a/drivers/mmc/core/core.c b/drivers/mmc/core/core.c
> index d03a080..132da0c 100644
> --- a/drivers/mmc/core/core.c
> +++ b/drivers/mmc/core/core.c
> @@ -2658,6 +2658,134 @@ int mmc_pm_notify(struct notifier_block *notify_block,
> return 0;
> }
> #endif
> +/*
> + * Fill in the mmc_request structure given a set of transfer parameters.
> + */
> +void mmc_prepare_mrq(struct mmc_card *card,
> + struct mmc_request *mrq, struct scatterlist *sg, unsigned sg_len,
> + unsigned dev_addr, unsigned blocks, unsigned blksz, int write)
> +{
> + BUG_ON(!mrq || !mrq->cmd || !mrq->data || !mrq->stop);
> +
> + if (blocks > 1) {
> + mrq->cmd->opcode = write ?
> + MMC_WRITE_MULTIPLE_BLOCK : MMC_READ_MULTIPLE_BLOCK;
> + } else {
> + mrq->cmd->opcode = write ?
> + MMC_WRITE_BLOCK : MMC_READ_SINGLE_BLOCK;
> + }
> +
> + mrq->cmd->arg = dev_addr;
> + if (!mmc_card_blockaddr(card))
> + mrq->cmd->arg <<= 9;
> +
> + mrq->cmd->flags = MMC_RSP_R1 | MMC_CMD_ADTC;
> +
> + if (blocks == 1)
> + mrq->stop = NULL;
> + else {
> + mrq->stop->opcode = MMC_STOP_TRANSMISSION;
> + mrq->stop->arg = 0;
> + mrq->stop->flags = MMC_RSP_R1B | MMC_CMD_AC;
> + }
> +
> + mrq->data->blksz = blksz;
> + mrq->data->blocks = blocks;
> + mrq->data->flags = write ? MMC_DATA_WRITE : MMC_DATA_READ;
> + mrq->data->sg = sg;
> + mrq->data->sg_len = sg_len;
> +
> + mmc_set_data_timeout(mrq->data, card);
> +}
> +EXPORT_SYMBOL(mmc_prepare_mrq);
> +
> +static int mmc_busy(struct mmc_command *cmd)
> +{
> + return !(cmd->resp[0] & R1_READY_FOR_DATA) ||
> + (R1_CURRENT_STATE(cmd->resp[0]) == R1_STATE_PRG);
> +}
What's function?
> +
> +/*
> + * Wait for the card to finish the busy state
> + */
> +int mmc_wait_busy(struct mmc_card *card)
> +{
> + int ret, busy = 0;
> + struct mmc_command cmd = {0};
> +
> + memset(&cmd, 0, sizeof(struct mmc_command));
> + cmd.opcode = MMC_SEND_STATUS;
> + cmd.arg = card->rca << 16;
> + cmd.flags = MMC_RSP_SPI_R2 | MMC_RSP_R1 | MMC_CMD_AC;
> +
> + do {
> + ret = mmc_wait_for_cmd(card->host, &cmd, 0);
> + if (ret)
> + break;
> +
> + if (!busy && mmc_busy(&cmd)) {
> + busy = 1;
> + if (card->host->caps & MMC_CAP_WAIT_WHILE_BUSY) {
> + pr_warn("%s: Warning: Host did not "
> + "wait for busy state to end.\n",
> + mmc_hostname(card->host));
> + }
> + }
> +
> + } while (mmc_busy(&cmd));
> +
> + return ret;
> +}
> +EXPORT_SYMBOL(mmc_wait_busy);
> +
> +int mmc_check_result(struct mmc_request *mrq)
> +{
> + int ret;
> +
> + BUG_ON(!mrq || !mrq->cmd || !mrq->data);
> +
> + ret = 0;
Why do you initialized at here?
if ret is 0, why do you check "if (!ret && xxxx)" at the below condition?
> +
> + if (!ret && mrq->cmd->error)
> + ret = mrq->cmd->error;
> + if (!ret && mrq->data->error)
> + ret = mrq->data->error;
> + if (!ret && mrq->stop && mrq->stop->error)
> + ret = mrq->stop->error;
> + if (!ret && mrq->data->bytes_xfered !=
> + mrq->data->blocks * mrq->data->blksz)
> + ret = -EPERM;
> +
> + return ret;
> +}
> +EXPORT_SYMBOL(mmc_check_result);
> +
> +/*
> ++ * transfer with certain parameters
> + */
> +int mmc_simple_transfer(struct mmc_card *card,
> + struct scatterlist *sg, unsigned sg_len, unsigned dev_addr,
> + unsigned blocks, unsigned blksz, int write)
> +{
> + struct mmc_request mrq = {0};
> + struct mmc_command cmd = {0};
> + struct mmc_command stop = {0};
> + struct mmc_data data = {0};
> +
> + mrq.cmd = &cmd;
> + mrq.data = &data;
> + mrq.stop = &stop;
> +
> + mmc_prepare_mrq(card, &mrq, sg, sg_len, dev_addr,
> + blocks, blksz, write);
> +
> + mmc_wait_for_req(card->host, &mrq);
> +
> + mmc_wait_busy(card);
> +
> + return mmc_check_result(&mrq);
> +}
> +EXPORT_SYMBOL(mmc_simple_transfer);
>
> /**
> * mmc_init_context_info() - init synchronization context
> diff --git a/include/linux/mmc/core.h b/include/linux/mmc/core.h
> index f206e29..92540d0 100644
> --- a/include/linux/mmc/core.h
> +++ b/include/linux/mmc/core.h
> @@ -196,6 +196,14 @@ extern void mmc_put_card(struct mmc_card *card);
> extern int mmc_flush_cache(struct mmc_card *);
>
> extern int mmc_detect_card_removed(struct mmc_host *host);
> +extern void mmc_prepare_mrq(struct mmc_card *card,
> + struct mmc_request *mrq, struct scatterlist *sg, unsigned sg_len,
> + unsigned dev_addr, unsigned blocks, unsigned blksz, int write);
> +extern int mmc_wait_busy(struct mmc_card *card);
> +extern int mmc_check_result(struct mmc_request *mrq);
> +extern int mmc_simple_transfer(struct mmc_card *card,
> + struct scatterlist *sg, unsigned sg_len, unsigned dev_addr,
> + unsigned blocks, unsigned blksz, int write);
>
> /**
> * mmc_claim_host - exclusively claim a host
>
prev parent reply other threads:[~2014-11-11 3:30 UTC|newest]
Thread overview: 88+ messages / expand[flat|nested] mbox.gz Atom feed top
[not found] <n@samsung.com>
2012-08-05 13:08 ` [RFC/PATCH] mmc: core: Add support for idle time BKOPs Maya Erez
2012-08-05 13:08 ` Maya Erez
2012-08-30 7:36 ` Jaehoon Chung
2012-09-04 5:42 ` merez
2012-09-04 5:42 ` merez
2012-10-04 22:28 ` [PATCH v2] mmc: core: Add support for idle time BKOPS Maya Erez
2012-10-04 22:28 ` Maya Erez
2012-10-09 3:52 ` merez
2012-10-09 3:52 ` merez
2012-10-16 7:53 ` Jaehoon Chung
2012-11-07 4:28 ` merez
2012-11-07 4:28 ` merez
2012-11-08 5:26 ` Jaehoon Chung
2012-11-11 9:25 ` Subhash Jadavani
2012-10-18 16:31 ` [PATCH 1/6] mmc: core: sdio_io.c: Fixed lines with > 80 chars Sangho Yi
2012-10-18 16:31 ` [PATCH 2/6] mmc: core: sdio_bus.c: Removed trailing whitespace error Sangho Yi
2012-10-18 16:31 ` [PATCH 3/6] mmc: core: sdio_bus.c: Fixed lines > 80 chars Sangho Yi
2012-10-18 23:54 ` Jaehoon Chung
2012-10-18 16:31 ` [PATCH 4/6] mmc: core: sdio_bus.c: Removed space between func name and () Sangho Yi
2012-10-18 16:31 ` [PATCH 5/6] mmc: core: sdio_bus.c: Fixed a warning for the pr_warning( Sangho Yi
2012-10-18 16:31 ` [PATCH 6/6] mmc: core: sdio_bus.c: Removed unnecessary NULL check routine Sangho Yi
2012-10-18 16:47 ` [PATCH 1/6] mmc: core: sdio_io.c: Fixed lines with > 80 chars Joe Perches
2012-11-01 14:40 ` [PATCH v2] mmc: fix async request mechanism for sequential read scenarios Konstantin Dorfman
2012-11-05 6:20 ` Per Förlin
2012-11-05 7:15 ` Jaehoon Chung
2012-11-12 12:10 ` Konstantin Dorfman
2012-11-08 10:41 ` Jaehoon Chung
2012-11-08 12:51 ` merez
2012-11-09 5:46 ` Jaehoon Chung
2012-11-12 12:49 ` Konstantin Dorfman
2012-11-06 8:40 ` Jaehoon Chung
2012-11-12 12:42 ` Konstantin Dorfman
2012-11-12 16:51 ` [PATCH v3] " Konstantin Dorfman
2012-11-13 13:42 ` Seungwon Jeon
2012-11-15 10:23 ` Seungwon Jeon
2012-11-20 2:05 ` Seungwon Jeon
2012-11-25 11:56 ` [PATCH v3] mmc: core: Add support for idle time BKOPS Maya Erez
2012-11-25 11:56 ` Maya Erez
2012-11-25 12:46 ` merez
2012-11-25 12:46 ` merez
2012-11-28 14:22 ` Chris Ball
2012-11-29 12:40 ` Jaehoon Chung
2012-12-03 9:49 ` merez
2012-12-04 9:52 ` Ulf Hansson
2012-12-04 21:17 ` merez
2012-12-06 10:18 ` Ulf Hansson
2012-12-12 12:32 ` merez
2012-12-13 10:17 ` Ulf Hansson
2012-12-21 8:35 ` Maya Erez
2012-12-21 8:35 ` Maya Erez
2012-12-21 9:56 ` Ulf Hansson
2012-12-21 10:24 ` Jaehoon Chung
2012-12-05 13:38 ` [PATCH v4] mmc: fix async request mechanism for sequential read scenarios Konstantin Dorfman
2012-12-06 5:24 ` Seungwon Jeon
2012-12-06 14:23 ` Konstantin Dorfman
2012-12-10 14:23 ` [RESEND PATCH " Konstantin Dorfman
2012-12-12 9:26 ` Seungwon Jeon
2012-12-17 12:26 ` Seungwon Jeon
2012-12-18 16:00 ` Konstantin Dorfman
2012-12-18 16:19 ` Chris Ball
2012-12-20 7:39 ` Seungwon Jeon
2012-12-26 9:26 ` [PATCH v5] " Konstantin Dorfman
2012-12-28 10:16 ` Seungwon Jeon
2013-01-14 19:31 ` Chris Ball
2013-01-15 12:00 ` Konstantin Dorfman
2013-01-22 10:48 ` [PATCH 1/2] mmc: core: fix permanent sleep of mmcqd during card removal Seungwon Jeon
2013-01-31 11:05 ` Jaehoon Chung
2013-01-31 11:25 ` Seungwon Jeon
2013-02-08 12:07 ` Konstantin Dorfman
2013-02-11 17:00 ` Chris Ball
2013-01-30 6:30 ` Seungwon Jeon
2013-01-31 6:53 ` Subhash Jadavani
2013-02-04 11:43 ` Subhash Jadavani
2013-02-05 5:57 ` Seungwon Jeon
2013-02-05 7:05 ` Jaehoon Chung
2013-02-05 7:32 ` Subhash Jadavani
2013-02-04 19:27 ` Konstantin Dorfman
2013-01-10 20:15 ` [PATCH v5 0/3] Add support for periodic BKOPS Maya Erez
2013-01-11 11:33 ` Jaehoon Chung
2014-11-10 17:13 ` [PATCH 0/3] mmc: Support FFU for eMMC v5.0 Avi Shchislowski
2014-11-11 3:33 ` Jaehoon Chung
2014-11-10 17:13 ` [PATCH 1/3] " Avi Shchislowski
2014-11-10 17:13 ` Avi Shchislowski
2014-11-11 3:07 ` Jaehoon Chung
2014-11-11 8:44 ` Avi Shchislowski
2014-11-10 17:18 ` [PATCH 2/3] " Avi Shchislowski
2014-11-10 17:18 ` Avi Shchislowski
2014-11-11 3:30 ` Jaehoon Chung [this message]
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=546182D9.7040107@samsung.com \
--to=jh80.chung@samsung.com \
--cc=Alex.Lemberg@sandisk.com \
--cc=avi.shchislowski@sandisk.com \
--cc=chris@printf.net \
--cc=cpgs@samsung.com \
--cc=gwendal@google.com \
--cc=linux-kernel@vger.kernel.org \
--cc=linux-mmc@vger.kernel.org \
--cc=ulf.hansson@linaro.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.