Source file xoshiro256plusplus_pure.ml
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
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
module LowLevel = struct
type t = int64 array
let of_int64_array a =
if Array.length a <> 4 then
invalid_arg "Xoshiro256plusplus.LowLevel.of_int64_array";
Array.copy a
let to_int64_array = Array.copy
let rotl x k =
let open Int64 in
logor (shift_left x k) (shift_right_logical x (64 - k))
let next s =
let open Int64 in
let result = Int64.add (rotl (Int64.add s.(0) s.(3)) 23) s.(0) in
let t = shift_left s.(1) 17 in
s.(2) <- logxor s.(2) s.(0);
s.(3) <- logxor s.(3) s.(1);
s.(1) <- logxor s.(1) s.(2);
s.(0) <- logxor s.(0) s.(3);
s.(2) <- logxor s.(2) t;
s.(3) <- rotl s.(3) 45;
result
let jump = [|
0x180ec6d33cfd0abaL; 0xd5a61266f0c9392cL;
0xa9582618e03fc9aaL; 0x39abdc4529b1661cL;
|]
let jump s =
let open Int64 in
let s0 = ref 0L in
let s1 = ref 0L in
let s2 = ref 0L in
let s3 = ref 0L in
for i = 0 to 4 - 1 do
for b = 0 to 64 - 1 do
if logand jump.(i) (shift_left 1L b) <> 0L then
(
s0 := logxor !s0 s.(0);
s1 := logxor !s1 s.(1);
s2 := logxor !s2 s.(2);
s3 := logxor !s3 s.(3)
);
ignore (next s)
done
done;
s.(0) <- !s0;
s.(1) <- !s1;
s.(2) <- !s2;
s.(3) <- !s3
let long_jump = [|
0x76e15d3efefdcbbfL; 0xc5004e441c522fb3L;
0x77710069854ee241L; 0x39109bb02acbe635L;
|]
let long_jump s =
let open Int64 in
let s0 = ref 0L in
let s1 = ref 0L in
let s2 = ref 0L in
let s3 = ref 0L in
for i = 0 to 4 - 1 do
for b = 0 to 64 - 1 do
if logand long_jump.(i) (shift_left 1L b) <> 0L then
(
s0 := logxor !s0 s.(0);
s1 := logxor !s1 s.(1);
s2 := logxor !s2 s.(2);
s3 := logxor !s3 s.(3)
);
ignore (next s)
done
done;
s.(0) <- !s0;
s.(1) <- !s1;
s.(2) <- !s2;
s.(3) <- !s3
end
include MakeRandom.Full64(struct
type state = int64 array
let bits = LowLevel.next
let new_state () =
Array.make 4 Int64.zero
let assign state1 state2 =
Array.blit state2 0 state1 0 4
let init_size = 4
let init state seed =
assign state seed
let default_seed = 135801055
end)