summaryrefslogtreecommitdiff
path: root/string.c
diff options
context:
space:
mode:
authorAlan Wu <XrXr@users.noreply.github.com>2023-08-23 17:37:16 -0400
committerAlan Wu <XrXr@users.noreply.github.com>2023-08-23 18:07:49 -0400
commit2214bcb70d9f9120f1f3790ca340236c8f080991 (patch)
tree29776035af965344bb372e579de938e0dec4153a /string.c
parentd7f1ea71555c4d359de529b6058e4338ae247063 (diff)
Fix premature string collection during append
Previously, the following crashed due to use-after-free with AArch64 Alpine Linux 3.18.3 (aarch64-linux-musl): ```ruby str = 'a' * (32*1024*1024) p({z: str}) ``` 32 MiB is the default for `GC_MALLOC_LIMIT_MAX`, and the crash could be dodged by setting `RUBY_GC_MALLOC_LIMIT_MAX` to large values. Under a debugger, one can see the `str2` of rb_str_buf_append() getting prematurely collected while str_buf_cat4() allocates capacity. Add GC guards so the buffer of `str2` lives across the GC run initiated in str_buf_cat4(). [Bug #19792]
Diffstat (limited to 'string.c')
-rw-r--r--string.c2
1 files changed, 2 insertions, 0 deletions
diff --git a/string.c b/string.c
index 819844de06..0b9ede4e2c 100644
--- a/string.c
+++ b/string.c
@@ -3243,6 +3243,7 @@ rb_str_buf_append(VALUE str, VALUE str2)
case ENC_CODERANGE_7BIT:
// If RHS is 7bit we can do simple concatenation
str_buf_cat4(str, RSTRING_PTR(str2), RSTRING_LEN(str2), true);
+ RB_GC_GUARD(str2);
return str;
case ENC_CODERANGE_VALID:
// If RHS is valid, we can do simple concatenation if encodings are the same
@@ -3252,6 +3253,7 @@ rb_str_buf_append(VALUE str, VALUE str2)
if (UNLIKELY(str_cr != ENC_CODERANGE_VALID)) {
ENC_CODERANGE_SET(str, RB_ENC_CODERANGE_AND(str_cr, str2_cr));
}
+ RB_GC_GUARD(str2);
return str;
}
}