Переглянути джерело

Implement strerror_r. This is per SuSv3, not glibc which does
something different.
-Erik

Eric Andersen 23 роки тому
батько
коміт
6ba832b158
2 змінених файлів з 40 додано та 19 видалено
  1. 1 1
      include/string.h
  2. 39 18
      libc/string/strerror.c

+ 1 - 1
include/string.h

@@ -235,7 +235,7 @@ extern char *strerror (int __errnum) __THROW;
 #ifdef	__USE_MISC
 #ifdef	__USE_MISC
 /* Reentrant version of `strerror'.  If a temporary buffer is required, at
 /* Reentrant version of `strerror'.  If a temporary buffer is required, at
    most BUFLEN bytes of BUF will be used.  */
    most BUFLEN bytes of BUF will be used.  */
-extern char *strerror_r (int __errnum, char *__buf, size_t __buflen) __THROW;
+extern int strerror_r (int __errnum, char *__buf, size_t buflen) __THROW;
 #endif
 #endif
 
 
 /* We define this function always since `bzero' is sometimes needed when
 /* We define this function always since `bzero' is sometimes needed when

+ 39 - 18
libc/string/strerror.c

@@ -32,6 +32,11 @@ Cambridge, MA 02139, USA.  */
  * Manuel Novoa III       Feb 2002
  * Manuel Novoa III       Feb 2002
  *
  *
  * Change to _int10tostr and fix a bug in end-of-buf arg.
  * Change to _int10tostr and fix a bug in end-of-buf arg.
+ *
+ * Erik Andersen          June 2002
+ *
+ * Added strerror_r (per SuSv3 which differs from glibc) and adapted
+ * strerror to match.
  */
  */
 
 
 #define WANT_ERRORLIST     1
 #define WANT_ERRORLIST     1
@@ -41,35 +46,51 @@ Cambridge, MA 02139, USA.  */
 #include <string.h>
 #include <string.h>
 #include <errno.h>
 #include <errno.h>
 
 
+int strerror_r(int err, char *retbuf, size_t buflen)
+{
 #if WANT_ERRORLIST
 #if WANT_ERRORLIST
-static char retbuf[48];
+    if (err < 0 ||  err >= sys_nerr || sys_errlist[err] == NULL) {
+	return -EINVAL;
+    }
+    if (retbuf==NULL || buflen < 1) {
+	return -ERANGE;
+    }
+    strncpy(retbuf, sys_errlist[err], buflen);
+    retbuf[buflen-1] = '\0';
+    return 0;
 #else
 #else
-#if __BUFLEN_INT10TOSTR > 12
+    char *pos;
-#error currently set up for 32 bit ints max!
+    static const char unknown_error[] = "Unknown Error: errno"; /* = */
-#endif
+
-static char retbuf[33];			/* 33 is sufficient for 32 bit ints */
+    if (err < 0 ||  err >= sys_nerr || sys_errlist[err] == NULL) {
+	return -EINVAL;
+    }
+    /* unknown error -- leave space for the '=' */
+    pos = _int10tostr(retbuf+sizeof(retbuf)-1, err) - sizeof(unknown_error);
+    strcpy(pos, unknown_error);
+    *(pos + sizeof(unknown_error) - 1) = '=';
+    return 0;
 #endif
 #endif
-static const char unknown_error[] = "Unknown Error: errno"; /* = */
+}
 
 
 /* Return a string descibing the errno code in ERRNUM.
 /* Return a string descibing the errno code in ERRNUM.
    The storage is good only until the next call to strerror.
    The storage is good only until the next call to strerror.
    Writing to the storage causes undefined behavior.  */
    Writing to the storage causes undefined behavior.  */
 char *strerror(int err)
 char *strerror(int err)
 {
 {
-	char *pos;
-
 #if WANT_ERRORLIST
 #if WANT_ERRORLIST
-	if ((err >= 0) && (err < sys_nerr)) {
+    static char retbuf[48];
-		strcpy(retbuf, sys_errlist[err]);
+#else
-		return retbuf;
+#if __BUFLEN_INT10TOSTR > 12
-	}
+#error currently set up for 32 bit ints max!
 #endif
 #endif
-
+    static char retbuf[33];			/* 33 is sufficient for 32 bit ints */
-	/* unknown error -- leave space for the '=' */
+#endif
-	pos = _int10tostr(retbuf+sizeof(retbuf)-1, err)	- sizeof(unknown_error);
+    
-	strcpy(pos, unknown_error);
+    if (strerror_r(err, retbuf, sizeof(retbuf)) != 0) {
-	*(pos + sizeof(unknown_error) - 1) = '=';
+	return NULL;
-	return pos;
+    }
+    return(retbuf);
 }
 }
 
 
 #ifdef CHECK_BUF
 #ifdef CHECK_BUF