All of lore.kernel.org
 help / color / mirror / Atom feed
From: Jason Gunthorpe <jgg@nvidia.com>
To: Jonathan Cameron <Jonathan.Cameron@huawei.com>
Cc: Jonathan Corbet <corbet@lwn.net>,
	Itay Avraham <itayavr@nvidia.com>,
	Jakub Kicinski <kuba@kernel.org>,
	Leon Romanovsky <leon@kernel.org>,
	linux-doc@vger.kernel.org, linux-rdma@vger.kernel.org,
	netdev@vger.kernel.org, Paolo Abeni <pabeni@redhat.com>,
	Saeed Mahameed <saeedm@nvidia.com>,
	Tariq Toukan <tariqt@nvidia.com>,
	Andy Gospodarek <andrew.gospodarek@broadcom.com>,
	Aron Silverton <aron.silverton@oracle.com>,
	Dan Williams <dan.j.williams@intel.com>,
	David Ahern <dsahern@kernel.org>,
	Christoph Hellwig <hch@infradead.org>,
	Jiri Pirko <jiri@nvidia.com>, Leonid Bloch <lbloch@nvidia.com>,
	Leon Romanovsky <leonro@nvidia.com>,
	linux-cxl@vger.kernel.org, patches@lists.linux.dev
Subject: Re: [PATCH v2 1/8] fwctl: Add basic structure for a class subsystem with a cdev
Date: Mon, 29 Jul 2024 14:30:38 -0300	[thread overview]
Message-ID: <20240729173038.GF3625856@nvidia.com> (raw)
In-Reply-To: <20240726153042.00002749@Huawei.com>

On Fri, Jul 26, 2024 at 03:30:42PM +0100, Jonathan Cameron wrote:

> Mostly looking at this to get my head around what the details are,
> but whilst I'm reading might as well offer some review comments.

Thanks!
 
> I'm not a fan of too many mini patches as it makes it harder
> to review rather than easier, but meh, I know others prefer
> it this way.  If you are going to do it though, comments
> need to be carefully tracking what they are talking about.

Yeah, I don't like it so much either, but given the debate on this
series I structured it so you can read the commit messages only and
have a pretty good idea what is inside.

> > +// SPDX-License-Identifier: GPL-2.0-only
> > +/*
> > + * Copyright (c) 2024, NVIDIA CORPORATION & AFFILIATES
> > + */
> > +#define pr_fmt(fmt) "fwctl: " fmt
> > +#include <linux/fwctl.h>
> > +#include <linux/module.h>
> > +#include <linux/slab.h>
> > +#include <linux/container_of.h>
> > +#include <linux/fs.h>
> 
> Trivial: Pick an ordering scheme perhaps as then we know where you'd
> like new headers to be added.

Heh, I think it is random ordered :) But sure lets sort by name,
though linux/fwctl.h does go first. Putting headers first in at least
one c file is a neat trick to ensure they self-compile and don't miss
their own #includess

#define pr_fmt(fmt) "fwctl: " fmt
#include <linux/fwctl.h>

#include <linux/container_of.h>
#include <linux/fs.h>
#include <linux/module.h>
#include <linux/slab.h>

> > +static struct fwctl_device *
> > +_alloc_device(struct device *parent, const struct fwctl_ops *ops, size_t size)
> > +{
> > +	struct fwctl_device *fwctl __free(kfree) = kzalloc(size, GFP_KERNEL);
> > +	int devnum;
> > +
> > +	if (!fwctl)
> > +		return NULL;
> 
> I'd put a blank line here.

Done
> > +/* Drivers use the fwctl_alloc_device() wrapper */
> > +struct fwctl_device *_fwctl_alloc_device(struct device *parent,
> > +					 const struct fwctl_ops *ops,
> > +					 size_t size)
> > +{
> > +	struct fwctl_device *fwctl __free(fwctl) =
> > +		_alloc_device(parent, ops, size);
> > +
> > +	if (!fwctl)
> > +		return NULL;
> > +
> > +	cdev_init(&fwctl->cdev, &fwctl_fops);
> > +	fwctl->cdev.owner = THIS_MODULE;
> 
> Owned by fwctl core, not the parent driver?  Perhaps a comment on why.
> I guess related to the lifetime being independent of parent driver.

Yes.

	/*
	 * The driver module is protected by fwctl_register/unregister(),
	 * unregister won't complete until we are done with the driver's module. 
	 */
	fwctl->cdev.owner = THIS_MODULE;


> > +int fwctl_register(struct fwctl_device *fwctl)
> > +{
> > +	int ret;
> > +
> > +	ret = cdev_device_add(&fwctl->cdev, &fwctl->dev);
> > +	if (ret)
> > +		return ret;
> > +	return 0;
> 
> Doesn't look like this ever gets more complex so 
> 
> 	return cdev_device_add(...)
> 
> If you expect to see more here in near future maybe fair enough
> to keep the handling as is.

Sure, I was expecting more when I wrote it then it turned out there
wasn't

> > + * fwctl_unregister - Unregister a device from the subsystem
> > + * @fwctl: Previously allocated and registered fwctl_device
> > + *
> > + * Undoes fwctl_register(). On return no driver ops will be called. The
> > + * caller must still call fwctl_put() to free the fwctl.
> > + *
> > + * Unregister will return even if userspace still has file descriptors open.
> > + * This will call ops->close_uctx() on any open FDs and after return no driver
> > + * op will be called. The FDs remain open but all fops will return -ENODEV.
> 
> Perhaps bring the docs in with the support?  I got (briefly) confused
> by the lack of a path to close_uctx() in here.

Okay, that paragraph can be shifted

> > + *
> > + * The design of fwctl allows this sort of disassociation of the driver from the
> > + * subsystem primarily by keeping memory allocations owned by the core subsytem.
> > + * The fwctl_device and fwctl_uctx can both be freed without requiring a driver
> > + * callback. This allows the module to remain unlocked while FDs are open.
> > + */

And this explains the above a 2nd way

> > +void fwctl_unregister(struct fwctl_device *fwctl)
> > +{
> > +	cdev_device_del(&fwctl->cdev, &fwctl->dev);
> > +
> > +	/*
> > +	 * The driver module may unload after this returns, the op pointer will
> > +	 * not be valid.
> > +	 */
> > +	fwctl->ops = NULL;
> I'd bring that in with the logic doing close_uctx() etc as then it will align
> with the comments that I'd also suggest only adding there (patch 2 I think).

Ok

> > +/**
> > + * fwctl_alloc_device - Allocate a fwctl
> > + * @parent: Physical device that provides the FW interface
> > + * @ops: Driver ops to register
> > + * @drv_struct: 'struct driver_fwctl' that holds the struct fwctl_device
> > + * @member: Name of the struct fwctl_device in @drv_struct
> > + *
> > + * This allocates and initializes the fwctl_device embedded in the drv_struct.
> > + * Upon success the pointer must be freed via fwctl_put(). Returns NULL on
> > + * failure. Returns a 'drv_struct *' on success, NULL on error.
> > + */
> > +#define fwctl_alloc_device(parent, ops, drv_struct, member)                  \
> > +	container_of(_fwctl_alloc_device(                                    \
> > +			     parent, ops,                                    \
> > +			     sizeof(drv_struct) +                            \
> > +				     BUILD_BUG_ON_ZERO(                      \
> > +					     offsetof(drv_struct, member))), \
> Doesn't that fire a build_bug when the member is at the start of drv_struct?
> Or do I have that backwards?

BUILD_BUG_ON(true) == failure, evaluates to void
BUILD_BUG_ON_ZERO(true) == fails, evaluates to 0
BUILD_BUG_ON_ZERO(false) == false, evaluates to 0

It is a bit confusing name, it is not ON_ZERO it is BUG_ON return ZERO

> Does container_of() safely handle a NULL?

Generally no, nor does it handle ERR_PTR, but it does work for both if
the offset is 0.

The BUILD_BUG guarentees the 0 offset both so that the casting inside
_fwctl_alloc_device() works and we can use safely use container_of()
to enforce the type check.

What do you think about writing it like this instead:

#define fwctl_alloc_device(parent, ops, drv_struct, member)               \
	({                                                                \
		static_assert(__same_type(struct fwctl_device,            \
					  ((drv_struct *)NULL)->member)); \
		static_assert(offsetof(drv_struct, member) == 0);         \
		(drv_struct *)_fwctl_alloc_device(parent, ops,            \
						  sizeof(drv_struct));    \
	})

?

In some ways I like it better..

Thanks,
Jason

  reply	other threads:[~2024-07-29 17:30 UTC|newest]

Thread overview: 48+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2024-06-24 22:47 [PATCH v2 0/8] Introduce fwctl subystem Jason Gunthorpe
2024-06-24 22:47 ` [PATCH v2 1/8] fwctl: Add basic structure for a class subsystem with a cdev Jason Gunthorpe
2024-06-25  4:47   ` Bagas Sanjaya
2024-07-22 16:04     ` Jason Gunthorpe
2024-07-26 14:30   ` Jonathan Cameron
2024-07-29 17:30     ` Jason Gunthorpe [this message]
2024-07-30 17:15       ` Jonathan Cameron
2024-06-24 22:47 ` [PATCH v2 2/8] fwctl: Basic ioctl dispatch for the character device Jason Gunthorpe
2024-07-26 15:01   ` Jonathan Cameron
2024-07-29 17:05     ` Jason Gunthorpe
2024-07-30 17:28       ` Jonathan Cameron
2024-08-01 13:05         ` Jason Gunthorpe
2024-08-06  7:36   ` Daniel Vetter
2024-08-08 12:34     ` Jason Gunthorpe
2024-06-24 22:47 ` [PATCH v2 3/8] fwctl: FWCTL_INFO to return basic information about the device Jason Gunthorpe
2024-07-26 15:15   ` Jonathan Cameron
2024-07-29 16:35     ` Jason Gunthorpe
2024-07-30 17:34       ` Jonathan Cameron
2024-08-01 13:11         ` Jason Gunthorpe
2024-06-24 22:47 ` [PATCH v2 4/8] taint: Add TAINT_FWCTL Jason Gunthorpe
2024-06-25 19:03   ` Randy Dunlap
2024-07-10 16:04     ` Jason Gunthorpe
2024-06-24 22:47 ` [PATCH v2 5/8] fwctl: FWCTL_RPC to execute a Remote Procedure Call to device firmware Jason Gunthorpe
2024-07-26 15:30   ` Jonathan Cameron
2024-07-29 16:28     ` Jason Gunthorpe
2024-07-30  8:00   ` Leon Romanovsky
2024-08-01 12:58     ` Jason Gunthorpe
2024-08-01 17:26       ` Leon Romanovsky
2024-08-02 13:59         ` Jonathan Cameron
2024-08-02 15:57           ` Leon Romanovsky
2024-08-07  7:44   ` Oded Gabbay
2024-08-08 11:46     ` Jason Gunthorpe
2024-06-24 22:47 ` [PATCH v2 6/8] fwctl: Add documentation Jason Gunthorpe
2024-06-25 22:04   ` Randy Dunlap
2024-07-22 16:18     ` Jason Gunthorpe
2024-07-22 20:40       ` Randy Dunlap
2024-07-26 15:50   ` Jonathan Cameron
2024-07-29 16:11     ` Jason Gunthorpe
2024-08-06  8:03   ` Daniel Vetter
2024-08-08 12:24     ` Jason Gunthorpe
2024-08-09  9:21       ` Daniel Vetter
2024-06-24 22:47 ` [PATCH v2 7/8] fwctl/mlx5: Support for communicating with mlx5 fw Jason Gunthorpe
2024-07-26 16:10   ` Jonathan Cameron
2024-07-29 16:22     ` Jason Gunthorpe
2024-07-31 11:52       ` Jonathan Cameron
2024-08-01 13:25         ` Jason Gunthorpe
2024-06-24 22:47 ` [PATCH v2 8/8] mlx5: Create an auxiliary device for fwctl_mlx5 Jason Gunthorpe
2024-06-24 23:18 ` [PATCH v2 0/8] Introduce fwctl subystem Jakub Kicinski

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=20240729173038.GF3625856@nvidia.com \
    --to=jgg@nvidia.com \
    --cc=Jonathan.Cameron@huawei.com \
    --cc=andrew.gospodarek@broadcom.com \
    --cc=aron.silverton@oracle.com \
    --cc=corbet@lwn.net \
    --cc=dan.j.williams@intel.com \
    --cc=dsahern@kernel.org \
    --cc=hch@infradead.org \
    --cc=itayavr@nvidia.com \
    --cc=jiri@nvidia.com \
    --cc=kuba@kernel.org \
    --cc=lbloch@nvidia.com \
    --cc=leon@kernel.org \
    --cc=leonro@nvidia.com \
    --cc=linux-cxl@vger.kernel.org \
    --cc=linux-doc@vger.kernel.org \
    --cc=linux-rdma@vger.kernel.org \
    --cc=netdev@vger.kernel.org \
    --cc=pabeni@redhat.com \
    --cc=patches@lists.linux.dev \
    --cc=saeedm@nvidia.com \
    --cc=tariqt@nvidia.com \
    /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.