mirror of
https://github.com/trapexit/mergerfs.git
synced 2025-04-15 15:52:40 +08:00
Update wyhash to 4.2
This commit is contained in:
parent
a9ae36a3e4
commit
fd33df04a3
@ -1,8 +1,9 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
#include <string.h>
|
||||||
|
|
||||||
#define DIRENT_NAMELEN(X) ((X)->reclen - offsetof(linux_dirent64_t,name))
|
#define DIRENT_NAMELEN(X) (strlen((X)->name))
|
||||||
|
|
||||||
typedef struct linux_dirent64_t linux_dirent64_t;
|
typedef struct linux_dirent64_t linux_dirent64_t;
|
||||||
struct linux_dirent64_t
|
struct linux_dirent64_t
|
||||||
|
83
src/wyhash.h
83
src/wyhash.h
@ -8,8 +8,8 @@
|
|||||||
uint64_t hash=wyhash(s.c_str(), s.size(), 0, _wyp);
|
uint64_t hash=wyhash(s.c_str(), s.size(), 0, _wyp);
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef wyhash_final_version_4
|
#ifndef wyhash_final_version_4_2
|
||||||
#define wyhash_final_version_4
|
#define wyhash_final_version_4_2
|
||||||
|
|
||||||
#ifndef WYHASH_CONDOM
|
#ifndef WYHASH_CONDOM
|
||||||
//protections that produce different results:
|
//protections that produce different results:
|
||||||
@ -21,7 +21,7 @@
|
|||||||
#ifndef WYHASH_32BIT_MUM
|
#ifndef WYHASH_32BIT_MUM
|
||||||
//0: normal version, slow on 32 bit systems
|
//0: normal version, slow on 32 bit systems
|
||||||
//1: faster on 32 bit systems but produces different results, incompatible with wy2u0k function
|
//1: faster on 32 bit systems but produces different results, incompatible with wy2u0k function
|
||||||
#define WYHASH_32BIT_MUM 0
|
#define WYHASH_32BIT_MUM 0
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
//includes
|
//includes
|
||||||
@ -52,7 +52,7 @@ static inline void _wymum(uint64_t *A, uint64_t *B){
|
|||||||
*A=_wyrot(hl)^hh; *B=_wyrot(lh)^ll;
|
*A=_wyrot(hl)^hh; *B=_wyrot(lh)^ll;
|
||||||
#endif
|
#endif
|
||||||
#elif defined(__SIZEOF_INT128__)
|
#elif defined(__SIZEOF_INT128__)
|
||||||
__uint128_t r=*A; r*=*B;
|
__uint128_t r=*A; r*=*B;
|
||||||
#if(WYHASH_CONDOM>1)
|
#if(WYHASH_CONDOM>1)
|
||||||
*A^=(uint64_t)r; *B^=(uint64_t)(r>>64);
|
*A^=(uint64_t)r; *B^=(uint64_t)(r>>64);
|
||||||
#else
|
#else
|
||||||
@ -123,15 +123,15 @@ static inline uint64_t wyhash(const void *key, size_t len, uint64_t seed, const
|
|||||||
else a=b=0;
|
else a=b=0;
|
||||||
}
|
}
|
||||||
else{
|
else{
|
||||||
size_t i=len;
|
size_t i=len;
|
||||||
if(_unlikely_(i>48)){
|
if(_unlikely_(i>=48)){
|
||||||
uint64_t see1=seed, see2=seed;
|
uint64_t see1=seed, see2=seed;
|
||||||
do{
|
do{
|
||||||
seed=_wymix(_wyr8(p)^secret[1],_wyr8(p+8)^seed);
|
seed=_wymix(_wyr8(p)^secret[1],_wyr8(p+8)^seed);
|
||||||
see1=_wymix(_wyr8(p+16)^secret[2],_wyr8(p+24)^see1);
|
see1=_wymix(_wyr8(p+16)^secret[2],_wyr8(p+24)^see1);
|
||||||
see2=_wymix(_wyr8(p+32)^secret[3],_wyr8(p+40)^see2);
|
see2=_wymix(_wyr8(p+32)^secret[3],_wyr8(p+40)^see2);
|
||||||
p+=48; i-=48;
|
p+=48; i-=48;
|
||||||
}while(_likely_(i>48));
|
}while(_likely_(i>=48));
|
||||||
seed^=see1^see2;
|
seed^=see1^see2;
|
||||||
}
|
}
|
||||||
while(_unlikely_(i>16)){ seed=_wymix(_wyr8(p)^secret[1],_wyr8(p+8)^seed); i-=16; p+=16; }
|
while(_unlikely_(i>16)){ seed=_wymix(_wyr8(p)^secret[1],_wyr8(p+8)^seed); i-=16; p+=16; }
|
||||||
@ -142,13 +142,13 @@ static inline uint64_t wyhash(const void *key, size_t len, uint64_t seed, const
|
|||||||
}
|
}
|
||||||
|
|
||||||
//the default secret parameters
|
//the default secret parameters
|
||||||
static const uint64_t _wyp[4] = {0xa0761d6478bd642full, 0xe7037ed1a0b428dbull, 0x8ebc6af09c88c6e3ull, 0x589965cc75374cc3ull};
|
static const uint64_t _wyp[4] = {0x2d358dccaa6c78a5ull, 0x8bb84b93962eacc9ull, 0x4b33a62ed433d4a3ull, 0x4d5a2da51de1aa47ull};
|
||||||
|
|
||||||
//a useful 64bit-64bit mix function to produce deterministic pseudo random numbers that can pass BigCrush and PractRand
|
//a useful 64bit-64bit mix function to produce deterministic pseudo random numbers that can pass BigCrush and PractRand
|
||||||
static inline uint64_t wyhash64(uint64_t A, uint64_t B){ A^=0xa0761d6478bd642full; B^=0xe7037ed1a0b428dbull; _wymum(&A,&B); return _wymix(A^0xa0761d6478bd642full,B^0xe7037ed1a0b428dbull);}
|
static inline uint64_t wyhash64(uint64_t A, uint64_t B){ A^=0x2d358dccaa6c78a5ull; B^=0x8bb84b93962eacc9ull; _wymum(&A,&B); return _wymix(A^0x2d358dccaa6c78a5ull,B^0x8bb84b93962eacc9ull);}
|
||||||
|
|
||||||
//The wyrand PRNG that pass BigCrush and PractRand
|
//The wyrand PRNG that pass BigCrush and PractRand
|
||||||
static inline uint64_t wyrand(uint64_t *seed){ *seed+=0xa0761d6478bd642full; return _wymix(*seed,*seed^0xe7037ed1a0b428dbull);}
|
static inline uint64_t wyrand(uint64_t *seed){ *seed+=0x2d358dccaa6c78a5ull; return _wymix(*seed,*seed^0x8bb84b93962eacc9ull);}
|
||||||
|
|
||||||
//convert any 64 bit pseudo random numbers to uniform distribution [0,1). It can be combined with wyrand, wyhash64 or wyhash.
|
//convert any 64 bit pseudo random numbers to uniform distribution [0,1). It can be combined with wyrand, wyhash64 or wyhash.
|
||||||
static inline double wy2u01(uint64_t r){ const double _wynorm=1.0/(1ull<<52); return (r>>12)*_wynorm;}
|
static inline double wy2u01(uint64_t r){ const double _wynorm=1.0/(1ull<<52); return (r>>12)*_wynorm;}
|
||||||
@ -173,6 +173,68 @@ static inline uint64_t wytrand(uint64_t *seed){
|
|||||||
static inline uint64_t wy2u0k(uint64_t r, uint64_t k){ _wymum(&r,&k); return k; }
|
static inline uint64_t wy2u0k(uint64_t r, uint64_t k){ _wymum(&r,&k); return k; }
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
// modified from https://github.com/going-digital/Prime64
|
||||||
|
static inline unsigned long long mul_mod(unsigned long long a, unsigned long long b, unsigned long long m) {
|
||||||
|
unsigned long long r=0;
|
||||||
|
while (b) {
|
||||||
|
if (b & 1) {
|
||||||
|
unsigned long long r2 = r + a;
|
||||||
|
if (r2 < r) r2 -= m;
|
||||||
|
r = r2 % m;
|
||||||
|
}
|
||||||
|
b >>= 1;
|
||||||
|
if (b) {
|
||||||
|
unsigned long long a2 = a + a;
|
||||||
|
if (a2 < a) a2 -= m;
|
||||||
|
a = a2 % m;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
static inline unsigned long long pow_mod(unsigned long long a, unsigned long long b, unsigned long long m) {
|
||||||
|
unsigned long long r=1;
|
||||||
|
while (b) {
|
||||||
|
if (b&1) r=mul_mod(r,a,m);
|
||||||
|
b>>=1;
|
||||||
|
if (b) a=mul_mod(a,a,m);
|
||||||
|
}
|
||||||
|
return r;
|
||||||
|
}
|
||||||
|
static inline unsigned sprp(unsigned long long n, unsigned long long a) {
|
||||||
|
unsigned long long d=n-1;
|
||||||
|
unsigned char s=0;
|
||||||
|
while (!(d & 0xff)) { d>>=8; s+=8; }
|
||||||
|
if (!(d & 0xf)) { d>>=4; s+=4; }
|
||||||
|
if (!(d & 0x3)) { d>>=2; s+=2; }
|
||||||
|
if (!(d & 0x1)) { d>>=1; s+=1; }
|
||||||
|
unsigned long long b=pow_mod(a,d,n);
|
||||||
|
if ((b==1) || (b==(n-1))) return 1;
|
||||||
|
unsigned char r;
|
||||||
|
for (r=1; r<s; r++) {
|
||||||
|
b=mul_mod(b,b,n);
|
||||||
|
if (b<=1) return 0;
|
||||||
|
if (b==(n-1)) return 1;
|
||||||
|
}
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
static inline unsigned is_prime(unsigned long long n) {
|
||||||
|
if (n<2||!(n&1)) return 0;
|
||||||
|
if (n<4) return 1;
|
||||||
|
if (!sprp(n,2)) return 0;
|
||||||
|
if (n<2047) return 1;
|
||||||
|
if (!sprp(n,3)) return 0;
|
||||||
|
if (!sprp(n,5)) return 0;
|
||||||
|
if (!sprp(n,7)) return 0;
|
||||||
|
if (!sprp(n,11)) return 0;
|
||||||
|
if (!sprp(n,13)) return 0;
|
||||||
|
if (!sprp(n,17)) return 0;
|
||||||
|
if (!sprp(n,19)) return 0;
|
||||||
|
if (!sprp(n,23)) return 0;
|
||||||
|
if (!sprp(n,29)) return 0;
|
||||||
|
if (!sprp(n,31)) return 0;
|
||||||
|
if (!sprp(n,37)) return 0;
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
//make your own secret
|
//make your own secret
|
||||||
static inline void make_secret(uint64_t seed, uint64_t *secret){
|
static inline void make_secret(uint64_t seed, uint64_t *secret){
|
||||||
uint8_t c[] = {15, 23, 27, 29, 30, 39, 43, 45, 46, 51, 53, 54, 57, 58, 60, 71, 75, 77, 78, 83, 85, 86, 89, 90, 92, 99, 101, 102, 105, 106, 108, 113, 114, 116, 120, 135, 139, 141, 142, 147, 149, 150, 153, 154, 156, 163, 165, 166, 169, 170, 172, 177, 178, 180, 184, 195, 197, 198, 201, 202, 204, 209, 210, 212, 216, 225, 226, 228, 232, 240 };
|
uint8_t c[] = {15, 23, 27, 29, 30, 39, 43, 45, 46, 51, 53, 54, 57, 58, 60, 71, 75, 77, 78, 83, 85, 86, 89, 90, 92, 99, 101, 102, 105, 106, 108, 113, 114, 116, 120, 135, 139, 141, 142, 147, 149, 150, 153, 154, 156, 163, 165, 166, 169, 170, 172, 177, 178, 180, 184, 195, 197, 198, 201, 202, 204, 209, 210, 212, 216, 225, 226, 228, 232, 240 };
|
||||||
@ -197,6 +259,7 @@ static inline void make_secret(uint64_t seed, uint64_t *secret){
|
|||||||
if(x!=32){ ok=0; break; }
|
if(x!=32){ ok=0; break; }
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
if(ok&&!is_prime(secret[i])) ok=0;
|
||||||
}while(!ok);
|
}while(!ok);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user