[svn:parrot] r49298 - trunk/src/io

nwellnhof at svn.parrot.org nwellnhof at svn.parrot.org
Fri Sep 24 16:39:28 UTC 2010


Author: nwellnhof
Date: Fri Sep 24 16:39:27 2010
New Revision: 49298
URL: https://trac.parrot.org/parrot/changeset/49298

Log:
[io] Fix GC-related bug in Parrot_io_read_buffer

If Parrot_str_new_init triggers a GC run, out_buf might become invalid.

Modified:
   trunk/src/io/buffer.c

Modified: trunk/src/io/buffer.c
==============================================================================
--- trunk/src/io/buffer.c	Fri Sep 24 13:13:12 2010	(r49297)
+++ trunk/src/io/buffer.c	Fri Sep 24 16:39:27 2010	(r49298)
@@ -272,7 +272,7 @@
               ARGMOD(STRING **buf))
 {
     ASSERT_ARGS(Parrot_io_read_buffer)
-    unsigned char *out_buf, *buffer_start, *buffer_next, *buffer_end;
+    unsigned char *buffer_start, *buffer_next, *buffer_end;
     STRING        *s;
     size_t         len;
     size_t         current      = 0;
@@ -297,14 +297,13 @@
 
     s       = *buf;
     len     = s->bufused;
-    out_buf = (unsigned char *)s->strstart;
 
     /* read Data from buffer */
     if (buffer_flags & PIO_BF_READBUF) {
         const size_t avail = buffer_end - buffer_next;
         current            = avail < len ? avail : len;
 
-        memcpy(out_buf, buffer_next, current);
+        memcpy(s->strstart, buffer_next, current);
         buffer_next += current;
         Parrot_io_set_buffer_next(interp, filehandle, buffer_next);
         Parrot_io_set_file_position(interp, filehandle, (current +
@@ -327,7 +326,6 @@
         }
         else {
             /* more data needed */
-            out_buf += current;
             len -= current;
         }
     }
@@ -337,11 +335,12 @@
         size_t got;
 
         if (len >= Parrot_io_get_buffer_size(interp, filehandle)) {
-            STRING *sf = Parrot_str_new_init(interp, (char *)out_buf, len,
-                Parrot_default_encoding_ptr,
-                PObj_external_FLAG);
-            got                 = PIO_READ(interp, filehandle, &sf);
-            s->strlen           = s->bufused = current + got;
+            STRING *sf;
+
+            s->strlen = s->bufused = current + len;
+            sf        = Parrot_str_substr(interp, s, current, len);
+            got       = PIO_READ(interp, filehandle, &sf);
+            s->strlen = s->bufused = current + got;
 
             Parrot_io_set_file_position(interp, filehandle,
                     (got + Parrot_io_get_file_position(interp, filehandle)));
@@ -357,7 +356,7 @@
     buffer_next  = Parrot_io_get_buffer_next(interp, filehandle);
     buffer_end   = Parrot_io_get_buffer_end(interp, filehandle);
 
-    memcpy(out_buf, buffer_next, len);
+    memcpy(s->strstart + current, buffer_next, len);
     s->strlen    = s->bufused = current + len;
     buffer_next += len;
 


More information about the parrot-commits mailing list