ribei...@gmail.com writes:
> I need help to implement the algorithm of my own in C language.
For C, I'd post in comp.lang.c. This group is for C++.
Since I've included C source, I've set the followup-to header to avoid a
language debate. If you reply, please honour that header.
> Someone can help me ?
>
> Here is the algorithm:
>
> Melgo a csprng by Ribeiro Alvo 2017
>
> Description
>
> a,b,c,d and n as ( 16 bit )
> i as ( 64 bit )
> n = 2**16-1
> a = Initialzed in [ 0 , n ]
> b = Initialzed in [ 0 , n ]
> c = Initialzed in [ 0 , n ]
> d = 2**13
> X[ from 0 to n ] = Initialzed with a 61 bit values
How are a, b, c and X initialised? Below, there's a hint you mean
62-bit values.
> Key-scheduling algorithm
>
> for i from 0 to n
Does i ever get to n? I.e. is the upper bound of the for inclusive or
not?
> a = 1 + [ a + c ] mod n
> b = 1 + [ b + a ] mod n
> c = 1 + [ c + b ] mod n
What do the []s mean here? Is it grouping the "mod n"? I.e.
a = 1 + ((a + c) mod n))
> X[i] = X[i] + a * b * c * d + a
Are the X[i] supposed to be reduced to being 61-bit (or 62-bit) values?
I'm guessing yes.
> endfor
>
> Pseudo-random generation algorithm
>
> i = 0
> while GeneratingOutput:
>
> i = i + 1
> X(a) = [X(a) + X(b)] mod 2**62
> a = [a + c + i] mod [n + 1]
> Output [X(a) + X(b)] mod 2**56
> b = [b + a] mod [n + 1]
> Output [X(b) + x(c)] mod 2**56
> c = [c + b] mod [n + 1]
> Output [X(c) + x(a)] mod 2**56
>
> endwhile
It would be much better to use consistent notation. Keep [] for
indexing and use () for arithmetic grouping.
It's not clear if the output refers to three separate outputs or of the
generator is to make one 168-bit number at a time. Since making three
separate 56-bit values is more interesting, that's the interpretation
I've chosen.
Here's a first draft. You need C99 or later.
#include <stdio.h>
unsigned long long csprng(void)
{
const unsigned d = 1 << 13;
const unsigned n = 0xFFFF;
const unsigned long long mask_62_bits = (1ull << 62) - 1;
const unsigned long long mask_56_bits = (1ull << 56) - 1;
static unsigned a, b, c;
static unsigned long long X[0x10000];
static int state = 0;
static unsigned long long i = 0;
switch (state) {
case 0:
if (i == 0) {
/*
* Here we want to set initial values for a, b, c an X,
* but I don't know how that is supposed to be done.
*/
for (unsigned long i = 0; i <= n; i++) {
a = 1 + ((a + c) % n);
b = 1 + ((b + a) % n);
c = 1 + ((c + b) % n);
X[i] += (unsigned long long)a * b * c * d + a;
X[i] &= mask_62_bits;
}
}
i += 1;
X[a] = (X[a] + X[b]) & mask_62_bits;
a = (a + c + i) & n;
state = 1;
return (X[a] + X[b]) & mask_56_bits;
case 1:
b = (b + a) & n;
state = 2;
return (X[b] + X[c]) & mask_56_bits;
case 2:
c = (c + b) & n;
state = 0;
return (X[c] + X[a]) & mask_56_bits;
}
}
int main(int argc, char **argv)
{
for (int i = 0; i < 100; i++)
printf("%llu\n", csprng());
}
--
Ben.