System Interface Guide

Getting Lock Information

You can determine which process, if any, is holding a lock. Use this as a simple test or to find locks on a file. A lock is set, as in the previous examples, and F_GETLK is used in fcntl(2). The next example finds and prints indentifying data on all the locked segments of a file.


Example 5-2

struct flock lck;

 	lck.l_whence = 0;
 	lck.l_start = 0L;
 	lck.l_len = 0L;
 	do {
 		lck.l_type = F_WRLCK;
 		(void) fcntl(fd, F_GETLK, &lck);
 		if (lck.l_type != F_UNLCK) {
 			(void) printf("%d %d %c %8ld %8ld\n", lck.l_sysid, lck.l_pid, 
						(lck.l_type == F_WRLCK) ? 'W' : 'R', lck.l_start, lck.l_len);
 			/* If this lock goes to the end of the address space, no
 			 * need to look further, so break out. */
 			if (lck.l_len == 0) {
 			/* else, look for new lock after the one just found. */
 					lck.l_start += lck.l_len;
 			}
 		}
 	} while (lck.l_type != F_UNLCK);

fcntl(2) with the F_GETLK command can sleep while waiting for a server to respond, and it can fail (returning ENOLCK) if there is a resource shortage on either the client or server.

lockf(3C) with the F_TEST command can be used to test if a process is holding a lock. This function does not return information about where the lock is and which process owns it.


(void) lseek(fd, 0, 0L);
 /* set the size of the test region to zero (0). to test until the
    end of the file address space. */
 if (lockf(fd, (off_t)0, SEEK_SET) < 0) {
 	switch (errno) {
 		case EACCES:
 		case EAGAIN:
 			(void) printf("file is locked by another process\n");
 			break;
 		case EBADF:
 			/* bad argument passed to lockf */
 			perror("lockf");
 			break;
 		default:
 			(void) printf("lockf: unexpected error <%d>\n", errno);
 			break;
 	}