openssl 3.3.2 → 4.0.0

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.
Files changed (55) hide show
  1. checksums.yaml +4 -4
  2. data/CONTRIBUTING.md +3 -0
  3. data/History.md +85 -0
  4. data/README.md +12 -11
  5. data/ext/openssl/extconf.rb +30 -69
  6. data/ext/openssl/openssl_missing.h +0 -206
  7. data/ext/openssl/ossl.c +280 -301
  8. data/ext/openssl/ossl.h +15 -10
  9. data/ext/openssl/ossl_asn1.c +598 -406
  10. data/ext/openssl/ossl_asn1.h +15 -1
  11. data/ext/openssl/ossl_bio.c +3 -3
  12. data/ext/openssl/ossl_bn.c +286 -291
  13. data/ext/openssl/ossl_cipher.c +252 -203
  14. data/ext/openssl/ossl_cipher.h +10 -1
  15. data/ext/openssl/ossl_config.c +1 -6
  16. data/ext/openssl/ossl_digest.c +74 -43
  17. data/ext/openssl/ossl_digest.h +9 -1
  18. data/ext/openssl/ossl_engine.c +39 -103
  19. data/ext/openssl/ossl_hmac.c +30 -36
  20. data/ext/openssl/ossl_kdf.c +42 -53
  21. data/ext/openssl/ossl_ns_spki.c +31 -37
  22. data/ext/openssl/ossl_ocsp.c +214 -241
  23. data/ext/openssl/ossl_pkcs12.c +26 -26
  24. data/ext/openssl/ossl_pkcs7.c +175 -145
  25. data/ext/openssl/ossl_pkey.c +162 -178
  26. data/ext/openssl/ossl_pkey.h +99 -99
  27. data/ext/openssl/ossl_pkey_dh.c +31 -68
  28. data/ext/openssl/ossl_pkey_dsa.c +15 -54
  29. data/ext/openssl/ossl_pkey_ec.c +179 -237
  30. data/ext/openssl/ossl_pkey_rsa.c +56 -103
  31. data/ext/openssl/ossl_provider.c +0 -7
  32. data/ext/openssl/ossl_rand.c +7 -14
  33. data/ext/openssl/ossl_ssl.c +478 -353
  34. data/ext/openssl/ossl_ssl.h +8 -8
  35. data/ext/openssl/ossl_ssl_session.c +93 -97
  36. data/ext/openssl/ossl_ts.c +81 -127
  37. data/ext/openssl/ossl_x509.c +9 -28
  38. data/ext/openssl/ossl_x509attr.c +33 -54
  39. data/ext/openssl/ossl_x509cert.c +69 -100
  40. data/ext/openssl/ossl_x509crl.c +78 -89
  41. data/ext/openssl/ossl_x509ext.c +45 -66
  42. data/ext/openssl/ossl_x509name.c +63 -88
  43. data/ext/openssl/ossl_x509req.c +55 -62
  44. data/ext/openssl/ossl_x509revoked.c +27 -41
  45. data/ext/openssl/ossl_x509store.c +38 -56
  46. data/lib/openssl/buffering.rb +30 -24
  47. data/lib/openssl/digest.rb +1 -1
  48. data/lib/openssl/pkey.rb +71 -49
  49. data/lib/openssl/ssl.rb +12 -79
  50. data/lib/openssl/version.rb +2 -1
  51. data/lib/openssl/x509.rb +9 -0
  52. data/lib/openssl.rb +9 -6
  53. metadata +1 -3
  54. data/ext/openssl/openssl_missing.c +0 -40
  55. data/lib/openssl/asn1.rb +0 -188
@@ -13,14 +13,14 @@
13
13
  TypedData_Wrap_Struct((klass), &ossl_x509rev_type, 0)
14
14
  #define SetX509Rev(obj, rev) do { \
15
15
  if (!(rev)) { \
16
- ossl_raise(rb_eRuntimeError, "REV wasn't initialized!"); \
16
+ ossl_raise(rb_eRuntimeError, "REV wasn't initialized!"); \
17
17
  } \
18
18
  RTYPEDDATA_DATA(obj) = (rev); \
19
19
  } while (0)
20
20
  #define GetX509Rev(obj, rev) do { \
21
21
  TypedData_Get_Struct((obj), X509_REVOKED, &ossl_x509rev_type, (rev)); \
22
22
  if (!(rev)) { \
23
- ossl_raise(rb_eRuntimeError, "REV wasn't initialized!"); \
23
+ ossl_raise(rb_eRuntimeError, "REV wasn't initialized!"); \
24
24
  } \
25
25
  } while (0)
26
26
 
@@ -39,7 +39,7 @@ ossl_x509rev_free(void *ptr)
39
39
  static const rb_data_type_t ossl_x509rev_type = {
40
40
  "OpenSSL/X509/REV",
41
41
  {
42
- 0, ossl_x509rev_free,
42
+ 0, ossl_x509rev_free,
43
43
  },
44
44
  0, 0, RUBY_TYPED_FREE_IMMEDIATELY | RUBY_TYPED_WB_PROTECTED,
45
45
  };
@@ -54,14 +54,9 @@ ossl_x509revoked_new(X509_REVOKED *rev)
54
54
  VALUE obj;
55
55
 
56
56
  obj = NewX509Rev(cX509Rev);
57
- if (!rev) {
58
- new = X509_REVOKED_new();
59
- } else {
60
- new = X509_REVOKED_dup(rev);
61
- }
62
- if (!new) {
63
- ossl_raise(eX509RevError, NULL);
64
- }
57
+ new = X509_REVOKED_dup(rev);
58
+ if (!new)
59
+ ossl_raise(eX509RevError, "X509_REVOKED_dup");
65
60
  SetX509Rev(obj, new);
66
61
 
67
62
  return obj;
@@ -74,7 +69,7 @@ DupX509RevokedPtr(VALUE obj)
74
69
 
75
70
  GetX509Rev(obj, rev);
76
71
  if (!(new = X509_REVOKED_dup(rev))) {
77
- ossl_raise(eX509RevError, NULL);
72
+ ossl_raise(eX509RevError, NULL);
78
73
  }
79
74
 
80
75
  return new;
@@ -91,7 +86,7 @@ ossl_x509revoked_alloc(VALUE klass)
91
86
 
92
87
  obj = NewX509Rev(klass);
93
88
  if (!(rev = X509_REVOKED_new())) {
94
- ossl_raise(eX509RevError, NULL);
89
+ ossl_raise(eX509RevError, NULL);
95
90
  }
96
91
  SetX509Rev(obj, rev);
97
92
 
@@ -105,6 +100,7 @@ ossl_x509revoked_initialize(int argc, VALUE *argv, VALUE self)
105
100
  return self;
106
101
  }
107
102
 
103
+ /* :nodoc: */
108
104
  static VALUE
109
105
  ossl_x509revoked_initialize_copy(VALUE self, VALUE other)
110
106
  {
@@ -116,7 +112,7 @@ ossl_x509revoked_initialize_copy(VALUE self, VALUE other)
116
112
 
117
113
  rev_new = X509_REVOKED_dup(rev_other);
118
114
  if (!rev_new)
119
- ossl_raise(eX509RevError, "X509_REVOKED_dup");
115
+ ossl_raise(eX509RevError, "X509_REVOKED_dup");
120
116
 
121
117
  SetX509Rev(self, rev_new);
122
118
  X509_REVOKED_free(rev);
@@ -143,8 +139,8 @@ ossl_x509revoked_set_serial(VALUE self, VALUE num)
143
139
  GetX509Rev(self, rev);
144
140
  asn1int = num_to_asn1integer(num, NULL);
145
141
  if (!X509_REVOKED_set_serialNumber(rev, asn1int)) {
146
- ASN1_INTEGER_free(asn1int);
147
- ossl_raise(eX509RevError, "X509_REVOKED_set_serialNumber");
142
+ ASN1_INTEGER_free(asn1int);
143
+ ossl_raise(eX509RevError, "X509_REVOKED_set_serialNumber");
148
144
  }
149
145
  ASN1_INTEGER_free(asn1int);
150
146
 
@@ -160,7 +156,7 @@ ossl_x509revoked_get_time(VALUE self)
160
156
  GetX509Rev(self, rev);
161
157
  time = X509_REVOKED_get0_revocationDate(rev);
162
158
  if (!time)
163
- return Qnil;
159
+ return Qnil;
164
160
 
165
161
  return asn1time_to_time(time);
166
162
  }
@@ -174,8 +170,8 @@ ossl_x509revoked_set_time(VALUE self, VALUE time)
174
170
  GetX509Rev(self, rev);
175
171
  asn1time = ossl_x509_time_adjust(NULL, time);
176
172
  if (!X509_REVOKED_set_revocationDate(rev, asn1time)) {
177
- ASN1_TIME_free(asn1time);
178
- ossl_raise(eX509RevError, "X509_REVOKED_set_revocationDate");
173
+ ASN1_TIME_free(asn1time);
174
+ ossl_raise(eX509RevError, "X509_REVOKED_set_revocationDate");
179
175
  }
180
176
  ASN1_TIME_free(asn1time);
181
177
 
@@ -194,14 +190,10 @@ ossl_x509revoked_get_extensions(VALUE self)
194
190
 
195
191
  GetX509Rev(self, rev);
196
192
  count = X509_REVOKED_get_ext_count(rev);
197
- if (count < 0) {
198
- OSSL_Debug("count < 0???");
199
- return rb_ary_new();
200
- }
201
- ary = rb_ary_new2(count);
193
+ ary = rb_ary_new_capa(count);
202
194
  for (i=0; i<count; i++) {
203
- ext = X509_REVOKED_get_ext(rev, i);
204
- rb_ary_push(ary, ossl_x509ext_new(ext));
195
+ ext = X509_REVOKED_get_ext(rev, i);
196
+ rb_ary_push(ary, ossl_x509ext_new(ext));
205
197
  }
206
198
 
207
199
  return ary;
@@ -220,17 +212,17 @@ ossl_x509revoked_set_extensions(VALUE self, VALUE ary)
220
212
 
221
213
  Check_Type(ary, T_ARRAY);
222
214
  for (i=0; i<RARRAY_LEN(ary); i++) {
223
- OSSL_Check_Kind(RARRAY_AREF(ary, i), cX509Ext);
215
+ OSSL_Check_Kind(RARRAY_AREF(ary, i), cX509Ext);
224
216
  }
225
217
  GetX509Rev(self, rev);
226
218
  for (i = X509_REVOKED_get_ext_count(rev); i > 0; i--)
227
219
  X509_EXTENSION_free(X509_REVOKED_delete_ext(rev, 0));
228
220
  for (i=0; i<RARRAY_LEN(ary); i++) {
229
- item = RARRAY_AREF(ary, i);
230
- ext = GetX509ExtPtr(item);
231
- if(!X509_REVOKED_add_ext(rev, ext, -1)) {
232
- ossl_raise(eX509RevError, "X509_REVOKED_add_ext");
233
- }
221
+ item = RARRAY_AREF(ary, i);
222
+ ext = GetX509ExtPtr(item);
223
+ if(!X509_REVOKED_add_ext(rev, ext, -1)) {
224
+ ossl_raise(eX509RevError, "X509_REVOKED_add_ext");
225
+ }
234
226
  }
235
227
 
236
228
  return ary;
@@ -243,7 +235,7 @@ ossl_x509revoked_add_extension(VALUE self, VALUE ext)
243
235
 
244
236
  GetX509Rev(self, rev);
245
237
  if (!X509_REVOKED_add_ext(rev, GetX509ExtPtr(ext), -1)) {
246
- ossl_raise(eX509RevError, NULL);
238
+ ossl_raise(eX509RevError, NULL);
247
239
  }
248
240
 
249
241
  return ext;
@@ -260,11 +252,11 @@ ossl_x509revoked_to_der(VALUE self)
260
252
  GetX509Rev(self, rev);
261
253
  len = i2d_X509_REVOKED(rev, NULL);
262
254
  if (len <= 0)
263
- ossl_raise(eX509RevError, "i2d_X509_REVOKED");
255
+ ossl_raise(eX509RevError, "i2d_X509_REVOKED");
264
256
  str = rb_str_new(NULL, len);
265
257
  p = (unsigned char *)RSTRING_PTR(str);
266
258
  if (i2d_X509_REVOKED(rev, &p) <= 0)
267
- ossl_raise(eX509RevError, "i2d_X509_REVOKED");
259
+ ossl_raise(eX509RevError, "i2d_X509_REVOKED");
268
260
  ossl_str_adjust(str, p);
269
261
  return str;
270
262
  }
@@ -275,12 +267,6 @@ ossl_x509revoked_to_der(VALUE self)
275
267
  void
276
268
  Init_ossl_x509revoked(void)
277
269
  {
278
- #if 0
279
- mOSSL = rb_define_module("OpenSSL");
280
- eOSSLError = rb_define_class_under(mOSSL, "OpenSSLError", rb_eStandardError);
281
- mX509 = rb_define_module_under(mOSSL, "X509");
282
- #endif
283
-
284
270
  eX509RevError = rb_define_class_under(mX509, "RevokedError", eOSSLError);
285
271
 
286
272
  cX509Rev = rb_define_class_under(mX509, "Revoked", rb_cObject);
@@ -13,14 +13,14 @@
13
13
  TypedData_Wrap_Struct((klass), &ossl_x509store_type, 0)
14
14
  #define SetX509Store(obj, st) do { \
15
15
  if (!(st)) { \
16
- ossl_raise(rb_eRuntimeError, "STORE wasn't initialized!"); \
16
+ ossl_raise(rb_eRuntimeError, "STORE wasn't initialized!"); \
17
17
  } \
18
18
  RTYPEDDATA_DATA(obj) = (st); \
19
19
  } while (0)
20
20
  #define GetX509Store(obj, st) do { \
21
21
  TypedData_Get_Struct((obj), X509_STORE, &ossl_x509store_type, (st)); \
22
22
  if (!(st)) { \
23
- ossl_raise(rb_eRuntimeError, "STORE wasn't initialized!"); \
23
+ ossl_raise(rb_eRuntimeError, "STORE wasn't initialized!"); \
24
24
  } \
25
25
  } while (0)
26
26
 
@@ -28,14 +28,14 @@
28
28
  TypedData_Wrap_Struct((klass), &ossl_x509stctx_type, 0)
29
29
  #define SetX509StCtx(obj, ctx) do { \
30
30
  if (!(ctx)) { \
31
- ossl_raise(rb_eRuntimeError, "STORE_CTX wasn't initialized!"); \
31
+ ossl_raise(rb_eRuntimeError, "STORE_CTX wasn't initialized!"); \
32
32
  } \
33
33
  RTYPEDDATA_DATA(obj) = (ctx); \
34
34
  } while (0)
35
35
  #define GetX509StCtx(obj, ctx) do { \
36
36
  TypedData_Get_Struct((obj), X509_STORE_CTX, &ossl_x509stctx_type, (ctx)); \
37
37
  if (!(ctx)) { \
38
- ossl_raise(rb_eRuntimeError, "STORE_CTX is out of scope!"); \
38
+ ossl_raise(rb_eRuntimeError, "STORE_CTX is out of scope!"); \
39
39
  } \
40
40
  } while (0)
41
41
 
@@ -62,7 +62,7 @@ call_verify_cb_proc(VALUE arg)
62
62
  {
63
63
  struct ossl_verify_cb_args *args = (struct ossl_verify_cb_args *)arg;
64
64
  return rb_funcall(args->proc, rb_intern("call"), 2,
65
- args->preverify_ok, args->store_ctx);
65
+ args->preverify_ok, args->store_ctx);
66
66
  }
67
67
 
68
68
  int
@@ -73,33 +73,33 @@ ossl_verify_cb_call(VALUE proc, int ok, X509_STORE_CTX *ctx)
73
73
  int state;
74
74
 
75
75
  if (NIL_P(proc))
76
- return ok;
76
+ return ok;
77
77
 
78
78
  ret = Qfalse;
79
79
  rctx = rb_protect(ossl_x509stctx_new_i, (VALUE)ctx, &state);
80
80
  if (state) {
81
- rb_set_errinfo(Qnil);
82
- rb_warn("StoreContext initialization failure");
81
+ rb_set_errinfo(Qnil);
82
+ rb_warn("StoreContext initialization failure");
83
83
  }
84
84
  else {
85
- args.proc = proc;
86
- args.preverify_ok = ok ? Qtrue : Qfalse;
87
- args.store_ctx = rctx;
88
- ret = rb_protect(call_verify_cb_proc, (VALUE)&args, &state);
89
- if (state) {
90
- rb_set_errinfo(Qnil);
91
- rb_warn("exception in verify_callback is ignored");
92
- }
93
- RTYPEDDATA_DATA(rctx) = NULL;
85
+ args.proc = proc;
86
+ args.preverify_ok = ok ? Qtrue : Qfalse;
87
+ args.store_ctx = rctx;
88
+ ret = rb_protect(call_verify_cb_proc, (VALUE)&args, &state);
89
+ if (state) {
90
+ rb_set_errinfo(Qnil);
91
+ rb_warn("exception in verify_callback is ignored");
92
+ }
93
+ RTYPEDDATA_DATA(rctx) = NULL;
94
94
  }
95
95
  if (ret == Qtrue) {
96
- X509_STORE_CTX_set_error(ctx, X509_V_OK);
97
- ok = 1;
96
+ X509_STORE_CTX_set_error(ctx, X509_V_OK);
97
+ ok = 1;
98
98
  }
99
99
  else {
100
- if (X509_STORE_CTX_get_error(ctx) == X509_V_OK)
101
- X509_STORE_CTX_set_error(ctx, X509_V_ERR_CERT_REJECTED);
102
- ok = 0;
100
+ if (X509_STORE_CTX_get_error(ctx) == X509_V_OK)
101
+ X509_STORE_CTX_set_error(ctx, X509_V_ERR_CERT_REJECTED);
102
+ ok = 0;
103
103
  }
104
104
 
105
105
  return ok;
@@ -159,10 +159,10 @@ x509store_verify_cb(int ok, X509_STORE_CTX *ctx)
159
159
 
160
160
  proc = (VALUE)X509_STORE_CTX_get_ex_data(ctx, stctx_ex_verify_cb_idx);
161
161
  if (!proc)
162
- proc = (VALUE)X509_STORE_get_ex_data(X509_STORE_CTX_get0_store(ctx),
163
- store_ex_verify_cb_idx);
162
+ proc = (VALUE)X509_STORE_get_ex_data(X509_STORE_CTX_get0_store(ctx),
163
+ store_ex_verify_cb_idx);
164
164
  if (!proc)
165
- return ok;
165
+ return ok;
166
166
 
167
167
  return ossl_verify_cb_call(proc, ok, ctx);
168
168
  }
@@ -191,8 +191,8 @@ ossl_x509store_set_vfy_cb(VALUE self, VALUE cb)
191
191
 
192
192
  GetX509Store(self, store);
193
193
  rb_iv_set(self, "@verify_callback", cb);
194
- // We don't need to trigger a write barrier because `rb_iv_set` did it.
195
194
  X509_STORE_set_ex_data(store, store_ex_verify_cb_idx, (void *)cb);
195
+ RB_OBJ_WRITTEN(self, Qundef, cb);
196
196
 
197
197
  return cb;
198
198
  }
@@ -212,10 +212,6 @@ ossl_x509store_initialize(int argc, VALUE *argv, VALUE self)
212
212
  GetX509Store(self, store);
213
213
  if (argc != 0)
214
214
  rb_warn("OpenSSL::X509::Store.new does not take any arguments");
215
- #if !defined(HAVE_OPAQUE_OPENSSL)
216
- /* [Bug #405] [Bug #1678] [Bug #3000]; already fixed? */
217
- store->ex_data.sk = NULL;
218
- #endif
219
215
  X509_STORE_set_verify_cb(store, x509store_verify_cb);
220
216
  ossl_x509store_set_vfy_cb(self, Qnil);
221
217
 
@@ -332,11 +328,7 @@ ossl_x509store_set_time(VALUE self, VALUE time)
332
328
  X509_VERIFY_PARAM *param;
333
329
 
334
330
  GetX509Store(self, store);
335
- #ifdef HAVE_X509_STORE_GET0_PARAM
336
331
  param = X509_STORE_get0_param(store);
337
- #else
338
- param = store->param;
339
- #endif
340
332
  X509_VERIFY_PARAM_set_time(param, NUM2LONG(rb_Integer(time)));
341
333
  return time;
342
334
  }
@@ -365,15 +357,6 @@ ossl_x509store_add_file(VALUE self, VALUE file)
365
357
  ossl_raise(eX509StoreError, "X509_STORE_add_lookup");
366
358
  if (X509_LOOKUP_load_file(lookup, path, X509_FILETYPE_PEM) != 1)
367
359
  ossl_raise(eX509StoreError, "X509_LOOKUP_load_file");
368
- #if OPENSSL_VERSION_NUMBER < 0x10101000 || defined(LIBRESSL_VERSION_NUMBER)
369
- /*
370
- * X509_load_cert_crl_file() which is called from X509_LOOKUP_load_file()
371
- * did not check the return value of X509_STORE_add_{cert,crl}(), leaking
372
- * "cert already in hash table" errors on the error queue, if duplicate
373
- * certificates are found. This will be fixed by OpenSSL 1.1.1.
374
- */
375
- ossl_clear_error();
376
- #endif
377
360
 
378
361
  return self;
379
362
  }
@@ -501,7 +484,7 @@ ossl_x509store_verify(int argc, VALUE *argv, VALUE self)
501
484
  rb_scan_args(argc, argv, "11", &cert, &chain);
502
485
  ctx = rb_funcall(cX509StoreContext, rb_intern("new"), 3, self, cert, chain);
503
486
  proc = rb_block_given_p() ? rb_block_proc() :
504
- rb_iv_get(self, "@verify_callback");
487
+ rb_iv_get(self, "@verify_callback");
505
488
  rb_iv_set(ctx, "@verify_callback", proc);
506
489
  result = rb_funcall(ctx, rb_intern("verify"), 0);
507
490
 
@@ -530,9 +513,9 @@ ossl_x509stctx_free(void *ptr)
530
513
  {
531
514
  X509_STORE_CTX *ctx = ptr;
532
515
  if (X509_STORE_CTX_get0_untrusted(ctx))
533
- sk_X509_pop_free(X509_STORE_CTX_get0_untrusted(ctx), X509_free);
516
+ sk_X509_pop_free(X509_STORE_CTX_get0_untrusted(ctx), X509_free);
534
517
  if (X509_STORE_CTX_get0_cert(ctx))
535
- X509_free(X509_STORE_CTX_get0_cert(ctx));
518
+ X509_free(X509_STORE_CTX_get0_cert(ctx));
536
519
  X509_STORE_CTX_free(ctx);
537
520
  }
538
521
 
@@ -628,6 +611,7 @@ ossl_x509stctx_verify(VALUE self)
628
611
  GetX509StCtx(self, ctx);
629
612
  VALUE cb = rb_iv_get(self, "@verify_callback");
630
613
  X509_STORE_CTX_set_ex_data(ctx, stctx_ex_verify_cb_idx, (void *)cb);
614
+ RB_OBJ_WRITTEN(self, Qundef, cb);
631
615
 
632
616
  switch (X509_verify_cert(ctx)) {
633
617
  case 1:
@@ -752,10 +736,14 @@ static VALUE
752
736
  ossl_x509stctx_get_curr_cert(VALUE self)
753
737
  {
754
738
  X509_STORE_CTX *ctx;
739
+ X509 *x509;
755
740
 
756
741
  GetX509StCtx(self, ctx);
742
+ x509 = X509_STORE_CTX_get_current_cert(ctx);
743
+ if (!x509)
744
+ return Qnil;
757
745
 
758
- return ossl_x509_new(X509_STORE_CTX_get_current_cert(ctx));
746
+ return ossl_x509_new(x509);
759
747
  }
760
748
 
761
749
  /*
@@ -775,7 +763,7 @@ ossl_x509stctx_get_curr_crl(VALUE self)
775
763
  GetX509StCtx(self, ctx);
776
764
  crl = X509_STORE_CTX_get0_current_crl(ctx);
777
765
  if (!crl)
778
- return Qnil;
766
+ return Qnil;
779
767
 
780
768
  return ossl_x509crl_new(crl);
781
769
  }
@@ -871,19 +859,13 @@ void
871
859
  Init_ossl_x509store(void)
872
860
  {
873
861
  #undef rb_intern
874
- #if 0
875
- mOSSL = rb_define_module("OpenSSL");
876
- eOSSLError = rb_define_class_under(mOSSL, "OpenSSLError", rb_eStandardError);
877
- mX509 = rb_define_module_under(mOSSL, "X509");
878
- #endif
879
-
880
862
  /* Register ext_data slot for verify callback Proc */
881
863
  stctx_ex_verify_cb_idx = X509_STORE_CTX_get_ex_new_index(0, (void *)"stctx_ex_verify_cb_idx", 0, 0, 0);
882
864
  if (stctx_ex_verify_cb_idx < 0)
883
- ossl_raise(eOSSLError, "X509_STORE_CTX_get_ex_new_index");
865
+ ossl_raise(eOSSLError, "X509_STORE_CTX_get_ex_new_index");
884
866
  store_ex_verify_cb_idx = X509_STORE_get_ex_new_index(0, (void *)"store_ex_verify_cb_idx", 0, 0, 0);
885
867
  if (store_ex_verify_cb_idx < 0)
886
- ossl_raise(eOSSLError, "X509_STORE_get_ex_new_index");
868
+ ossl_raise(eOSSLError, "X509_STORE_get_ex_new_index");
887
869
 
888
870
  eX509StoreError = rb_define_class_under(mX509, "StoreError", eOSSLError);
889
871
 
@@ -24,25 +24,21 @@ module OpenSSL::Buffering
24
24
 
25
25
  # A buffer which will retain binary encoding.
26
26
  class Buffer < String
27
- BINARY = Encoding::BINARY
28
-
29
- def initialize
30
- super
31
-
32
- force_encoding(BINARY)
33
- end
27
+ unless String.method_defined?(:append_as_bytes)
28
+ alias_method :_append, :<<
29
+ def append_as_bytes(string)
30
+ if string.encoding == Encoding::BINARY
31
+ _append(string)
32
+ else
33
+ _append(string.b)
34
+ end
34
35
 
35
- def << string
36
- if string.encoding == BINARY
37
- super(string)
38
- else
39
- super(string.b)
36
+ self
40
37
  end
41
-
42
- return self
43
38
  end
44
39
 
45
- alias concat <<
40
+ undef_method :concat
41
+ undef_method :<<
46
42
  end
47
43
 
48
44
  ##
@@ -77,7 +73,7 @@ module OpenSSL::Buffering
77
73
 
78
74
  def fill_rbuff
79
75
  begin
80
- @rbuffer << self.sysread(BLOCK_SIZE)
76
+ @rbuffer.append_as_bytes(self.sysread(BLOCK_SIZE))
81
77
  rescue Errno::EAGAIN
82
78
  retry
83
79
  rescue EOFError
@@ -352,22 +348,32 @@ module OpenSSL::Buffering
352
348
 
353
349
  def do_write(s)
354
350
  @wbuffer = Buffer.new unless defined? @wbuffer
355
- @wbuffer << s
356
- @wbuffer.force_encoding(Encoding::BINARY)
351
+ @wbuffer.append_as_bytes(s)
352
+
357
353
  @sync ||= false
358
- buffer_size = @wbuffer.size
354
+ buffer_size = @wbuffer.bytesize
359
355
  if @sync or buffer_size > BLOCK_SIZE
360
356
  nwrote = 0
361
357
  begin
362
358
  while nwrote < buffer_size do
363
359
  begin
364
- nwrote += syswrite(@wbuffer[nwrote, buffer_size - nwrote])
360
+ chunk = if nwrote > 0
361
+ @wbuffer.byteslice(nwrote, @wbuffer.bytesize)
362
+ else
363
+ @wbuffer
364
+ end
365
+
366
+ nwrote += syswrite(chunk)
365
367
  rescue Errno::EAGAIN
366
368
  retry
367
369
  end
368
370
  end
369
371
  ensure
370
- @wbuffer[0, nwrote] = ""
372
+ if nwrote < @wbuffer.bytesize
373
+ @wbuffer[0, nwrote] = ""
374
+ else
375
+ @wbuffer.clear
376
+ end
371
377
  end
372
378
  end
373
379
  end
@@ -444,10 +450,10 @@ module OpenSSL::Buffering
444
450
  def puts(*args)
445
451
  s = Buffer.new
446
452
  if args.empty?
447
- s << "\n"
453
+ s.append_as_bytes("\n")
448
454
  end
449
455
  args.each{|arg|
450
- s << arg.to_s
456
+ s.append_as_bytes(arg.to_s)
451
457
  s.sub!(/(?<!\n)\z/, "\n")
452
458
  }
453
459
  do_write(s)
@@ -461,7 +467,7 @@ module OpenSSL::Buffering
461
467
 
462
468
  def print(*args)
463
469
  s = Buffer.new
464
- args.each{ |arg| s << arg.to_s }
470
+ args.each{ |arg| s.append_as_bytes(arg.to_s) }
465
471
  do_write(s)
466
472
  nil
467
473
  end
@@ -57,7 +57,7 @@ module OpenSSL
57
57
  # OpenSSL::Digest("MD5")
58
58
  # # => OpenSSL::Digest::MD5
59
59
  #
60
- # Digest("Foo")
60
+ # OpenSSL::Digest("Foo")
61
61
  # # => NameError: wrong constant name Foo
62
62
 
63
63
  def Digest(name)