rubysl-openssl 2.10 → 2.11
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.
- checksums.yaml +5 -5
- data/ext/rubysl/openssl/deprecation.rb +7 -3
- data/ext/rubysl/openssl/extconf.rb +148 -103
- data/ext/rubysl/openssl/openssl_missing.c +94 -275
- data/ext/rubysl/openssl/openssl_missing.h +167 -98
- data/ext/rubysl/openssl/ossl.c +266 -212
- data/ext/rubysl/openssl/ossl.h +27 -89
- data/ext/rubysl/openssl/ossl_asn1.c +157 -221
- data/ext/rubysl/openssl/ossl_asn1.h +11 -3
- data/ext/rubysl/openssl/ossl_bio.c +10 -40
- data/ext/rubysl/openssl/ossl_bio.h +1 -2
- data/ext/rubysl/openssl/ossl_bn.c +144 -100
- data/ext/rubysl/openssl/ossl_bn.h +3 -1
- data/ext/rubysl/openssl/ossl_cipher.c +270 -195
- data/ext/rubysl/openssl/ossl_config.c +7 -1
- data/ext/rubysl/openssl/ossl_config.h +0 -1
- data/ext/rubysl/openssl/ossl_digest.c +40 -29
- data/ext/rubysl/openssl/ossl_engine.c +23 -62
- data/ext/rubysl/openssl/ossl_hmac.c +82 -55
- data/ext/rubysl/openssl/ossl_ns_spki.c +22 -22
- data/ext/rubysl/openssl/ossl_ocsp.c +894 -144
- data/ext/rubysl/openssl/ossl_ocsp.h +1 -1
- data/ext/rubysl/openssl/ossl_pkcs12.c +47 -19
- data/ext/rubysl/openssl/ossl_pkcs5.c +7 -15
- data/ext/rubysl/openssl/ossl_pkcs7.c +38 -15
- data/ext/rubysl/openssl/ossl_pkey.c +151 -99
- data/ext/rubysl/openssl/ossl_pkey.h +123 -29
- data/ext/rubysl/openssl/ossl_pkey_dh.c +143 -92
- data/ext/rubysl/openssl/ossl_pkey_dsa.c +149 -104
- data/ext/rubysl/openssl/ossl_pkey_ec.c +646 -524
- data/ext/rubysl/openssl/ossl_pkey_rsa.c +180 -121
- data/ext/rubysl/openssl/ossl_rand.c +25 -21
- data/ext/rubysl/openssl/ossl_ssl.c +795 -413
- data/ext/rubysl/openssl/ossl_ssl.h +3 -0
- data/ext/rubysl/openssl/ossl_ssl_session.c +83 -77
- data/ext/rubysl/openssl/ossl_version.h +1 -1
- data/ext/rubysl/openssl/ossl_x509.c +92 -8
- data/ext/rubysl/openssl/ossl_x509.h +14 -5
- data/ext/rubysl/openssl/ossl_x509attr.c +77 -41
- data/ext/rubysl/openssl/ossl_x509cert.c +45 -46
- data/ext/rubysl/openssl/ossl_x509crl.c +51 -57
- data/ext/rubysl/openssl/ossl_x509ext.c +39 -33
- data/ext/rubysl/openssl/ossl_x509name.c +68 -45
- data/ext/rubysl/openssl/ossl_x509req.c +32 -38
- data/ext/rubysl/openssl/ossl_x509revoked.c +43 -9
- data/ext/rubysl/openssl/ossl_x509store.c +309 -104
- data/ext/rubysl/openssl/ruby_missing.h +8 -6
- data/lib/openssl/buffering.rb +11 -5
- data/lib/openssl/cipher.rb +23 -15
- data/lib/openssl/digest.rb +7 -10
- data/lib/openssl/pkey.rb +15 -8
- data/lib/openssl/ssl.rb +81 -105
- data/lib/rubysl/openssl.rb +1 -4
- data/lib/rubysl/openssl/version.rb +1 -1
- metadata +3 -4
@@ -6,17 +6,6 @@
|
|
6
6
|
|
7
7
|
#if !defined(OPENSSL_NO_EC) && (OPENSSL_VERSION_NUMBER >= 0x0090802fL)
|
8
8
|
|
9
|
-
typedef struct {
|
10
|
-
EC_GROUP *group;
|
11
|
-
int dont_free;
|
12
|
-
} ossl_ec_group;
|
13
|
-
|
14
|
-
typedef struct {
|
15
|
-
EC_POINT *point;
|
16
|
-
int dont_free;
|
17
|
-
} ossl_ec_point;
|
18
|
-
|
19
|
-
|
20
9
|
#define EXPORT_PEM 0
|
21
10
|
#define EXPORT_DER 1
|
22
11
|
|
@@ -25,70 +14,43 @@ static const rb_data_type_t ossl_ec_point_type;
|
|
25
14
|
|
26
15
|
#define GetPKeyEC(obj, pkey) do { \
|
27
16
|
GetPKey((obj), (pkey)); \
|
28
|
-
if (
|
17
|
+
if (EVP_PKEY_base_id(pkey) != EVP_PKEY_EC) { \
|
29
18
|
ossl_raise(rb_eRuntimeError, "THIS IS NOT A EC PKEY!"); \
|
30
19
|
} \
|
31
20
|
} while (0)
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
} while(0)
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
GetPKeyEC((obj), pkey); \
|
41
|
-
(key) = pkey->pkey.ec; \
|
42
|
-
} while(0)
|
43
|
-
|
44
|
-
#define Require_EC_KEY(obj, key) do { \
|
45
|
-
Get_EC_KEY((obj), (key)); \
|
46
|
-
if ((key) == NULL) \
|
47
|
-
ossl_raise(eECError, "EC_KEY is not initialized"); \
|
48
|
-
} while(0)
|
49
|
-
|
50
|
-
#define SafeRequire_EC_KEY(obj, key) do { \
|
51
|
-
OSSL_Check_Kind((obj), cEC); \
|
52
|
-
Require_EC_KEY((obj), (key)); \
|
21
|
+
#define GetEC(obj, key) do { \
|
22
|
+
EVP_PKEY *_pkey; \
|
23
|
+
GetPKeyEC(obj, _pkey); \
|
24
|
+
(key) = EVP_PKEY_get0_EC_KEY(_pkey); \
|
25
|
+
} while (0)
|
26
|
+
#define SafeGetEC(obj, key) do { \
|
27
|
+
OSSL_Check_Kind(obj, cEC); \
|
28
|
+
GetEC(obj, key); \
|
53
29
|
} while (0)
|
54
30
|
|
55
|
-
#define
|
56
|
-
|
57
|
-
TypedData_Get_Struct((obj), ossl_ec_group, &ossl_ec_group_type, ec_group); \
|
58
|
-
if (ec_group == NULL) \
|
59
|
-
ossl_raise(eEC_GROUP, "missing ossl_ec_group structure"); \
|
60
|
-
(g) = ec_group->group; \
|
61
|
-
} while(0)
|
62
|
-
|
63
|
-
#define Require_EC_GROUP(obj, group) do { \
|
64
|
-
Get_EC_GROUP((obj), (group)); \
|
31
|
+
#define GetECGroup(obj, group) do { \
|
32
|
+
TypedData_Get_Struct(obj, EC_GROUP, &ossl_ec_group_type, group); \
|
65
33
|
if ((group) == NULL) \
|
66
|
-
|
67
|
-
} while(0)
|
68
|
-
|
69
|
-
#define SafeRequire_EC_GROUP(obj, group) do { \
|
34
|
+
ossl_raise(eEC_GROUP, "EC_GROUP is not initialized"); \
|
35
|
+
} while (0)
|
36
|
+
#define SafeGetECGroup(obj, group) do { \
|
70
37
|
OSSL_Check_Kind((obj), cEC_GROUP); \
|
71
|
-
|
72
|
-
} while(0)
|
73
|
-
|
74
|
-
#define Get_EC_POINT(obj, p) do { \
|
75
|
-
ossl_ec_point *ec_point; \
|
76
|
-
TypedData_Get_Struct((obj), ossl_ec_point, &ossl_ec_point_type, ec_point); \
|
77
|
-
if (ec_point == NULL) \
|
78
|
-
ossl_raise(eEC_POINT, "missing ossl_ec_point structure"); \
|
79
|
-
(p) = ec_point->point; \
|
80
|
-
} while(0)
|
38
|
+
GetECGroup(obj, group); \
|
39
|
+
} while (0)
|
81
40
|
|
82
|
-
#define
|
83
|
-
|
41
|
+
#define GetECPoint(obj, point) do { \
|
42
|
+
TypedData_Get_Struct(obj, EC_POINT, &ossl_ec_point_type, point); \
|
84
43
|
if ((point) == NULL) \
|
85
|
-
|
86
|
-
} while(0)
|
87
|
-
|
88
|
-
#define SafeRequire_EC_POINT(obj, point) do { \
|
44
|
+
ossl_raise(eEC_POINT, "EC_POINT is not initialized"); \
|
45
|
+
} while (0)
|
46
|
+
#define SafeGetECPoint(obj, point) do { \
|
89
47
|
OSSL_Check_Kind((obj), cEC_POINT); \
|
90
|
-
|
48
|
+
GetECPoint(obj, point); \
|
91
49
|
} while(0)
|
50
|
+
#define GetECPointGroup(obj, group) do { \
|
51
|
+
VALUE _group = rb_attr_get(obj, id_i_group); \
|
52
|
+
SafeGetECGroup(_group, group); \
|
53
|
+
} while (0)
|
92
54
|
|
93
55
|
VALUE cEC;
|
94
56
|
VALUE eECError;
|
@@ -108,6 +70,11 @@ static ID ID_uncompressed;
|
|
108
70
|
static ID ID_compressed;
|
109
71
|
static ID ID_hybrid;
|
110
72
|
|
73
|
+
static ID id_i_group;
|
74
|
+
|
75
|
+
static VALUE ec_group_new(const EC_GROUP *group);
|
76
|
+
static VALUE ec_point_new(const EC_POINT *point, const EC_GROUP *group);
|
77
|
+
|
111
78
|
static VALUE ec_instance(VALUE klass, EC_KEY *ec)
|
112
79
|
{
|
113
80
|
EVP_PKEY *pkey;
|
@@ -137,7 +104,7 @@ VALUE ossl_ec_new(EVP_PKEY *pkey)
|
|
137
104
|
obj = ec_instance(cEC, EC_KEY_new());
|
138
105
|
} else {
|
139
106
|
obj = NewPKey(cEC);
|
140
|
-
if (
|
107
|
+
if (EVP_PKEY_base_id(pkey) != EVP_PKEY_EC) {
|
141
108
|
ossl_raise(rb_eTypeError, "Not a EC key!");
|
142
109
|
}
|
143
110
|
SetPKey(obj, pkey);
|
@@ -149,168 +116,196 @@ VALUE ossl_ec_new(EVP_PKEY *pkey)
|
|
149
116
|
return obj;
|
150
117
|
}
|
151
118
|
|
119
|
+
/*
|
120
|
+
* Creates a new EC_KEY on the EC group obj. arg can be an EC::Group or a String
|
121
|
+
* representing an OID.
|
122
|
+
*/
|
123
|
+
static EC_KEY *
|
124
|
+
ec_key_new_from_group(VALUE arg)
|
125
|
+
{
|
126
|
+
EC_KEY *ec;
|
127
|
+
|
128
|
+
if (rb_obj_is_kind_of(arg, cEC_GROUP)) {
|
129
|
+
EC_GROUP *group;
|
130
|
+
|
131
|
+
SafeGetECGroup(arg, group);
|
132
|
+
if (!(ec = EC_KEY_new()))
|
133
|
+
ossl_raise(eECError, NULL);
|
134
|
+
|
135
|
+
if (!EC_KEY_set_group(ec, group)) {
|
136
|
+
EC_KEY_free(ec);
|
137
|
+
ossl_raise(eECError, NULL);
|
138
|
+
}
|
139
|
+
} else {
|
140
|
+
int nid = OBJ_sn2nid(StringValueCStr(arg));
|
141
|
+
|
142
|
+
if (nid == NID_undef)
|
143
|
+
ossl_raise(eECError, "invalid curve name");
|
152
144
|
|
153
|
-
|
154
|
-
|
155
|
-
|
156
|
-
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
145
|
+
if (!(ec = EC_KEY_new_by_curve_name(nid)))
|
146
|
+
ossl_raise(eECError, NULL);
|
147
|
+
|
148
|
+
EC_KEY_set_asn1_flag(ec, OPENSSL_EC_NAMED_CURVE);
|
149
|
+
EC_KEY_set_conv_form(ec, POINT_CONVERSION_UNCOMPRESSED);
|
150
|
+
}
|
151
|
+
|
152
|
+
return ec;
|
153
|
+
}
|
154
|
+
|
155
|
+
/*
|
156
|
+
* call-seq:
|
157
|
+
* EC.generate(ec_group) -> ec
|
158
|
+
* EC.generate(string) -> ec
|
161
159
|
*
|
162
|
-
*
|
163
|
-
|
160
|
+
* Creates a new EC instance with a new random private and public key.
|
161
|
+
*/
|
162
|
+
static VALUE
|
163
|
+
ossl_ec_key_s_generate(VALUE klass, VALUE arg)
|
164
|
+
{
|
165
|
+
EC_KEY *ec;
|
166
|
+
VALUE obj;
|
167
|
+
|
168
|
+
ec = ec_key_new_from_group(arg);
|
169
|
+
|
170
|
+
obj = ec_instance(klass, ec);
|
171
|
+
if (obj == Qfalse) {
|
172
|
+
EC_KEY_free(ec);
|
173
|
+
ossl_raise(eECError, NULL);
|
174
|
+
}
|
175
|
+
|
176
|
+
if (!EC_KEY_generate_key(ec))
|
177
|
+
ossl_raise(eECError, "EC_KEY_generate_key");
|
178
|
+
|
179
|
+
return obj;
|
180
|
+
}
|
181
|
+
|
182
|
+
/*
|
183
|
+
* call-seq:
|
184
|
+
* OpenSSL::PKey::EC.new
|
185
|
+
* OpenSSL::PKey::EC.new(ec_key)
|
186
|
+
* OpenSSL::PKey::EC.new(ec_group)
|
187
|
+
* OpenSSL::PKey::EC.new("secp112r1")
|
188
|
+
* OpenSSL::PKey::EC.new(pem_string [, pwd])
|
189
|
+
* OpenSSL::PKey::EC.new(der_string)
|
190
|
+
*
|
191
|
+
* Creates a new EC object from given arguments.
|
164
192
|
*/
|
165
193
|
static VALUE ossl_ec_key_initialize(int argc, VALUE *argv, VALUE self)
|
166
194
|
{
|
167
195
|
EVP_PKEY *pkey;
|
168
|
-
EC_KEY *ec
|
196
|
+
EC_KEY *ec;
|
169
197
|
VALUE arg, pass;
|
170
|
-
VALUE group = Qnil;
|
171
|
-
char *passwd = NULL;
|
172
198
|
|
173
199
|
GetPKey(self, pkey);
|
174
|
-
if (pkey
|
200
|
+
if (EVP_PKEY_base_id(pkey) != EVP_PKEY_NONE)
|
175
201
|
ossl_raise(eECError, "EC_KEY already initialized");
|
176
202
|
|
177
203
|
rb_scan_args(argc, argv, "02", &arg, &pass);
|
178
204
|
|
179
205
|
if (NIL_P(arg)) {
|
180
|
-
ec = EC_KEY_new()
|
206
|
+
if (!(ec = EC_KEY_new()))
|
207
|
+
ossl_raise(eECError, NULL);
|
208
|
+
} else if (rb_obj_is_kind_of(arg, cEC)) {
|
209
|
+
EC_KEY *other_ec = NULL;
|
210
|
+
|
211
|
+
SafeGetEC(arg, other_ec);
|
212
|
+
if (!(ec = EC_KEY_dup(other_ec)))
|
213
|
+
ossl_raise(eECError, NULL);
|
214
|
+
} else if (rb_obj_is_kind_of(arg, cEC_GROUP)) {
|
215
|
+
ec = ec_key_new_from_group(arg);
|
181
216
|
} else {
|
182
|
-
|
183
|
-
EC_KEY *other_ec = NULL;
|
184
|
-
|
185
|
-
SafeRequire_EC_KEY(arg, other_ec);
|
186
|
-
ec = EC_KEY_dup(other_ec);
|
187
|
-
} else if (rb_obj_is_kind_of(arg, cEC_GROUP)) {
|
188
|
-
ec = EC_KEY_new();
|
189
|
-
group = arg;
|
190
|
-
} else {
|
191
|
-
BIO *in = ossl_obj2bio(arg);
|
192
|
-
|
193
|
-
if (!NIL_P(pass)) {
|
194
|
-
passwd = StringValuePtr(pass);
|
195
|
-
}
|
196
|
-
ec = PEM_read_bio_ECPrivateKey(in, NULL, ossl_pem_passwd_cb, passwd);
|
197
|
-
if (!ec) {
|
198
|
-
OSSL_BIO_reset(in);
|
199
|
-
ec = PEM_read_bio_EC_PUBKEY(in, NULL, ossl_pem_passwd_cb, passwd);
|
200
|
-
}
|
201
|
-
if (!ec) {
|
202
|
-
OSSL_BIO_reset(in);
|
203
|
-
ec = d2i_ECPrivateKey_bio(in, NULL);
|
204
|
-
}
|
205
|
-
if (!ec) {
|
206
|
-
OSSL_BIO_reset(in);
|
207
|
-
ec = d2i_EC_PUBKEY_bio(in, NULL);
|
208
|
-
}
|
209
|
-
|
210
|
-
BIO_free(in);
|
211
|
-
|
212
|
-
if (ec == NULL) {
|
213
|
-
const char *name = StringValueCStr(arg);
|
214
|
-
int nid = OBJ_sn2nid(name);
|
217
|
+
BIO *in;
|
215
218
|
|
216
|
-
|
217
|
-
|
218
|
-
ossl_raise(eECError, "unknown curve name (%s)\n", name);
|
219
|
+
pass = ossl_pem_passwd_value(pass);
|
220
|
+
in = ossl_obj2bio(&arg);
|
219
221
|
|
220
|
-
|
221
|
-
|
222
|
+
ec = PEM_read_bio_ECPrivateKey(in, NULL, ossl_pem_passwd_cb, (void *)pass);
|
223
|
+
if (!ec) {
|
224
|
+
OSSL_BIO_reset(in);
|
225
|
+
ec = PEM_read_bio_EC_PUBKEY(in, NULL, ossl_pem_passwd_cb, (void *)pass);
|
226
|
+
}
|
227
|
+
if (!ec) {
|
228
|
+
OSSL_BIO_reset(in);
|
229
|
+
ec = d2i_ECPrivateKey_bio(in, NULL);
|
230
|
+
}
|
231
|
+
if (!ec) {
|
232
|
+
OSSL_BIO_reset(in);
|
233
|
+
ec = d2i_EC_PUBKEY_bio(in, NULL);
|
234
|
+
}
|
235
|
+
BIO_free(in);
|
222
236
|
|
223
|
-
|
224
|
-
|
225
|
-
|
226
|
-
|
237
|
+
if (!ec) {
|
238
|
+
ossl_clear_error();
|
239
|
+
ec = ec_key_new_from_group(arg);
|
240
|
+
}
|
227
241
|
}
|
228
242
|
|
229
|
-
if (ec == NULL)
|
230
|
-
ossl_raise(eECError, NULL);
|
231
|
-
|
232
243
|
if (!EVP_PKEY_assign_EC_KEY(pkey, ec)) {
|
233
244
|
EC_KEY_free(ec);
|
234
245
|
ossl_raise(eECError, "EVP_PKEY_assign_EC_KEY");
|
235
246
|
}
|
236
247
|
|
237
|
-
|
248
|
+
return self;
|
249
|
+
}
|
238
250
|
|
239
|
-
|
240
|
-
|
251
|
+
static VALUE
|
252
|
+
ossl_ec_key_initialize_copy(VALUE self, VALUE other)
|
253
|
+
{
|
254
|
+
EVP_PKEY *pkey;
|
255
|
+
EC_KEY *ec, *ec_new;
|
256
|
+
|
257
|
+
GetPKey(self, pkey);
|
258
|
+
if (EVP_PKEY_base_id(pkey) != EVP_PKEY_NONE)
|
259
|
+
ossl_raise(eECError, "EC already initialized");
|
260
|
+
SafeGetEC(other, ec);
|
261
|
+
|
262
|
+
ec_new = EC_KEY_dup(ec);
|
263
|
+
if (!ec_new)
|
264
|
+
ossl_raise(eECError, "EC_KEY_dup");
|
265
|
+
if (!EVP_PKEY_assign_EC_KEY(pkey, ec_new)) {
|
266
|
+
EC_KEY_free(ec_new);
|
267
|
+
ossl_raise(eECError, "EVP_PKEY_assign_EC_KEY");
|
268
|
+
}
|
241
269
|
|
242
270
|
return self;
|
243
271
|
}
|
244
272
|
|
245
273
|
/*
|
246
|
-
*
|
247
|
-
*
|
274
|
+
* call-seq:
|
275
|
+
* key.group => group
|
248
276
|
*
|
249
|
-
*
|
250
|
-
*
|
277
|
+
* Returns the EC::Group that the key is associated with. Modifying the returned
|
278
|
+
* group does not affect +key+.
|
251
279
|
*/
|
252
|
-
static VALUE
|
280
|
+
static VALUE
|
281
|
+
ossl_ec_key_get_group(VALUE self)
|
253
282
|
{
|
254
|
-
VALUE group_v;
|
255
283
|
EC_KEY *ec;
|
256
|
-
|
257
|
-
EC_GROUP *group;
|
258
|
-
|
259
|
-
Require_EC_KEY(self, ec);
|
260
|
-
|
261
|
-
group_v = rb_iv_get(self, "@group");
|
262
|
-
if (!NIL_P(group_v))
|
263
|
-
return group_v;
|
284
|
+
const EC_GROUP *group;
|
264
285
|
|
265
|
-
|
266
|
-
|
267
|
-
|
268
|
-
|
269
|
-
ec_group->dont_free = 1;
|
270
|
-
rb_iv_set(group_v, "@key", self);
|
271
|
-
rb_iv_set(self, "@group", group_v);
|
272
|
-
return group_v;
|
273
|
-
}
|
286
|
+
GetEC(self, ec);
|
287
|
+
group = EC_KEY_get0_group(ec);
|
288
|
+
if (!group)
|
289
|
+
return Qnil;
|
274
290
|
|
275
|
-
return
|
291
|
+
return ec_group_new(group);
|
276
292
|
}
|
277
293
|
|
278
294
|
/*
|
279
|
-
*
|
280
|
-
*
|
281
|
-
*
|
282
|
-
* Returns the same object passed, not the group object associated with the key.
|
283
|
-
* If you wish to access the group object tied to the key call key.group after setting
|
284
|
-
* the group.
|
295
|
+
* call-seq:
|
296
|
+
* key.group = group
|
285
297
|
*
|
286
|
-
*
|
287
|
-
*
|
288
|
-
* assignment will not effect the internal key structure.
|
289
|
-
* (your changes may be lost). BE CAREFUL.
|
290
|
-
*
|
291
|
-
* EC_KEY_set_group calls EC_GROUP_free(key->group) then EC_GROUP_dup(), not EC_GROUP_copy.
|
292
|
-
* This documentation is accurate for OpenSSL 0.9.8b.
|
298
|
+
* Sets the EC::Group for the key. The group structure is internally copied so
|
299
|
+
* modification to +group+ after assigning to a key has no effect on the key.
|
293
300
|
*/
|
294
|
-
static VALUE
|
301
|
+
static VALUE
|
302
|
+
ossl_ec_key_set_group(VALUE self, VALUE group_v)
|
295
303
|
{
|
296
|
-
VALUE old_group_v;
|
297
304
|
EC_KEY *ec;
|
298
305
|
EC_GROUP *group;
|
299
306
|
|
300
|
-
|
301
|
-
|
302
|
-
|
303
|
-
old_group_v = rb_iv_get(self, "@group");
|
304
|
-
if (!NIL_P(old_group_v)) {
|
305
|
-
ossl_ec_group *old_ec_group;
|
306
|
-
SafeGet_ec_group(old_group_v, old_ec_group);
|
307
|
-
|
308
|
-
old_ec_group->group = NULL;
|
309
|
-
old_ec_group->dont_free = 0;
|
310
|
-
rb_iv_set(old_group_v, "@key", Qnil);
|
311
|
-
}
|
312
|
-
|
313
|
-
rb_iv_set(self, "@group", Qnil);
|
307
|
+
GetEC(self, ec);
|
308
|
+
SafeGetECGroup(group_v, group);
|
314
309
|
|
315
310
|
if (EC_KEY_set_group(ec, group) != 1)
|
316
311
|
ossl_raise(eECError, "EC_KEY_set_group");
|
@@ -329,8 +324,7 @@ static VALUE ossl_ec_key_get_private_key(VALUE self)
|
|
329
324
|
EC_KEY *ec;
|
330
325
|
const BIGNUM *bn;
|
331
326
|
|
332
|
-
|
333
|
-
|
327
|
+
GetEC(self, ec);
|
334
328
|
if ((bn = EC_KEY_get0_private_key(ec)) == NULL)
|
335
329
|
return Qnil;
|
336
330
|
|
@@ -348,7 +342,7 @@ static VALUE ossl_ec_key_set_private_key(VALUE self, VALUE private_key)
|
|
348
342
|
EC_KEY *ec;
|
349
343
|
BIGNUM *bn = NULL;
|
350
344
|
|
351
|
-
|
345
|
+
GetEC(self, ec);
|
352
346
|
if (!NIL_P(private_key))
|
353
347
|
bn = GetBNPtr(private_key);
|
354
348
|
|
@@ -365,26 +359,6 @@ static VALUE ossl_ec_key_set_private_key(VALUE self, VALUE private_key)
|
|
365
359
|
return private_key;
|
366
360
|
}
|
367
361
|
|
368
|
-
|
369
|
-
static VALUE ossl_ec_point_dup(const EC_POINT *point, VALUE group_v)
|
370
|
-
{
|
371
|
-
VALUE obj;
|
372
|
-
const EC_GROUP *group;
|
373
|
-
ossl_ec_point *new_point;
|
374
|
-
|
375
|
-
obj = rb_obj_alloc(cEC_POINT);
|
376
|
-
TypedData_Get_Struct(obj, ossl_ec_point, &ossl_ec_point_type, new_point);
|
377
|
-
|
378
|
-
SafeRequire_EC_GROUP(group_v, group);
|
379
|
-
|
380
|
-
new_point->point = EC_POINT_dup(point, group);
|
381
|
-
if (new_point->point == NULL)
|
382
|
-
ossl_raise(eEC_POINT, "EC_POINT_dup");
|
383
|
-
rb_iv_set(obj, "@group", group_v);
|
384
|
-
|
385
|
-
return obj;
|
386
|
-
}
|
387
|
-
|
388
362
|
/*
|
389
363
|
* call-seq:
|
390
364
|
* key.public_key => OpenSSL::PKey::EC::Point
|
@@ -395,18 +369,12 @@ static VALUE ossl_ec_key_get_public_key(VALUE self)
|
|
395
369
|
{
|
396
370
|
EC_KEY *ec;
|
397
371
|
const EC_POINT *point;
|
398
|
-
VALUE group;
|
399
|
-
|
400
|
-
Require_EC_KEY(self, ec);
|
401
372
|
|
373
|
+
GetEC(self, ec);
|
402
374
|
if ((point = EC_KEY_get0_public_key(ec)) == NULL)
|
403
375
|
return Qnil;
|
404
376
|
|
405
|
-
|
406
|
-
if (NIL_P(group))
|
407
|
-
ossl_raise(eECError, "EC_KEY_get0_get0_group (has public_key but no group???");
|
408
|
-
|
409
|
-
return ossl_ec_point_dup(point, group);
|
377
|
+
return ec_point_new(point, EC_KEY_get0_group(ec));
|
410
378
|
}
|
411
379
|
|
412
380
|
/*
|
@@ -420,9 +388,9 @@ static VALUE ossl_ec_key_set_public_key(VALUE self, VALUE public_key)
|
|
420
388
|
EC_KEY *ec;
|
421
389
|
EC_POINT *point = NULL;
|
422
390
|
|
423
|
-
|
391
|
+
GetEC(self, ec);
|
424
392
|
if (!NIL_P(public_key))
|
425
|
-
|
393
|
+
SafeGetECPoint(public_key, point);
|
426
394
|
|
427
395
|
switch (EC_KEY_set_public_key(ec, point)) {
|
428
396
|
case 1:
|
@@ -439,32 +407,34 @@ static VALUE ossl_ec_key_set_public_key(VALUE self, VALUE public_key)
|
|
439
407
|
|
440
408
|
/*
|
441
409
|
* call-seq:
|
442
|
-
* key.
|
410
|
+
* key.public? => true or false
|
443
411
|
*
|
444
|
-
*
|
412
|
+
* Returns whether this EC instance has a public key. The public key
|
413
|
+
* (EC::Point) can be retrieved with EC#public_key.
|
445
414
|
*/
|
446
|
-
static VALUE
|
415
|
+
static VALUE ossl_ec_key_is_public(VALUE self)
|
447
416
|
{
|
448
417
|
EC_KEY *ec;
|
449
418
|
|
450
|
-
|
419
|
+
GetEC(self, ec);
|
451
420
|
|
452
|
-
return
|
421
|
+
return EC_KEY_get0_public_key(ec) ? Qtrue : Qfalse;
|
453
422
|
}
|
454
423
|
|
455
424
|
/*
|
456
425
|
* call-seq:
|
457
|
-
* key.
|
426
|
+
* key.private? => true or false
|
458
427
|
*
|
459
|
-
*
|
428
|
+
* Returns whether this EC instance has a private key. The private key (BN) can
|
429
|
+
* be retrieved with EC#private_key.
|
460
430
|
*/
|
461
|
-
static VALUE
|
431
|
+
static VALUE ossl_ec_key_is_private(VALUE self)
|
462
432
|
{
|
463
433
|
EC_KEY *ec;
|
464
434
|
|
465
|
-
|
435
|
+
GetEC(self, ec);
|
466
436
|
|
467
|
-
return
|
437
|
+
return EC_KEY_get0_private_key(ec) ? Qtrue : Qfalse;
|
468
438
|
}
|
469
439
|
|
470
440
|
static VALUE ossl_ec_key_to_string(VALUE self, VALUE ciph, VALUE pass, int format)
|
@@ -473,11 +443,10 @@ static VALUE ossl_ec_key_to_string(VALUE self, VALUE ciph, VALUE pass, int forma
|
|
473
443
|
BIO *out;
|
474
444
|
int i = -1;
|
475
445
|
int private = 0;
|
476
|
-
char *password = NULL;
|
477
446
|
VALUE str;
|
478
447
|
const EVP_CIPHER *cipher = NULL;
|
479
448
|
|
480
|
-
|
449
|
+
GetEC(self, ec);
|
481
450
|
|
482
451
|
if (EC_KEY_get0_public_key(ec) == NULL)
|
483
452
|
ossl_raise(eECError, "can't export - no public key set");
|
@@ -490,12 +459,7 @@ static VALUE ossl_ec_key_to_string(VALUE self, VALUE ciph, VALUE pass, int forma
|
|
490
459
|
|
491
460
|
if (!NIL_P(ciph)) {
|
492
461
|
cipher = GetCipherPtr(ciph);
|
493
|
-
|
494
|
-
StringValue(pass);
|
495
|
-
if (RSTRING_LENINT(pass) < OSSL_MIN_PWD_LEN)
|
496
|
-
ossl_raise(eOSSLError, "OpenSSL requires passwords to be at least four characters long");
|
497
|
-
password = RSTRING_PTR(pass);
|
498
|
-
}
|
462
|
+
pass = ossl_pem_passwd_value(pass);
|
499
463
|
}
|
500
464
|
|
501
465
|
if (!(out = BIO_new(BIO_s_mem())))
|
@@ -504,7 +468,7 @@ static VALUE ossl_ec_key_to_string(VALUE self, VALUE ciph, VALUE pass, int forma
|
|
504
468
|
switch(format) {
|
505
469
|
case EXPORT_PEM:
|
506
470
|
if (private) {
|
507
|
-
i = PEM_write_bio_ECPrivateKey(out, ec, cipher, NULL, 0,
|
471
|
+
i = PEM_write_bio_ECPrivateKey(out, ec, cipher, NULL, 0, ossl_pem_passwd_cb, (void *)pass);
|
508
472
|
} else {
|
509
473
|
i = PEM_write_bio_EC_PUBKEY(out, ec);
|
510
474
|
}
|
@@ -538,12 +502,10 @@ static VALUE ossl_ec_key_to_string(VALUE self, VALUE ciph, VALUE pass, int forma
|
|
538
502
|
* key.export([cipher, pass_phrase]) => String
|
539
503
|
* key.to_pem([cipher, pass_phrase]) => String
|
540
504
|
*
|
541
|
-
* Outputs the EC key in PEM encoding. If +cipher+ and +pass_phrase+ are
|
542
|
-
*
|
543
|
-
*
|
544
|
-
*
|
545
|
-
* text.
|
546
|
-
*
|
505
|
+
* Outputs the EC key in PEM encoding. If +cipher+ and +pass_phrase+ are given
|
506
|
+
* they will be used to encrypt the key. +cipher+ must be an OpenSSL::Cipher
|
507
|
+
* instance. Note that encryption will only be effective for a private key,
|
508
|
+
* public keys will always be encoded in plain text.
|
547
509
|
*/
|
548
510
|
static VALUE ossl_ec_key_export(int argc, VALUE *argv, VALUE self)
|
549
511
|
{
|
@@ -575,7 +537,7 @@ static VALUE ossl_ec_key_to_text(VALUE self)
|
|
575
537
|
BIO *out;
|
576
538
|
VALUE str;
|
577
539
|
|
578
|
-
|
540
|
+
GetEC(self, ec);
|
579
541
|
if (!(out = BIO_new(BIO_s_mem()))) {
|
580
542
|
ossl_raise(eECError, "BIO_new(BIO_s_mem())");
|
581
543
|
}
|
@@ -590,16 +552,23 @@ static VALUE ossl_ec_key_to_text(VALUE self)
|
|
590
552
|
|
591
553
|
/*
|
592
554
|
* call-seq:
|
593
|
-
* key.generate_key => self
|
555
|
+
* key.generate_key! => self
|
556
|
+
*
|
557
|
+
* Generates a new random private and public key.
|
594
558
|
*
|
595
|
-
*
|
559
|
+
* See also the OpenSSL documentation for EC_KEY_generate_key()
|
560
|
+
*
|
561
|
+
* === Example
|
562
|
+
* ec = OpenSSL::PKey::EC.new("prime256v1")
|
563
|
+
* p ec.private_key # => nil
|
564
|
+
* ec.generate_key!
|
565
|
+
* p ec.private_key # => #<OpenSSL::BN XXXXXX>
|
596
566
|
*/
|
597
567
|
static VALUE ossl_ec_key_generate_key(VALUE self)
|
598
568
|
{
|
599
569
|
EC_KEY *ec;
|
600
570
|
|
601
|
-
|
602
|
-
|
571
|
+
GetEC(self, ec);
|
603
572
|
if (EC_KEY_generate_key(ec) != 1)
|
604
573
|
ossl_raise(eECError, "EC_KEY_generate_key");
|
605
574
|
|
@@ -618,8 +587,7 @@ static VALUE ossl_ec_key_check_key(VALUE self)
|
|
618
587
|
{
|
619
588
|
EC_KEY *ec;
|
620
589
|
|
621
|
-
|
622
|
-
|
590
|
+
GetEC(self, ec);
|
623
591
|
if (EC_KEY_check_key(ec) != 1)
|
624
592
|
ossl_raise(eECError, "EC_KEY_check_key");
|
625
593
|
|
@@ -639,8 +607,8 @@ static VALUE ossl_ec_key_dh_compute_key(VALUE self, VALUE pubkey)
|
|
639
607
|
int buf_len;
|
640
608
|
VALUE str;
|
641
609
|
|
642
|
-
|
643
|
-
|
610
|
+
GetEC(self, ec);
|
611
|
+
SafeGetECPoint(pubkey, point);
|
644
612
|
|
645
613
|
/* BUG: need a way to figure out the maximum string size */
|
646
614
|
buf_len = 1024;
|
@@ -669,17 +637,16 @@ static VALUE ossl_ec_key_dsa_sign_asn1(VALUE self, VALUE data)
|
|
669
637
|
unsigned int buf_len;
|
670
638
|
VALUE str;
|
671
639
|
|
672
|
-
|
640
|
+
GetEC(self, ec);
|
673
641
|
StringValue(data);
|
674
642
|
|
675
643
|
if (EC_KEY_get0_private_key(ec) == NULL)
|
676
644
|
ossl_raise(eECError, "Private EC key needed!");
|
677
645
|
|
678
|
-
str = rb_str_new(0, ECDSA_size(ec)
|
646
|
+
str = rb_str_new(0, ECDSA_size(ec));
|
679
647
|
if (ECDSA_sign(0, (unsigned char *) RSTRING_PTR(data), RSTRING_LENINT(data), (unsigned char *) RSTRING_PTR(str), &buf_len, ec) != 1)
|
680
|
-
|
681
|
-
|
682
|
-
rb_str_resize(str, buf_len);
|
648
|
+
ossl_raise(eECError, "ECDSA_sign");
|
649
|
+
rb_str_set_len(str, buf_len);
|
683
650
|
|
684
651
|
return str;
|
685
652
|
}
|
@@ -694,7 +661,7 @@ static VALUE ossl_ec_key_dsa_verify_asn1(VALUE self, VALUE data, VALUE sig)
|
|
694
661
|
{
|
695
662
|
EC_KEY *ec;
|
696
663
|
|
697
|
-
|
664
|
+
GetEC(self, ec);
|
698
665
|
StringValue(data);
|
699
666
|
StringValue(sig);
|
700
667
|
|
@@ -709,12 +676,13 @@ static VALUE ossl_ec_key_dsa_verify_asn1(VALUE self, VALUE data, VALUE sig)
|
|
709
676
|
UNREACHABLE;
|
710
677
|
}
|
711
678
|
|
712
|
-
|
679
|
+
/*
|
680
|
+
* OpenSSL::PKey::EC::Group
|
681
|
+
*/
|
682
|
+
static void
|
683
|
+
ossl_ec_group_free(void *ptr)
|
713
684
|
{
|
714
|
-
|
715
|
-
if (!ec_group->dont_free && ec_group->group)
|
716
|
-
EC_GROUP_clear_free(ec_group->group);
|
717
|
-
ruby_xfree(ec_group);
|
685
|
+
EC_GROUP_clear_free(ptr);
|
718
686
|
}
|
719
687
|
|
720
688
|
static const rb_data_type_t ossl_ec_group_type = {
|
@@ -725,40 +693,55 @@ static const rb_data_type_t ossl_ec_group_type = {
|
|
725
693
|
0, 0, RUBY_TYPED_FREE_IMMEDIATELY,
|
726
694
|
};
|
727
695
|
|
728
|
-
static VALUE
|
696
|
+
static VALUE
|
697
|
+
ossl_ec_group_alloc(VALUE klass)
|
698
|
+
{
|
699
|
+
return TypedData_Wrap_Struct(klass, &ossl_ec_group_type, NULL);
|
700
|
+
}
|
701
|
+
|
702
|
+
static VALUE
|
703
|
+
ec_group_new(const EC_GROUP *group)
|
729
704
|
{
|
730
|
-
ossl_ec_group *ec_group;
|
731
705
|
VALUE obj;
|
706
|
+
EC_GROUP *group_new;
|
732
707
|
|
733
|
-
obj =
|
708
|
+
obj = ossl_ec_group_alloc(cEC_GROUP);
|
709
|
+
group_new = EC_GROUP_dup(group);
|
710
|
+
if (!group_new)
|
711
|
+
ossl_raise(eEC_GROUP, "EC_GROUP_dup");
|
712
|
+
RTYPEDDATA_DATA(obj) = group_new;
|
734
713
|
|
735
714
|
return obj;
|
736
715
|
}
|
737
716
|
|
738
|
-
/*
|
739
|
-
*
|
740
|
-
*
|
741
|
-
*
|
742
|
-
*
|
743
|
-
*
|
744
|
-
*
|
745
|
-
*
|
746
|
-
*
|
747
|
-
*
|
748
|
-
*
|
749
|
-
*
|
750
|
-
*
|
717
|
+
/*
|
718
|
+
* call-seq:
|
719
|
+
* OpenSSL::PKey::EC::Group.new(ec_group)
|
720
|
+
* OpenSSL::PKey::EC::Group.new(pem_or_der_encoded)
|
721
|
+
* OpenSSL::PKey::EC::Group.new(ec_method)
|
722
|
+
* OpenSSL::PKey::EC::Group.new(:GFp, bignum_p, bignum_a, bignum_b)
|
723
|
+
* OpenSSL::PKey::EC::Group.new(:GF2m, bignum_p, bignum_a, bignum_b)
|
724
|
+
*
|
725
|
+
* Creates a new EC::Group object.
|
726
|
+
*
|
727
|
+
* +ec_method+ is a symbol that represents an EC_METHOD. Currently the following
|
728
|
+
* are supported:
|
729
|
+
*
|
730
|
+
* * :GFp_simple
|
731
|
+
* * :GFp_mont
|
732
|
+
* * :GFp_nist
|
733
|
+
* * :GF2m_simple
|
751
734
|
*
|
752
|
-
*
|
735
|
+
* If the first argument is :GFp or :GF2m, creates a new curve with given
|
736
|
+
* parameters.
|
753
737
|
*/
|
754
738
|
static VALUE ossl_ec_group_initialize(int argc, VALUE *argv, VALUE self)
|
755
739
|
{
|
756
740
|
VALUE arg1, arg2, arg3, arg4;
|
757
|
-
|
758
|
-
EC_GROUP *group = NULL;
|
741
|
+
EC_GROUP *group;
|
759
742
|
|
760
|
-
TypedData_Get_Struct(self,
|
761
|
-
if (
|
743
|
+
TypedData_Get_Struct(self, EC_GROUP, &ossl_ec_group_type, group);
|
744
|
+
if (group)
|
762
745
|
ossl_raise(rb_eRuntimeError, "EC_GROUP is already initialized");
|
763
746
|
|
764
747
|
switch (rb_scan_args(argc, argv, "13", &arg1, &arg2, &arg3, &arg4)) {
|
@@ -788,11 +771,11 @@ static VALUE ossl_ec_group_initialize(int argc, VALUE *argv, VALUE self)
|
|
788
771
|
} else if (rb_obj_is_kind_of(arg1, cEC_GROUP)) {
|
789
772
|
const EC_GROUP *arg1_group;
|
790
773
|
|
791
|
-
|
774
|
+
SafeGetECGroup(arg1, arg1_group);
|
792
775
|
if ((group = EC_GROUP_dup(arg1_group)) == NULL)
|
793
776
|
ossl_raise(eEC_GROUP, "EC_GROUP_dup");
|
794
777
|
} else {
|
795
|
-
BIO *in = ossl_obj2bio(arg1);
|
778
|
+
BIO *in = ossl_obj2bio(&arg1);
|
796
779
|
|
797
780
|
group = PEM_read_bio_ECPKParameters(in, NULL, NULL, NULL);
|
798
781
|
if (!group) {
|
@@ -806,13 +789,13 @@ static VALUE ossl_ec_group_initialize(int argc, VALUE *argv, VALUE self)
|
|
806
789
|
const char *name = StringValueCStr(arg1);
|
807
790
|
int nid = OBJ_sn2nid(name);
|
808
791
|
|
809
|
-
(
|
792
|
+
ossl_clear_error(); /* ignore errors in d2i_ECPKParameters_bio() */
|
810
793
|
if (nid == NID_undef)
|
811
|
-
ossl_raise(eEC_GROUP, "unknown curve name (%
|
794
|
+
ossl_raise(eEC_GROUP, "unknown curve name (%"PRIsVALUE")", arg1);
|
812
795
|
|
813
796
|
group = EC_GROUP_new_by_curve_name(nid);
|
814
797
|
if (group == NULL)
|
815
|
-
ossl_raise(eEC_GROUP, "unable to create curve (%
|
798
|
+
ossl_raise(eEC_GROUP, "unable to create curve (%"PRIsVALUE")", arg1);
|
816
799
|
|
817
800
|
EC_GROUP_set_asn1_flag(group, OPENSSL_EC_NAMED_CURVE);
|
818
801
|
EC_GROUP_set_point_conversion_form(group, POINT_CONVERSION_UNCOMPRESSED);
|
@@ -851,23 +834,43 @@ static VALUE ossl_ec_group_initialize(int argc, VALUE *argv, VALUE self)
|
|
851
834
|
|
852
835
|
if (group == NULL)
|
853
836
|
ossl_raise(eEC_GROUP, "");
|
837
|
+
RTYPEDDATA_DATA(self) = group;
|
838
|
+
|
839
|
+
return self;
|
840
|
+
}
|
841
|
+
|
842
|
+
static VALUE
|
843
|
+
ossl_ec_group_initialize_copy(VALUE self, VALUE other)
|
844
|
+
{
|
845
|
+
EC_GROUP *group, *group_new;
|
846
|
+
|
847
|
+
TypedData_Get_Struct(self, EC_GROUP, &ossl_ec_group_type, group_new);
|
848
|
+
if (group_new)
|
849
|
+
ossl_raise(eEC_GROUP, "EC::Group already initialized");
|
850
|
+
SafeGetECGroup(other, group);
|
854
851
|
|
855
|
-
|
852
|
+
group_new = EC_GROUP_dup(group);
|
853
|
+
if (!group_new)
|
854
|
+
ossl_raise(eEC_GROUP, "EC_GROUP_dup");
|
855
|
+
RTYPEDDATA_DATA(self) = group_new;
|
856
856
|
|
857
857
|
return self;
|
858
858
|
}
|
859
859
|
|
860
|
-
/*
|
861
|
-
*
|
862
|
-
*
|
860
|
+
/*
|
861
|
+
* call-seq:
|
862
|
+
* group1.eql?(group2) => true | false
|
863
|
+
* group1 == group2 => true | false
|
863
864
|
*
|
865
|
+
* Returns true if the two groups use the same curve and have the same
|
866
|
+
* parameters, false otherwise.
|
864
867
|
*/
|
865
868
|
static VALUE ossl_ec_group_eql(VALUE a, VALUE b)
|
866
869
|
{
|
867
870
|
EC_GROUP *group1 = NULL, *group2 = NULL;
|
868
871
|
|
869
|
-
|
870
|
-
|
872
|
+
GetECGroup(a, group1);
|
873
|
+
SafeGetECGroup(b, group2);
|
871
874
|
|
872
875
|
if (EC_GROUP_cmp(group1, group2, ossl_bn_ctx) == 1)
|
873
876
|
return Qfalse;
|
@@ -875,27 +878,35 @@ static VALUE ossl_ec_group_eql(VALUE a, VALUE b)
|
|
875
878
|
return Qtrue;
|
876
879
|
}
|
877
880
|
|
878
|
-
/*
|
879
|
-
*
|
881
|
+
/*
|
882
|
+
* call-seq:
|
883
|
+
* group.generator => ec_point
|
880
884
|
*
|
881
|
-
*
|
885
|
+
* Returns the generator of the group.
|
886
|
+
*
|
887
|
+
* See the OpenSSL documentation for EC_GROUP_get0_generator()
|
882
888
|
*/
|
883
889
|
static VALUE ossl_ec_group_get_generator(VALUE self)
|
884
890
|
{
|
885
|
-
|
886
|
-
|
887
|
-
|
888
|
-
Require_EC_GROUP(self, group);
|
891
|
+
EC_GROUP *group;
|
892
|
+
const EC_POINT *generator;
|
889
893
|
|
890
|
-
|
894
|
+
GetECGroup(self, group);
|
895
|
+
generator = EC_GROUP_get0_generator(group);
|
896
|
+
if (!generator)
|
897
|
+
return Qnil;
|
891
898
|
|
892
|
-
return
|
899
|
+
return ec_point_new(generator, group);
|
893
900
|
}
|
894
901
|
|
895
|
-
/*
|
896
|
-
*
|
902
|
+
/*
|
903
|
+
* call-seq:
|
904
|
+
* group.set_generator(generator, order, cofactor) => self
|
897
905
|
*
|
898
|
-
*
|
906
|
+
* Sets the curve parameters. +generator+ must be an instance of EC::Point that
|
907
|
+
* is on the curve. +order+ and +cofactor+ are integers.
|
908
|
+
*
|
909
|
+
* See the OpenSSL documentation for EC_GROUP_set_generator()
|
899
910
|
*/
|
900
911
|
static VALUE ossl_ec_group_set_generator(VALUE self, VALUE generator, VALUE order, VALUE cofactor)
|
901
912
|
{
|
@@ -903,8 +914,8 @@ static VALUE ossl_ec_group_set_generator(VALUE self, VALUE generator, VALUE orde
|
|
903
914
|
const EC_POINT *point;
|
904
915
|
const BIGNUM *o, *co;
|
905
916
|
|
906
|
-
|
907
|
-
|
917
|
+
GetECGroup(self, group);
|
918
|
+
SafeGetECPoint(generator, point);
|
908
919
|
o = GetBNPtr(order);
|
909
920
|
co = GetBNPtr(cofactor);
|
910
921
|
|
@@ -914,10 +925,13 @@ static VALUE ossl_ec_group_set_generator(VALUE self, VALUE generator, VALUE orde
|
|
914
925
|
return self;
|
915
926
|
}
|
916
927
|
|
917
|
-
/*
|
918
|
-
*
|
928
|
+
/*
|
929
|
+
* call-seq:
|
930
|
+
* group.get_order => order_bn
|
919
931
|
*
|
920
|
-
*
|
932
|
+
* Returns the order of the group.
|
933
|
+
*
|
934
|
+
* See the OpenSSL documentation for EC_GROUP_get_order()
|
921
935
|
*/
|
922
936
|
static VALUE ossl_ec_group_get_order(VALUE self)
|
923
937
|
{
|
@@ -925,7 +939,7 @@ static VALUE ossl_ec_group_get_order(VALUE self)
|
|
925
939
|
BIGNUM *bn;
|
926
940
|
EC_GROUP *group = NULL;
|
927
941
|
|
928
|
-
|
942
|
+
GetECGroup(self, group);
|
929
943
|
|
930
944
|
bn_obj = ossl_bn_new(NULL);
|
931
945
|
bn = GetBNPtr(bn_obj);
|
@@ -936,10 +950,13 @@ static VALUE ossl_ec_group_get_order(VALUE self)
|
|
936
950
|
return bn_obj;
|
937
951
|
}
|
938
952
|
|
939
|
-
/*
|
940
|
-
*
|
953
|
+
/*
|
954
|
+
* call-seq:
|
955
|
+
* group.get_cofactor => cofactor_bn
|
941
956
|
*
|
942
|
-
*
|
957
|
+
* Returns the cofactor of the group.
|
958
|
+
*
|
959
|
+
* See the OpenSSL documentation for EC_GROUP_get_cofactor()
|
943
960
|
*/
|
944
961
|
static VALUE ossl_ec_group_get_cofactor(VALUE self)
|
945
962
|
{
|
@@ -947,7 +964,7 @@ static VALUE ossl_ec_group_get_cofactor(VALUE self)
|
|
947
964
|
BIGNUM *bn;
|
948
965
|
EC_GROUP *group = NULL;
|
949
966
|
|
950
|
-
|
967
|
+
GetECGroup(self, group);
|
951
968
|
|
952
969
|
bn_obj = ossl_bn_new(NULL);
|
953
970
|
bn = GetBNPtr(bn_obj);
|
@@ -958,17 +975,20 @@ static VALUE ossl_ec_group_get_cofactor(VALUE self)
|
|
958
975
|
return bn_obj;
|
959
976
|
}
|
960
977
|
|
961
|
-
/*
|
962
|
-
*
|
978
|
+
/*
|
979
|
+
* call-seq:
|
980
|
+
* group.curve_name => String
|
963
981
|
*
|
964
|
-
*
|
982
|
+
* Returns the curve name (sn).
|
983
|
+
*
|
984
|
+
* See the OpenSSL documentation for EC_GROUP_get_curve_name()
|
965
985
|
*/
|
966
986
|
static VALUE ossl_ec_group_get_curve_name(VALUE self)
|
967
987
|
{
|
968
988
|
EC_GROUP *group = NULL;
|
969
989
|
int nid;
|
970
990
|
|
971
|
-
|
991
|
+
GetECGroup(self, group);
|
972
992
|
if (group == NULL)
|
973
993
|
return Qnil;
|
974
994
|
|
@@ -978,10 +998,14 @@ static VALUE ossl_ec_group_get_curve_name(VALUE self)
|
|
978
998
|
return rb_str_new2(OBJ_nid2sn(nid));
|
979
999
|
}
|
980
1000
|
|
981
|
-
/*
|
982
|
-
*
|
1001
|
+
/*
|
1002
|
+
* call-seq:
|
1003
|
+
* EC.builtin_curves => [[sn, comment], ...]
|
983
1004
|
*
|
984
|
-
*
|
1005
|
+
* Obtains a list of all predefined curves by the OpenSSL. Curve names are
|
1006
|
+
* returned as sn.
|
1007
|
+
*
|
1008
|
+
* See the OpenSSL documentation for EC_get_builtin_curves().
|
985
1009
|
*/
|
986
1010
|
static VALUE ossl_s_builtin_curves(VALUE self)
|
987
1011
|
{
|
@@ -1011,43 +1035,56 @@ static VALUE ossl_s_builtin_curves(VALUE self)
|
|
1011
1035
|
return ret;
|
1012
1036
|
}
|
1013
1037
|
|
1014
|
-
/*
|
1015
|
-
*
|
1038
|
+
/*
|
1039
|
+
* call-seq:
|
1040
|
+
* group.asn1_flag -> Integer
|
1016
1041
|
*
|
1017
|
-
*
|
1042
|
+
* Returns the flags set on the group.
|
1043
|
+
*
|
1044
|
+
* See also #asn1_flag=.
|
1018
1045
|
*/
|
1019
1046
|
static VALUE ossl_ec_group_get_asn1_flag(VALUE self)
|
1020
1047
|
{
|
1021
1048
|
EC_GROUP *group = NULL;
|
1022
1049
|
int flag;
|
1023
1050
|
|
1024
|
-
|
1025
|
-
|
1051
|
+
GetECGroup(self, group);
|
1026
1052
|
flag = EC_GROUP_get_asn1_flag(group);
|
1027
1053
|
|
1028
|
-
return
|
1054
|
+
return INT2NUM(flag);
|
1029
1055
|
}
|
1030
1056
|
|
1031
|
-
/*
|
1032
|
-
*
|
1057
|
+
/*
|
1058
|
+
* call-seq:
|
1059
|
+
* group.asn1_flag = flags
|
1060
|
+
*
|
1061
|
+
* Sets flags on the group. The flag value is used to determine how to encode
|
1062
|
+
* the group: encode explicit parameters or named curve using an OID.
|
1063
|
+
*
|
1064
|
+
* The flag value can be either of:
|
1033
1065
|
*
|
1034
|
-
*
|
1066
|
+
* * EC::NAMED_CURVE
|
1067
|
+
* * EC::EXPLICIT_CURVE
|
1068
|
+
*
|
1069
|
+
* See the OpenSSL documentation for EC_GROUP_set_asn1_flag().
|
1035
1070
|
*/
|
1036
1071
|
static VALUE ossl_ec_group_set_asn1_flag(VALUE self, VALUE flag_v)
|
1037
1072
|
{
|
1038
1073
|
EC_GROUP *group = NULL;
|
1039
1074
|
|
1040
|
-
|
1041
|
-
|
1075
|
+
GetECGroup(self, group);
|
1042
1076
|
EC_GROUP_set_asn1_flag(group, NUM2INT(flag_v));
|
1043
1077
|
|
1044
1078
|
return flag_v;
|
1045
1079
|
}
|
1046
1080
|
|
1047
|
-
/*
|
1048
|
-
*
|
1081
|
+
/*
|
1082
|
+
* call-seq:
|
1083
|
+
* group.point_conversion_form -> Symbol
|
1084
|
+
*
|
1085
|
+
* Returns the form how EC::Point data is encoded as ASN.1.
|
1049
1086
|
*
|
1050
|
-
*
|
1087
|
+
* See also #point_conversion_form=.
|
1051
1088
|
*/
|
1052
1089
|
static VALUE ossl_ec_group_get_point_conversion_form(VALUE self)
|
1053
1090
|
{
|
@@ -1055,8 +1092,7 @@ static VALUE ossl_ec_group_get_point_conversion_form(VALUE self)
|
|
1055
1092
|
point_conversion_form_t form;
|
1056
1093
|
VALUE ret;
|
1057
1094
|
|
1058
|
-
|
1059
|
-
|
1095
|
+
GetECGroup(self, group);
|
1060
1096
|
form = EC_GROUP_get_point_conversion_form(group);
|
1061
1097
|
|
1062
1098
|
switch (form) {
|
@@ -1069,46 +1105,67 @@ static VALUE ossl_ec_group_get_point_conversion_form(VALUE self)
|
|
1069
1105
|
return ID2SYM(ret);
|
1070
1106
|
}
|
1071
1107
|
|
1072
|
-
|
1073
|
-
|
1108
|
+
static point_conversion_form_t
|
1109
|
+
parse_point_conversion_form_symbol(VALUE sym)
|
1110
|
+
{
|
1111
|
+
ID id = SYM2ID(sym);
|
1112
|
+
|
1113
|
+
if (id == ID_uncompressed)
|
1114
|
+
return POINT_CONVERSION_UNCOMPRESSED;
|
1115
|
+
else if (id == ID_compressed)
|
1116
|
+
return POINT_CONVERSION_COMPRESSED;
|
1117
|
+
else if (id == ID_hybrid)
|
1118
|
+
return POINT_CONVERSION_HYBRID;
|
1119
|
+
else
|
1120
|
+
ossl_raise(rb_eArgError, "unsupported point conversion form %+"PRIsVALUE
|
1121
|
+
" (expected :compressed, :uncompressed, or :hybrid)", sym);
|
1122
|
+
}
|
1123
|
+
|
1124
|
+
/*
|
1125
|
+
* call-seq:
|
1126
|
+
* group.point_conversion_form = form
|
1127
|
+
*
|
1128
|
+
* Sets the form how EC::Point data is encoded as ASN.1 as defined in X9.62.
|
1129
|
+
*
|
1130
|
+
* +format+ can be one of these:
|
1131
|
+
*
|
1132
|
+
* :compressed::
|
1133
|
+
* Encoded as z||x, where z is an octet indicating which solution of the
|
1134
|
+
* equation y is. z will be 0x02 or 0x03.
|
1135
|
+
* :uncompressed::
|
1136
|
+
* Encoded as z||x||y, where z is an octet 0x04.
|
1137
|
+
* :hybrid::
|
1138
|
+
* Encodes as z||x||y, where z is an octet indicating which solution of the
|
1139
|
+
* equation y is. z will be 0x06 or 0x07.
|
1074
1140
|
*
|
1075
|
-
*
|
1141
|
+
* See the OpenSSL documentation for EC_GROUP_set_point_conversion_form()
|
1076
1142
|
*/
|
1077
|
-
static VALUE
|
1143
|
+
static VALUE
|
1144
|
+
ossl_ec_group_set_point_conversion_form(VALUE self, VALUE form_v)
|
1078
1145
|
{
|
1079
|
-
EC_GROUP *group
|
1146
|
+
EC_GROUP *group;
|
1080
1147
|
point_conversion_form_t form;
|
1081
|
-
ID form_id = SYM2ID(form_v);
|
1082
|
-
|
1083
|
-
Require_EC_GROUP(self, group);
|
1084
1148
|
|
1085
|
-
|
1086
|
-
|
1087
|
-
} else if (form_id == ID_compressed) {
|
1088
|
-
form = POINT_CONVERSION_COMPRESSED;
|
1089
|
-
} else if (form_id == ID_hybrid) {
|
1090
|
-
form = POINT_CONVERSION_HYBRID;
|
1091
|
-
} else {
|
1092
|
-
ossl_raise(rb_eArgError, "form must be :compressed, :uncompressed, or :hybrid");
|
1093
|
-
}
|
1149
|
+
GetECGroup(self, group);
|
1150
|
+
form = parse_point_conversion_form_symbol(form_v);
|
1094
1151
|
|
1095
1152
|
EC_GROUP_set_point_conversion_form(group, form);
|
1096
1153
|
|
1097
1154
|
return form_v;
|
1098
1155
|
}
|
1099
1156
|
|
1100
|
-
/*
|
1101
|
-
*
|
1157
|
+
/*
|
1158
|
+
* call-seq:
|
1159
|
+
* group.seed => String or nil
|
1102
1160
|
*
|
1103
|
-
*
|
1161
|
+
* See the OpenSSL documentation for EC_GROUP_get0_seed()
|
1104
1162
|
*/
|
1105
1163
|
static VALUE ossl_ec_group_get_seed(VALUE self)
|
1106
1164
|
{
|
1107
1165
|
EC_GROUP *group = NULL;
|
1108
1166
|
size_t seed_len;
|
1109
1167
|
|
1110
|
-
|
1111
|
-
|
1168
|
+
GetECGroup(self, group);
|
1112
1169
|
seed_len = EC_GROUP_get_seed_len(group);
|
1113
1170
|
|
1114
1171
|
if (seed_len == 0)
|
@@ -1117,16 +1174,17 @@ static VALUE ossl_ec_group_get_seed(VALUE self)
|
|
1117
1174
|
return rb_str_new((const char *)EC_GROUP_get0_seed(group), seed_len);
|
1118
1175
|
}
|
1119
1176
|
|
1120
|
-
/*
|
1121
|
-
*
|
1177
|
+
/*
|
1178
|
+
* call-seq:
|
1179
|
+
* group.seed = seed => seed
|
1122
1180
|
*
|
1123
|
-
*
|
1181
|
+
* See the OpenSSL documentation for EC_GROUP_set_seed()
|
1124
1182
|
*/
|
1125
1183
|
static VALUE ossl_ec_group_set_seed(VALUE self, VALUE seed)
|
1126
1184
|
{
|
1127
1185
|
EC_GROUP *group = NULL;
|
1128
1186
|
|
1129
|
-
|
1187
|
+
GetECGroup(self, group);
|
1130
1188
|
StringValue(seed);
|
1131
1189
|
|
1132
1190
|
if (EC_GROUP_set_seed(group, (unsigned char *)RSTRING_PTR(seed), RSTRING_LEN(seed)) != (size_t)RSTRING_LEN(seed))
|
@@ -1137,16 +1195,17 @@ static VALUE ossl_ec_group_set_seed(VALUE self, VALUE seed)
|
|
1137
1195
|
|
1138
1196
|
/* get/set curve GFp, GF2m */
|
1139
1197
|
|
1140
|
-
/*
|
1141
|
-
*
|
1198
|
+
/*
|
1199
|
+
* call-seq:
|
1200
|
+
* group.degree => integer
|
1142
1201
|
*
|
1143
|
-
*
|
1202
|
+
* See the OpenSSL documentation for EC_GROUP_get_degree()
|
1144
1203
|
*/
|
1145
1204
|
static VALUE ossl_ec_group_get_degree(VALUE self)
|
1146
1205
|
{
|
1147
1206
|
EC_GROUP *group = NULL;
|
1148
1207
|
|
1149
|
-
|
1208
|
+
GetECGroup(self, group);
|
1150
1209
|
|
1151
1210
|
return INT2NUM(EC_GROUP_get_degree(group));
|
1152
1211
|
}
|
@@ -1158,7 +1217,7 @@ static VALUE ossl_ec_group_to_string(VALUE self, int format)
|
|
1158
1217
|
int i = -1;
|
1159
1218
|
VALUE str;
|
1160
1219
|
|
1161
|
-
|
1220
|
+
GetECGroup(self, group);
|
1162
1221
|
|
1163
1222
|
if (!(out = BIO_new(BIO_s_mem())))
|
1164
1223
|
ossl_raise(eEC_GROUP, "BIO_new(BIO_s_mem())");
|
@@ -1185,8 +1244,9 @@ static VALUE ossl_ec_group_to_string(VALUE self, int format)
|
|
1185
1244
|
return str;
|
1186
1245
|
}
|
1187
1246
|
|
1188
|
-
/*
|
1189
|
-
*
|
1247
|
+
/*
|
1248
|
+
* call-seq:
|
1249
|
+
* group.to_pem => String
|
1190
1250
|
*
|
1191
1251
|
* See the OpenSSL documentation for PEM_write_bio_ECPKParameters()
|
1192
1252
|
*/
|
@@ -1195,20 +1255,22 @@ static VALUE ossl_ec_group_to_pem(VALUE self)
|
|
1195
1255
|
return ossl_ec_group_to_string(self, EXPORT_PEM);
|
1196
1256
|
}
|
1197
1257
|
|
1198
|
-
/*
|
1199
|
-
*
|
1258
|
+
/*
|
1259
|
+
* call-seq:
|
1260
|
+
* group.to_der => String
|
1200
1261
|
*
|
1201
|
-
*
|
1262
|
+
* See the OpenSSL documentation for i2d_ECPKParameters_bio()
|
1202
1263
|
*/
|
1203
1264
|
static VALUE ossl_ec_group_to_der(VALUE self)
|
1204
1265
|
{
|
1205
1266
|
return ossl_ec_group_to_string(self, EXPORT_DER);
|
1206
1267
|
}
|
1207
1268
|
|
1208
|
-
/*
|
1209
|
-
*
|
1269
|
+
/*
|
1270
|
+
* call-seq:
|
1271
|
+
* group.to_text => String
|
1210
1272
|
*
|
1211
|
-
*
|
1273
|
+
* See the OpenSSL documentation for ECPKParameters_print()
|
1212
1274
|
*/
|
1213
1275
|
static VALUE ossl_ec_group_to_text(VALUE self)
|
1214
1276
|
{
|
@@ -1216,7 +1278,7 @@ static VALUE ossl_ec_group_to_text(VALUE self)
|
|
1216
1278
|
BIO *out;
|
1217
1279
|
VALUE str;
|
1218
1280
|
|
1219
|
-
|
1281
|
+
GetECGroup(self, group);
|
1220
1282
|
if (!(out = BIO_new(BIO_s_mem()))) {
|
1221
1283
|
ossl_raise(eEC_GROUP, "BIO_new(BIO_s_mem())");
|
1222
1284
|
}
|
@@ -1230,50 +1292,62 @@ static VALUE ossl_ec_group_to_text(VALUE self)
|
|
1230
1292
|
}
|
1231
1293
|
|
1232
1294
|
|
1233
|
-
|
1295
|
+
/*
|
1296
|
+
* OpenSSL::PKey::EC::Point
|
1297
|
+
*/
|
1298
|
+
static void
|
1299
|
+
ossl_ec_point_free(void *ptr)
|
1234
1300
|
{
|
1235
|
-
|
1236
|
-
if (!ec_point->dont_free && ec_point->point)
|
1237
|
-
EC_POINT_clear_free(ec_point->point);
|
1238
|
-
ruby_xfree(ec_point);
|
1301
|
+
EC_POINT_clear_free(ptr);
|
1239
1302
|
}
|
1240
1303
|
|
1241
1304
|
static const rb_data_type_t ossl_ec_point_type = {
|
1242
|
-
"OpenSSL/
|
1305
|
+
"OpenSSL/EC_POINT",
|
1243
1306
|
{
|
1244
1307
|
0, ossl_ec_point_free,
|
1245
1308
|
},
|
1246
1309
|
0, 0, RUBY_TYPED_FREE_IMMEDIATELY,
|
1247
1310
|
};
|
1248
1311
|
|
1249
|
-
static VALUE
|
1312
|
+
static VALUE
|
1313
|
+
ossl_ec_point_alloc(VALUE klass)
|
1314
|
+
{
|
1315
|
+
return TypedData_Wrap_Struct(klass, &ossl_ec_point_type, NULL);
|
1316
|
+
}
|
1317
|
+
|
1318
|
+
static VALUE
|
1319
|
+
ec_point_new(const EC_POINT *point, const EC_GROUP *group)
|
1250
1320
|
{
|
1251
|
-
|
1321
|
+
EC_POINT *point_new;
|
1252
1322
|
VALUE obj;
|
1253
1323
|
|
1254
|
-
obj =
|
1324
|
+
obj = ossl_ec_point_alloc(cEC_POINT);
|
1325
|
+
point_new = EC_POINT_dup(point, group);
|
1326
|
+
if (!point_new)
|
1327
|
+
ossl_raise(eEC_POINT, "EC_POINT_dup");
|
1328
|
+
RTYPEDDATA_DATA(obj) = point_new;
|
1329
|
+
rb_ivar_set(obj, id_i_group, ec_group_new(group));
|
1255
1330
|
|
1256
1331
|
return obj;
|
1257
1332
|
}
|
1258
1333
|
|
1259
1334
|
/*
|
1260
|
-
*
|
1261
|
-
*
|
1262
|
-
*
|
1263
|
-
*
|
1335
|
+
* call-seq:
|
1336
|
+
* OpenSSL::PKey::EC::Point.new(point)
|
1337
|
+
* OpenSSL::PKey::EC::Point.new(group)
|
1338
|
+
* OpenSSL::PKey::EC::Point.new(group, bn)
|
1264
1339
|
*
|
1265
|
-
*
|
1340
|
+
* See the OpenSSL documentation for EC_POINT_*
|
1266
1341
|
*/
|
1267
1342
|
static VALUE ossl_ec_point_initialize(int argc, VALUE *argv, VALUE self)
|
1268
1343
|
{
|
1269
|
-
|
1270
|
-
EC_POINT *point = NULL;
|
1344
|
+
EC_POINT *point;
|
1271
1345
|
VALUE arg1, arg2;
|
1272
1346
|
VALUE group_v = Qnil;
|
1273
1347
|
const EC_GROUP *group = NULL;
|
1274
1348
|
|
1275
|
-
TypedData_Get_Struct(self,
|
1276
|
-
if (
|
1349
|
+
TypedData_Get_Struct(self, EC_POINT, &ossl_ec_point_type, point);
|
1350
|
+
if (point)
|
1277
1351
|
ossl_raise(eEC_POINT, "EC_POINT already initialized");
|
1278
1352
|
|
1279
1353
|
switch (rb_scan_args(argc, argv, "11", &arg1, &arg2)) {
|
@@ -1281,14 +1355,14 @@ static VALUE ossl_ec_point_initialize(int argc, VALUE *argv, VALUE self)
|
|
1281
1355
|
if (rb_obj_is_kind_of(arg1, cEC_POINT)) {
|
1282
1356
|
const EC_POINT *arg_point;
|
1283
1357
|
|
1284
|
-
|
1285
|
-
|
1286
|
-
|
1358
|
+
group_v = rb_attr_get(arg1, id_i_group);
|
1359
|
+
SafeGetECGroup(group_v, group);
|
1360
|
+
SafeGetECPoint(arg1, arg_point);
|
1287
1361
|
|
1288
1362
|
point = EC_POINT_dup(arg_point, group);
|
1289
1363
|
} else if (rb_obj_is_kind_of(arg1, cEC_GROUP)) {
|
1290
1364
|
group_v = arg1;
|
1291
|
-
|
1365
|
+
SafeGetECGroup(group_v, group);
|
1292
1366
|
|
1293
1367
|
point = EC_POINT_new(group);
|
1294
1368
|
} else {
|
@@ -1300,14 +1374,14 @@ static VALUE ossl_ec_point_initialize(int argc, VALUE *argv, VALUE self)
|
|
1300
1374
|
if (!rb_obj_is_kind_of(arg1, cEC_GROUP))
|
1301
1375
|
ossl_raise(rb_eArgError, "1st argument must be OpenSSL::PKey::EC::Group");
|
1302
1376
|
group_v = arg1;
|
1303
|
-
|
1377
|
+
SafeGetECGroup(group_v, group);
|
1304
1378
|
|
1305
1379
|
if (rb_obj_is_kind_of(arg2, cBN)) {
|
1306
1380
|
const BIGNUM *bn = GetBNPtr(arg2);
|
1307
1381
|
|
1308
1382
|
point = EC_POINT_bn2point(group, bn, NULL, ossl_bn_ctx);
|
1309
1383
|
} else {
|
1310
|
-
BIO *in = ossl_obj2bio(arg1);
|
1384
|
+
BIO *in = ossl_obj2bio(&arg1);
|
1311
1385
|
|
1312
1386
|
/* BUG: finish me */
|
1313
1387
|
|
@@ -1328,32 +1402,54 @@ static VALUE ossl_ec_point_initialize(int argc, VALUE *argv, VALUE self)
|
|
1328
1402
|
if (NIL_P(group_v))
|
1329
1403
|
ossl_raise(rb_eRuntimeError, "missing group (internal error)");
|
1330
1404
|
|
1331
|
-
|
1405
|
+
RTYPEDDATA_DATA(self) = point;
|
1406
|
+
rb_ivar_set(self, id_i_group, group_v);
|
1407
|
+
|
1408
|
+
return self;
|
1409
|
+
}
|
1410
|
+
|
1411
|
+
static VALUE
|
1412
|
+
ossl_ec_point_initialize_copy(VALUE self, VALUE other)
|
1413
|
+
{
|
1414
|
+
EC_POINT *point, *point_new;
|
1415
|
+
EC_GROUP *group;
|
1416
|
+
VALUE group_v;
|
1332
1417
|
|
1333
|
-
|
1418
|
+
TypedData_Get_Struct(self, EC_POINT, &ossl_ec_point_type, point_new);
|
1419
|
+
if (point_new)
|
1420
|
+
ossl_raise(eEC_POINT, "EC::Point already initialized");
|
1421
|
+
SafeGetECPoint(other, point);
|
1422
|
+
|
1423
|
+
group_v = rb_obj_dup(rb_attr_get(other, id_i_group));
|
1424
|
+
SafeGetECGroup(group_v, group);
|
1425
|
+
|
1426
|
+
point_new = EC_POINT_dup(point, group);
|
1427
|
+
if (!point_new)
|
1428
|
+
ossl_raise(eEC_POINT, "EC_POINT_dup");
|
1429
|
+
RTYPEDDATA_DATA(self) = point_new;
|
1430
|
+
rb_ivar_set(self, id_i_group, group_v);
|
1334
1431
|
|
1335
1432
|
return self;
|
1336
1433
|
}
|
1337
1434
|
|
1338
1435
|
/*
|
1339
|
-
*
|
1340
|
-
*
|
1341
|
-
*
|
1342
|
-
*
|
1436
|
+
* call-seq:
|
1437
|
+
* point1.eql?(point2) => true | false
|
1438
|
+
* point1 == point2 => true | false
|
1343
1439
|
*/
|
1344
1440
|
static VALUE ossl_ec_point_eql(VALUE a, VALUE b)
|
1345
1441
|
{
|
1346
1442
|
EC_POINT *point1, *point2;
|
1347
|
-
VALUE group_v1 =
|
1348
|
-
VALUE group_v2 =
|
1443
|
+
VALUE group_v1 = rb_attr_get(a, id_i_group);
|
1444
|
+
VALUE group_v2 = rb_attr_get(b, id_i_group);
|
1349
1445
|
const EC_GROUP *group;
|
1350
1446
|
|
1351
1447
|
if (ossl_ec_group_eql(group_v1, group_v2) == Qfalse)
|
1352
1448
|
return Qfalse;
|
1353
1449
|
|
1354
|
-
|
1355
|
-
|
1356
|
-
|
1450
|
+
GetECPoint(a, point1);
|
1451
|
+
SafeGetECPoint(b, point2);
|
1452
|
+
SafeGetECGroup(group_v1, group);
|
1357
1453
|
|
1358
1454
|
if (EC_POINT_cmp(group, point1, point2, ossl_bn_ctx) == 1)
|
1359
1455
|
return Qfalse;
|
@@ -1362,18 +1458,16 @@ static VALUE ossl_ec_point_eql(VALUE a, VALUE b)
|
|
1362
1458
|
}
|
1363
1459
|
|
1364
1460
|
/*
|
1365
|
-
*
|
1366
|
-
*
|
1367
|
-
*
|
1461
|
+
* call-seq:
|
1462
|
+
* point.infinity? => true | false
|
1368
1463
|
*/
|
1369
1464
|
static VALUE ossl_ec_point_is_at_infinity(VALUE self)
|
1370
1465
|
{
|
1371
1466
|
EC_POINT *point;
|
1372
|
-
VALUE group_v = rb_iv_get(self, "@group");
|
1373
1467
|
const EC_GROUP *group;
|
1374
1468
|
|
1375
|
-
|
1376
|
-
|
1469
|
+
GetECPoint(self, point);
|
1470
|
+
GetECPointGroup(self, group);
|
1377
1471
|
|
1378
1472
|
switch (EC_POINT_is_at_infinity(group, point)) {
|
1379
1473
|
case 1: return Qtrue;
|
@@ -1385,18 +1479,16 @@ static VALUE ossl_ec_point_is_at_infinity(VALUE self)
|
|
1385
1479
|
}
|
1386
1480
|
|
1387
1481
|
/*
|
1388
|
-
*
|
1389
|
-
*
|
1390
|
-
*
|
1482
|
+
* call-seq:
|
1483
|
+
* point.on_curve? => true | false
|
1391
1484
|
*/
|
1392
1485
|
static VALUE ossl_ec_point_is_on_curve(VALUE self)
|
1393
1486
|
{
|
1394
1487
|
EC_POINT *point;
|
1395
|
-
VALUE group_v = rb_iv_get(self, "@group");
|
1396
1488
|
const EC_GROUP *group;
|
1397
1489
|
|
1398
|
-
|
1399
|
-
|
1490
|
+
GetECPoint(self, point);
|
1491
|
+
GetECPointGroup(self, group);
|
1400
1492
|
|
1401
1493
|
switch (EC_POINT_is_on_curve(group, point, ossl_bn_ctx)) {
|
1402
1494
|
case 1: return Qtrue;
|
@@ -1408,18 +1500,16 @@ static VALUE ossl_ec_point_is_on_curve(VALUE self)
|
|
1408
1500
|
}
|
1409
1501
|
|
1410
1502
|
/*
|
1411
|
-
*
|
1412
|
-
*
|
1413
|
-
*
|
1503
|
+
* call-seq:
|
1504
|
+
* point.make_affine! => self
|
1414
1505
|
*/
|
1415
1506
|
static VALUE ossl_ec_point_make_affine(VALUE self)
|
1416
1507
|
{
|
1417
1508
|
EC_POINT *point;
|
1418
|
-
VALUE group_v = rb_iv_get(self, "@group");
|
1419
1509
|
const EC_GROUP *group;
|
1420
1510
|
|
1421
|
-
|
1422
|
-
|
1511
|
+
GetECPoint(self, point);
|
1512
|
+
GetECPointGroup(self, group);
|
1423
1513
|
|
1424
1514
|
if (EC_POINT_make_affine(group, point, ossl_bn_ctx) != 1)
|
1425
1515
|
ossl_raise(cEC_POINT, "EC_POINT_make_affine");
|
@@ -1428,18 +1518,16 @@ static VALUE ossl_ec_point_make_affine(VALUE self)
|
|
1428
1518
|
}
|
1429
1519
|
|
1430
1520
|
/*
|
1431
|
-
*
|
1432
|
-
*
|
1433
|
-
*
|
1521
|
+
* call-seq:
|
1522
|
+
* point.invert! => self
|
1434
1523
|
*/
|
1435
1524
|
static VALUE ossl_ec_point_invert(VALUE self)
|
1436
1525
|
{
|
1437
1526
|
EC_POINT *point;
|
1438
|
-
VALUE group_v = rb_iv_get(self, "@group");
|
1439
1527
|
const EC_GROUP *group;
|
1440
1528
|
|
1441
|
-
|
1442
|
-
|
1529
|
+
GetECPoint(self, point);
|
1530
|
+
GetECPointGroup(self, group);
|
1443
1531
|
|
1444
1532
|
if (EC_POINT_invert(group, point, ossl_bn_ctx) != 1)
|
1445
1533
|
ossl_raise(cEC_POINT, "EC_POINT_invert");
|
@@ -1448,18 +1536,16 @@ static VALUE ossl_ec_point_invert(VALUE self)
|
|
1448
1536
|
}
|
1449
1537
|
|
1450
1538
|
/*
|
1451
|
-
*
|
1452
|
-
*
|
1453
|
-
*
|
1539
|
+
* call-seq:
|
1540
|
+
* point.set_to_infinity! => self
|
1454
1541
|
*/
|
1455
1542
|
static VALUE ossl_ec_point_set_to_infinity(VALUE self)
|
1456
1543
|
{
|
1457
1544
|
EC_POINT *point;
|
1458
|
-
VALUE group_v = rb_iv_get(self, "@group");
|
1459
1545
|
const EC_GROUP *group;
|
1460
1546
|
|
1461
|
-
|
1462
|
-
|
1547
|
+
GetECPoint(self, point);
|
1548
|
+
GetECPointGroup(self, group);
|
1463
1549
|
|
1464
1550
|
if (EC_POINT_set_to_infinity(group, point) != 1)
|
1465
1551
|
ossl_raise(cEC_POINT, "EC_POINT_set_to_infinity");
|
@@ -1468,24 +1554,31 @@ static VALUE ossl_ec_point_set_to_infinity(VALUE self)
|
|
1468
1554
|
}
|
1469
1555
|
|
1470
1556
|
/*
|
1471
|
-
*
|
1472
|
-
*
|
1557
|
+
* call-seq:
|
1558
|
+
* point.to_bn(conversion_form = nil) => OpenSSL::BN
|
1473
1559
|
*
|
1474
|
-
*
|
1560
|
+
* Convert the EC point into an octet string and store in an OpenSSL::BN. If
|
1561
|
+
* +conversion_form+ is given, the point data is converted using the specified
|
1562
|
+
* form. If not given, the default form set in the EC::Group object is used.
|
1563
|
+
*
|
1564
|
+
* See also EC::Point#point_conversion_form=.
|
1475
1565
|
*/
|
1476
|
-
static VALUE
|
1566
|
+
static VALUE
|
1567
|
+
ossl_ec_point_to_bn(int argc, VALUE *argv, VALUE self)
|
1477
1568
|
{
|
1478
1569
|
EC_POINT *point;
|
1479
|
-
VALUE bn_obj;
|
1480
|
-
VALUE group_v = rb_iv_get(self, "@group");
|
1570
|
+
VALUE form_obj, bn_obj;
|
1481
1571
|
const EC_GROUP *group;
|
1482
1572
|
point_conversion_form_t form;
|
1483
1573
|
BIGNUM *bn;
|
1484
1574
|
|
1485
|
-
|
1486
|
-
|
1487
|
-
|
1488
|
-
|
1575
|
+
GetECPoint(self, point);
|
1576
|
+
GetECPointGroup(self, group);
|
1577
|
+
rb_scan_args(argc, argv, "01", &form_obj);
|
1578
|
+
if (NIL_P(form_obj))
|
1579
|
+
form = EC_GROUP_get_point_conversion_form(group);
|
1580
|
+
else
|
1581
|
+
form = parse_point_conversion_form_symbol(form_obj);
|
1489
1582
|
|
1490
1583
|
bn_obj = rb_obj_alloc(cBN);
|
1491
1584
|
bn = GetBNPtr(bn_obj);
|
@@ -1497,94 +1590,117 @@ static VALUE ossl_ec_point_to_bn(VALUE self)
|
|
1497
1590
|
}
|
1498
1591
|
|
1499
1592
|
/*
|
1500
|
-
*
|
1501
|
-
*
|
1502
|
-
*
|
1503
|
-
*
|
1504
|
-
*
|
1593
|
+
* call-seq:
|
1594
|
+
* point.mul(bn1 [, bn2]) => point
|
1595
|
+
* point.mul(bns, points [, bn2]) => point
|
1596
|
+
*
|
1597
|
+
* Performs elliptic curve point multiplication.
|
1598
|
+
*
|
1599
|
+
* The first form calculates <tt>bn1 * point + bn2 * G</tt>, where +G+ is the
|
1600
|
+
* generator of the group of +point+. +bn2+ may be omitted, and in that case,
|
1601
|
+
* the result is just <tt>bn1 * point</tt>.
|
1602
|
+
*
|
1603
|
+
* The second form calculates <tt>bns[0] * point + bns[1] * points[0] + ...
|
1604
|
+
* + bns[-1] * points[-1] + bn2 * G</tt>. +bn2+ may be omitted. +bns+ must be
|
1605
|
+
* an array of OpenSSL::BN. +points+ must be an array of
|
1606
|
+
* OpenSSL::PKey::EC::Point. Please note that <tt>points[0]</tt> is not
|
1607
|
+
* multiplied by <tt>bns[0]</tt>, but <tt>bns[1]</tt>.
|
1505
1608
|
*/
|
1506
1609
|
static VALUE ossl_ec_point_mul(int argc, VALUE *argv, VALUE self)
|
1507
1610
|
{
|
1508
|
-
EC_POINT *
|
1611
|
+
EC_POINT *point_self, *point_result;
|
1509
1612
|
const EC_GROUP *group;
|
1510
|
-
VALUE group_v =
|
1511
|
-
VALUE
|
1512
|
-
BIGNUM *
|
1613
|
+
VALUE group_v = rb_attr_get(self, id_i_group);
|
1614
|
+
VALUE arg1, arg2, arg3, result;
|
1615
|
+
const BIGNUM *bn_g = NULL;
|
1513
1616
|
|
1514
|
-
|
1515
|
-
|
1617
|
+
GetECPoint(self, point_self);
|
1618
|
+
SafeGetECGroup(group_v, group);
|
1516
1619
|
|
1517
|
-
|
1518
|
-
ossl_ec_point_initialize(1, &group_v,
|
1519
|
-
|
1620
|
+
result = rb_obj_alloc(cEC_POINT);
|
1621
|
+
ossl_ec_point_initialize(1, &group_v, result);
|
1622
|
+
GetECPoint(result, point_result);
|
1520
1623
|
|
1521
|
-
|
1624
|
+
rb_scan_args(argc, argv, "12", &arg1, &arg2, &arg3);
|
1625
|
+
if (!RB_TYPE_P(arg1, T_ARRAY)) {
|
1626
|
+
BIGNUM *bn = GetBNPtr(arg1);
|
1522
1627
|
|
1523
|
-
|
1524
|
-
|
1525
|
-
|
1526
|
-
|
1527
|
-
}
|
1528
|
-
if (EC_POINT_mul(group, point2, bn2, point1, bn1, ossl_bn_ctx) != 1)
|
1529
|
-
ossl_raise(eEC_POINT, "Multiplication failed");
|
1628
|
+
if (!NIL_P(arg2))
|
1629
|
+
bn_g = GetBNPtr(arg2);
|
1630
|
+
if (EC_POINT_mul(group, point_result, bn_g, point_self, bn, ossl_bn_ctx) != 1)
|
1631
|
+
ossl_raise(eEC_POINT, NULL);
|
1530
1632
|
} else {
|
1531
|
-
|
1532
|
-
|
1533
|
-
|
1534
|
-
|
1535
|
-
|
1536
|
-
|
1537
|
-
|
1538
|
-
|
1539
|
-
|
1540
|
-
|
1541
|
-
|
1633
|
+
/*
|
1634
|
+
* bignums | arg1[0] | arg1[1] | arg1[2] | ...
|
1635
|
+
* points | self | arg2[0] | arg2[1] | ...
|
1636
|
+
*/
|
1637
|
+
long i, num;
|
1638
|
+
VALUE bns_tmp, tmp_p, tmp_b;
|
1639
|
+
const EC_POINT **points;
|
1640
|
+
const BIGNUM **bignums;
|
1641
|
+
|
1642
|
+
Check_Type(arg1, T_ARRAY);
|
1643
|
+
Check_Type(arg2, T_ARRAY);
|
1644
|
+
if (RARRAY_LEN(arg1) != RARRAY_LEN(arg2) + 1) /* arg2 must be 1 larger */
|
1645
|
+
ossl_raise(rb_eArgError, "bns must be 1 longer than points; see the documentation");
|
1646
|
+
|
1647
|
+
num = RARRAY_LEN(arg1);
|
1648
|
+
bns_tmp = rb_ary_tmp_new(num);
|
1649
|
+
bignums = ALLOCV_N(const BIGNUM *, tmp_b, num);
|
1650
|
+
for (i = 0; i < num; i++) {
|
1651
|
+
VALUE item = RARRAY_AREF(arg1, i);
|
1652
|
+
bignums[i] = GetBNPtr(item);
|
1653
|
+
rb_ary_push(bns_tmp, item);
|
1654
|
+
}
|
1542
1655
|
|
1543
|
-
|
1544
|
-
|
1545
|
-
|
1546
|
-
|
1656
|
+
points = ALLOCV_N(const EC_POINT *, tmp_p, num);
|
1657
|
+
points[0] = point_self; /* self */
|
1658
|
+
for (i = 0; i < num - 1; i++)
|
1659
|
+
SafeGetECPoint(RARRAY_AREF(arg2, i), points[i + 1]);
|
1547
1660
|
|
1548
|
-
|
1549
|
-
|
1550
|
-
points = (const EC_POINT **)OPENSSL_malloc(points_len * (int)sizeof(EC_POINT *));
|
1661
|
+
if (!NIL_P(arg3))
|
1662
|
+
bn_g = GetBNPtr(arg3);
|
1551
1663
|
|
1552
|
-
|
1553
|
-
|
1554
|
-
|
1664
|
+
if (EC_POINTs_mul(group, point_result, bn_g, num, points, bignums, ossl_bn_ctx) != 1) {
|
1665
|
+
ALLOCV_END(tmp_b);
|
1666
|
+
ALLOCV_END(tmp_p);
|
1667
|
+
ossl_raise(eEC_POINT, NULL);
|
1668
|
+
}
|
1555
1669
|
|
1556
|
-
|
1557
|
-
|
1558
|
-
}
|
1559
|
-
if (EC_POINTs_mul(group, point2, bn2, points_len, points, bignums, ossl_bn_ctx) != 1) {
|
1560
|
-
OPENSSL_free((void *)bignums);
|
1561
|
-
OPENSSL_free((void *)points);
|
1562
|
-
ossl_raise(eEC_POINT, "Multiplication failed");
|
1563
|
-
}
|
1564
|
-
OPENSSL_free((void *)bignums);
|
1565
|
-
OPENSSL_free((void *)points);
|
1670
|
+
ALLOCV_END(tmp_b);
|
1671
|
+
ALLOCV_END(tmp_p);
|
1566
1672
|
}
|
1567
1673
|
|
1568
|
-
return
|
1569
|
-
}
|
1570
|
-
|
1571
|
-
static void no_copy(VALUE klass)
|
1572
|
-
{
|
1573
|
-
rb_undef_method(klass, "copy");
|
1574
|
-
rb_undef_method(klass, "clone");
|
1575
|
-
rb_undef_method(klass, "dup");
|
1576
|
-
rb_undef_method(klass, "initialize_copy");
|
1674
|
+
return result;
|
1577
1675
|
}
|
1578
1676
|
|
1579
1677
|
void Init_ossl_ec(void)
|
1580
1678
|
{
|
1581
|
-
#
|
1582
|
-
|
1679
|
+
#undef rb_intern
|
1680
|
+
#if 0
|
1583
1681
|
mPKey = rb_define_module_under(mOSSL, "PKey");
|
1682
|
+
cPKey = rb_define_class_under(mPKey, "PKey", rb_cObject);
|
1683
|
+
eOSSLError = rb_define_class_under(mOSSL, "OpenSSLError", rb_eStandardError);
|
1684
|
+
ePKeyError = rb_define_class_under(mPKey, "PKeyError", eOSSLError);
|
1584
1685
|
#endif
|
1585
1686
|
|
1586
1687
|
eECError = rb_define_class_under(mPKey, "ECError", ePKeyError);
|
1587
1688
|
|
1689
|
+
/*
|
1690
|
+
* Document-class: OpenSSL::PKey::EC
|
1691
|
+
*
|
1692
|
+
* OpenSSL::PKey::EC provides access to Elliptic Curve Digital Signature
|
1693
|
+
* Algorithm (ECDSA) and Elliptic Curve Diffie-Hellman (ECDH).
|
1694
|
+
*
|
1695
|
+
* === Key exchange
|
1696
|
+
* ec1 = OpenSSL::PKey::EC.generate("prime256v1")
|
1697
|
+
* ec2 = OpenSSL::PKey::EC.generate("prime256v1")
|
1698
|
+
* # ec1 and ec2 have own private key respectively
|
1699
|
+
* shared_key1 = ec1.dh_compute_key(ec2.public_key)
|
1700
|
+
* shared_key2 = ec2.dh_compute_key(ec1.public_key)
|
1701
|
+
*
|
1702
|
+
* p shared_key1 == shared_key2 #=> true
|
1703
|
+
*/
|
1588
1704
|
cEC = rb_define_class_under(mPKey, "EC", cPKey);
|
1589
1705
|
cEC_GROUP = rb_define_class_under(cEC, "Group", rb_cObject);
|
1590
1706
|
cEC_POINT = rb_define_class_under(cEC, "Point", rb_cObject);
|
@@ -1602,13 +1718,16 @@ void Init_ossl_ec(void)
|
|
1602
1718
|
ID_compressed = rb_intern("compressed");
|
1603
1719
|
ID_hybrid = rb_intern("hybrid");
|
1604
1720
|
|
1605
|
-
|
1606
|
-
|
1721
|
+
rb_define_const(cEC, "NAMED_CURVE", INT2NUM(OPENSSL_EC_NAMED_CURVE));
|
1722
|
+
#if defined(OPENSSL_EC_EXPLICIT_CURVE)
|
1723
|
+
rb_define_const(cEC, "EXPLICIT_CURVE", INT2NUM(OPENSSL_EC_EXPLICIT_CURVE));
|
1607
1724
|
#endif
|
1608
1725
|
|
1609
1726
|
rb_define_singleton_method(cEC, "builtin_curves", ossl_s_builtin_curves, 0);
|
1610
1727
|
|
1728
|
+
rb_define_singleton_method(cEC, "generate", ossl_ec_key_s_generate, 1);
|
1611
1729
|
rb_define_method(cEC, "initialize", ossl_ec_key_initialize, -1);
|
1730
|
+
rb_define_copy_func(cEC, ossl_ec_key_initialize_copy);
|
1612
1731
|
/* copy/dup/cmp */
|
1613
1732
|
|
1614
1733
|
rb_define_method(cEC, "group", ossl_ec_key_get_group, 0);
|
@@ -1617,8 +1736,10 @@ void Init_ossl_ec(void)
|
|
1617
1736
|
rb_define_method(cEC, "private_key=", ossl_ec_key_set_private_key, 1);
|
1618
1737
|
rb_define_method(cEC, "public_key", ossl_ec_key_get_public_key, 0);
|
1619
1738
|
rb_define_method(cEC, "public_key=", ossl_ec_key_set_public_key, 1);
|
1620
|
-
rb_define_method(cEC, "
|
1621
|
-
rb_define_method(cEC, "
|
1739
|
+
rb_define_method(cEC, "private?", ossl_ec_key_is_private, 0);
|
1740
|
+
rb_define_method(cEC, "public?", ossl_ec_key_is_public, 0);
|
1741
|
+
rb_define_alias(cEC, "private_key?", "private?");
|
1742
|
+
rb_define_alias(cEC, "public_key?", "public?");
|
1622
1743
|
/* rb_define_method(cEC, "", ossl_ec_key_get_, 0);
|
1623
1744
|
rb_define_method(cEC, "=", ossl_ec_key_set_ 1);
|
1624
1745
|
set/get enc_flags
|
@@ -1626,7 +1747,8 @@ void Init_ossl_ec(void)
|
|
1626
1747
|
set/get asn1_flag (can use ruby to call self.group.asn1_flag)
|
1627
1748
|
set/get precompute_mult
|
1628
1749
|
*/
|
1629
|
-
rb_define_method(cEC, "generate_key", ossl_ec_key_generate_key, 0);
|
1750
|
+
rb_define_method(cEC, "generate_key!", ossl_ec_key_generate_key, 0);
|
1751
|
+
rb_define_alias(cEC, "generate_key", "generate_key!");
|
1630
1752
|
rb_define_method(cEC, "check_key", ossl_ec_key_check_key, 0);
|
1631
1753
|
|
1632
1754
|
rb_define_method(cEC, "dh_compute_key", ossl_ec_key_dh_compute_key, 1);
|
@@ -1642,6 +1764,7 @@ void Init_ossl_ec(void)
|
|
1642
1764
|
|
1643
1765
|
rb_define_alloc_func(cEC_GROUP, ossl_ec_group_alloc);
|
1644
1766
|
rb_define_method(cEC_GROUP, "initialize", ossl_ec_group_initialize, -1);
|
1767
|
+
rb_define_copy_func(cEC_GROUP, ossl_ec_group_initialize_copy);
|
1645
1768
|
rb_define_method(cEC_GROUP, "eql?", ossl_ec_group_eql, 1);
|
1646
1769
|
rb_define_alias(cEC_GROUP, "==", "eql?");
|
1647
1770
|
/* copy/dup/cmp */
|
@@ -1677,6 +1800,7 @@ void Init_ossl_ec(void)
|
|
1677
1800
|
|
1678
1801
|
rb_define_alloc_func(cEC_POINT, ossl_ec_point_alloc);
|
1679
1802
|
rb_define_method(cEC_POINT, "initialize", ossl_ec_point_initialize, -1);
|
1803
|
+
rb_define_copy_func(cEC_POINT, ossl_ec_point_initialize_copy);
|
1680
1804
|
rb_attr(cEC_POINT, rb_intern("group"), 1, 0, 0);
|
1681
1805
|
rb_define_method(cEC_POINT, "eql?", ossl_ec_point_eql, 1);
|
1682
1806
|
rb_define_alias(cEC_POINT, "==", "eql?");
|
@@ -1688,12 +1812,10 @@ void Init_ossl_ec(void)
|
|
1688
1812
|
rb_define_method(cEC_POINT, "set_to_infinity!", ossl_ec_point_set_to_infinity, 0);
|
1689
1813
|
/* all the other methods */
|
1690
1814
|
|
1691
|
-
rb_define_method(cEC_POINT, "to_bn", ossl_ec_point_to_bn,
|
1815
|
+
rb_define_method(cEC_POINT, "to_bn", ossl_ec_point_to_bn, -1);
|
1692
1816
|
rb_define_method(cEC_POINT, "mul", ossl_ec_point_mul, -1);
|
1693
1817
|
|
1694
|
-
|
1695
|
-
no_copy(cEC_GROUP);
|
1696
|
-
no_copy(cEC_POINT);
|
1818
|
+
id_i_group = rb_intern("@group");
|
1697
1819
|
}
|
1698
1820
|
|
1699
1821
|
#else /* defined NO_EC */
|