// This software is in the public domain. Where that dedication is not
// recognized, you are granted a perpetual, irrevocable license to copy
// and modify this file as you see fit.
#include <cstdio>
#include <cstdint>
void gen_octaves_of_value_noise_linear(
uint32_t size,
uint32_t seed,
uint32_t octaves,
float a,
float *out)
{
if(octaves==0) return;
if(octaves>31) octaves=31;
while(size&(size-1)) size&=size-1;
if(size==0) return;
float b;
uint32_t rnd=seed;
while((size>>(octaves-1))==0) --octaves;
for(uint32_t v=0;v<size;++v)
for(uint32_t u=0;u<size;++u)
out[v*size+u]=0.0f;
b=1.0f;
for(uint32_t i=0;i<octaves;++i)
b=1.0f+a*b;
b=1.0f/b;
for(uint32_t i=0;i<octaves;++i)
{
uint32_t cursize=size>>(octaves-i-1);
uint32_t step=1<<(octaves-i-1);
// upscale step
if(i>0)
{
uint32_t mask=cursize-1;
for(uint32_t v=0;v<cursize;v+=2)
for(uint32_t u=1;u<cursize;u+=2)
out[v*step*size+u*step]=0.5f*(
out[v*step*size+((u-1)&mask)*step]+
out[v*step*size+((u+1)&mask)*step]);
for(uint32_t v=1;v<cursize;v+=2)
for(uint32_t u=0;u<cursize;++u)
out[v*step*size+u*step]=0.5f*(
out[((v-1)&mask)*step*size+u*step]+
out[((v+1)&mask)*step*size+u*step]);
}
// white noise step
for(uint32_t v=0;v<cursize;++v)
{
uint32_t index=v*step*size;
for(uint32_t u=0;u<cursize;++u)
{
float t=float(rnd)*2.32830644e-10; // 2^-32
rnd=rnd*1103515245ul+12345ul; // glibc LCG
out[index]+=b*t;
index+=step;
}
}
b*=a;
}
}
uint64_t rdtsc()
{
uint64_t ret;
asm volatile
(
"rdtsc"
:"=A"(ret)
);
return ret;
}
float image[1<<26];
int main()
{
for(uint32_t N=32;N<=8192;N*=2)
{
uint32_t octaves=7;
uint64_t tacts=rdtsc();
gen_octaves_of_value_noise_linear(N,0,7,0.73f,image);
tacts=rdtsc()-tacts;
printf("N=%d, time: %.0f tacts per texel.\n",N,double(tacts)/double(N*N));
}
for(uint32_t octaves=1;octaves<=16;++octaves)
{
uint32_t N=256;
uint64_t tacts=rdtsc();
gen_octaves_of_value_noise_linear(N,0,octaves,0.73f,image);
tacts=rdtsc()-tacts;
printf("octaves=%d, time: %.0f tacts per texel.\n",octaves,double(tacts)/double(N*N));
}
return 0;
}
Ly8gVGhpcyBzb2Z0d2FyZSBpcyBpbiB0aGUgcHVibGljIGRvbWFpbi4gV2hlcmUgdGhhdCBkZWRpY2F0aW9uIGlzIG5vdAovLyByZWNvZ25pemVkLCB5b3UgYXJlIGdyYW50ZWQgYSBwZXJwZXR1YWwsIGlycmV2b2NhYmxlIGxpY2Vuc2UgdG8gY29weQovLyBhbmQgbW9kaWZ5IHRoaXMgZmlsZSBhcyB5b3Ugc2VlIGZpdC4KCiNpbmNsdWRlIDxjc3RkaW8+CiNpbmNsdWRlIDxjc3RkaW50PgoKdm9pZCBnZW5fb2N0YXZlc19vZl92YWx1ZV9ub2lzZV9saW5lYXIoCiAgICB1aW50MzJfdCBzaXplLAogICAgdWludDMyX3Qgc2VlZCwKICAgIHVpbnQzMl90IG9jdGF2ZXMsCiAgICBmbG9hdCBhLAogICAgZmxvYXQgKm91dCkKewogICAgaWYob2N0YXZlcz09MCkgcmV0dXJuOwogICAgaWYob2N0YXZlcz4zMSkgb2N0YXZlcz0zMTsKICAgIHdoaWxlKHNpemUmKHNpemUtMSkpIHNpemUmPXNpemUtMTsKICAgIGlmKHNpemU9PTApIHJldHVybjsKICAgIGZsb2F0IGI7CiAgICB1aW50MzJfdCBybmQ9c2VlZDsKICAgIHdoaWxlKChzaXplPj4ob2N0YXZlcy0xKSk9PTApIC0tb2N0YXZlczsKICAgIGZvcih1aW50MzJfdCB2PTA7djxzaXplOysrdikKICAgICAgICBmb3IodWludDMyX3QgdT0wO3U8c2l6ZTsrK3UpCiAgICAgICAgICAgIG91dFt2KnNpemUrdV09MC4wZjsKICAgIGI9MS4wZjsKICAgIGZvcih1aW50MzJfdCBpPTA7aTxvY3RhdmVzOysraSkKICAgICAgICBiPTEuMGYrYSpiOwogICAgYj0xLjBmL2I7CiAgICBmb3IodWludDMyX3QgaT0wO2k8b2N0YXZlczsrK2kpCiAgICB7CiAgICAgICAgdWludDMyX3QgY3Vyc2l6ZT1zaXplPj4ob2N0YXZlcy1pLTEpOwogICAgICAgIHVpbnQzMl90IHN0ZXA9MTw8KG9jdGF2ZXMtaS0xKTsKICAgICAgICAvLyB1cHNjYWxlIHN0ZXAKICAgICAgICBpZihpPjApCiAgICAgICAgewogICAgICAgICAgICB1aW50MzJfdCBtYXNrPWN1cnNpemUtMTsKICAgICAgICAgICAgZm9yKHVpbnQzMl90IHY9MDt2PGN1cnNpemU7dis9MikKICAgICAgICAgICAgICAgIGZvcih1aW50MzJfdCB1PTE7dTxjdXJzaXplO3UrPTIpCiAgICAgICAgICAgICAgICAgICAgb3V0W3Yqc3RlcCpzaXplK3Uqc3RlcF09MC41ZiooCiAgICAgICAgICAgICAgICAgICAgICAgIG91dFt2KnN0ZXAqc2l6ZSsoKHUtMSkmbWFzaykqc3RlcF0rCiAgICAgICAgICAgICAgICAgICAgICAgIG91dFt2KnN0ZXAqc2l6ZSsoKHUrMSkmbWFzaykqc3RlcF0pOwogICAgICAgICAgICBmb3IodWludDMyX3Qgdj0xO3Y8Y3Vyc2l6ZTt2Kz0yKQogICAgICAgICAgICAgICAgZm9yKHVpbnQzMl90IHU9MDt1PGN1cnNpemU7Kyt1KQogICAgICAgICAgICAgICAgICAgIG91dFt2KnN0ZXAqc2l6ZSt1KnN0ZXBdPTAuNWYqKAogICAgICAgICAgICAgICAgICAgICAgICBvdXRbKCh2LTEpJm1hc2spKnN0ZXAqc2l6ZSt1KnN0ZXBdKwogICAgICAgICAgICAgICAgICAgICAgICBvdXRbKCh2KzEpJm1hc2spKnN0ZXAqc2l6ZSt1KnN0ZXBdKTsKICAgICAgICB9CiAgICAgICAgLy8gd2hpdGUgbm9pc2Ugc3RlcAogICAgICAgIGZvcih1aW50MzJfdCB2PTA7djxjdXJzaXplOysrdikKICAgICAgICB7CiAgICAgICAgICAgIHVpbnQzMl90IGluZGV4PXYqc3RlcCpzaXplOwogICAgICAgICAgICBmb3IodWludDMyX3QgdT0wO3U8Y3Vyc2l6ZTsrK3UpCiAgICAgICAgICAgIHsKICAgICAgICAgICAgICAgIGZsb2F0IHQ9ZmxvYXQocm5kKSoyLjMyODMwNjQ0ZS0xMDsgLy8gMl4tMzIKICAgICAgICAgICAgICAgIHJuZD1ybmQqMTEwMzUxNTI0NXVsKzEyMzQ1dWw7IC8vIGdsaWJjIExDRwogICAgICAgICAgICAgICAgb3V0W2luZGV4XSs9Yip0OwogICAgICAgICAgICAgICAgaW5kZXgrPXN0ZXA7CiAgICAgICAgICAgIH0KICAgICAgICB9CiAgICAgICAgYio9YTsKICAgIH0KfQoKdWludDY0X3QgcmR0c2MoKQp7CiAgICB1aW50NjRfdCByZXQ7CiAgICBhc20gdm9sYXRpbGUKICAgICgKICAgICAgICAicmR0c2MiCiAgICAgICAgOiI9QSIocmV0KQogICAgKTsKICAgIHJldHVybiByZXQ7Cn0KCmZsb2F0IGltYWdlWzE8PDI2XTsKCmludCBtYWluKCkKewogICAgZm9yKHVpbnQzMl90IE49MzI7Tjw9ODE5MjtOKj0yKQogICAgewogICAgCXVpbnQzMl90IG9jdGF2ZXM9NzsKICAgICAgICB1aW50NjRfdCB0YWN0cz1yZHRzYygpOwogICAgICAgIGdlbl9vY3RhdmVzX29mX3ZhbHVlX25vaXNlX2xpbmVhcihOLDAsNywwLjczZixpbWFnZSk7CiAgICAgICAgdGFjdHM9cmR0c2MoKS10YWN0czsKICAgICAgICBwcmludGYoIk49JWQsIHRpbWU6ICUuMGYgdGFjdHMgcGVyIHRleGVsLlxuIixOLGRvdWJsZSh0YWN0cykvZG91YmxlKE4qTikpOwogICAgfQogICAgZm9yKHVpbnQzMl90IG9jdGF2ZXM9MTtvY3RhdmVzPD0xNjsrK29jdGF2ZXMpCiAgICB7CiAgICAJdWludDMyX3QgTj0yNTY7CiAgICAgICAgdWludDY0X3QgdGFjdHM9cmR0c2MoKTsKICAgICAgICBnZW5fb2N0YXZlc19vZl92YWx1ZV9ub2lzZV9saW5lYXIoTiwwLG9jdGF2ZXMsMC43M2YsaW1hZ2UpOwogICAgICAgIHRhY3RzPXJkdHNjKCktdGFjdHM7CiAgICAgICAgcHJpbnRmKCJvY3RhdmVzPSVkLCB0aW1lOiAlLjBmIHRhY3RzIHBlciB0ZXhlbC5cbiIsb2N0YXZlcyxkb3VibGUodGFjdHMpL2RvdWJsZShOKk4pKTsKICAgIH0KICAgIHJldHVybiAwOwp9Cg==
N=32, time: 80 tacts per texel.
N=64, time: 74 tacts per texel.
N=128, time: 75 tacts per texel.
N=256, time: 75 tacts per texel.
N=512, time: 78 tacts per texel.
N=1024, time: 79 tacts per texel.
N=2048, time: 80 tacts per texel.
N=4096, time: 82 tacts per texel.
N=8192, time: 86 tacts per texel.
octaves=1, time: 50 tacts per texel.
octaves=2, time: 65 tacts per texel.
octaves=3, time: 69 tacts per texel.
octaves=4, time: 70 tacts per texel.
octaves=5, time: 71 tacts per texel.
octaves=6, time: 71 tacts per texel.
octaves=7, time: 71 tacts per texel.
octaves=8, time: 71 tacts per texel.
octaves=9, time: 71 tacts per texel.
octaves=10, time: 71 tacts per texel.
octaves=11, time: 71 tacts per texel.
octaves=12, time: 71 tacts per texel.
octaves=13, time: 71 tacts per texel.
octaves=14, time: 71 tacts per texel.
octaves=15, time: 71 tacts per texel.
octaves=16, time: 71 tacts per texel.