Blender  V2.93
util_murmurhash.cpp
Go to the documentation of this file.
1 /*
2  * Copyright 2018 Blender Foundation
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 /* This is taken from alShaders/Cryptomatte/MurmurHash3.h:
18  *
19  * MurmurHash3 was written by Austin Appleby, and is placed in the public
20  * domain. The author hereby disclaims copyright to this source code.
21  */
22 
23 #include <stdlib.h>
24 #include <string.h>
25 
26 #include "util/util_algorithm.h"
27 #include "util/util_murmurhash.h"
28 
29 #if defined(_MSC_VER)
30 # define ROTL32(x, y) _rotl(x, y)
31 # define ROTL64(x, y) _rotl64(x, y)
32 # define BIG_CONSTANT(x) (x)
33 #else
35 {
36  return (x << r) | (x >> (32 - r));
37 }
38 # define ROTL32(x, y) rotl32(x, y)
39 # define BIG_CONSTANT(x) (x##LLU)
40 #endif
41 
43 
44 /* Block read - if your platform needs to do endian-swapping or can only
45  * handle aligned reads, do the conversion here. */
47 {
48  return p[i];
49 }
50 
51 /* Finalization mix - force all bits of a hash block to avalanche */
53 {
54  h ^= h >> 16;
55  h *= 0x85ebca6b;
56  h ^= h >> 13;
57  h *= 0xc2b2ae35;
58  h ^= h >> 16;
59  return h;
60 }
61 
62 uint32_t util_murmur_hash3(const void *key, int len, uint32_t seed)
63 {
64  const uint8_t *data = (const uint8_t *)key;
65  const int nblocks = len / 4;
66 
67  uint32_t h1 = seed;
68 
69  const uint32_t c1 = 0xcc9e2d51;
70  const uint32_t c2 = 0x1b873593;
71 
72  const uint32_t *blocks = (const uint32_t *)(data + nblocks * 4);
73 
74  for (int i = -nblocks; i; i++) {
75  uint32_t k1 = mm_hash_getblock32(blocks, i);
76 
77  k1 *= c1;
78  k1 = ROTL32(k1, 15);
79  k1 *= c2;
80 
81  h1 ^= k1;
82  h1 = ROTL32(h1, 13);
83  h1 = h1 * 5 + 0xe6546b64;
84  }
85 
86  const uint8_t *tail = (const uint8_t *)(data + nblocks * 4);
87 
88  uint32_t k1 = 0;
89 
90  switch (len & 3) {
91  case 3:
92  k1 ^= tail[2] << 16;
94  case 2:
95  k1 ^= tail[1] << 8;
97  case 1:
98  k1 ^= tail[0];
99  k1 *= c1;
100  k1 = ROTL32(k1, 15);
101  k1 *= c2;
102  h1 ^= k1;
103  }
104 
105  h1 ^= len;
106  h1 = mm_hash_fmix32(h1);
107  return h1;
108 }
109 
110 /* This is taken from the cryptomatte specification 1.0 */
112 {
113  uint32_t mantissa = hash & ((1 << 23) - 1);
114  uint32_t exponent = (hash >> 23) & ((1 << 8) - 1);
115  exponent = max(exponent, (uint32_t)1);
116  exponent = min(exponent, (uint32_t)254);
117  exponent = exponent << 23;
118  uint32_t sign = (hash >> 31);
119  sign = sign << 31;
120  uint32_t float_bits = sign | exponent | mantissa;
121  float f;
122  memcpy(&f, &float_bits, sizeof(uint32_t));
123  return f;
124 }
125 
#define ATTR_FALLTHROUGH
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint GLsizei GLsizei GLenum type _GL_VOID_RET _GL_VOID GLsizei GLenum GLenum const void *pixels _GL_VOID_RET _GL_VOID const void *pointer _GL_VOID_RET _GL_VOID GLdouble v _GL_VOID_RET _GL_VOID GLfloat v _GL_VOID_RET _GL_VOID GLint GLint i2 _GL_VOID_RET _GL_VOID GLint j _GL_VOID_RET _GL_VOID GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble GLdouble GLdouble zFar _GL_VOID_RET _GL_UINT GLdouble *equation _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLenum GLfloat *v _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLfloat *values _GL_VOID_RET _GL_VOID GLushort *values _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLenum GLdouble *params _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_BOOL GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLushort pattern _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble u2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLdouble GLdouble v2 _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLdouble GLdouble nz _GL_VOID_RET _GL_VOID GLfloat GLfloat nz _GL_VOID_RET _GL_VOID GLint GLint nz _GL_VOID_RET _GL_VOID GLshort GLshort nz _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const GLfloat *values _GL_VOID_RET _GL_VOID GLsizei const GLushort *values _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID const GLuint const GLclampf *priorities _GL_VOID_RET _GL_VOID GLdouble y _GL_VOID_RET _GL_VOID GLfloat y _GL_VOID_RET _GL_VOID GLint y _GL_VOID_RET _GL_VOID GLshort y _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLfloat GLfloat z _GL_VOID_RET _GL_VOID GLint GLint z _GL_VOID_RET _GL_VOID GLshort GLshort z _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble w _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat w _GL_VOID_RET _GL_VOID GLint GLint GLint w _GL_VOID_RET _GL_VOID GLshort GLshort GLshort w _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble y2 _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat y2 _GL_VOID_RET _GL_VOID GLint GLint GLint y2 _GL_VOID_RET _GL_VOID GLshort GLshort GLshort y2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLuint *buffer _GL_VOID_RET _GL_VOID GLdouble t _GL_VOID_RET _GL_VOID GLfloat t _GL_VOID_RET _GL_VOID GLint t _GL_VOID_RET _GL_VOID GLshort t _GL_VOID_RET _GL_VOID GLdouble GLdouble r _GL_VOID_RET _GL_VOID GLfloat GLfloat r _GL_VOID_RET _GL_VOID GLint GLint r _GL_VOID_RET _GL_VOID GLshort GLshort r _GL_VOID_RET _GL_VOID GLdouble GLdouble r
static unsigned long seed
Definition: btSoftBody.h:39
#define ccl_device_inline
#define CCL_NAMESPACE_END
double sign(double arg)
Definition: utility.h:250
#define hash
Definition: noise.c:169
#define min(a, b)
Definition: sort.c:51
unsigned int uint32_t
Definition: stdint.h:83
unsigned char uint8_t
Definition: stdint.h:81
signed char int8_t
Definition: stdint.h:78
float max
float util_hash_to_float(uint32_t hash)
uint32_t util_murmur_hash3(const void *key, int len, uint32_t seed)
ccl_device_inline uint32_t rotl32(uint32_t x, int8_t r)
CCL_NAMESPACE_BEGIN ccl_device_inline uint32_t mm_hash_getblock32(const uint32_t *p, int i)
#define ROTL32(x, y)
ccl_device_inline uint32_t mm_hash_fmix32(uint32_t h)
uint len