svn commit: trunk/uClibc/libc/misc/utmp

vapier at uclibc.org vapier at uclibc.org
Sat Feb 11 05:36:45 UTC 2006


Author: vapier
Date: 2006-02-10 21:36:43 -0800 (Fri, 10 Feb 2006)
New Revision: 13916

Log:
rholzmann writes in Bug 716:
utent.c has a few problems with mutex locking when used in a binary that was linked with pthreads. The are a few deadlock conditions where functions may be called which lock the utmplock but never release it and where a function that hold the lock calls other functions which try to relock the same lock.  For example, notice in the __getutent function the error condition does not unlock the semaphore. The problem is not visible when pthreads isn't used since the lock/unlock functions are NOOP functions.


Modified:
   trunk/uClibc/libc/misc/utmp/utent.c


Changeset:
Modified: trunk/uClibc/libc/misc/utmp/utent.c
===================================================================
--- trunk/uClibc/libc/misc/utmp/utent.c	2006-02-11 04:58:21 UTC (rev 13915)
+++ trunk/uClibc/libc/misc/utmp/utent.c	2006-02-11 05:36:43 UTC (rev 13916)
@@ -64,20 +64,22 @@
 	}
 	if (ret < 0) {
 bummer:
-	    UNLOCK;
 	    static_fd = -1;
 	    close(static_fd);
+unlock_and_ret:
+	    UNLOCK;
 	    return;
 	}
     }
     lseek(static_fd, 0, SEEK_SET);
-    UNLOCK;
-    return;
+    goto unlock_and_ret;
 }
 libc_hidden_def(setutent)
 
 static struct utmp *__getutent(int utmp_fd)
 {
+    struct utmp *ret = NULL;
+
     if (utmp_fd == -1) {
 	setutent();
     }
@@ -86,13 +88,13 @@
     }
 
     LOCK;
-    if (read(utmp_fd, (char *) &static_utmp, sizeof(struct utmp)) != sizeof(struct utmp)) 
+    if (read(utmp_fd, (char *) &static_utmp, sizeof(struct utmp)) == sizeof(struct utmp)) 
     {
-	return NULL;
+	ret = &static_utmp;
     }
 
     UNLOCK;
-    return &static_utmp;
+    return ret;
 }
 
 void endutent(void)
@@ -163,15 +165,12 @@
        the file pointer where they want it, everything will work out. */
     lseek(static_fd, (off_t) - sizeof(struct utmp), SEEK_CUR);
 
-    if (getutid(utmp_entry) != NULL) {
+    if (getutid(utmp_entry) != NULL)
 	lseek(static_fd, (off_t) - sizeof(struct utmp), SEEK_CUR);
-	if (write(static_fd, utmp_entry, sizeof(struct utmp)) != sizeof(struct utmp))
-	    return NULL;
-    } else {
+    else
 	lseek(static_fd, (off_t) 0, SEEK_END);
-	if (write(static_fd, utmp_entry, sizeof(struct utmp)) != sizeof(struct utmp))
-	    return NULL;
-    }
+    if (write(static_fd, utmp_entry, sizeof(struct utmp)) != sizeof(struct utmp))
+	utmp_entry = NULL;
 
     UNLOCK;
     return (struct utmp *)utmp_entry;




More information about the uClibc-cvs mailing list