Re: [PATCH] RDMA/mlx4: Make check for invalid flags stricter

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

 



On Tue, Jul 04, 2023 at 05:07:17PM +0300, Dan Carpenter wrote:
> On Tue, Jul 04, 2023 at 04:38:41PM +0300, Leon Romanovsky wrote:
> > On Thu, Jun 29, 2023 at 09:07:37AM +0300, Dan Carpenter wrote:
> > > This code is trying to ensure that only the flags specified in the list
> > > are allowed.  The problem is that ucmd->rx_hash_fields_mask is a u64 and
> > > the flags are an enum which is treated as a u32 in this context.  That
> > > means the test doesn't check whether the highest 32 bits are zero.
> > > 
> > > Fixes: 4d02ebd9bbbd ("IB/mlx4: Fix RSS hash fields restrictions")
> > > Signed-off-by: Dan Carpenter <dan.carpenter@xxxxxxxxxx>
> > > ---
> > > The MLX4_IB_RX_HASH_INNER value is declared as
> > > "MLX4_IB_RX_HASH_INNER           = 1ULL << 31," which suggests that it
> > > should be type ULL but that doesn't work.  It will still be basically a
> > > u32.  (Enum types are weird).
> > 
> > Can you please elaborate more why enum left to be int? It is surprise to me.
> 
> Enum types are not defined very strictly in C so it's up to the
> compiler.
> 
> Clang, GCC and Sparse implement them in the same way.  They default
> to u32 unless the values can't fit, then they become whatever type fits.
> So if you have a negative, it becomes an int or a big value changes the
> type to unsigned long.
> 
> Since 1ULL < 31 fits in u32 the type is just u32.

Thanks for an explanation, I found the relevant sentence in the C
standard as well.

"The choice of type is implementation-defined, 128) but shall be
capable of representing the values of all the members of the enumeration."

Thanks

> 
> regards,
> dan carpenter
> 
> #include <stdio.h>
> 
> enum example_one {
> 	VAL = 1ULL << 31,
> };
> 
> enum example_two {
> 	NEGATIVE = -2,
> };
> 
> enum example_three {
> 	BIG = 1ULL << 32,
> };
> 
> int main(void)
> {
> 	enum example_one one = -1;
> 	enum example_two two = -1;
> 	enum example_three three = -1;
> 
> 	printf("%lu\n", sizeof(enum example_one));
> 
> 	if (one > 0)
> 		printf("one unsigned\n");
> 	if (two < 0)
> 		printf("two signed\n");
> 
> 	printf("%lu\n", sizeof(enum example_three));
> 	if (three > 0)
> 		printf("three unsigned\n");
> 
> 	return 0;
> }
> 
> 



[Index of Archives]     [Kernel Development]     [Kernel Announce]     [Kernel Newbies]     [Linux Networking Development]     [Share Photos]     [IDE]     [Security]     [Git]     [Netfilter]     [Yosemite News]     [MIPS Linux]     [ARM Linux]     [Device Mapper]

  Powered by Linux