Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On Wed, Sep 23, 2015 at 3:26 PM, Ulf Hansson wrote: ... >> Ulf, >> is the git repo visible publicly? > > git://git.linaro.org/people/ulf.hansson/mmc.git Sorry - my bad : I had looked at mmc.git and saw "2014-10-15" as the last commit. Scrolling down to the bottom of the page shows the "next" branch as active. I'll work from that branch. :) thanks! grant -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On 24 September 2015 at 00:06, Grant Grundler wrote: > On Wed, Sep 23, 2015 at 2:42 PM, Ulf Hansson wrote: >> On 22 September 2015 at 11:27, Jon Hunter wrote: >>> Certain eMMC devices allow vendor specific device information to be read >>> via a sequence of vendor commands. These vendor commands must be issued >>> in sequence and an atomic fashion. One way to support this would be to >>> add an ioctl function for sending a sequence of commands to the device >>> atomically as proposed here. These multi commands are simple array of >>> the existing mmc_ioc_cmd structure. >>> >>> The structure passed via the ioctl uses a __u64 type to specify the number >>> of commands (so that the structure is aligned on a 64-bit boundary) and a >>> zero length array as a header for list of commands to be issued. The >>> maximum number of commands that can be sent is determined by >>> MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than >>> sufficient). >>> >>> This based upon work by Seshagiri Holi . >>> >>> Signed-off-by: Seshagiri Holi >>> Signed-off-by: Jon Hunter >> >> Thanks, applied for next! > > Ulf, > is the git repo visible publicly? git://git.linaro.org/people/ulf.hansson/mmc.git > > Your linaro.org mmc.git seems to be stale and Chris Ball's tree on > kernel.org is the only other mention of mmc I'm finding. Chris' tree hasn't been used for a long time. > > cheers > grant Kind regards Uffe -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On Wed, Sep 23, 2015 at 2:42 PM, Ulf Hansson wrote: > On 22 September 2015 at 11:27, Jon Hunter wrote: >> Certain eMMC devices allow vendor specific device information to be read >> via a sequence of vendor commands. These vendor commands must be issued >> in sequence and an atomic fashion. One way to support this would be to >> add an ioctl function for sending a sequence of commands to the device >> atomically as proposed here. These multi commands are simple array of >> the existing mmc_ioc_cmd structure. >> >> The structure passed via the ioctl uses a __u64 type to specify the number >> of commands (so that the structure is aligned on a 64-bit boundary) and a >> zero length array as a header for list of commands to be issued. The >> maximum number of commands that can be sent is determined by >> MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than >> sufficient). >> >> This based upon work by Seshagiri Holi . >> >> Signed-off-by: Seshagiri Holi >> Signed-off-by: Jon Hunter > > Thanks, applied for next! Ulf, is the git repo visible publicly? Your linaro.org mmc.git seems to be stale and Chris Ball's tree on kernel.org is the only other mention of mmc I'm finding. cheers grant -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On Wed, Sep 23, 2015 at 2:42 PM, Ulf Hansson wrote: > On 22 September 2015 at 11:27, Jon Hunter wrote: >> Certain eMMC devices allow vendor specific device information to be read >> via a sequence of vendor commands. These vendor commands must be issued >> in sequence and an atomic fashion. One way to support this would be to >> add an ioctl function for sending a sequence of commands to the device >> atomically as proposed here. These multi commands are simple array of >> the existing mmc_ioc_cmd structure. >> >> The structure passed via the ioctl uses a __u64 type to specify the number >> of commands (so that the structure is aligned on a 64-bit boundary) and a >> zero length array as a header for list of commands to be issued. The >> maximum number of commands that can be sent is determined by >> MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than >> sufficient). >> >> This based upon work by Seshagiri Holi . >> >> Signed-off-by: Seshagiri Holi >> Signed-off-by: Jon Hunter > > Thanks, applied for next! Awesome! Thanks Ulf! (and Jon for preparing the patches) I'll prepare a patch to implement Gwendal's previous suggestion based on this 3.18 patch: https://chromium-review.googlesource.com/#/c/299956/ cheers, grant > > Kind regards > Uffe > >> --- >> V4 changes: >> - Moved duplicated test in mmc_blk_ioc_cmd() and mmc_blk_ioc_multi_cmd() >> to mmc_blk_ioctl(). Changed author. >> V3 changes: >> - Updated mmc_ioc_multi_cmd structure per Grant's preference >> V2 changes: >> - Updated changelog and patch per Arnd's feedback >> - Moved mmc_put/get_card() outside of __mmc_blk_ioctl_cmd() >> >> drivers/mmc/card/block.c | 206 >> ++--- >> include/uapi/linux/mmc/ioctl.h | 19 +++- >> 2 files changed, 169 insertions(+), 56 deletions(-) >> >> diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c >> index c742cfd7674e..f6acf0f6c410 100644 >> --- a/drivers/mmc/card/block.c >> +++ b/drivers/mmc/card/block.c >> @@ -387,6 +387,24 @@ out: >> return ERR_PTR(err); >> } >> >> +static int mmc_blk_ioctl_copy_to_user(struct mmc_ioc_cmd __user *ic_ptr, >> + struct mmc_blk_ioc_data *idata) >> +{ >> + struct mmc_ioc_cmd *ic = >ic; >> + >> + if (copy_to_user(&(ic_ptr->response), ic->response, >> +sizeof(ic->response))) >> + return -EFAULT; >> + >> + if (!idata->ic.write_flag) { >> + if (copy_to_user((void __user *)(unsigned long)ic->data_ptr, >> +idata->buf, idata->buf_bytes)) >> + return -EFAULT; >> + } >> + >> + return 0; >> +} >> + >> static int ioctl_rpmb_card_status_poll(struct mmc_card *card, u32 *status, >>u32 retries_max) >> { >> @@ -447,12 +465,9 @@ out: >> return err; >> } >> >> -static int mmc_blk_ioctl_cmd(struct block_device *bdev, >> - struct mmc_ioc_cmd __user *ic_ptr) >> +static int __mmc_blk_ioctl_cmd(struct mmc_card *card, struct mmc_blk_data >> *md, >> + struct mmc_blk_ioc_data *idata) >> { >> - struct mmc_blk_ioc_data *idata; >> - struct mmc_blk_data *md; >> - struct mmc_card *card; >> struct mmc_command cmd = {0}; >> struct mmc_data data = {0}; >> struct mmc_request mrq = {NULL}; >> @@ -461,33 +476,12 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, >> int is_rpmb = false; >> u32 status = 0; >> >> - /* >> -* The caller must have CAP_SYS_RAWIO, and must be calling this on >> the >> -* whole block device, not on a partition. This prevents overspray >> -* between sibling partitions. >> -*/ >> - if ((!capable(CAP_SYS_RAWIO)) || (bdev != bdev->bd_contains)) >> - return -EPERM; >> - >> - idata = mmc_blk_ioctl_copy_from_user(ic_ptr); >> - if (IS_ERR(idata)) >> - return PTR_ERR(idata); >> - >> - md = mmc_blk_get(bdev->bd_disk); >> - if (!md) { >> - err = -EINVAL; >> - goto cmd_err; >> - } >> + if (!card || !md || !idata) >> + return -EINVAL; >> >> if (md->area_type & MMC_BLK_DATA_AREA_RPMB) >> is_rpmb = true; >> >> - card = md->queue.card; >> - if (IS_ERR(card)) { >> - err = PTR_ERR(card); >> - goto cmd_done; >> - } >> - >> cmd.opcode = idata->ic.opcode; >> cmd.arg = idata->ic.arg; >> cmd.flags = idata->ic.flags; >> @@ -530,23 +524,21 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, >> >> mrq.cmd = >> >> - mmc_get_card(card); >> - >> err = mmc_blk_part_switch(card, md); >> if (err) >> - goto cmd_rel_host; >> + return err; >> >> if (idata->ic.is_acmd) { >> err =
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On 22 September 2015 at 11:27, Jon Hunter wrote: > Certain eMMC devices allow vendor specific device information to be read > via a sequence of vendor commands. These vendor commands must be issued > in sequence and an atomic fashion. One way to support this would be to > add an ioctl function for sending a sequence of commands to the device > atomically as proposed here. These multi commands are simple array of > the existing mmc_ioc_cmd structure. > > The structure passed via the ioctl uses a __u64 type to specify the number > of commands (so that the structure is aligned on a 64-bit boundary) and a > zero length array as a header for list of commands to be issued. The > maximum number of commands that can be sent is determined by > MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than > sufficient). > > This based upon work by Seshagiri Holi . > > Signed-off-by: Seshagiri Holi > Signed-off-by: Jon Hunter Thanks, applied for next! Kind regards Uffe > --- > V4 changes: > - Moved duplicated test in mmc_blk_ioc_cmd() and mmc_blk_ioc_multi_cmd() > to mmc_blk_ioctl(). Changed author. > V3 changes: > - Updated mmc_ioc_multi_cmd structure per Grant's preference > V2 changes: > - Updated changelog and patch per Arnd's feedback > - Moved mmc_put/get_card() outside of __mmc_blk_ioctl_cmd() > > drivers/mmc/card/block.c | 206 > ++--- > include/uapi/linux/mmc/ioctl.h | 19 +++- > 2 files changed, 169 insertions(+), 56 deletions(-) > > diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c > index c742cfd7674e..f6acf0f6c410 100644 > --- a/drivers/mmc/card/block.c > +++ b/drivers/mmc/card/block.c > @@ -387,6 +387,24 @@ out: > return ERR_PTR(err); > } > > +static int mmc_blk_ioctl_copy_to_user(struct mmc_ioc_cmd __user *ic_ptr, > + struct mmc_blk_ioc_data *idata) > +{ > + struct mmc_ioc_cmd *ic = >ic; > + > + if (copy_to_user(&(ic_ptr->response), ic->response, > +sizeof(ic->response))) > + return -EFAULT; > + > + if (!idata->ic.write_flag) { > + if (copy_to_user((void __user *)(unsigned long)ic->data_ptr, > +idata->buf, idata->buf_bytes)) > + return -EFAULT; > + } > + > + return 0; > +} > + > static int ioctl_rpmb_card_status_poll(struct mmc_card *card, u32 *status, >u32 retries_max) > { > @@ -447,12 +465,9 @@ out: > return err; > } > > -static int mmc_blk_ioctl_cmd(struct block_device *bdev, > - struct mmc_ioc_cmd __user *ic_ptr) > +static int __mmc_blk_ioctl_cmd(struct mmc_card *card, struct mmc_blk_data > *md, > + struct mmc_blk_ioc_data *idata) > { > - struct mmc_blk_ioc_data *idata; > - struct mmc_blk_data *md; > - struct mmc_card *card; > struct mmc_command cmd = {0}; > struct mmc_data data = {0}; > struct mmc_request mrq = {NULL}; > @@ -461,33 +476,12 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, > int is_rpmb = false; > u32 status = 0; > > - /* > -* The caller must have CAP_SYS_RAWIO, and must be calling this on the > -* whole block device, not on a partition. This prevents overspray > -* between sibling partitions. > -*/ > - if ((!capable(CAP_SYS_RAWIO)) || (bdev != bdev->bd_contains)) > - return -EPERM; > - > - idata = mmc_blk_ioctl_copy_from_user(ic_ptr); > - if (IS_ERR(idata)) > - return PTR_ERR(idata); > - > - md = mmc_blk_get(bdev->bd_disk); > - if (!md) { > - err = -EINVAL; > - goto cmd_err; > - } > + if (!card || !md || !idata) > + return -EINVAL; > > if (md->area_type & MMC_BLK_DATA_AREA_RPMB) > is_rpmb = true; > > - card = md->queue.card; > - if (IS_ERR(card)) { > - err = PTR_ERR(card); > - goto cmd_done; > - } > - > cmd.opcode = idata->ic.opcode; > cmd.arg = idata->ic.arg; > cmd.flags = idata->ic.flags; > @@ -530,23 +524,21 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, > > mrq.cmd = > > - mmc_get_card(card); > - > err = mmc_blk_part_switch(card, md); > if (err) > - goto cmd_rel_host; > + return err; > > if (idata->ic.is_acmd) { > err = mmc_app_cmd(card->host, card); > if (err) > - goto cmd_rel_host; > + return err; > } > > if (is_rpmb) { > err = mmc_set_blockcount(card, data.blocks, > idata->ic.write_flag & (1 << 31)); > if (err) > - goto cmd_rel_host; > + return err; > } > >
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On 22 September 2015 at 11:27, Jon Hunterwrote: > Certain eMMC devices allow vendor specific device information to be read > via a sequence of vendor commands. These vendor commands must be issued > in sequence and an atomic fashion. One way to support this would be to > add an ioctl function for sending a sequence of commands to the device > atomically as proposed here. These multi commands are simple array of > the existing mmc_ioc_cmd structure. > > The structure passed via the ioctl uses a __u64 type to specify the number > of commands (so that the structure is aligned on a 64-bit boundary) and a > zero length array as a header for list of commands to be issued. The > maximum number of commands that can be sent is determined by > MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than > sufficient). > > This based upon work by Seshagiri Holi . > > Signed-off-by: Seshagiri Holi > Signed-off-by: Jon Hunter Thanks, applied for next! Kind regards Uffe > --- > V4 changes: > - Moved duplicated test in mmc_blk_ioc_cmd() and mmc_blk_ioc_multi_cmd() > to mmc_blk_ioctl(). Changed author. > V3 changes: > - Updated mmc_ioc_multi_cmd structure per Grant's preference > V2 changes: > - Updated changelog and patch per Arnd's feedback > - Moved mmc_put/get_card() outside of __mmc_blk_ioctl_cmd() > > drivers/mmc/card/block.c | 206 > ++--- > include/uapi/linux/mmc/ioctl.h | 19 +++- > 2 files changed, 169 insertions(+), 56 deletions(-) > > diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c > index c742cfd7674e..f6acf0f6c410 100644 > --- a/drivers/mmc/card/block.c > +++ b/drivers/mmc/card/block.c > @@ -387,6 +387,24 @@ out: > return ERR_PTR(err); > } > > +static int mmc_blk_ioctl_copy_to_user(struct mmc_ioc_cmd __user *ic_ptr, > + struct mmc_blk_ioc_data *idata) > +{ > + struct mmc_ioc_cmd *ic = >ic; > + > + if (copy_to_user(&(ic_ptr->response), ic->response, > +sizeof(ic->response))) > + return -EFAULT; > + > + if (!idata->ic.write_flag) { > + if (copy_to_user((void __user *)(unsigned long)ic->data_ptr, > +idata->buf, idata->buf_bytes)) > + return -EFAULT; > + } > + > + return 0; > +} > + > static int ioctl_rpmb_card_status_poll(struct mmc_card *card, u32 *status, >u32 retries_max) > { > @@ -447,12 +465,9 @@ out: > return err; > } > > -static int mmc_blk_ioctl_cmd(struct block_device *bdev, > - struct mmc_ioc_cmd __user *ic_ptr) > +static int __mmc_blk_ioctl_cmd(struct mmc_card *card, struct mmc_blk_data > *md, > + struct mmc_blk_ioc_data *idata) > { > - struct mmc_blk_ioc_data *idata; > - struct mmc_blk_data *md; > - struct mmc_card *card; > struct mmc_command cmd = {0}; > struct mmc_data data = {0}; > struct mmc_request mrq = {NULL}; > @@ -461,33 +476,12 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, > int is_rpmb = false; > u32 status = 0; > > - /* > -* The caller must have CAP_SYS_RAWIO, and must be calling this on the > -* whole block device, not on a partition. This prevents overspray > -* between sibling partitions. > -*/ > - if ((!capable(CAP_SYS_RAWIO)) || (bdev != bdev->bd_contains)) > - return -EPERM; > - > - idata = mmc_blk_ioctl_copy_from_user(ic_ptr); > - if (IS_ERR(idata)) > - return PTR_ERR(idata); > - > - md = mmc_blk_get(bdev->bd_disk); > - if (!md) { > - err = -EINVAL; > - goto cmd_err; > - } > + if (!card || !md || !idata) > + return -EINVAL; > > if (md->area_type & MMC_BLK_DATA_AREA_RPMB) > is_rpmb = true; > > - card = md->queue.card; > - if (IS_ERR(card)) { > - err = PTR_ERR(card); > - goto cmd_done; > - } > - > cmd.opcode = idata->ic.opcode; > cmd.arg = idata->ic.arg; > cmd.flags = idata->ic.flags; > @@ -530,23 +524,21 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, > > mrq.cmd = > > - mmc_get_card(card); > - > err = mmc_blk_part_switch(card, md); > if (err) > - goto cmd_rel_host; > + return err; > > if (idata->ic.is_acmd) { > err = mmc_app_cmd(card->host, card); > if (err) > - goto cmd_rel_host; > + return err; > } > > if (is_rpmb) { > err = mmc_set_blockcount(card, data.blocks, > idata->ic.write_flag & (1 << 31)); > if (err) > -
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On 24 September 2015 at 00:06, Grant Grundlerwrote: > On Wed, Sep 23, 2015 at 2:42 PM, Ulf Hansson wrote: >> On 22 September 2015 at 11:27, Jon Hunter wrote: >>> Certain eMMC devices allow vendor specific device information to be read >>> via a sequence of vendor commands. These vendor commands must be issued >>> in sequence and an atomic fashion. One way to support this would be to >>> add an ioctl function for sending a sequence of commands to the device >>> atomically as proposed here. These multi commands are simple array of >>> the existing mmc_ioc_cmd structure. >>> >>> The structure passed via the ioctl uses a __u64 type to specify the number >>> of commands (so that the structure is aligned on a 64-bit boundary) and a >>> zero length array as a header for list of commands to be issued. The >>> maximum number of commands that can be sent is determined by >>> MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than >>> sufficient). >>> >>> This based upon work by Seshagiri Holi . >>> >>> Signed-off-by: Seshagiri Holi >>> Signed-off-by: Jon Hunter >> >> Thanks, applied for next! > > Ulf, > is the git repo visible publicly? git://git.linaro.org/people/ulf.hansson/mmc.git > > Your linaro.org mmc.git seems to be stale and Chris Ball's tree on > kernel.org is the only other mention of mmc I'm finding. Chris' tree hasn't been used for a long time. > > cheers > grant Kind regards Uffe -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On Wed, Sep 23, 2015 at 2:42 PM, Ulf Hanssonwrote: > On 22 September 2015 at 11:27, Jon Hunter wrote: >> Certain eMMC devices allow vendor specific device information to be read >> via a sequence of vendor commands. These vendor commands must be issued >> in sequence and an atomic fashion. One way to support this would be to >> add an ioctl function for sending a sequence of commands to the device >> atomically as proposed here. These multi commands are simple array of >> the existing mmc_ioc_cmd structure. >> >> The structure passed via the ioctl uses a __u64 type to specify the number >> of commands (so that the structure is aligned on a 64-bit boundary) and a >> zero length array as a header for list of commands to be issued. The >> maximum number of commands that can be sent is determined by >> MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than >> sufficient). >> >> This based upon work by Seshagiri Holi . >> >> Signed-off-by: Seshagiri Holi >> Signed-off-by: Jon Hunter > > Thanks, applied for next! Awesome! Thanks Ulf! (and Jon for preparing the patches) I'll prepare a patch to implement Gwendal's previous suggestion based on this 3.18 patch: https://chromium-review.googlesource.com/#/c/299956/ cheers, grant > > Kind regards > Uffe > >> --- >> V4 changes: >> - Moved duplicated test in mmc_blk_ioc_cmd() and mmc_blk_ioc_multi_cmd() >> to mmc_blk_ioctl(). Changed author. >> V3 changes: >> - Updated mmc_ioc_multi_cmd structure per Grant's preference >> V2 changes: >> - Updated changelog and patch per Arnd's feedback >> - Moved mmc_put/get_card() outside of __mmc_blk_ioctl_cmd() >> >> drivers/mmc/card/block.c | 206 >> ++--- >> include/uapi/linux/mmc/ioctl.h | 19 +++- >> 2 files changed, 169 insertions(+), 56 deletions(-) >> >> diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c >> index c742cfd7674e..f6acf0f6c410 100644 >> --- a/drivers/mmc/card/block.c >> +++ b/drivers/mmc/card/block.c >> @@ -387,6 +387,24 @@ out: >> return ERR_PTR(err); >> } >> >> +static int mmc_blk_ioctl_copy_to_user(struct mmc_ioc_cmd __user *ic_ptr, >> + struct mmc_blk_ioc_data *idata) >> +{ >> + struct mmc_ioc_cmd *ic = >ic; >> + >> + if (copy_to_user(&(ic_ptr->response), ic->response, >> +sizeof(ic->response))) >> + return -EFAULT; >> + >> + if (!idata->ic.write_flag) { >> + if (copy_to_user((void __user *)(unsigned long)ic->data_ptr, >> +idata->buf, idata->buf_bytes)) >> + return -EFAULT; >> + } >> + >> + return 0; >> +} >> + >> static int ioctl_rpmb_card_status_poll(struct mmc_card *card, u32 *status, >>u32 retries_max) >> { >> @@ -447,12 +465,9 @@ out: >> return err; >> } >> >> -static int mmc_blk_ioctl_cmd(struct block_device *bdev, >> - struct mmc_ioc_cmd __user *ic_ptr) >> +static int __mmc_blk_ioctl_cmd(struct mmc_card *card, struct mmc_blk_data >> *md, >> + struct mmc_blk_ioc_data *idata) >> { >> - struct mmc_blk_ioc_data *idata; >> - struct mmc_blk_data *md; >> - struct mmc_card *card; >> struct mmc_command cmd = {0}; >> struct mmc_data data = {0}; >> struct mmc_request mrq = {NULL}; >> @@ -461,33 +476,12 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, >> int is_rpmb = false; >> u32 status = 0; >> >> - /* >> -* The caller must have CAP_SYS_RAWIO, and must be calling this on >> the >> -* whole block device, not on a partition. This prevents overspray >> -* between sibling partitions. >> -*/ >> - if ((!capable(CAP_SYS_RAWIO)) || (bdev != bdev->bd_contains)) >> - return -EPERM; >> - >> - idata = mmc_blk_ioctl_copy_from_user(ic_ptr); >> - if (IS_ERR(idata)) >> - return PTR_ERR(idata); >> - >> - md = mmc_blk_get(bdev->bd_disk); >> - if (!md) { >> - err = -EINVAL; >> - goto cmd_err; >> - } >> + if (!card || !md || !idata) >> + return -EINVAL; >> >> if (md->area_type & MMC_BLK_DATA_AREA_RPMB) >> is_rpmb = true; >> >> - card = md->queue.card; >> - if (IS_ERR(card)) { >> - err = PTR_ERR(card); >> - goto cmd_done; >> - } >> - >> cmd.opcode = idata->ic.opcode; >> cmd.arg = idata->ic.arg; >> cmd.flags = idata->ic.flags; >> @@ -530,23 +524,21 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, >> >> mrq.cmd = >> >> - mmc_get_card(card); >> - >> err = mmc_blk_part_switch(card, md); >> if (err) >> - goto cmd_rel_host; >> +
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On Wed, Sep 23, 2015 at 2:42 PM, Ulf Hanssonwrote: > On 22 September 2015 at 11:27, Jon Hunter wrote: >> Certain eMMC devices allow vendor specific device information to be read >> via a sequence of vendor commands. These vendor commands must be issued >> in sequence and an atomic fashion. One way to support this would be to >> add an ioctl function for sending a sequence of commands to the device >> atomically as proposed here. These multi commands are simple array of >> the existing mmc_ioc_cmd structure. >> >> The structure passed via the ioctl uses a __u64 type to specify the number >> of commands (so that the structure is aligned on a 64-bit boundary) and a >> zero length array as a header for list of commands to be issued. The >> maximum number of commands that can be sent is determined by >> MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than >> sufficient). >> >> This based upon work by Seshagiri Holi . >> >> Signed-off-by: Seshagiri Holi >> Signed-off-by: Jon Hunter > > Thanks, applied for next! Ulf, is the git repo visible publicly? Your linaro.org mmc.git seems to be stale and Chris Ball's tree on kernel.org is the only other mention of mmc I'm finding. cheers grant -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
Re: [PATCH V4] mmc: block: Add new ioctl to send multi commands
On Wed, Sep 23, 2015 at 3:26 PM, Ulf Hanssonwrote: ... >> Ulf, >> is the git repo visible publicly? > > git://git.linaro.org/people/ulf.hansson/mmc.git Sorry - my bad : I had looked at mmc.git and saw "2014-10-15" as the last commit. Scrolling down to the bottom of the page shows the "next" branch as active. I'll work from that branch. :) thanks! grant -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
[PATCH V4] mmc: block: Add new ioctl to send multi commands
Certain eMMC devices allow vendor specific device information to be read via a sequence of vendor commands. These vendor commands must be issued in sequence and an atomic fashion. One way to support this would be to add an ioctl function for sending a sequence of commands to the device atomically as proposed here. These multi commands are simple array of the existing mmc_ioc_cmd structure. The structure passed via the ioctl uses a __u64 type to specify the number of commands (so that the structure is aligned on a 64-bit boundary) and a zero length array as a header for list of commands to be issued. The maximum number of commands that can be sent is determined by MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than sufficient). This based upon work by Seshagiri Holi . Signed-off-by: Seshagiri Holi Signed-off-by: Jon Hunter --- V4 changes: - Moved duplicated test in mmc_blk_ioc_cmd() and mmc_blk_ioc_multi_cmd() to mmc_blk_ioctl(). Changed author. V3 changes: - Updated mmc_ioc_multi_cmd structure per Grant's preference V2 changes: - Updated changelog and patch per Arnd's feedback - Moved mmc_put/get_card() outside of __mmc_blk_ioctl_cmd() drivers/mmc/card/block.c | 206 ++--- include/uapi/linux/mmc/ioctl.h | 19 +++- 2 files changed, 169 insertions(+), 56 deletions(-) diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c index c742cfd7674e..f6acf0f6c410 100644 --- a/drivers/mmc/card/block.c +++ b/drivers/mmc/card/block.c @@ -387,6 +387,24 @@ out: return ERR_PTR(err); } +static int mmc_blk_ioctl_copy_to_user(struct mmc_ioc_cmd __user *ic_ptr, + struct mmc_blk_ioc_data *idata) +{ + struct mmc_ioc_cmd *ic = >ic; + + if (copy_to_user(&(ic_ptr->response), ic->response, +sizeof(ic->response))) + return -EFAULT; + + if (!idata->ic.write_flag) { + if (copy_to_user((void __user *)(unsigned long)ic->data_ptr, +idata->buf, idata->buf_bytes)) + return -EFAULT; + } + + return 0; +} + static int ioctl_rpmb_card_status_poll(struct mmc_card *card, u32 *status, u32 retries_max) { @@ -447,12 +465,9 @@ out: return err; } -static int mmc_blk_ioctl_cmd(struct block_device *bdev, - struct mmc_ioc_cmd __user *ic_ptr) +static int __mmc_blk_ioctl_cmd(struct mmc_card *card, struct mmc_blk_data *md, + struct mmc_blk_ioc_data *idata) { - struct mmc_blk_ioc_data *idata; - struct mmc_blk_data *md; - struct mmc_card *card; struct mmc_command cmd = {0}; struct mmc_data data = {0}; struct mmc_request mrq = {NULL}; @@ -461,33 +476,12 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, int is_rpmb = false; u32 status = 0; - /* -* The caller must have CAP_SYS_RAWIO, and must be calling this on the -* whole block device, not on a partition. This prevents overspray -* between sibling partitions. -*/ - if ((!capable(CAP_SYS_RAWIO)) || (bdev != bdev->bd_contains)) - return -EPERM; - - idata = mmc_blk_ioctl_copy_from_user(ic_ptr); - if (IS_ERR(idata)) - return PTR_ERR(idata); - - md = mmc_blk_get(bdev->bd_disk); - if (!md) { - err = -EINVAL; - goto cmd_err; - } + if (!card || !md || !idata) + return -EINVAL; if (md->area_type & MMC_BLK_DATA_AREA_RPMB) is_rpmb = true; - card = md->queue.card; - if (IS_ERR(card)) { - err = PTR_ERR(card); - goto cmd_done; - } - cmd.opcode = idata->ic.opcode; cmd.arg = idata->ic.arg; cmd.flags = idata->ic.flags; @@ -530,23 +524,21 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, mrq.cmd = - mmc_get_card(card); - err = mmc_blk_part_switch(card, md); if (err) - goto cmd_rel_host; + return err; if (idata->ic.is_acmd) { err = mmc_app_cmd(card->host, card); if (err) - goto cmd_rel_host; + return err; } if (is_rpmb) { err = mmc_set_blockcount(card, data.blocks, idata->ic.write_flag & (1 << 31)); if (err) - goto cmd_rel_host; + return err; } if ((MMC_EXTRACT_INDEX_FROM_ARG(cmd.arg) == EXT_CSD_SANITIZE_START) && @@ -557,7 +549,7 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, pr_err("%s: ioctl_do_sanitize() failed. err = %d", __func__, err); - goto cmd_rel_host; + return err; }
[PATCH V4] mmc: block: Add new ioctl to send multi commands
Certain eMMC devices allow vendor specific device information to be read via a sequence of vendor commands. These vendor commands must be issued in sequence and an atomic fashion. One way to support this would be to add an ioctl function for sending a sequence of commands to the device atomically as proposed here. These multi commands are simple array of the existing mmc_ioc_cmd structure. The structure passed via the ioctl uses a __u64 type to specify the number of commands (so that the structure is aligned on a 64-bit boundary) and a zero length array as a header for list of commands to be issued. The maximum number of commands that can be sent is determined by MMC_IOC_MAX_CMDS (which defaults to 255 and should be more than sufficient). This based upon work by Seshagiri Holi. Signed-off-by: Seshagiri Holi Signed-off-by: Jon Hunter --- V4 changes: - Moved duplicated test in mmc_blk_ioc_cmd() and mmc_blk_ioc_multi_cmd() to mmc_blk_ioctl(). Changed author. V3 changes: - Updated mmc_ioc_multi_cmd structure per Grant's preference V2 changes: - Updated changelog and patch per Arnd's feedback - Moved mmc_put/get_card() outside of __mmc_blk_ioctl_cmd() drivers/mmc/card/block.c | 206 ++--- include/uapi/linux/mmc/ioctl.h | 19 +++- 2 files changed, 169 insertions(+), 56 deletions(-) diff --git a/drivers/mmc/card/block.c b/drivers/mmc/card/block.c index c742cfd7674e..f6acf0f6c410 100644 --- a/drivers/mmc/card/block.c +++ b/drivers/mmc/card/block.c @@ -387,6 +387,24 @@ out: return ERR_PTR(err); } +static int mmc_blk_ioctl_copy_to_user(struct mmc_ioc_cmd __user *ic_ptr, + struct mmc_blk_ioc_data *idata) +{ + struct mmc_ioc_cmd *ic = >ic; + + if (copy_to_user(&(ic_ptr->response), ic->response, +sizeof(ic->response))) + return -EFAULT; + + if (!idata->ic.write_flag) { + if (copy_to_user((void __user *)(unsigned long)ic->data_ptr, +idata->buf, idata->buf_bytes)) + return -EFAULT; + } + + return 0; +} + static int ioctl_rpmb_card_status_poll(struct mmc_card *card, u32 *status, u32 retries_max) { @@ -447,12 +465,9 @@ out: return err; } -static int mmc_blk_ioctl_cmd(struct block_device *bdev, - struct mmc_ioc_cmd __user *ic_ptr) +static int __mmc_blk_ioctl_cmd(struct mmc_card *card, struct mmc_blk_data *md, + struct mmc_blk_ioc_data *idata) { - struct mmc_blk_ioc_data *idata; - struct mmc_blk_data *md; - struct mmc_card *card; struct mmc_command cmd = {0}; struct mmc_data data = {0}; struct mmc_request mrq = {NULL}; @@ -461,33 +476,12 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, int is_rpmb = false; u32 status = 0; - /* -* The caller must have CAP_SYS_RAWIO, and must be calling this on the -* whole block device, not on a partition. This prevents overspray -* between sibling partitions. -*/ - if ((!capable(CAP_SYS_RAWIO)) || (bdev != bdev->bd_contains)) - return -EPERM; - - idata = mmc_blk_ioctl_copy_from_user(ic_ptr); - if (IS_ERR(idata)) - return PTR_ERR(idata); - - md = mmc_blk_get(bdev->bd_disk); - if (!md) { - err = -EINVAL; - goto cmd_err; - } + if (!card || !md || !idata) + return -EINVAL; if (md->area_type & MMC_BLK_DATA_AREA_RPMB) is_rpmb = true; - card = md->queue.card; - if (IS_ERR(card)) { - err = PTR_ERR(card); - goto cmd_done; - } - cmd.opcode = idata->ic.opcode; cmd.arg = idata->ic.arg; cmd.flags = idata->ic.flags; @@ -530,23 +524,21 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, mrq.cmd = - mmc_get_card(card); - err = mmc_blk_part_switch(card, md); if (err) - goto cmd_rel_host; + return err; if (idata->ic.is_acmd) { err = mmc_app_cmd(card->host, card); if (err) - goto cmd_rel_host; + return err; } if (is_rpmb) { err = mmc_set_blockcount(card, data.blocks, idata->ic.write_flag & (1 << 31)); if (err) - goto cmd_rel_host; + return err; } if ((MMC_EXTRACT_INDEX_FROM_ARG(cmd.arg) == EXT_CSD_SANITIZE_START) && @@ -557,7 +549,7 @@ static int mmc_blk_ioctl_cmd(struct block_device *bdev, pr_err("%s: ioctl_do_sanitize() failed. err = %d", __func__, err); - goto