Bug in mmap or ruby with ruby-1.8.0

Searching for a non-existing string in a mmapped region produces a segfault.
Run the following little program:

require 'mmap’
file = “/usr/bin/ruby"
fma = Mmap.new(file, “r”, Mmap::MAP_SHARED, {‘offset’ => 8192, ‘length’ => 4096})
puts fma.index(”\n#\n", 12)
fma.unmap

Under 1.8.0:

tt.rb:10: [BUG] Segmentation fault
ruby 1.8.0 (2003-08-04) [i686-linux]

Aborted

With 1.6.8:
nil

Cheers,

Han Holl

Searching for a non-existing string in a mmapped region produces a
segfault.

bug in ruby :-))

re.c (line 142)

  while (s < e) {
      if (hx == hy && memcmp(x, s, m) == 0) {
    return s-y;
      }
      hy = KR_REHASH(*s, *(s+d), hy);
      s++;
  }

s+d can be > e

illegal access which give with a mapped file a segfault, with a normal
string it can work

Guy Decoux

Hi,

···

At Mon, 1 Sep 2003 23:20:37 +0900, ts wrote:

s+d can be > e

illegal access which give with a mapped file a segfault, with a normal
string it can work

Indeed.

Index: re.c

RCS file: /cvs/ruby/src/ruby/re.c,v
retrieving revision 1.110
diff -u -2 -p -r1.110 re.c
— re.c 16 Aug 2003 14:58:33 -0000 1.110
+++ re.c 1 Sep 2003 14:50:52 -0000
@@ -108,5 +108,6 @@ rb_memsearch(x0, m, y0, n)
#define KR_REHASH(a, b, h) (((h) << 1) - ((a)<<d) + (b))

  • s = y; e = s + n - m + 1;
  • if (m > n) return -1;

  • s = y; e = s + n - m;

    /* Preprocessing */
    @@ -117,4 +118,7 @@ rb_memsearch(x0, m, y0, n)

    if (ruby_ignorecase) {

  • if (n == m) {

  •   return rb_memcicmp(x, s, m) == 0 ? 0 : -1;
    
  • }
    /* Prepare hash value /
    for (hy = hx = i = 0; i < d; ++i) {
    @@ -123,8 +127,6 @@ rb_memsearch(x0, m, y0, n)
    }
    /
    Searching */

  • while (s < e) {
  •   if (hx == hy && rb_memcicmp(x, s, m) == 0) {
    
  •   return s-y;
    
  •   }
    
  • while (hx != hy || rb_memcicmp(x, s, m)) {
  •   if (s >= e) return -1;
      hy = KR_REHASH(casetable[*s], casetable[*(s+d)], hy);
      s++;
    

@@ -132,4 +134,7 @@ rb_memsearch(x0, m, y0, n)
}
else {

  • if (n == m) {
  •   return memcmp(x, s, m) == 0 ? 0 : -1;
    
  • }
    /* Prepare hash value /
    for (hy = hx = i = 0; i < d; ++i) {
    @@ -138,13 +143,11 @@ rb_memsearch(x0, m, y0, n)
    }
    /
    Searching */
  • while (s < e) {
  •   if (hx == hy && memcmp(x, s, m) == 0) {
    
  •   return s-y;
    
  •   }
    
  • while (hx != hy || memcmp(x, s, m)) {
  •   if (s >= e) return -1;
      hy = KR_REHASH(*s, *(s+d), hy);
      s++;
    
    }
    }
  • return -1;
  • return s-y;
    }


Nobu Nakada

Hi,

···

In message “Re: Bug in mmap or ruby with ruby-1.8.0” on 03/09/01, nobu.nokada@softhome.net nobu.nokada@softhome.net writes:

At Mon, 1 Sep 2003 23:20:37 +0900, >ts wrote:

s+d can be > e

illegal access which give with a mapped file a segfault, with a normal
string it can work

Indeed.

Commit the fix, please.
matz.

nobu.nokada@softhome.net wrote in message
[ patch cut ]

Many thanks to you and Guy for the speedy reply.
Works fine now.

Cheers,

Han Holl