Re: [PATCH net-next 2/4] netconsole: Add option to auto-populate CPU number in userdata

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

 



Hello Jakub,

On Mon, Nov 18, 2024 at 06:33:36PM -0800, Jakub Kicinski wrote:
> Sorry for the late review, I think this will miss v6.13 :(

That is fine, there is no rush for this change.

> On Wed, 13 Nov 2024 07:10:53 -0800 Breno Leitao wrote:
> >  /**
> >   * struct netconsole_target - Represents a configured netconsole target.
> >   * @list:	Links this target into the target_list.
> > @@ -97,6 +105,7 @@ static struct console netconsole_ext;
> >   * @userdata_group:	Links to the userdata configfs hierarchy
> >   * @userdata_complete:	Cached, formatted string of append
> >   * @userdata_length:	String length of userdata_complete
> > + * @userdata_auto:	Kernel auto-populated bitwise fields in userdata.
> >   * @enabled:	On / off knob to enable / disable target.
> >   *		Visible from userspace (read-write).
> >   *		We maintain a strict 1:1 correspondence between this and
> > @@ -123,6 +132,7 @@ struct netconsole_target {
> >  	struct config_group	userdata_group;
> >  	char userdata_complete[MAX_USERDATA_ENTRY_LENGTH * MAX_USERDATA_ITEMS];
> >  	size_t			userdata_length;
> > +	enum userdata_auto	userdata_auto;
> 
> If you want to set multiple bits here type should probably be unsigned
> long. Otherwise the enum will contain combination of its values, which
> are in themselves not valid enum values ... if that makes sense.

Yes, it does make sense. I had the feeling that something was off as
well, but I was unclear if using something different than `enum
userdata_auto` would be better. I will change to `unsigned long`
> 
> >  #endif
> >  	bool			enabled;
> >  	bool			extended;
> 
> > +	/* Check if CPU NR should be populated, and append it to the user
> > +	 * dictionary.
> > +	 */
> > +	if (child_count < MAX_USERDATA_ITEMS && nt->userdata_auto & AUTO_CPU_NR)
> > +		scnprintf(&nt->userdata_complete[complete_idx],
> > +			  MAX_USERDATA_ENTRY_LENGTH, " cpu=%u\n",
> > +			  raw_smp_processor_id());
> 
> I guess it may be tricky for backward compat, but shouldn't we return
> an error rather than silently skip?

yes, this should be easy to do, in fact. Probably return -E2BIG to
userspace when trying to update the entry. I thought about something as
the following patch, and piggy-back into it.

   Author: Breno Leitao <leitao@xxxxxxxxxx>
   Date:   Tue Nov 19 04:32:56 2024 -0800
   
       netconsole: Enforce userdata entry limit
   
       Currently, attempting to add more than MAX_USERDATA_ITEMS to the userdata
       dictionary silently fails. This patch modifies the code to return -E2BIG
       when the number of elements exceeds the preallocated limit, providing clear
       feedback to userspace about the failure.
   
       Suggested-by: Jakub Kicinski <kuba@xxxxxxxxxx>
       Signed-off-by: Breno Leitao <leitao@xxxxxxxxxx>
   
   diff --git a/drivers/net/netconsole.c b/drivers/net/netconsole.c
   index 4ea44a2f48f7b..41cff8c8e8f42 100644
   --- a/drivers/net/netconsole.c
   +++ b/drivers/net/netconsole.c
   @@ -692,10 +692,11 @@ static ssize_t userdatum_value_show(struct config_item *item, char *buf)
    	return sysfs_emit(buf, "%s\n", &(to_userdatum(item)->value[0]));
    }
   
   -static void update_userdata(struct netconsole_target *nt)
   +static int update_userdata(struct netconsole_target *nt)
    {
    	int complete_idx = 0, child_count = 0;
    	struct list_head *entry;
   +	int ret = 0;
   
    	/* Clear the current string in case the last userdatum was deleted */
    	nt->userdata_length = 0;
   @@ -705,8 +706,10 @@ static void update_userdata(struct netconsole_target *nt)
    		struct userdatum *udm_item;
    		struct config_item *item;
   
   -		if (child_count >= MAX_USERDATA_ITEMS)
   +		if (child_count >= MAX_USERDATA_ITEMS) {
   +			ret = -E2BIG;
    			break;
   +		}
    		child_count++;
   
    		item = container_of(entry, struct config_item, ci_entry);
   @@ -726,6 +729,7 @@ static void update_userdata(struct netconsole_target *nt)
    	}
    	nt->userdata_length = strnlen(nt->userdata_complete,
    				      sizeof(nt->userdata_complete));
   +	return ret;
    }
   
    static ssize_t userdatum_value_store(struct config_item *item, const char *buf,
   @@ -748,8 +752,9 @@ static ssize_t userdatum_value_store(struct config_item *item, const char *buf,
   
    	ud = to_userdata(item->ci_parent);
    	nt = userdata_to_target(ud);
   -	update_userdata(nt);
   -	ret = count;
   +	ret = update_userdata(nt);
   +	if (!ret)
   +		ret = count;
    out_unlock:
    	mutex_unlock(&dynamic_netconsole_mutex);
    	return ret;
   

> 
> >  	nt->userdata_length = strnlen(nt->userdata_complete,
> >  				      sizeof(nt->userdata_complete));
> >  }
> > @@ -757,7 +788,36 @@ static ssize_t userdatum_value_store(struct config_item *item, const char *buf,
> >  	return ret;
> >  }
> >  
> > +static ssize_t populate_cpu_nr_store(struct config_item *item, const char *buf,
> > +				     size_t count)
> > +{
> > +	struct netconsole_target *nt = to_target(item->ci_parent);
> > +	bool cpu_nr_enabled;
> > +	ssize_t ret;
> > +
> > +	if (!nt)
> > +		return -EINVAL;
> 
> Can this happen? Only if function gets called with a NULL @item
> which would be pretty nutty.

Probably not. It is just me being chicken here. I will remove it for the
next version.

Thanks for the review,
--breno




[Index of Archives]     [Linux Wireless]     [Linux Kernel]     [ATH6KL]     [Linux Bluetooth]     [Linux Netdev]     [Kernel Newbies]     [Share Photos]     [IDE]     [Security]     [Git]     [Netfilter]     [Bugtraq]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux ATA RAID]     [Samba]     [Device Mapper]

  Powered by Linux