scrypty 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
data/ext/extconf.rb ADDED
@@ -0,0 +1,32 @@
1
+ require 'mkmf'
2
+
3
+ have_library('rt', 'clock_gettime')
4
+ have_library('crypto', 'AES_set_encrypt_key')
5
+ %w{err.h fcntl.h inttypes.h memory.h stddef.h stdint.h stdlib.h string.h strings.h sys/endian.h sys/param.h sys/stat.h sys/time.h sys/types.h termios.h unistd.h}.each do |header|
6
+ have_header(header)
7
+ end
8
+ have_type('size_t')
9
+ have_type('ssize_t')
10
+ have_type('uint32_t')
11
+ have_type('uint64_t')
12
+ have_type('uint8_t')
13
+ if have_header('sys/sysinfo.h')
14
+ if have_type('struct sysinfo', 'sys/sysinfo.h')
15
+ have_struct_member('struct sysinfo', 'mem_unit', 'sys/sysinfo.h')
16
+ have_struct_member('struct sysinfo', 'totalram', 'sys/sysinfo.h')
17
+ end
18
+ end
19
+ have_func('malloc')
20
+ have_func('mmap')
21
+ have_func('strtod')
22
+ %w{clock_gettime gettimeofday memmove memset munmap posix_memalign strcspn strdup strerror strtoumax sysinfo}.each do |func|
23
+ have_func(func)
24
+ end
25
+ have_const('be64enc')
26
+
27
+ system("sysctl hw.usermem >/dev/null 2>/dev/null")
28
+ if $?.exitstatus == 0
29
+ $defs.push("-DHAVE_SYSCTL_HW_USERMEM=1")
30
+ end
31
+ create_header
32
+ create_makefile('scrypty_ext')
data/ext/memlimit.c ADDED
@@ -0,0 +1,302 @@
1
+ /*-
2
+ * Copyright 2009 Colin Percival
3
+ * All rights reserved.
4
+ *
5
+ * Redistribution and use in source and binary forms, with or without
6
+ * modification, are permitted provided that the following conditions
7
+ * are met:
8
+ * 1. Redistributions of source code must retain the above copyright
9
+ * notice, this list of conditions and the following disclaimer.
10
+ * 2. Redistributions in binary form must reproduce the above copyright
11
+ * notice, this list of conditions and the following disclaimer in the
12
+ * documentation and/or other materials provided with the distribution.
13
+ *
14
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24
+ * SUCH DAMAGE.
25
+ *
26
+ * This file was originally written by Colin Percival as part of the Tarsnap
27
+ * online backup system.
28
+ */
29
+ #include "scrypt_platform.h"
30
+
31
+ #include <sys/types.h>
32
+ #include <sys/resource.h>
33
+
34
+ #ifdef HAVE_SYS_PARAM_H
35
+ #include <sys/param.h>
36
+ #endif
37
+ #ifdef HAVE_SYSCTL_HW_USERMEM
38
+ #include <sys/sysctl.h>
39
+ #endif
40
+ #ifdef HAVE_SYS_SYSINFO_H
41
+ #include <sys/sysinfo.h>
42
+ #endif
43
+
44
+ #include <errno.h>
45
+ #include <stddef.h>
46
+ #include <stdint.h>
47
+ #include <unistd.h>
48
+
49
+ #ifdef DEBUG
50
+ #include <stdio.h>
51
+ #endif
52
+
53
+ #include "memlimit.h"
54
+
55
+ #ifdef HAVE_SYSCTL_HW_USERMEM
56
+ static int
57
+ memlimit_sysctl_hw_usermem(size_t * memlimit)
58
+ {
59
+ int mib[2];
60
+ uint8_t usermembuf[8];
61
+ size_t usermemlen = 8;
62
+ uint64_t usermem;
63
+
64
+ /* Ask the kernel how much RAM we have. */
65
+ mib[0] = CTL_HW;
66
+ mib[1] = HW_USERMEM;
67
+ if (sysctl(mib, 2, usermembuf, &usermemlen, NULL, 0))
68
+ return (1);
69
+
70
+ /*
71
+ * Parse as either a uint64_t or a uint32_t based on the length of
72
+ * output the kernel reports having copied out. It appears that all
73
+ * systems providing a sysctl interface for reading integers copy
74
+ * them out as system-endian values, so we don't need to worry about
75
+ * parsing them.
76
+ */
77
+ if (usermemlen == sizeof(uint64_t))
78
+ usermem = *(uint64_t *)usermembuf;
79
+ else if (usermemlen == sizeof(uint32_t))
80
+ usermem = *(uint32_t *)usermembuf;
81
+ else
82
+ return (1);
83
+
84
+ /* Return the sysctl value, but clamp to SIZE_MAX if necessary. */
85
+ #if UINT64_MAX > SIZE_MAX
86
+ if (usermem > SIZE_MAX)
87
+ *memlimit = SIZE_MAX;
88
+ else
89
+ *memlimit = usermem;
90
+ #else
91
+ *memlimit = usermem;
92
+ #endif
93
+
94
+ /* Success! */
95
+ return (0);
96
+ }
97
+ #endif
98
+
99
+ /* If we don't HAVE_STRUCT_SYSINFO, we can't use sysinfo. */
100
+ #ifndef HAVE_STRUCT_SYSINFO
101
+ #undef HAVE_SYSINFO
102
+ #endif
103
+
104
+ /* If we don't HAVE_STRUCT_SYSINFO_TOTALRAM, we can't use sysinfo. */
105
+ #ifndef HAVE_STRUCT_SYSINFO_TOTALRAM
106
+ #undef HAVE_SYSINFO
107
+ #endif
108
+
109
+ #ifdef HAVE_SYSINFO
110
+ static int
111
+ memlimit_sysinfo(size_t * memlimit)
112
+ {
113
+ struct sysinfo info;
114
+ uint64_t totalmem;
115
+
116
+ /* Get information from the kernel. */
117
+ if (sysinfo(&info))
118
+ return (1);
119
+ totalmem = info.totalram;
120
+
121
+ /* If we're on a modern kernel, adjust based on mem_unit. */
122
+ #ifdef HAVE_STRUCT_SYSINFO_MEM_UNIT
123
+ totalmem = totalmem * info.mem_unit;
124
+ #endif
125
+
126
+ /* Return the value, but clamp to SIZE_MAX if necessary. */
127
+ #if UINT64_MAX > SIZE_MAX
128
+ if (totalmem > SIZE_MAX)
129
+ *memlimit = SIZE_MAX;
130
+ else
131
+ *memlimit = totalmem;
132
+ #else
133
+ *memlimit = totalmem;
134
+ #endif
135
+
136
+ /* Success! */
137
+ return (0);
138
+ }
139
+ #endif /* HAVE_SYSINFO */
140
+
141
+ static int
142
+ memlimit_rlimit(size_t * memlimit)
143
+ {
144
+ struct rlimit rl;
145
+ uint64_t memrlimit;
146
+
147
+ /* Find the least of... */
148
+ memrlimit = (uint64_t)(-1);
149
+
150
+ /* ... RLIMIT_AS... */
151
+ #ifdef RLIMIT_AS
152
+ if (getrlimit(RLIMIT_AS, &rl))
153
+ return (1);
154
+ if ((rl.rlim_cur != RLIM_INFINITY) &&
155
+ ((uint64_t)rl.rlim_cur < memrlimit))
156
+ memrlimit = rl.rlim_cur;
157
+ #endif
158
+
159
+ /* ... RLIMIT_DATA... */
160
+ if (getrlimit(RLIMIT_DATA, &rl))
161
+ return (1);
162
+ if ((rl.rlim_cur != RLIM_INFINITY) &&
163
+ ((uint64_t)rl.rlim_cur < memrlimit))
164
+ memrlimit = rl.rlim_cur;
165
+
166
+ /* ... and RLIMIT_RSS. */
167
+ #ifdef RLIMIT_RSS
168
+ if (getrlimit(RLIMIT_RSS, &rl))
169
+ return (1);
170
+ if ((rl.rlim_cur != RLIM_INFINITY) &&
171
+ ((uint64_t)rl.rlim_cur < memrlimit))
172
+ memrlimit = rl.rlim_cur;
173
+ #endif
174
+
175
+ /* Return the value, but clamp to SIZE_MAX if necessary. */
176
+ #if UINT64_MAX > SIZE_MAX
177
+ if (memrlimit > SIZE_MAX)
178
+ *memlimit = SIZE_MAX;
179
+ else
180
+ *memlimit = memrlimit;
181
+ #else
182
+ *memlimit = memrlimit;
183
+ #endif
184
+
185
+ /* Success! */
186
+ return (0);
187
+ }
188
+
189
+ #ifdef _SC_PHYS_PAGES
190
+
191
+ /* Some systems define _SC_PAGESIZE instead of _SC_PAGE_SIZE. */
192
+ #ifndef _SC_PAGE_SIZE
193
+ #define _SC_PAGE_SIZE _SC_PAGESIZE
194
+ #endif
195
+
196
+ static int
197
+ memlimit_sysconf(size_t * memlimit)
198
+ {
199
+ long pagesize;
200
+ long physpages;
201
+ uint64_t totalmem;
202
+
203
+ /* Set errno to 0 in order to distinguish "no limit" from "error". */
204
+ errno = 0;
205
+
206
+ /* Read the two limits. */
207
+ if (((pagesize = sysconf(_SC_PAGE_SIZE)) == -1) ||
208
+ ((physpages = sysconf(_SC_PHYS_PAGES)) == -1)) {
209
+ /* Did an error occur? */
210
+ if (errno != 0)
211
+ return (1);
212
+
213
+ /* If not, there is no limit. */
214
+ totalmem = (uint64_t)(-1);
215
+ } else {
216
+ /* Compute the limit. */
217
+ totalmem = (uint64_t)(pagesize) * (uint64_t)(physpages);
218
+ }
219
+
220
+ /* Return the value, but clamp to SIZE_MAX if necessary. */
221
+ #if UINT64_MAX > SIZE_MAX
222
+ if (totalmem > SIZE_MAX)
223
+ *memlimit = SIZE_MAX;
224
+ else
225
+ *memlimit = totalmem;
226
+ #else
227
+ *memlimit = totalmem;
228
+ #endif
229
+
230
+ /* Success! */
231
+ return (0);
232
+ }
233
+ #endif
234
+
235
+ int
236
+ memtouse(size_t maxmem, double maxmemfrac, size_t * memlimit)
237
+ {
238
+ size_t sysctl_memlimit, sysinfo_memlimit, rlimit_memlimit;
239
+ size_t sysconf_memlimit;
240
+ size_t memlimit_min;
241
+ size_t memavail;
242
+
243
+ /* Get memory limits. */
244
+ #ifdef HAVE_SYSCTL_HW_USERMEM
245
+ if (memlimit_sysctl_hw_usermem(&sysctl_memlimit))
246
+ return (1);
247
+ #else
248
+ sysctl_memlimit = (size_t)(-1);
249
+ #endif
250
+ #ifdef HAVE_SYSINFO
251
+ if (memlimit_sysinfo(&sysinfo_memlimit))
252
+ return (1);
253
+ #else
254
+ sysinfo_memlimit = (size_t)(-1);
255
+ #endif
256
+ if (memlimit_rlimit(&rlimit_memlimit))
257
+ return (1);
258
+ #ifdef _SC_PHYS_PAGES
259
+ if (memlimit_sysconf(&sysconf_memlimit))
260
+ return (1);
261
+ #else
262
+ sysconf_memlimit = (size_t)(-1);
263
+ #endif
264
+
265
+ #ifdef DEBUG
266
+ fprintf(stderr, "Memory limits are %zu %zu %zu %zu\n",
267
+ sysctl_memlimit, sysinfo_memlimit, rlimit_memlimit,
268
+ sysconf_memlimit);
269
+ #endif
270
+
271
+ /* Find the smallest of them. */
272
+ memlimit_min = (size_t)(-1);
273
+ if (memlimit_min > sysctl_memlimit)
274
+ memlimit_min = sysctl_memlimit;
275
+ if (memlimit_min > sysinfo_memlimit)
276
+ memlimit_min = sysinfo_memlimit;
277
+ if (memlimit_min > rlimit_memlimit)
278
+ memlimit_min = rlimit_memlimit;
279
+ if (memlimit_min > sysconf_memlimit)
280
+ memlimit_min = sysconf_memlimit;
281
+
282
+ /* Only use the specified fraction of the available memory. */
283
+ if ((maxmemfrac > 0.5) || (maxmemfrac == 0.0))
284
+ maxmemfrac = 0.5;
285
+ memavail = maxmemfrac * memlimit_min;
286
+
287
+ /* Don't use more than the specified maximum. */
288
+ if ((maxmem > 0) && (memavail > maxmem))
289
+ memavail = maxmem;
290
+
291
+ /* But always allow at least 1 MiB. */
292
+ if (memavail < 1048576)
293
+ memavail = 1048576;
294
+
295
+ #ifdef DEBUG
296
+ fprintf(stderr, "Allowing up to %zu memory to be used\n", memavail);
297
+ #endif
298
+
299
+ /* Return limit via the provided pointer. */
300
+ *memlimit = memavail;
301
+ return (0);
302
+ }
data/ext/memlimit.h ADDED
@@ -0,0 +1,42 @@
1
+ /*-
2
+ * Copyright 2009 Colin Percival
3
+ * All rights reserved.
4
+ *
5
+ * Redistribution and use in source and binary forms, with or without
6
+ * modification, are permitted provided that the following conditions
7
+ * are met:
8
+ * 1. Redistributions of source code must retain the above copyright
9
+ * notice, this list of conditions and the following disclaimer.
10
+ * 2. Redistributions in binary form must reproduce the above copyright
11
+ * notice, this list of conditions and the following disclaimer in the
12
+ * documentation and/or other materials provided with the distribution.
13
+ *
14
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
15
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
18
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
22
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
23
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
24
+ * SUCH DAMAGE.
25
+ *
26
+ * This file was originally written by Colin Percival as part of the Tarsnap
27
+ * online backup system.
28
+ */
29
+ #ifndef _MEMLIMIT_H_
30
+ #define _MEMLIMIT_H_
31
+
32
+ #include <stddef.h>
33
+
34
+ /**
35
+ * memtouse(maxmem, maxmemfrac, memlimit):
36
+ * Examine the system and return via memlimit the amount of RAM which should
37
+ * be used -- the specified fraction of the available RAM, but no more than
38
+ * maxmem, and no less than 1MiB.
39
+ */
40
+ int memtouse(size_t, double, size_t *);
41
+
42
+ #endif /* !_MEMLIMIT_H_ */
data/ext/ruby_ext.c ADDED
@@ -0,0 +1,239 @@
1
+ #include <ruby.h>
2
+ #include <stdio.h>
3
+ #include "scryptenc.h"
4
+
5
+ VALUE mScrypty;
6
+
7
+ VALUE eScryptyError;
8
+ VALUE eMemoryLimitError;
9
+ VALUE eClockTimeError;
10
+ VALUE eDerivedKeyError;
11
+ VALUE eSaltError;
12
+ VALUE eOpenSSLError;
13
+ /* Use NoMemoryError */
14
+ VALUE eInvalidBlockError;
15
+ VALUE eUnrecognizedFormatError;
16
+ VALUE eNotEnoughMemoryError;
17
+ VALUE eTooMuchTimeError;
18
+ VALUE eIncorrectPasswordError;
19
+ VALUE eWriteError;
20
+ VALUE eReadError;
21
+
22
+ /**
23
+ * Return codes from scrypt(enc|dec)_(buf|file):
24
+ * 0 success
25
+ * 1 getrlimit or sysctl(hw.usermem) failed
26
+ * 2 clock_getres or clock_gettime failed
27
+ * 3 error computing derived key
28
+ * 4 could not read salt from /dev/urandom
29
+ * 5 error in OpenSSL
30
+ * 6 malloc failed
31
+ * 7 data is not a valid scrypt-encrypted block
32
+ * 8 unrecognized scrypt format
33
+ * 9 decrypting file would take too much memory
34
+ * 10 decrypting file would take too long
35
+ * 11 password is incorrect
36
+ * 12 error writing output file
37
+ * 13 error reading input file
38
+ */
39
+ static void
40
+ raise_scrypty_error(errorcode)
41
+ int errorcode;
42
+ {
43
+ switch (errorcode) {
44
+ case 1:
45
+ rb_raise(eMemoryLimitError, "couldn't get memory limit");
46
+ break;
47
+ case 2:
48
+ rb_raise(eClockTimeError, "couldn't determine CPU speed");
49
+ break;
50
+ case 3:
51
+ rb_raise(eDerivedKeyError, "couldn't compute derived key");
52
+ break;
53
+ case 4:
54
+ rb_raise(eSaltError, "couldn't read salt from /dev/urandom");
55
+ break;
56
+ case 5:
57
+ rb_raise(eOpenSSLError, "OpenSSL error");
58
+ break;
59
+ case 6:
60
+ rb_raise(rb_eNoMemError, "couldn't allocate memory");
61
+ break;
62
+ case 7:
63
+ rb_raise(eInvalidBlockError, "data is not a valid scrypt-encrypted block");
64
+ break;
65
+ case 8:
66
+ rb_raise(eUnrecognizedFormatError, "unrecognized scrypt format");
67
+ break;
68
+ case 9:
69
+ rb_raise(eNotEnoughMemoryError, "decrypting would take too much memory");
70
+ break;
71
+ case 10:
72
+ rb_raise(eTooMuchTimeError, "decrypting would take too long");
73
+ break;
74
+ case 11:
75
+ rb_raise(eIncorrectPasswordError, "password is incorrect");
76
+ break;
77
+ case 12:
78
+ rb_raise(eWriteError, "error writing output file");
79
+ break;
80
+ case 13:
81
+ rb_raise(eReadError, "error reading input file");
82
+ break;
83
+ }
84
+ }
85
+
86
+ VALUE
87
+ scrypty_encrypt(rb_obj, rb_data, rb_password, rb_maxmem, rb_maxmemfrac, rb_maxtime)
88
+ VALUE rb_obj;
89
+ VALUE rb_data;
90
+ VALUE rb_password;
91
+ VALUE rb_maxmem;
92
+ VALUE rb_maxmemfrac;
93
+ VALUE rb_maxtime;
94
+ {
95
+ VALUE rb_out;
96
+ char *data, *password, *out;
97
+ size_t data_len, password_len, out_len, maxmem;
98
+ double maxmemfrac, maxtime;
99
+ int errorcode;
100
+
101
+ if (TYPE(rb_data) == T_STRING) {
102
+ data = RSTRING_PTR(rb_data);
103
+ data_len = (size_t) RSTRING_LEN(rb_data);
104
+ }
105
+ else {
106
+ rb_raise(rb_eTypeError, "first argument (data) must be a String");
107
+ }
108
+
109
+ if (TYPE(rb_password) == T_STRING) {
110
+ password = RSTRING_PTR(rb_password);
111
+ password_len = (size_t) RSTRING_LEN(rb_password);
112
+ }
113
+ else {
114
+ rb_raise(rb_eTypeError, "second argument (password) must be a String");
115
+ }
116
+
117
+ if (TYPE(rb_maxmem) == T_FIXNUM) {
118
+ maxmem = FIX2INT(rb_maxmem);
119
+ }
120
+ else {
121
+ rb_raise(rb_eTypeError, "third argument (maxmem) must be a Fixnum");
122
+ }
123
+
124
+ if (FIXNUM_P(rb_maxmemfrac) || TYPE(rb_maxmemfrac) == T_FLOAT) {
125
+ maxmemfrac = NUM2DBL(rb_maxmemfrac);
126
+ }
127
+ else {
128
+ rb_raise(rb_eTypeError, "fourth argument (maxmemfrac) must be a Fixnum or Float");
129
+ }
130
+
131
+ if (FIXNUM_P(rb_maxtime) || TYPE(rb_maxtime) == T_FLOAT) {
132
+ maxtime = NUM2DBL(rb_maxtime);
133
+ }
134
+ else {
135
+ rb_raise(rb_eTypeError, "fifth argument (maxtime) must be a Fixnum or Float");
136
+ }
137
+
138
+ out_len = data_len + 128;
139
+ rb_out = rb_str_new(NULL, out_len);
140
+ out = RSTRING_PTR(rb_out);
141
+
142
+ errorcode = scryptenc_buf((const uint8_t *) data, data_len,
143
+ (uint8_t *) out, (const uint8_t *) password, password_len,
144
+ maxmem, maxmemfrac, maxtime);
145
+ if (errorcode) {
146
+ raise_scrypt_error(errorcode);
147
+ }
148
+ rb_str_set_len(rb_out, out_len);
149
+
150
+ return rb_out;
151
+ }
152
+
153
+ VALUE
154
+ scrypty_decrypt(rb_obj, rb_data, rb_password, rb_maxmem, rb_maxmemfrac, rb_maxtime)
155
+ VALUE rb_obj;
156
+ VALUE rb_data;
157
+ VALUE rb_password;
158
+ VALUE rb_maxmem;
159
+ VALUE rb_maxmemfrac;
160
+ VALUE rb_maxtime;
161
+ {
162
+ VALUE rb_out;
163
+ char *data, *password, *out;
164
+ size_t data_len, password_len, out_len, maxmem;
165
+ double maxmemfrac, maxtime;
166
+ int errorcode;
167
+
168
+ if (TYPE(rb_data) == T_STRING) {
169
+ data = RSTRING_PTR(rb_data);
170
+ data_len = (size_t) RSTRING_LEN(rb_data);
171
+ }
172
+ else {
173
+ rb_raise(rb_eTypeError, "first argument (data) must be a String");
174
+ }
175
+
176
+ if (TYPE(rb_password) == T_STRING) {
177
+ password = RSTRING_PTR(rb_password);
178
+ password_len = (size_t) RSTRING_LEN(rb_password);
179
+ }
180
+ else {
181
+ rb_raise(rb_eTypeError, "second argument (password) must be a String");
182
+ }
183
+
184
+ if (TYPE(rb_maxmem) == T_FIXNUM) {
185
+ maxmem = FIX2INT(rb_maxmem);
186
+ }
187
+ else {
188
+ rb_raise(rb_eTypeError, "third argument (maxmem) must be a Fixnum");
189
+ }
190
+
191
+ if (FIXNUM_P(rb_maxmemfrac) || TYPE(rb_maxmemfrac) == T_FLOAT) {
192
+ maxmemfrac = NUM2DBL(rb_maxmemfrac);
193
+ }
194
+ else {
195
+ rb_raise(rb_eTypeError, "fourth argument (maxmemfrac) must be a Fixnum or Float");
196
+ }
197
+
198
+ if (FIXNUM_P(rb_maxtime) || TYPE(rb_maxtime) == T_FLOAT) {
199
+ maxtime = NUM2DBL(rb_maxtime);
200
+ }
201
+ else {
202
+ rb_raise(rb_eTypeError, "fifth argument (maxtime) must be a Fixnum or Float");
203
+ }
204
+
205
+ rb_out = rb_str_new(NULL, data_len);
206
+ out = RSTRING_PTR(rb_out);
207
+
208
+ errorcode = scryptdec_buf((const uint8_t *) data, data_len,
209
+ (uint8_t *) out, &out_len, (const uint8_t *) password, password_len,
210
+ maxmem, maxmemfrac, maxtime);
211
+ if (errorcode) {
212
+ raise_scrypty_error(errorcode);
213
+ }
214
+ rb_str_set_len(rb_out, out_len);
215
+
216
+ return rb_out;
217
+ }
218
+
219
+ void
220
+ Init_scrypty_ext(void)
221
+ {
222
+ mScrypty = rb_define_module("Scrypty");
223
+ rb_define_singleton_method(mScrypty, "encrypt", scrypty_encrypt, 5);
224
+ rb_define_singleton_method(mScrypty, "decrypt", scrypty_decrypt, 5);
225
+
226
+ eScryptyError = rb_define_class_under(mScrypty, "Exception", rb_eException);
227
+ eMemoryLimitError = rb_define_class_under(mScrypty, "MemoryLimitError", eScryptyError);
228
+ eClockTimeError = rb_define_class_under(mScrypty, "ClockTimeError", eScryptyError);
229
+ eDerivedKeyError = rb_define_class_under(mScrypty, "DerivedKeyError", eScryptyError);
230
+ eSaltError = rb_define_class_under(mScrypty, "SaltError", eScryptyError);
231
+ eOpenSSLError = rb_define_class_under(mScrypty, "OpenSSLError", eScryptyError);
232
+ eInvalidBlockError = rb_define_class_under(mScrypty, "InvalidBlockError", eScryptyError);
233
+ eUnrecognizedFormatError = rb_define_class_under(mScrypty, "UnrecognizedFormatError", eScryptyError);
234
+ eNotEnoughMemoryError = rb_define_class_under(mScrypty, "NotEnoughMemoryError", eScryptyError);
235
+ eTooMuchTimeError = rb_define_class_under(mScrypty, "TooMuchTimeError", eScryptyError);
236
+ eIncorrectPasswordError = rb_define_class_under(mScrypty, "IncorrectPasswordError", eScryptyError);
237
+ eWriteError = rb_define_class_under(mScrypty, "WriteError", eScryptyError);
238
+ eReadError = rb_define_class_under(mScrypty, "ReadError", eScryptyError);
239
+ }
@@ -0,0 +1,6 @@
1
+ #ifndef _SCRYPT_PLATFORM_H_
2
+ #define _SCRYPT_PLATFORM_H_
3
+
4
+ #include "extconf.h"
5
+
6
+ #endif /* !_SCRYPT_PLATFORM_H_ */