summaryrefslogtreecommitdiff
path: root/src/protocol_decoder/http/hash.h
blob: 3688f254e9c580c6c4d79e62f06afaca03400dbc (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
#ifndef _HASH_H
#define _HASH_H

#ifdef __cpluscplus
extern "C"
{
#endif

#define HASH_JEN_MIX(a, b, c) \
    do                        \
    {                         \
        a -= b;               \
        a -= c;               \
        a ^= (c >> 13);       \
        b -= c;               \
        b -= a;               \
        b ^= (a << 8);        \
        c -= a;               \
        c -= b;               \
        c ^= (b >> 13);       \
        a -= b;               \
        a -= c;               \
        a ^= (c >> 12);       \
        b -= c;               \
        b -= a;               \
        b ^= (a << 16);       \
        c -= a;               \
        c -= b;               \
        c ^= (b >> 5);        \
        a -= b;               \
        a -= c;               \
        a ^= (c >> 3);        \
        b -= c;               \
        b -= a;               \
        b ^= (a << 10);       \
        c -= a;               \
        c -= b;               \
        c ^= (b >> 15);       \
    } while (0)

#define HASH_JEN(key, keylen, hashv)                                                                                             \
    do                                                                                                                           \
    {                                                                                                                            \
        unsigned _hj_i, _hj_j, _hj_k;                                                                                            \
        unsigned const char *_hj_key = (unsigned const char *)(key);                                                             \
        hashv = 0xfeedbeefu;                                                                                                     \
        _hj_i = _hj_j = 0x9e3779b9u;                                                                                             \
        _hj_k = (unsigned)(keylen);                                                                                              \
        while (_hj_k >= 12U)                                                                                                     \
        {                                                                                                                        \
            _hj_i += (_hj_key[0] + ((unsigned)_hj_key[1] << 8) + ((unsigned)_hj_key[2] << 16) + ((unsigned)_hj_key[3] << 24));   \
            _hj_j += (_hj_key[4] + ((unsigned)_hj_key[5] << 8) + ((unsigned)_hj_key[6] << 16) + ((unsigned)_hj_key[7] << 24));   \
            hashv += (_hj_key[8] + ((unsigned)_hj_key[9] << 8) + ((unsigned)_hj_key[10] << 16) + ((unsigned)_hj_key[11] << 24)); \
                                                                                                                                 \
            HASH_JEN_MIX(_hj_i, _hj_j, hashv);                                                                                   \
                                                                                                                                 \
            _hj_key += 12;                                                                                                       \
            _hj_k -= 12U;                                                                                                        \
        }                                                                                                                        \
        hashv += (unsigned)(keylen);                                                                                             \
        switch (_hj_k)                                                                                                           \
        {                                                                                                                        \
        case 11:                                                                                                                 \
            hashv += ((unsigned)_hj_key[10] << 24); /* FALLTHROUGH */                                                            \
        case 10:                                                                                                                 \
            hashv += ((unsigned)_hj_key[9] << 16); /* FALLTHROUGH */                                                             \
        case 9:                                                                                                                  \
            hashv += ((unsigned)_hj_key[8] << 8); /* FALLTHROUGH */                                                              \
        case 8:                                                                                                                  \
            _hj_j += ((unsigned)_hj_key[7] << 24); /* FALLTHROUGH */                                                             \
        case 7:                                                                                                                  \
            _hj_j += ((unsigned)_hj_key[6] << 16); /* FALLTHROUGH */                                                             \
        case 6:                                                                                                                  \
            _hj_j += ((unsigned)_hj_key[5] << 8); /* FALLTHROUGH */                                                              \
        case 5:                                                                                                                  \
            _hj_j += _hj_key[4]; /* FALLTHROUGH */                                                                               \
        case 4:                                                                                                                  \
            _hj_i += ((unsigned)_hj_key[3] << 24); /* FALLTHROUGH */                                                             \
        case 3:                                                                                                                  \
            _hj_i += ((unsigned)_hj_key[2] << 16); /* FALLTHROUGH */                                                             \
        case 2:                                                                                                                  \
            _hj_i += ((unsigned)_hj_key[1] << 8); /* FALLTHROUGH */                                                              \
        case 1:                                                                                                                  \
            _hj_i += _hj_key[0]; /* FALLTHROUGH */                                                                               \
        default:;                                                                                                                \
        }                                                                                                                        \
        HASH_JEN_MIX(_hj_i, _hj_j, hashv);                                                                                       \
    } while (0)

#ifdef __cpluscplus
}
#endif

#endif