In message <[EMAIL PROTECTED]>
          Tom Hughes <[EMAIL PROTECTED]> wrote:

>   Syscall param open(pathname) contains uninitialised or unaddressable byte(s)
>      at 0x403F1892: __libc_open (__libc_open:31)
>      by 0x403829C3: _IO_fopen@@GLIBC_2.1 (iofopen.c:67)
>      by 0x809B287: cg_core (core.ops:138)
>      by 0x80955E0: runops_fast_core (runops_cores.c:34)
>      Address 0x4104051D is 3201 bytes inside a block of size 32824 alloc'd
>      at 0x4003DCC2: malloc (vg_clientmalloc.c:618)
>      by 0x8092E11: mem_sys_allocate (memory.c:74)
>      by 0x8098DAD: Parrot_alloc_new_block (resources.c:830)
>      by 0x8092EC0: mem_setup_allocator (memory.c:108)
> 
>   ERROR SUMMARY: 1 errors from 1 contexts (suppressed: 0 from 0)
>   malloc/free: in use at exit: 249652 bytes in 54 blocks.
>   malloc/free: 58 allocs, 4 frees, 381692 bytes allocated.
>   For a detailed leak analysis,  rerun with: --leak-check=yes
>   For counts of detected errors, rerun with: -v
> 
> I haven't attempted to look at this and see what is causing it.

I've had a look at it now. The problem is that we are passing
s->bufstart to fopen but there is no guarantee that there is a
nul byte at the end of the buffer as parrot strings are not nul
terminated.

I have developed patch for this in the form of a new routine
which returns a nul terminated C style string given a parrot
string as argument. It does this by making sure buflen is at
least one greater than bufused and then stuffing a nul in that
byte.

This isn't a particularly brilliant fix so I'm attaching it here
for comments before I commit it.

Of course we also need to think about encoding/charset issues
when passing strings to system calls...

Tom

-- 
Tom Hughes ([EMAIL PROTECTED])
http://www.compton.nu/
Index: core.ops
===================================================================
RCS file: /home/perlcvs/parrot/core.ops,v
retrieving revision 1.119
diff -u -w -r1.119 core.ops
--- core.ops    3 Apr 2002 23:03:37 -0000       1.119
+++ core.ops    13 Apr 2002 14:11:11 -0000
@@ -135,7 +135,7 @@
 =cut

 inline op open(out INT, in STR) {
-  $1 = (INTVAL)fopen(($2)->bufstart, "r+");
+  $1 = (INTVAL)fopen(string_to_cstring(interpreter, ($2)), "r+");
   if (!$1) {
     perror("Can't open");
     exit(1);
@@ -145,7 +145,7 @@
 }

 inline op open(out INT, in STR, in STR) {
-  $1 = (INTVAL)fopen(($2)->bufstart, ($3)->bufstart);
+  $1 = (INTVAL)fopen(string_to_cstring(interpreter, ($2)), 
+string_to_cstring(interpreter, ($3)));
   goto NEXT();
 }

@@ -246,7 +246,7 @@
 op print(in STR) {
   STRING *s = $1;
   if (s && string_length(s)) {
-    printf("%.*s", (int)string_length(s), (char *) s->bufstart);
+    printf("%s", string_to_cstring(interpreter, (s)));
   }
   goto NEXT();
 }
@@ -255,7 +255,7 @@
   PMC *p = $1;
   STRING *s = (p->vtable->get_string(interpreter, p));
   if (s) {
-    printf("%.*s",(int)string_length(s),(char *) s->bufstart);
+    printf("%s", string_to_cstring(interpreter, (s)));
   }
   goto NEXT();
 }
@@ -304,7 +304,7 @@
        default: file = (FILE *)$1;
   }
   if (s && string_length(s)) {
-    fprintf(file, "%.*s",(int)string_length(s),(char *) s->bufstart);
+    fprintf(file, "%s", string_to_cstring(interpreter, (s)));
   }
   goto NEXT();
 }
@@ -323,7 +323,7 @@
        default: file = (FILE *)$1;
   }
   if (s) {
-    fprintf(file, "%.*s",(int)string_length(s),(char *) s->bufstart);
+    fprintf(file, "%s", string_to_cstring(interpreter, (s)));
   }
   goto NEXT();
 }
Index: string.c
===================================================================
RCS file: /home/perlcvs/parrot/string.c,v
retrieving revision 1.68
diff -u -w -r1.68 string.c
--- string.c    12 Apr 2002 01:40:28 -0000      1.68
+++ string.c    13 Apr 2002 14:11:12 -0000
@@ -802,6 +802,21 @@
                             NULL, 0, NULL);
 }

+const char *
+string_to_cstring(struct Parrot_Interp * interpreter, STRING * s)
+{
+    char *cstring;
+
+    if (s->buflen == s->bufused)
+        string_grow(interpreter, s, 1);
+
+    cstring = s->bufstart;
+
+    cstring[s->bufused] = 0;
+
+    return cstring;
+}
+

 /*
  * Local variables:
Index: include/parrot/string_funcs.h
===================================================================
RCS file: /home/perlcvs/parrot/include/parrot/string_funcs.h,v
retrieving revision 1.6
diff -u -w -r1.6 string_funcs.h
--- include/parrot/string_funcs.h       22 Mar 2002 04:11:57 -0000      1.6
+++ include/parrot/string_funcs.h       13 Apr 2002 14:11:12 -0000
@@ -27,6 +27,7 @@
                              const STRING *, STRING **);
 INTVAL Parrot_string_compare(Parrot, const STRING *, const STRING *);
 Parrot_Bool Parrot_string_bool(const STRING *);
+const char *Parrot_string_cstring(const STRING *);

 /* Declarations of other functions */
 UINTVAL Parrot_string_length(const STRING *);
@@ -45,6 +46,7 @@
                                 STRING **dest_ptr);
 void Parrot_string_init(void);
 INTVAL Parrot_string_index(const STRING *, UINTVAL idx);
+const char *Parrot_string_to_cstring(struct Parrot_Interp *, STRING *);

 #ifdef PARROT_IN_CORE

@@ -56,6 +58,7 @@
 #define string_replace          Parrot_string_replace
 #define string_compare          Parrot_string_compare
 #define string_bool             Parrot_string_bool
+#define string_cstring          Parrot_string_cstring

 #define string_length           Parrot_string_length
 #define string_ord              Parrot_string_ord
@@ -69,6 +72,7 @@
 #define string_transcode        Parrot_string_transcode
 #define string_init             Parrot_string_init
 #define string_index            Parrot_string_index
+#define string_to_cstring       Parrot_string_to_cstring

 #endif

Reply via email to