Browse Source

libdpkg: Refactor file locking error message handling

Pass only the description of the resource being locked, and move generic
error strings inside the file lock funtions. Instead of changing locking
behaviour depending on the error strings passed, pass an explicit enum to
select it.
Guillem Jover 16 years ago
parent
commit
0cb6f131d8
4 changed files with 25 additions and 15 deletions
  1. 1 3
      lib/dpkg/dbmodify.c
  2. 16 8
      lib/dpkg/file.c
  3. 7 2
      lib/dpkg/file.h
  4. 1 2
      lib/dpkg/trigdeferred.l

+ 1 - 3
lib/dpkg/dbmodify.c

@@ -195,9 +195,7 @@ modstatdb_lock(const char *admindir)
     }
     }
   }
   }
 
 
-  file_lock(&dblockfd, dblockfile,
-            _("unable to lock dpkg status database"),
-            _("status database area is locked by another process"));
+  file_lock(&dblockfd, FILE_LOCK_NOWAIT, dblockfile, _("dpkg status database"));
 
 
   free(dblockfile);
   free(dblockfile);
 }
 }

+ 16 - 8
lib/dpkg/file.c

@@ -67,6 +67,7 @@ static void
 file_unlock_cleanup(int argc, void **argv)
 file_unlock_cleanup(int argc, void **argv)
 {
 {
 	int lockfd = *(int*)argv[0];
 	int lockfd = *(int*)argv[0];
+	const char *lock_desc = argv[1];
 	struct flock fl;
 	struct flock fl;
 
 
 	assert(lockfd >= 0);
 	assert(lockfd >= 0);
@@ -74,7 +75,7 @@ file_unlock_cleanup(int argc, void **argv)
 	file_lock_setup(&fl, F_UNLCK);
 	file_lock_setup(&fl, F_UNLCK);
 
 
 	if (fcntl(lockfd, F_SETLK, &fl) == -1)
 	if (fcntl(lockfd, F_SETLK, &fl) == -1)
-		ohshite(_("unable to unlock dpkg status database"));
+		ohshite(_("unable to unlock %s"), lock_desc);
 }
 }
 
 
 void
 void
@@ -108,21 +109,28 @@ file_is_locked(int lockfd, const char *filename)
 /* lockfd must be allocated statically as its addresses is passed to
 /* lockfd must be allocated statically as its addresses is passed to
  * a cleanup handler. */
  * a cleanup handler. */
 void
 void
-file_lock(int *lockfd, const char *filename,
-          const char *emsg, const char *emsg_eagain)
+file_lock(int *lockfd, enum file_lock_flags flags, const char *filename,
+          const char *desc)
 {
 {
 	struct flock fl;
 	struct flock fl;
+	int lock_cmd;
 
 
 	setcloexec(*lockfd, filename);
 	setcloexec(*lockfd, filename);
 
 
 	file_lock_setup(&fl, F_WRLCK);
 	file_lock_setup(&fl, F_WRLCK);
 
 
-	if (fcntl(*lockfd, emsg_eagain ? F_SETLK : F_SETLKW, &fl) == -1) {
-		if (emsg_eagain && (errno == EACCES || errno == EAGAIN))
-			ohshit(emsg_eagain);
-		ohshite(emsg);
+	if (flags == FILE_LOCK_WAIT)
+		lock_cmd = F_SETLKW;
+	else
+		lock_cmd = F_SETLK;
+
+	if (fcntl(*lockfd, lock_cmd, &fl) == -1) {
+		if (errno == EACCES || errno == EAGAIN)
+			ohshit(_("%s is locked by another process"), desc);
+		else
+			ohshite(_("unable to lock %s"), desc);
 	}
 	}
 
 
-	push_cleanup(file_unlock_cleanup, ~0, NULL, 0, 1, lockfd);
+	push_cleanup(file_unlock_cleanup, ~0, NULL, 0, 2, lockfd, desc);
 }
 }
 
 

+ 7 - 2
lib/dpkg/file.h

@@ -32,9 +32,14 @@ DPKG_BEGIN_DECLS
  */
  */
 void file_copy_perms(const char *src, const char *dst);
 void file_copy_perms(const char *src, const char *dst);
 
 
+enum file_lock_flags {
+	FILE_LOCK_NOWAIT,
+	FILE_LOCK_WAIT,
+};
+
 bool file_is_locked(int lockfd, const char *filename);
 bool file_is_locked(int lockfd, const char *filename);
-void file_lock(int *lockfd, const char *filename,
-               const char *emsg, const char *emsg_eagain);
+void file_lock(int *lockfd, enum file_lock_flags flags, const char *filename,
+               const char *desc);
 void file_unlock(void);
 void file_unlock(void);
 
 
 DPKG_END_DECLS
 DPKG_END_DECLS

+ 1 - 2
lib/dpkg/trigdeferred.l

@@ -126,8 +126,7 @@ trigdef_update_start(enum trigdef_updateflags uf, const char *admindir)
 			}
 			}
 		}
 		}
 
 
-		file_lock(&lock_fd, fn.buf, _("unable to lock triggers area"),
-		          NULL);
+		file_lock(&lock_fd, FILE_LOCK_WAIT, fn.buf, _("triggers area"));
 	} else {
 	} else {
 		/* Dummy for pop_cleanups. */
 		/* Dummy for pop_cleanups. */
 		push_cleanup(NULL, 0, NULL, 0, 0);
 		push_cleanup(NULL, 0, NULL, 0, 0);