diff options
author | Kazuki Yamaguchi <k@rhe.jp> | 2021-08-30 16:09:04 +0900 |
---|---|---|
committer | Kazuki Yamaguchi <k@rhe.jp> | 2021-09-27 00:15:30 +0900 |
commit | aea874bc6eae69a74c5832b499eb9e3132175d2f (patch) | |
tree | beefdbc69e79fc28631f4195e95ee6c47372e860 /ext/openssl | |
parent | 657a4736d2ad723bbcd66c603677a77b8ee4eacc (diff) | |
download | ruby-openssl-aea874bc6eae69a74c5832b499eb9e3132175d2f.tar.gz |
ssl: create a temporary frozen string buffer when writing
Since a blocking SSLSocket#syswrite call allows context switches while
waiting for the underlying socket to be ready, we must freeze the string
buffer to prevent other threads from modifying it.
Reference: https://github.com/ruby/openssl/issues/452
Diffstat (limited to 'ext/openssl')
-rw-r--r-- | ext/openssl/ossl_ssl.c | 10 |
1 files changed, 5 insertions, 5 deletions
diff --git a/ext/openssl/ossl_ssl.c b/ext/openssl/ossl_ssl.c index a9e3948e..5d2c1e83 100644 --- a/ext/openssl/ossl_ssl.c +++ b/ext/openssl/ossl_ssl.c @@ -1954,21 +1954,21 @@ ossl_ssl_write_internal(VALUE self, VALUE str, VALUE opts) int nwrite = 0; rb_io_t *fptr; int nonblock = opts != Qfalse; - VALUE io; + VALUE tmp, io; - StringValue(str); + tmp = rb_str_new_frozen(StringValue(str)); GetSSL(self, ssl); io = rb_attr_get(self, id_i_io); GetOpenFile(io, fptr); if (ssl_started(ssl)) { - for (;;){ - int num = RSTRING_LENINT(str); + for (;;) { + int num = RSTRING_LENINT(tmp); /* SSL_write(3ssl) manpage states num == 0 is undefined */ if (num == 0) goto end; - nwrite = SSL_write(ssl, RSTRING_PTR(str), num); + nwrite = SSL_write(ssl, RSTRING_PTR(tmp), num); switch(ssl_get_error(ssl, nwrite)){ case SSL_ERROR_NONE: goto end; |