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 );