Skip to content

Make sure shared buffer is copied on mutation #117

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 4 commits into from
Feb 20, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions ext/stringio/stringio.c
Original file line number Diff line number Diff line change
Expand Up @@ -180,6 +180,7 @@ check_modifiable(struct StringIO *ptr)
else if (OBJ_FROZEN_RAW(ptr->string)) {
rb_raise(rb_eIOError, "not modifiable string");
}
rb_str_modify(ptr->string);
}

static VALUE
Expand Down
18 changes: 18 additions & 0 deletions test/stringio/test_stringio.rb
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,24 @@

include TestEOF::Seek

def test_do_not_mutate_shared_buffers
# Ensure we have two strings that are not embedded but have the same shared
# string reference.
#
# In this case, we must use eval because we need two strings literals that
# are long enough they cannot be embedded, but also contain the same bytes.

a = eval(("x" * 1024).dump)
b = eval(("x" * 1024).dump)

s = StringIO.new(b)
s.getc
s.ungetc '#'

# We mutated b, so a should not be mutated
assert_equal("x", a[0])
end

def test_version
assert_kind_of(String, StringIO::VERSION)
end
Expand All @@ -22,7 +40,7 @@
assert_kind_of StringIO, StringIO.new
assert_kind_of StringIO, StringIO.new('str')
assert_kind_of StringIO, StringIO.new('str', 'r+')
assert_kind_of StringIO, StringIO.new(nil)

Check failure on line 43 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Error

TypeError: no implicit conversion of nil into String org/jruby/ext/stringio/StringIO.java:275:in `initialize' org/jruby/RubyClass.java:923:in `new' org/jruby/ext/stringio/StringIO.java:170:in `new' /home/runner/work/stringio/stringio/test/stringio/test_stringio.rb:43:in `test_initialize' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch'

Check failure on line 43 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Error

TypeError: no implicit conversion of nil into String org/jruby/ext/stringio/StringIO.java:275:in `initialize' org/jruby/RubyClass.java:923:in `new' org/jruby/ext/stringio/StringIO.java:170:in `new' /home/runner/work/stringio/stringio/test/stringio/test_stringio.rb:43:in `test_initialize' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch'
assert_raise(ArgumentError) { StringIO.new('', 'x') }
assert_raise(ArgumentError) { StringIO.new('', 'rx') }
assert_raise(ArgumentError) { StringIO.new('', 'rbt') }
Expand All @@ -42,7 +60,7 @@
end

def test_null
io = StringIO.new(nil)

Check failure on line 63 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Error

TypeError: no implicit conversion of nil into String org/jruby/ext/stringio/StringIO.java:275:in `initialize' org/jruby/RubyClass.java:923:in `new' org/jruby/ext/stringio/StringIO.java:170:in `new' /home/runner/work/stringio/stringio/test/stringio/test_stringio.rb:63:in `test_null' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch'

Check failure on line 63 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Error

TypeError: no implicit conversion of nil into String org/jruby/ext/stringio/StringIO.java:275:in `initialize' org/jruby/RubyClass.java:923:in `new' org/jruby/ext/stringio/StringIO.java:170:in `new' /home/runner/work/stringio/stringio/test/stringio/test_stringio.rb:63:in `test_null' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch'
assert_nil io.gets
io.puts "abc"
assert_nil io.string
Expand All @@ -55,7 +73,7 @@
io.puts "def"
assert_equal("\0\0\0\0def\n", io.string, "[ruby-dev:24190]")
assert_raise(Errno::EINVAL) { io.truncate(-1) }
assert_equal(0, io.truncate(10))

Check failure on line 76 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Failure

<0> expected but was <10>.

Check failure on line 76 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Failure

<0> expected but was <10>.
assert_equal("\0\0\0\0def\n\0\0", io.string)
end

Expand Down Expand Up @@ -280,7 +298,7 @@
assert_equal("foo\x83".b, f.gets)

f = StringIO.new()
f.set_encoding("ISO-8859-16:ISO-8859-1")

Check failure on line 301 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Error

ArgumentError: unknown encoding name - ISO-8859-16:ISO-8859-1 org/jruby/ext/stringio/StringIO.java:1630:in `set_encoding' /home/runner/work/stringio/stringio/test/stringio/test_stringio.rb:301:in `test_set_encoding' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch'

Check failure on line 301 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Error

ArgumentError: unknown encoding name - ISO-8859-16:ISO-8859-1 org/jruby/ext/stringio/StringIO.java:1630:in `set_encoding' /home/runner/work/stringio/stringio/test/stringio/test_stringio.rb:301:in `test_set_encoding' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch'
assert_equal(Encoding::ISO_8859_16, f.external_encoding)
assert_equal(Encoding::ISO_8859_16, f.string.encoding)
assert_nil(f.internal_encoding)
Expand Down Expand Up @@ -587,7 +605,7 @@
russian_part = io.read(40).force_encoding('UTF-8')

assert_equal("你好", chinese_part)
assert_equal("построить", russian_part)

Check failure on line 608 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Failure

<"построить"> expected but was <"好построить">. diff: - построить + 好построить ? ++

Check failure on line 608 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Failure

<"построить"> expected but was <"好построить">. diff: - построить + 好построить ? ++
end

def test_gets2
Expand Down Expand Up @@ -706,7 +724,7 @@
s = ""
assert_equal(Encoding::UTF_8, s.encoding, bug20418)
f.read(4, s)
assert_equal(Encoding::UTF_8, s.encoding, bug20418)

Check failure on line 727 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Failure

[Bug #20418] ™€®. <#<Encoding:UTF-8>> expected but was <#<Encoding:ASCII-8BIT>>.

Check failure on line 727 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Failure

[Bug #20418] ™€®. <#<Encoding:UTF-8>> expected but was <#<Encoding:ASCII-8BIT>>.

f.rewind
s = ""
Expand Down Expand Up @@ -779,7 +797,7 @@
assert_raise(ArgumentError) { f.pread(-1, 0) }
assert_raise(Errno::EINVAL) { f.pread(3, -1) }

assert_equal "".b, StringIO.new("").pread(0, 0)

Check failure on line 800 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Error

EOFError: End of file reached org/jruby/ext/stringio/StringIO.java:1110:in `pread' /home/runner/work/stringio/stringio/test/stringio/test_stringio.rb:800:in `test_pread' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch'

Check failure on line 800 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Error

EOFError: End of file reached org/jruby/ext/stringio/StringIO.java:1110:in `pread' /home/runner/work/stringio/stringio/test/stringio/test_stringio.rb:800:in `test_pread' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyArray.java:2009:in `each' org/jruby/RubyKernel.java:1426:in `catch' org/jruby/RubyKernel.java:1421:in `catch'
assert_equal "".b, StringIO.new("").pread(0, -10)

buf = "stale".b
Expand Down Expand Up @@ -883,7 +901,7 @@
s = StringIO.new
s.print 'a' * count
s.ungetbyte('b' * (count * 5))
assert_equal((count * 5), s.string.size)

Check failure on line 904 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Failure

<500> expected but was <900>.

Check failure on line 904 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Failure

<500> expected but was <900>.
assert_match(/\Ab+\z/, s.string)
end

Expand Down Expand Up @@ -962,12 +980,12 @@
def test_encoding_write
s = StringIO.new("", "w:utf-32be")
s.print "abc"
assert_equal("abc".encode("utf-32be"), s.string)

Check failure on line 983 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Failure

<"abc">("UTF-32BE") expected but was <"abc">("UTF-8").

Check failure on line 983 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Failure

<"abc">("UTF-32BE") expected but was <"abc">("UTF-8").
end

def test_encoding_read
s = StringIO.new("abc".encode("utf-32be"), "r:utf-8")
assert_equal("\0\0\0a\0\0\0b\0\0\0c", s.read)

Check failure on line 988 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-24.04 jruby-head

Failure

<"\u0000\u0000\u0000a\u0000\u0000\u0000b\u0000\u0000\u0000c">("UTF-8") expected but was <"abc">("UTF-32BE").

Check failure on line 988 in test/stringio/test_stringio.rb

View workflow job for this annotation

GitHub Actions / ubuntu-22.04 jruby-head

Failure

<"\u0000\u0000\u0000a\u0000\u0000\u0000b\u0000\u0000\u0000c">("UTF-8") expected but was <"abc">("UTF-32BE").
end

%w/UTF-8 UTF-16BE UTF-16LE UTF-32BE UTF-32LE/.each do |name|
Expand Down