If the pre-handler for the execve system call fails to state the file
being executed then propagate the error from the stat instead of just
return ENOACCES all the time. Fixes bug #110208.


git-svn-id: svn://svn.valgrind.org/valgrind/trunk@4330 a5019735-40e9-0310-863c-91ae7b9d1cf9
diff --git a/coregrind/m_debuginfo/symtab.c b/coregrind/m_debuginfo/symtab.c
index 7af4e9e..0d1beda 100644
--- a/coregrind/m_debuginfo/symtab.c
+++ b/coregrind/m_debuginfo/symtab.c
@@ -1278,8 +1278,8 @@
       line number info out of it.  It will be munmapped immediately
       thereafter; it is only aboard transiently. */
 
-   i = VG_(stat)(si->filename, &stat_buf);
-   if (i != 0) {
+   fd = VG_(stat)(si->filename, &stat_buf);
+   if (fd.isError) {
       ML_(symerr)("Can't stat .so/.exe (to determine its size)?!");
       return False;
    }
diff --git a/coregrind/m_libcfile.c b/coregrind/m_libcfile.c
index 16c8087..ff20a31 100644
--- a/coregrind/m_libcfile.c
+++ b/coregrind/m_libcfile.c
@@ -119,10 +119,10 @@
    return res.isError ? (-1) : 0;
 }
 
-Int VG_(stat) ( Char* file_name, struct vki_stat* buf )
+SysRes VG_(stat) ( Char* file_name, struct vki_stat* buf )
 {
    SysRes res = VG_(do_syscall2)(__NR_stat, (UWord)file_name, (UWord)buf);
-   return res.isError ? (-1) : 0;
+   return res;
 }
 
 Int VG_(fstat) ( Int fd, struct vki_stat* buf )
diff --git a/coregrind/m_syswrap/syswrap-generic.c b/coregrind/m_syswrap/syswrap-generic.c
index e4e9391..b0d2f10 100644
--- a/coregrind/m_syswrap/syswrap-generic.c
+++ b/coregrind/m_syswrap/syswrap-generic.c
@@ -2306,11 +2306,11 @@
       exec. */
    {
       struct vki_stat st;
-      Int i = VG_(stat)((Char *)ARG1, &st);
+      SysRes r = VG_(stat)((Char *)ARG1, &st);
 
-      if (i == -1) {
+      if (r.isError) {
          /* stat failed */
-         SET_STATUS_Failure( VKI_EACCES/*really, we should copy stat's result*/ );
+         SET_STATUS_from_SysRes( r );
 	 return;
       }
       /* just look for regular file with any X bit set
diff --git a/include/pub_tool_libcfile.h b/include/pub_tool_libcfile.h
index bdc9787..2d89c5d 100644
--- a/include/pub_tool_libcfile.h
+++ b/include/pub_tool_libcfile.h
@@ -42,7 +42,7 @@
 extern Int    VG_(pipe)   ( Int fd[2] );
 extern OffT   VG_(lseek)  ( Int fd, OffT offset, Int whence);
 
-extern Int    VG_(stat)   ( Char* file_name, struct vki_stat* buf );
+extern SysRes VG_(stat)   ( Char* file_name, struct vki_stat* buf );
 extern Int    VG_(fstat)  ( Int   fd,        struct vki_stat* buf );
 extern Int    VG_(dup2)   ( Int oldfd, Int newfd );
 extern Int    VG_(rename) ( Char* old_name, Char* new_name );