On Fri, Nov 16, 2018 at 05:59:19PM +1100, NeilBrown wrote: > > NULLS_MARKER assumes a hash value in which the bottom bits are most > likely to be unique. To convert this to a pointer which certainly not > valid, it shifts left by 1 and sets the lsb. > We aren't passing a hash value, but are passing an address instead. > In this case the bottom 2 bits are certain to be 0, and the top bit > could contain valuable information (on a 32bit system). > The best way to turn a pointer into a certainly-invalid pointer > is to just set the lsb. By shifting right by one, we discard an > uninteresting bit, preserve all the interesting bits, and effectively > just set the lsb. > > I could add a comment explaining that if you like.
The top-bit is most likely to be fixed and offer no real value. > >> diff --git a/lib/rhashtable.c b/lib/rhashtable.c > >> index 30526afa8343..852ffa5160f1 100644 > >> --- a/lib/rhashtable.c > >> +++ b/lib/rhashtable.c > >> @@ -1179,8 +1179,7 @@ struct rhash_head __rcu **rht_bucket_nested(const > >> struct bucket_table *tbl, > >> unsigned int hash) > >> { > >> const unsigned int shift = PAGE_SHIFT - ilog2(sizeof(void *)); > >> - static struct rhash_head __rcu *rhnull = > >> - (struct rhash_head __rcu *)NULLS_MARKER(0); > >> + static struct rhash_head __rcu *rhnull; > > > > I don't understand why you can't continue to do NULLS_MARKER(0) or > > RHT_NULLS_MARKER(0). > > Because then the test > > + } while (he != RHT_NULLS_MARKER(head)); > > in __rhashtable_lookup() would always succeed, and it would loop > forever. This change is only necessary because of your shifting change above, which AFAICS adds no real benefit. Cheers, -- Email: Herbert Xu <herb...@gondor.apana.org.au> Home Page: http://gondor.apana.org.au/~herbert/ PGP Key: http://gondor.apana.org.au/~herbert/pubkey.txt