Re: [PATCH 4/4] PCI,sriov: provide method to reduce the number of total VFs supported

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



On Mon, Nov 5, 2012 at 1:20 PM, Donald Dutile <ddutile@xxxxxxxxxx> wrote:
> Some implementations of SRIOV provide a capability structure
> value of TotalVFs that is greater than what the software can support.
> Provide a method to reduce the capability structure reported value
> to the value the driver can support.
> This ensures sysfs reports the current capability of the system,
> hardware and software.
> Example for its use: igb & ixgbe -- report 8 & 64 as TotalVFs,
> but drivers only support 7 & 63 maximum.
>
> Signed-off-by: Donald Dutile <ddutile@xxxxxxxxxx>

I don't really understand the purpose of pci_sriov_set_totalvfs().  I
think a driver should enforce its limit at the point where it enables
the VFs.  I think the driver should do that to be defensive regardless
of whether we add pci_sriov_set_totalvfs().

So is this just to make the driver's limit visible to user-space?  How
is it better than having the user specify the number he'd like, and
having the driver reduce that if necessary?  The user will be able to
read sriov_numvfs to learn how many the driver enabled, right?

If we allow sriov_totalvfs to contain a different number than the
SR-IOV capability has (as seen via "lspci"), then we have to explain
to users why they might be different.

I'm playing devil's advocate a bit here because I really don't know
that much about SR-IOV or what the administrative interfaces look
like.

>  drivers/pci/iov.c       | 48 ++++++++++++++++++++++++++++++++++++++++++++++++
>  drivers/pci/pci-sysfs.c |  4 ++--
>  drivers/pci/pci.h       |  1 +
>  include/linux/pci.h     | 10 ++++++++++
>  4 files changed, 61 insertions(+), 2 deletions(-)
>
> diff --git a/drivers/pci/iov.c b/drivers/pci/iov.c
> index aeccc91..3b4a905 100644
> --- a/drivers/pci/iov.c
> +++ b/drivers/pci/iov.c
> @@ -735,3 +735,51 @@ int pci_num_vf(struct pci_dev *dev)
>                 return dev->sriov->nr_virtfn;
>  }
>  EXPORT_SYMBOL_GPL(pci_num_vf);
> +
> +/**
> + * pci_sriov_set_totalvfs -- reduce the TotalVFs available
> + * @dev: the PCI PF device
> + * numvfs: number that should be used for TotalVFs supported
> + *
> + * Should be called from PF driver's probe routine with
> + * device's mutex held.
> + *
> + * Returns 0 if PF is an SRIOV-capable device and
> + * value of numvfs valid. If not a PF with VFS, return -EINVAL;
> + * if VFs already enabled, return -EBUSY.
> + */
> +int pci_sriov_set_totalvfs(struct pci_dev *dev, u16 numvfs)
> +{
> +       if (!dev || !dev->is_physfn || (numvfs > dev->sriov->total))
> +               return -EINVAL;
> +
> +       /* Shouldn't change if VFs already enabled */
> +       if (dev->sriov->ctrl & PCI_SRIOV_CTRL_VFE)
> +               return -EBUSY;
> +       else
> +               dev->sriov->drvttl = numvfs;
> +
> +       return 0;
> +}
> +EXPORT_SYMBOL_GPL(pci_sriov_set_totalvfs);
> +
> +/**
> + * pci_sriov_get_totalvfs -- get total VFs supported on this devic3
> + * @dev: the PCI PF device
> + *
> + * For a PCIe device with SRIOV support, return the PCIe
> + * SRIOV capability value of TotalVFs or the value of drvttl
> + * if the driver reduced it.  Otherwise, -EINVAL.
> + */
> +int pci_sriov_get_totalvfs(struct pci_dev *dev)
> +{
> +       if (!dev || !dev->is_physfn)
> +               return -EINVAL;
> +
> +       if (dev->sriov->drvttl)
> +               return dev->sriov->drvttl;
> +       else
> +               return dev->sriov->total;
> +}
> +EXPORT_SYMBOL_GPL(pci_sriov_get_totalvfs);
> +
> diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
> index cbcdd8d..e9c967f 100644
> --- a/drivers/pci/pci-sysfs.c
> +++ b/drivers/pci/pci-sysfs.c
> @@ -413,7 +413,7 @@ static ssize_t sriov_totalvfs_show(struct device *dev,
>         u16 total;
>
>         pdev = to_pci_dev(dev);
> -       total = pdev->sriov->total;
> +       total = pci_sriov_get_totalvfs(pdev);
>         return sprintf(buf, "%u\n", total);
>  }
>
> @@ -459,7 +459,7 @@ static ssize_t sriov_numvfs_store(struct device *dev,
>         }
>
>         /* if enabling vf's ... */
> -       total = pdev->sriov->total;
> +       total = pci_sriov_get_totalvfs(pdev);
>         /* Requested VFs to enable < totalvfs and none enabled already */
>         if ((num_vfs > 0) && (num_vfs <= total)) {
>                 if (pdev->sriov->nr_virtfn == 0) {
> diff --git a/drivers/pci/pci.h b/drivers/pci/pci.h
> index 6f6cd14..553bbba 100644
> --- a/drivers/pci/pci.h
> +++ b/drivers/pci/pci.h
> @@ -240,6 +240,7 @@ struct pci_sriov {
>         u16 stride;             /* following VF stride */
>         u32 pgsz;               /* page size for BAR alignment */
>         u8 link;                /* Function Dependency Link */
> +       u16 drvttl;             /* max num VFs driver supports */
>         struct pci_dev *dev;    /* lowest numbered PF */
>         struct pci_dev *self;   /* this PF */
>         struct mutex lock;      /* lock for VF bus */
> diff --git a/include/linux/pci.h b/include/linux/pci.h
> index 7ef8fba..1ad8249 100644
> --- a/include/linux/pci.h
> +++ b/include/linux/pci.h
> @@ -1611,6 +1611,8 @@ extern int pci_enable_sriov(struct pci_dev *dev, int nr_virtfn);
>  extern void pci_disable_sriov(struct pci_dev *dev);
>  extern irqreturn_t pci_sriov_migration(struct pci_dev *dev);
>  extern int pci_num_vf(struct pci_dev *dev);
> +extern int pci_sriov_set_totalvfs(struct pci_dev *dev, u16 numvfs);
> +extern int pci_sriov_get_totalvfs(struct pci_dev *dev);
>  #else
>  static inline int pci_enable_sriov(struct pci_dev *dev, int nr_virtfn)
>  {
> @@ -1627,6 +1629,14 @@ static inline int pci_num_vf(struct pci_dev *dev)
>  {
>         return 0;
>  }
> +static inline int pci_sriov_set_totalvfs(struct pci_dev *dev, u16 numvfs)
> +{
> +       return 0;
> +}
> +static inline int pci_sriov_get_totalvfs(struct pci_dev *dev)
> +{
> +       return 0;
> +}
>  #endif
>
>  #if defined(CONFIG_HOTPLUG_PCI) || defined(CONFIG_HOTPLUG_PCI_MODULE)
> --
> 1.7.10.2.552.gaa3bb87
>
--
To unsubscribe from this list: send the line "unsubscribe linux-pci" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[Index of Archives]     [DMA Engine]     [Linux Coverity]     [Linux USB]     [Video for Linux]     [Linux Audio Users]     [Yosemite News]     [Linux Kernel]     [Linux SCSI]     [Greybus]

  Powered by Linux