sysrandom 1.0.0-java

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: e24cd46b6417b143899bcec5491ded930fdff1b9
4
+ data.tar.gz: b4c37eded4ec30f2860538b3db047f3b12b5db78
5
+ SHA512:
6
+ metadata.gz: d91f8eb67cfa6c2a070fd06e7e15de5379e172d33d248eecce50e592fc8b1ebf1ab9d0bc22cfaef5380c34da9b8a8f979ee466406ece07270c158bead8976ee9
7
+ data.tar.gz: 708ede372c5493228dcdc63237c398a814df9b4ce47baac08dce981397346f945580cf29931c1dcd6cac2ff9afdb0c07b3d3ae208ae6e519499e3fe630ca40f6
data/.gitignore ADDED
@@ -0,0 +1,12 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /Gemfile.lock
4
+ /_yardoc/
5
+ /coverage/
6
+ /doc/
7
+ /pkg/
8
+ /spec/reports/
9
+ /tmp/
10
+ *.so
11
+ *.bundle
12
+ *.dll
data/.rspec ADDED
@@ -0,0 +1,2 @@
1
+ --format documentation
2
+ --color
data/.rubocop.yml ADDED
@@ -0,0 +1,34 @@
1
+ AllCops:
2
+ DisplayCopNames: true
3
+
4
+ #
5
+ # Style
6
+ #
7
+
8
+ LineLength:
9
+ Max: 128
10
+
11
+ Style/StringLiterals:
12
+ EnforcedStyle: double_quotes
13
+
14
+ Style/SpaceBeforeFirstArg:
15
+ Enabled: false
16
+
17
+ Style/ConditionalAssignment:
18
+ Enabled: false
19
+
20
+ #
21
+ # Metrics
22
+ #
23
+
24
+ Metrics/MethodLength:
25
+ Max: 22
26
+
27
+ Metrics/AbcSize:
28
+ Max: 20
29
+
30
+ AllCops:
31
+ Include:
32
+ - '**/Rakefile'
33
+ Exclude:
34
+ - 'spec/**/*'
data/.travis.yml ADDED
@@ -0,0 +1,9 @@
1
+ sudo: false
2
+ language: ruby
3
+ rvm:
4
+ - 2.0
5
+ - 2.1
6
+ - 2.2
7
+ - 2.3.1
8
+ - jruby-9.1.1.0
9
+ before_install: gem install bundler -v 1.12.3
data/CHANGES.md ADDED
@@ -0,0 +1,3 @@
1
+ ## 1.0.0 (2016-05-28)
2
+
3
+ * Initial release.
data/Gemfile ADDED
@@ -0,0 +1,10 @@
1
+ source "https://rubygems.org"
2
+
3
+ gemspec
4
+
5
+ group :development, :test do
6
+ gem "rake"
7
+ gem "rake-compiler"
8
+ gem "rspec"
9
+ gem "rubocop", "= 0.40.0"
10
+ end
data/LICENSE.txt ADDED
@@ -0,0 +1,15 @@
1
+ Copyright (c) 2013-2016
2
+ Frank Denis <j at pureftpd dot org>
3
+ Tony Arcieri <bascule at gmail dot com>
4
+
5
+ Permission to use, copy, modify, and/or distribute this software for any
6
+ purpose with or without fee is hereby granted, provided that the above
7
+ copyright notice and this permission notice appear in all copies.
8
+
9
+ THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10
+ WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11
+ MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12
+ ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13
+ WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14
+ ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15
+ OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
data/README.md ADDED
@@ -0,0 +1,112 @@
1
+ # Sysrandom
2
+
3
+ [![Gem Version](https://badge.fury.io/rb/sysrandom.svg)](https://rubygems.org/gems/sysrandom)
4
+ [![Build Status](https://secure.travis-ci.org/cryptosphere/sysrandom.svg?branch=master)](https://travis-ci.org/cryptosphere/sysrandom)
5
+ [![ISC licensed](https://img.shields.io/badge/license-ISC-blue.svg)](https://github.com/cryptosphere/sysrandom/blob/master/LICENSE.txt)
6
+
7
+ Secure random number generation for Ruby using system RNG facilities e.g. `/dev/urandom`, `getrandom(2)`
8
+
9
+ ## Description
10
+
11
+ [Concerns have been raised][concerns] about the current implementation of Ruby's built-in
12
+ `SecureRandom` functionality, as it presently leverages the poorly reputed OpenSSL RNG.
13
+
14
+ In cryptography circles, [the prevailing advice is to use OS RNG functionality][/dev/urandom],
15
+ namely `/dev/urandom` or equivalent calls which use an OS-level CSPRNG to
16
+ produce random numbers.
17
+
18
+ This gem provides an easy-to-install repackaging of the `randombytes`
19
+ functionality from [libsodium] for the purpose of generating secure random
20
+ numbers trustworthy for use in cryptographic contexts, such as generating
21
+ cryptographic keys, initialization vectors, or nonces.
22
+
23
+ The following random number generators are utilized:
24
+
25
+ | OS | RNG |
26
+ |---------|-------------------------------------------------------------------|
27
+ | Linux | [getrandom(2)] if available, otherwise [/dev/urandom] |
28
+ | Windows | [RtlGenRandom] |
29
+ | OpenBSD | [arc4random(3)] with ChaCha20 CSPRNG (not RC4) |
30
+ | JRuby | [SecureRandom.getInstanceStrong] if available, otherwise SHA1PRNG |
31
+ | Others | [/dev/urandom] |
32
+
33
+ [concerns]: https://bugs.ruby-lang.org/issues/9569
34
+ [libsodium]: https://github.com/jedisct1/libsodium
35
+ [getrandom(2)]: http://man7.org/linux/man-pages/man2/getrandom.2.html
36
+ [/dev/urandom]: http://sockpuppet.org/blog/2014/02/25/safely-generate-random-numbers/
37
+ [RtlGenRandom]: https://msdn.microsoft.com/en-us/library/windows/desktop/aa387694(v=vs.85).aspx
38
+ [arc4random(3)]: http://man.openbsd.org/arc4random.3
39
+ [SecureRandom.getInstanceStrong]: https://docs.oracle.com/javase/8/docs/api/java/security/SecureRandom.html#getInstanceStrong--
40
+
41
+ ## Supported Platforms
42
+
43
+ Sysrandom is tested on the following Ruby implementations:
44
+
45
+ * Ruby (MRI) 2.0, 2.1, 2.2, 2.3
46
+ * JRuby 9.1.1.0
47
+
48
+ ## Installation
49
+
50
+ Add this line to your application's Gemfile:
51
+
52
+ ```ruby
53
+ gem 'sysrandom'
54
+ ```
55
+
56
+ And then execute:
57
+
58
+ $ bundle
59
+
60
+ Or install it yourself as:
61
+
62
+ $ gem install sysrandom
63
+
64
+ ## Usage
65
+
66
+ `Sysrandom` aims to be API-compatible with Ruby's built-in `SecureRandom` class,
67
+ but always prefers OS-level RNG wherever it's available:
68
+
69
+ ```ruby
70
+ >> Sysrandom.random_number(42)
71
+ => 15
72
+ >> Sysrandom.random_bytes(32)
73
+ => "\xD6J\xB3\xD2\x8B\x7F*9D\xB7\xF9\xEA\xE2\\\xAAH\tV#\xEC\x84\xE3E\r\x97\xB9\b\xFCH\x17\xA0\v"
74
+ >> Sysrandom.base64(32)
75
+ => "WXPkxfAuLRpnI6Z4zFb4E+MIenx6w6vKhe01+rMPuIQ="
76
+ >> Sysrandom.urlsafe_base64(32)
77
+ => "37rsMfR4X8g7Bb-uDJEekRHnB3r_7nO03cv52ilaWqE="
78
+ >> Sysrandom.hex(32)
79
+ => "c950496ce200abf7d18eb1414e9206c6335f971a37d0394114f56439b59831ba"
80
+ >> Sysrandom.uuid
81
+ => "391c6f52-8017-4838-9790-131a9b979c63"
82
+ ```
83
+
84
+ * [SecureRandom API docs](http://ruby-doc.org/stdlib-2.0.0/libdoc/securerandom/rdoc/SecureRandom.html)
85
+
86
+ ## Patching SecureRandom with Sysrandom
87
+
88
+ Since Sysrandom is SecureRandom-compatible, it can be patched in-place of
89
+ SecureRandom if you prefer its RNG behavior.
90
+
91
+ To do this, require `sysrandom/securerandom`:
92
+
93
+ ```ruby
94
+ >> SecureRandom
95
+ => SecureRandom
96
+ >> require "sysrandom/securerandom"
97
+ => true
98
+ >> SecureRandom
99
+ => Sysrandom
100
+ >> SecureRandom.hex(32)
101
+ => "d1bbe8c1ab78fc2fe514c5623d913a27ffd2dcdc9e002f3b358bb01a996962f1"
102
+ ```
103
+
104
+ ## Contributing
105
+
106
+ * Fork this repository on Github
107
+ * Make your changes and send a pull request
108
+ * If your changes look good, we'll merge them
109
+
110
+ ## Copyright
111
+
112
+ Copyright (c) 2013-2016 Frank Denis, Tony Arcieri. See LICENSE.txt for further details.
data/Rakefile ADDED
@@ -0,0 +1,21 @@
1
+ require "bundler/gem_tasks"
2
+ require "rspec/core/rake_task"
3
+ require "rubocop/rake_task"
4
+ require "rake/clean"
5
+
6
+ unless defined? JRUBY_VERSION
7
+ require "rake/extensiontask"
8
+ Rake::ExtensionTask.new("sysrandom_ext") do |ext|
9
+ ext.ext_dir = "ext/sysrandom"
10
+ end
11
+ end
12
+
13
+ RSpec::Core::RakeTask.new(:spec)
14
+ RuboCop::RakeTask.new
15
+
16
+ default_tasks = %w(spec rubocop)
17
+ default_tasks.unshift("compile") unless defined?(JRUBY_VERSION)
18
+
19
+ task default: default_tasks
20
+
21
+ CLEAN.include "**/*.o", "**/*.so", "**/*.bundle", "pkg", "tmp"
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "sysrandom"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start
data/bin/setup ADDED
@@ -0,0 +1,8 @@
1
+ #!/usr/bin/env bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+ set -vx
5
+
6
+ bundle install
7
+
8
+ # Do any other automated setup that you need to do here
@@ -0,0 +1,4 @@
1
+ require "mkmf"
2
+
3
+ dir_config "sysrandom_ext"
4
+ create_makefile "sysrandom_ext"
@@ -0,0 +1,275 @@
1
+ /*
2
+ * __randombytes_sysrandom.c: adapted from libsodium
3
+ * Copyright (c) 2013-2016 Frank Denis <j at pureftpd dot org>
4
+ * https://github.com/jedisct1/libsodium
5
+ */
6
+
7
+ #include <stdlib.h>
8
+ #include <sys/types.h>
9
+ #ifndef _WIN32
10
+ # include <sys/stat.h>
11
+ # include <sys/time.h>
12
+ #endif
13
+ #ifdef __linux__
14
+ # include <sys/syscall.h>
15
+ #endif
16
+
17
+ #include <assert.h>
18
+ #include <errno.h>
19
+ #include <fcntl.h>
20
+ #include <limits.h>
21
+ #include <stdint.h>
22
+ #include <string.h>
23
+ #ifndef _WIN32
24
+ # include <unistd.h>
25
+ #endif
26
+
27
+ #ifdef _WIN32
28
+ # include <windows.h>
29
+ # define RtlGenRandom SystemFunction036
30
+ # if defined(__cplusplus)
31
+ extern "C"
32
+ # endif
33
+ BOOLEAN NTAPI RtlGenRandom(PVOID RandomBuffer, ULONG RandomBufferLength);
34
+ # pragma comment(lib, "advapi32.lib")
35
+ #endif
36
+
37
+ #if defined(__OpenBSD__) || defined(__CloudABI__)
38
+ # define HAVE_SAFE_ARC4RANDOM 1
39
+ #endif
40
+
41
+ #ifndef SSIZE_MAX
42
+ # define SSIZE_MAX (SIZE_MAX / 2 - 1)
43
+ #endif
44
+
45
+ #ifdef HAVE_SAFE_ARC4RANDOM
46
+
47
+ uint32_t
48
+ __randombytes_sysrandom(void)
49
+ {
50
+ return arc4random();
51
+ }
52
+
53
+ static void
54
+ __randombytes_sysrandom_stir(void)
55
+ {
56
+ }
57
+
58
+ void
59
+ __randombytes_sysrandom_buf(void * const buf, const size_t size)
60
+ {
61
+ return arc4random_buf(buf, size);
62
+ }
63
+
64
+ #else /* __OpenBSD__ */
65
+
66
+ typedef struct SysRandom_ {
67
+ int random_data_source_fd;
68
+ int initialized;
69
+ int getrandom_available;
70
+ } SysRandom;
71
+
72
+ static SysRandom stream = {
73
+ .random_data_source_fd = -1,
74
+ .initialized = 0,
75
+ .getrandom_available = 0
76
+ };
77
+
78
+ #ifndef _WIN32
79
+ static ssize_t
80
+ safe_read(const int fd, void * const buf_, size_t size)
81
+ {
82
+ unsigned char *buf = (unsigned char *) buf_;
83
+ ssize_t readnb;
84
+
85
+ assert(size > (size_t) 0U);
86
+ assert(size <= SSIZE_MAX);
87
+ do {
88
+ while ((readnb = read(fd, buf, size)) < (ssize_t) 0 &&
89
+ (errno == EINTR || errno == EAGAIN)); /* LCOV_EXCL_LINE */
90
+ if (readnb < (ssize_t) 0) {
91
+ return readnb; /* LCOV_EXCL_LINE */
92
+ }
93
+ if (readnb == (ssize_t) 0) {
94
+ break; /* LCOV_EXCL_LINE */
95
+ }
96
+ size -= (size_t) readnb;
97
+ buf += readnb;
98
+ } while (size > (ssize_t) 0);
99
+
100
+ return (ssize_t) (buf - (unsigned char *) buf_);
101
+ }
102
+ #endif
103
+
104
+ #ifndef _WIN32
105
+ static int
106
+ __randombytes_sysrandom_random_dev_open(void)
107
+ {
108
+ /* LCOV_EXCL_START */
109
+ struct stat st;
110
+ static const char *devices[] = {
111
+ # ifndef USE_BLOCKING_RANDOM
112
+ "/dev/urandom",
113
+ # endif
114
+ "/dev/random", NULL
115
+ };
116
+ const char ** device = devices;
117
+ int fd;
118
+
119
+ do {
120
+ fd = open(*device, O_RDONLY);
121
+ if (fd != -1) {
122
+ if (fstat(fd, &st) == 0 &&
123
+ # ifdef __COMPCERT__
124
+ 1
125
+ # elif defined(S_ISNAM)
126
+ (S_ISNAM(st.st_mode) || S_ISCHR(st.st_mode))
127
+ # else
128
+ S_ISCHR(st.st_mode)
129
+ # endif
130
+ ) {
131
+ # if defined(F_SETFD) && defined(FD_CLOEXEC)
132
+ (void) fcntl(fd, F_SETFD, fcntl(fd, F_GETFD) | FD_CLOEXEC);
133
+ # endif
134
+ return fd;
135
+ }
136
+ (void) close(fd);
137
+ } else if (errno == EINTR) {
138
+ continue;
139
+ }
140
+ device++;
141
+ } while (*device != NULL);
142
+
143
+ errno = EIO;
144
+ return -1;
145
+ /* LCOV_EXCL_STOP */
146
+ }
147
+
148
+ # ifdef SYS_getrandom
149
+ static int
150
+ _randombytes_linux_getrandom(void * const buf, const size_t size)
151
+ {
152
+ int readnb;
153
+
154
+ assert(size <= 256U);
155
+ do {
156
+ readnb = syscall(SYS_getrandom, buf, (int) size, 0);
157
+ } while (readnb < 0 && (errno == EINTR || errno == EAGAIN));
158
+
159
+ return (readnb == (int) size) - 1;
160
+ }
161
+
162
+ static int
163
+ randombytes_linux_getrandom(void * const buf_, size_t size)
164
+ {
165
+ unsigned char *buf = (unsigned char *) buf_;
166
+ size_t chunk_size = 256U;
167
+
168
+ do {
169
+ if (size < chunk_size) {
170
+ chunk_size = size;
171
+ assert(chunk_size > (size_t) 0U);
172
+ }
173
+ if (_randombytes_linux_getrandom(buf, chunk_size) != 0) {
174
+ return -1;
175
+ }
176
+ size -= chunk_size;
177
+ buf += chunk_size;
178
+ } while (size > (size_t) 0U);
179
+
180
+ return 0;
181
+ }
182
+ # endif
183
+
184
+ static void
185
+ __randombytes_sysrandom_init(void)
186
+ {
187
+ const int errno_save = errno;
188
+
189
+ # ifdef SYS_getrandom
190
+ {
191
+ unsigned char fodder[16];
192
+
193
+ if (randombytes_linux_getrandom(fodder, sizeof fodder) == 0) {
194
+ stream.getrandom_available = 1;
195
+ errno = errno_save;
196
+ return;
197
+ }
198
+ stream.getrandom_available = 0;
199
+ }
200
+ # endif
201
+
202
+ if ((stream.random_data_source_fd =
203
+ __randombytes_sysrandom_random_dev_open()) == -1) {
204
+ abort(); /* LCOV_EXCL_LINE */
205
+ }
206
+ errno = errno_save;
207
+ }
208
+
209
+ #else /* _WIN32 */
210
+
211
+ static void
212
+ __randombytes_sysrandom_init(void)
213
+ {
214
+ }
215
+ #endif
216
+
217
+ static void
218
+ __randombytes_sysrandom_stir(void)
219
+ {
220
+ if (stream.initialized == 0) {
221
+ __randombytes_sysrandom_init();
222
+ stream.initialized = 1;
223
+ }
224
+ }
225
+
226
+ static void
227
+ __randombytes_sysrandom_stir_if_needed(void)
228
+ {
229
+ if (stream.initialized == 0) {
230
+ __randombytes_sysrandom_stir();
231
+ }
232
+ }
233
+
234
+ void
235
+ __randombytes_sysrandom_buf(void * const buf, const size_t size)
236
+ {
237
+ __randombytes_sysrandom_stir_if_needed();
238
+ #ifdef ULONG_LONG_MAX
239
+ /* coverity[result_independent_of_operands] */
240
+ assert(size <= ULONG_LONG_MAX);
241
+ #endif
242
+ #ifndef _WIN32
243
+ # ifdef SYS_getrandom
244
+ if (stream.getrandom_available != 0) {
245
+ if (randombytes_linux_getrandom(buf, size) != 0) {
246
+ abort();
247
+ }
248
+ return;
249
+ }
250
+ # endif
251
+ if (stream.random_data_source_fd == -1 ||
252
+ safe_read(stream.random_data_source_fd, buf, size) != (ssize_t) size) {
253
+ abort(); /* LCOV_EXCL_LINE */
254
+ }
255
+ #else
256
+ if (size > (size_t) 0xffffffff) {
257
+ abort(); /* LCOV_EXCL_LINE */
258
+ }
259
+ if (! RtlGenRandom((PVOID) buf, (ULONG) size)) {
260
+ abort(); /* LCOV_EXCL_LINE */
261
+ }
262
+ #endif
263
+ }
264
+
265
+ uint32_t
266
+ __randombytes_sysrandom(void)
267
+ {
268
+ uint32_t r;
269
+
270
+ __randombytes_sysrandom_buf(&r, sizeof r);
271
+
272
+ return r;
273
+ }
274
+
275
+ #endif /* __OpenBSD__ */
@@ -0,0 +1,77 @@
1
+ #include "ruby.h"
2
+
3
+ /* How many bytes to generate by default, matching SecureRandom
4
+ * Why SecureRandom has a default size argument is beyond me */
5
+ #define DEFAULT_N_BYTES 16
6
+
7
+ static VALUE mSysrandom = Qnil;
8
+
9
+ static VALUE Sysrandom_random_uint32(VALUE self);
10
+ static VALUE Sysrandom_random_bytes(int argc, VALUE *argv, VALUE self);
11
+
12
+ /* From randombytes_sysrandom.c */
13
+ uint32_t __randombytes_sysrandom(void);
14
+ void __randombytes_sysrandom_buf(void * const buf, const size_t size);
15
+
16
+ void Init_sysrandom_ext()
17
+ {
18
+ mSysrandom = rb_define_module("Sysrandom");
19
+
20
+ rb_define_singleton_method(mSysrandom, "__random_uint32", Sysrandom_random_uint32, 0);
21
+ rb_define_method(mSysrandom, "__random_uint32", Sysrandom_random_uint32, 0);
22
+
23
+ rb_define_singleton_method(mSysrandom, "random_bytes", Sysrandom_random_bytes, -1);
24
+ rb_define_method(mSysrandom, "random_bytes", Sysrandom_random_bytes, -1);
25
+ }
26
+
27
+ /**
28
+ * call-seq:
29
+ * Sysrandom#__random_uint32 -> Fixnum
30
+ *
31
+ * Generates a random unsigned 32-bit integer using the OS CSPRNG
32
+ *
33
+ */
34
+ static VALUE
35
+ Sysrandom_random_uint32(VALUE self)
36
+ {
37
+ return UINT2NUM(__randombytes_sysrandom());
38
+ }
39
+
40
+ /**
41
+ * call-seq:
42
+ * Sysrandom#random_bytes(n=nil) -> String
43
+ *
44
+ * ::random_bytes generates a random binary string via the OS CSPRNG.
45
+ *
46
+ * The argument n specifies how long the resulting string should be.
47
+ *
48
+ * For compatibility with SecureRandom, if n is not specified, 16 is assumed.
49
+ *
50
+ * The resulting string may contain any byte (i.e. "x00" - "xff")
51
+ *
52
+ */
53
+ static VALUE
54
+ Sysrandom_random_bytes(int argc, VALUE * argv, VALUE self)
55
+ {
56
+ VALUE n_obj, str;
57
+ int n;
58
+
59
+ if (rb_scan_args(argc, argv, "01", &n_obj) == 1) {
60
+ n = NUM2INT(n_obj);
61
+
62
+ if(n < 0) {
63
+ rb_raise(rb_eArgError, "negative string size");
64
+ }
65
+ } else {
66
+ n = DEFAULT_N_BYTES;
67
+ }
68
+
69
+ if(n > 0) {
70
+ str = rb_str_new(0, n);
71
+ __randombytes_sysrandom_buf(RSTRING_PTR(str), n);
72
+ } else {
73
+ str = rb_str_new2("");
74
+ }
75
+
76
+ return str;
77
+ }
@@ -0,0 +1,7 @@
1
+ require "sysrandom"
2
+
3
+ # Make sure SecureRandom has been loaded before we patch it
4
+ require "securerandom"
5
+
6
+ Object.send(:remove_const, :SecureRandom)
7
+ SecureRandom = Sysrandom
@@ -0,0 +1,3 @@
1
+ module Sysrandom
2
+ VERSION = "1.0.0".freeze
3
+ end
data/lib/sysrandom.rb ADDED
@@ -0,0 +1,64 @@
1
+ require "sysrandom/version"
2
+
3
+ require "base64"
4
+
5
+ # Secure random number generation using system RNG facilities
6
+ module Sysrandom
7
+ module_function
8
+
9
+ # For some reason SecureRandom defaults to 16 bytes
10
+ DEFAULT_LENGTH = 16
11
+
12
+ if defined?(JRUBY_VERSION)
13
+ require "java"
14
+
15
+ if java.security.SecureRandom.respond_to?(:getInstanceStrong)
16
+ @_java_secure_random = java.security.SecureRandom.getInstanceStrong
17
+ else
18
+ @_java_secure_random = java.security.SecureRandom.getInstance("SHA1PRNG")
19
+ end
20
+
21
+ # Random uint32, used by random_number. The C extension provides an equivalent method
22
+ def __random_uint32
23
+ @_java_secure_random.nextLong & 0xFFFFFFFF
24
+ end
25
+
26
+ def random_bytes(n = DEFAULT_LENGTH)
27
+ raise ArgumentError, "negative string size" if n < 0
28
+
29
+ bytes = Java::byte[n].new
30
+ @_java_secure_random.nextBytes(bytes)
31
+ String.from_java_bytes(bytes)
32
+ end
33
+ else
34
+ require "sysrandom_ext"
35
+ end
36
+
37
+ def random_number(n = 0)
38
+ result = __random_uint32 / (2**32).to_f
39
+
40
+ if n <= 0
41
+ result
42
+ else
43
+ result *= n
44
+ n.is_a?(Fixnum) ? result.floor : result
45
+ end
46
+ end
47
+
48
+ def base64(n = DEFAULT_LENGTH)
49
+ Base64.encode64(random_bytes(n)).chomp
50
+ end
51
+
52
+ def urlsafe_base64(n = DEFAULT_LENGTH)
53
+ Base64.urlsafe_encode64(random_bytes(n)).chomp
54
+ end
55
+
56
+ def hex(n = DEFAULT_LENGTH)
57
+ random_bytes(n).unpack("h*").first
58
+ end
59
+
60
+ def uuid
61
+ values = SecureRandom.hex(16).match(/\A(.{8})(.{4})(.)(.{3})(.)(.{3})(.{12})\z/)
62
+ "#{values[1]}-#{values[2]}-4#{values[4]}-#{'89ab'[values[5].ord % 4]}#{values[6]}-#{values[7]}"
63
+ end
64
+ end
data/sysrandom.gemspec ADDED
@@ -0,0 +1,26 @@
1
+ lib = File.expand_path("../lib", __FILE__)
2
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
3
+ require "sysrandom/version"
4
+
5
+ Gem::Specification.new do |spec|
6
+ spec.name = "sysrandom"
7
+ spec.version = Sysrandom::VERSION
8
+ spec.authors = ["Tony Arcieri"]
9
+ spec.email = ["bascule@gmail.com"]
10
+
11
+ spec.summary = "Secure random number generation using system RNG facilities"
12
+ spec.description = "Sysrandom generates secure random numbers using /dev/urandom, getrandom(), etc"
13
+ spec.homepage = "https://github.com/cryptosphere/sysrandom"
14
+ spec.licenses = ["ISC"]
15
+
16
+ spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
17
+ spec.bindir = "exe"
18
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
19
+ spec.require_paths = ["lib"]
20
+
21
+ if defined? JRUBY_VERSION
22
+ spec.platform = "java"
23
+ else
24
+ spec.extensions = ["ext/sysrandom/extconf.rb"]
25
+ end
26
+ end
metadata ADDED
@@ -0,0 +1,62 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: sysrandom
3
+ version: !ruby/object:Gem::Version
4
+ version: 1.0.0
5
+ platform: java
6
+ authors:
7
+ - Tony Arcieri
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2016-05-29 00:00:00.000000000 Z
12
+ dependencies: []
13
+ description: Sysrandom generates secure random numbers using /dev/urandom, getrandom(), etc
14
+ email:
15
+ - bascule@gmail.com
16
+ executables: []
17
+ extensions: []
18
+ extra_rdoc_files: []
19
+ files:
20
+ - ".gitignore"
21
+ - ".rspec"
22
+ - ".rubocop.yml"
23
+ - ".travis.yml"
24
+ - CHANGES.md
25
+ - Gemfile
26
+ - LICENSE.txt
27
+ - README.md
28
+ - Rakefile
29
+ - bin/console
30
+ - bin/setup
31
+ - ext/sysrandom/extconf.rb
32
+ - ext/sysrandom/randombytes_sysrandom.c
33
+ - ext/sysrandom/sysrandom_ext.c
34
+ - lib/sysrandom.rb
35
+ - lib/sysrandom/securerandom.rb
36
+ - lib/sysrandom/version.rb
37
+ - sysrandom.gemspec
38
+ homepage: https://github.com/cryptosphere/sysrandom
39
+ licenses:
40
+ - ISC
41
+ metadata: {}
42
+ post_install_message:
43
+ rdoc_options: []
44
+ require_paths:
45
+ - lib
46
+ required_ruby_version: !ruby/object:Gem::Requirement
47
+ requirements:
48
+ - - ">="
49
+ - !ruby/object:Gem::Version
50
+ version: '0'
51
+ required_rubygems_version: !ruby/object:Gem::Requirement
52
+ requirements:
53
+ - - ">="
54
+ - !ruby/object:Gem::Version
55
+ version: '0'
56
+ requirements: []
57
+ rubyforge_project:
58
+ rubygems_version: 2.4.8
59
+ signing_key:
60
+ specification_version: 4
61
+ summary: Secure random number generation using system RNG facilities
62
+ test_files: []