[comp.unix.ultrix] Problems with file locking

fkittred@bbn.com (Fletcher Kittredge) (07/10/90)

I have been testing Posix style file locking on Ultrix 4.0(FT 2)
and 3.1 on both RISC and VAX in preparation for using it in a
product.  I have had strange results.  And was hoping someone could
enlighten me.  

Problem description:

On all 4 systems, advisory file locking works correctly on local files.
However, on Ultrix 3.1 systems, locking a NFS mounted file is extremely
slow (200 times slower than locking a local file).  This seems to be
the case whether the Ultrix 3.1 system is the locking client or the
NFS server.  I tested this with the following systems being both
client and server:

Sun-3 running Sun O/S 4.0.3
Sun-4 running Sun O/S 4.0.3

HP9000 Series 800 running HP-UX 7.0
HP9000 Series 300 running HP-UX 7.0

VAX Ultrix 3.1
VAX Ultrix 4.0

RISC Ultrix 3.1
RISC Ultrix 4.0

In addition, when Ultrix 4.0(FT 2) is the client platform, and HP-UX is
the server platform, I am unable to get a lock at all.  Calling fnctl()
to lock the first time returns -1 and perror() prints the following
message on Ultrix:

No locks available

The debugger shows errno set to 75 which, according to the header
file errno.h, corresponds to the Posix error condition ENOLCK.

My test code follows.

Questions:

1) It appears that the slowness of Ultrix 3.1 locking is a known
problem which will be fixed in 4.0.  In the meantime is there a
work-around for 3.1?

2) Is the problem with locking between Ultrix 4.0 and HP-UX a known
problem, whose problem is it, and when will it be fixed?  (I am
reporting it to Ultrix Field Test).

many grateful thanks for any information,

regards,
fletcher
Fletcher E. Kittredge  fkittred@bbn.com
Lead Programmer
Platforms and Tools Group
BBN Software Products Company
10 Fawcett St.
Cambridge, MA. 02138

%%%%%%%%%%%%%Cut here %%%%%%%%%%%%%%%%

/*
 *  Program to test file locking using Posix fnctl() based file locking.
 *
 *
 *  Usage:
 *
 *     locktst [ -v level -c count ] files
 *
 * where level is the amount of verbose status information and c is the
 * number of times to lock/write/read the data.  Foreach file supplied on
 * the command line, this program opens the file, locks the file for
 * read+write, writes and reads data, and unlocks the file.
 *
 */

#include <stdio.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/file.h>
#include <unistd.h>
#include <fcntl.h>
#include <signal.h>

    char *progname;

#ifdef __STDC__
main(int argc, char *argv[])
#else
main(argc, argv)
      int argc;
      char *argv[];
#endif      
{
    extern int optind, opterr;
    extern char *optarg;
    extern int errno;
    struct flock lock;	/* Posix fcntl() lock structure */
    int c;
    int fd;			/* File Des for table */
    int outbuf[1024];		/* garbage out */
    int inbuf[1024];		/* garbage in */
    int times = 100;
    int i;
    int verbose_level = 0;
    progname = argv[0];
    /* process options */
    while ((c = getopt (argc, argv, "c:v:")) != EOF)
	switch (c)
	    {
	case 'c':
	    times = atoi(optarg);
	    break;
	case 'v':
	    verbose_level = atoi(optarg);
	    break;
	default:
	    usage(1);
	    }
    /* Set values to lock whole file */
    lock.l_whence = 0;
    lock.l_start = 0;
    lock.l_len = 0;
    /*
     * For each file
     *     open the file
     * 	 for times
     * 	     lock the file
     * 	     write garbage
     * 	     read garbage
     * 	     compare garbage
     * 	     unlock file
     *     close the file
     *
     */
    for(; optind < argc; optind++)
	{
	if((fd = open(argv[optind], O_RDWR | O_CREAT, 0664)) < 0)
	    {
	    fprintf(stderr, "Failed to open file %s for read+write\n",
		    argv[optind]);
	    perror("");
	    exit(1);
	    }
	if(verbose_level > 0)
	    fprintf(stdout, "Opened file %s\n", argv[optind]);
	
	for(i=0; i < times;i++)
	    {
	    /* lock the file */
	    lock.l_type = F_WRLCK;
	    if(fcntl(fd, F_SETLK, &lock) < 0)
		switch(errno)
		    {
		    /*
		     * These three error conditions mean we can retry lock.
		     */
		case EACCES :
		case EAGAIN :
		case ETIMEDOUT :
		    fprintf(stderr, "couldn't lock file %s, retrying\n",
			    argv[optind]);
		    perror("");
		    exit(3);
		default:
		    fprintf(stderr, "couldn't lock file %s, aborting\n",
			    argv[optind]);
		    perror("");
		    exit(4);
		    }
	    if(verbose_level > 1)
		fprintf(stdout, "Locked file %s\n", argv[optind]);

	    /* write junk, read junk, compare junk */
	    if(write(fd, outbuf, sizeof(outbuf)) < 0)
		{
		fprintf(stderr, "Write on file %s failed\n",
			argv[optind]);
		perror("");
		}
	    (void)lseek(fd, SEEK_SET, 0L);
	    if(read(fd, inbuf, sizeof(inbuf)) < 0)
		{
		fprintf(stderr, "Read on file %s failed\n",
			argv[optind]);
		perror("");
		}
	    if(bcmp(outbuf, inbuf, sizeof(inbuf)) != 0)
		fprintf(stderr,
			"Data written and read do not compare.\n");
		
	    /* Unlock the file */
	    lock.l_type = F_UNLCK;
	    if(fcntl(fd, F_SETLK, &lock) < 0)
		switch(errno)
		    {
		    /*
		     * These three error conditions mean we can retry lock.
		     */
		case EACCES :
		case EAGAIN :
		case ETIMEDOUT :
		    fprintf(stderr, "couldn't unlock file %s, retrying\n",
			    argv[optind]);
		    perror("");
		    exit(3);
		default:
		    fprintf(stderr, "couldn't lock file %s, aborting\n",
			    argv[optind]);
		    perror("");
		    exit(4);
		    }
	    if(verbose_level > 1)
		fprintf(stdout, "Unlocked file %s\n", argv[optind]);
	    } /* for times */
	(void)close(fd);
	(void)unlink(argv[optind]);
	
	}
    }    

#ifdef __STDC__
usage(int status)
#else
usage(status)
      int status;
#endif      
{
    
    fprintf(stderr, "usage: %s [-v level -c count] files ...\n", progname);
    exit(1);
    }



Fletcher E. Kittredge  fkittred@bbn.com
Lead Programmer
Platforms and Tools Group
BBN Software Products Company
10 Fawcett St.
Cambridge, MA. 02138

grr@cbmvax.commodore.com (George Robbins) (07/10/90)

In article <58061@bbn.BBN.COM> fkittred@spca.bbn.com (Fletcher Kittredge) writes:
> 
> I have been testing Posix style file locking on Ultrix 4.0(FT 2)
> and 3.1 on both RISC and VAX in preparation for using it in a
> product.  I have had strange results.  And was hoping someone could
> enlighten me.  
> 
> However, on Ultrix 3.1 systems, locking a NFS mounted file is extremely
> slow (200 times slower than locking a local file).  This seems to be
> the case whether the Ultrix 3.1 system is the locking client or the
> NFS server.  I tested this with the following systems being both
> client and server:

There is a patch against the base 3.1 release having to do with NFS
file locking.  I know it applies to the VAX release, but is included in
the latter RISC child releases.  Check with the support center...

lockd, klm_lockmgr.o
--------------------
On systems using nfs locking, this daemon and kernel patch will cause
the locks to perform at a much faster rate. In addition, there is a
bug fix or two included.

> In addition, when Ultrix 4.0(FT 2) is the client platform, and HP-UX is
> the server platform, I am unable to get a lock at all.  Calling fnctl()
> to lock the first time returns -1 and perror() prints the following
> message on Ultrix:
> 
> 2) Is the problem with locking between Ultrix 4.0 and HP-UX a known
> problem, whose problem is it, and when will it be fixed?  (I am
> reporting it to Ultrix Field Test).

I think that reporting it as a field test problem would have to be the
starting point - that's what field test releases are for...

-- 
George Robbins - now working for,     uucp:   {uunet|pyramid|rutgers}!cbmvax!grr
but no way officially representing:   domain: grr@cbmvax.commodore.com
Commodore, Engineering Department     phone:  215-431-9349 (only by moonlite)