diff options
Diffstat (limited to 'crypto/heimdal/lib/roken/flock.c')
-rw-r--r-- | crypto/heimdal/lib/roken/flock.c | 93 |
1 files changed, 80 insertions, 13 deletions
diff --git a/crypto/heimdal/lib/roken/flock.c b/crypto/heimdal/lib/roken/flock.c index 911d5ff..068d099 100644 --- a/crypto/heimdal/lib/roken/flock.c +++ b/crypto/heimdal/lib/roken/flock.c @@ -1,23 +1,23 @@ /* - * Copyright (c) 1995, 1996, 1997 Kungliga Tekniska Högskolan + * Copyright (c) 1995, 1996, 1997 Kungliga Tekniska Högskolan * (Royal Institute of Technology, Stockholm, Sweden). * All rights reserved. - * + * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: - * + * * 1. Redistributions of source code must retain the above copyright * notice, this list of conditions and the following disclaimer. - * + * * 2. Redistributions in binary form must reproduce the above copyright * notice, this list of conditions and the following disclaimer in the * documentation and/or other materials provided with the distribution. - * + * * 3. Neither the name of the Institute nor the names of its contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. - * + * * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE @@ -31,25 +31,22 @@ * SUCH DAMAGE. */ -#ifdef HAVE_CONFIG_H #include <config.h> -#endif #ifndef HAVE_FLOCK -RCSID("$Id: flock.c 14773 2005-04-12 11:29:18Z lha $"); #include "roken.h" - #define OP_MASK (LOCK_SH | LOCK_EX | LOCK_UN) -int ROKEN_LIB_FUNCTION -flock(int fd, int operation) + +ROKEN_LIB_FUNCTION int ROKEN_LIB_CALL +rk_flock(int fd, int operation) { #if defined(HAVE_FCNTL) && defined(F_SETLK) struct flock arg; int code, cmd; - + arg.l_whence = SEEK_SET; arg.l_start = 0; arg.l_len = 0; /* means to EOF */ @@ -78,6 +75,76 @@ flock(int fd, int operation) break; } return code; + +#elif defined(_WIN32) + /* Windows */ + +#define FLOCK_OFFSET_LOW 0 +#define FLOCK_OFFSET_HIGH 0 +#define FLOCK_LENGTH_LOW 0x00000000 +#define FLOCK_LENGTH_HIGH 0x80000000 + + HANDLE hFile; + OVERLAPPED ov; + BOOL rv = FALSE; + DWORD f = 0; + + hFile = (HANDLE) _get_osfhandle(fd); + if (hFile == NULL || hFile == INVALID_HANDLE_VALUE) { + _set_errno(EBADF); + return -1; + } + + ZeroMemory(&ov, sizeof(ov)); + ov.hEvent = NULL; + ov.Offset = FLOCK_OFFSET_LOW; + ov.OffsetHigh = FLOCK_OFFSET_HIGH; + + if (operation & LOCK_NB) + f = LOCKFILE_FAIL_IMMEDIATELY; + + switch (operation & OP_MASK) { + case LOCK_UN: /* Unlock */ + rv = UnlockFileEx(hFile, 0, + FLOCK_LENGTH_LOW, FLOCK_LENGTH_HIGH, &ov); + break; + + case LOCK_SH: /* Shared lock */ + rv = LockFileEx(hFile, f, 0, + FLOCK_LENGTH_LOW, FLOCK_LENGTH_HIGH, &ov); + break; + + case LOCK_EX: /* Exclusive lock */ + rv = LockFileEx(hFile, f|LOCKFILE_EXCLUSIVE_LOCK, 0, + FLOCK_LENGTH_LOW, FLOCK_LENGTH_HIGH, + &ov); + break; + + default: + _set_errno(EINVAL); + return -1; + } + + if (!rv) { + switch (GetLastError()) { + case ERROR_SHARING_VIOLATION: + case ERROR_LOCK_VIOLATION: + case ERROR_IO_PENDING: + _set_errno(EWOULDBLOCK); + break; + + case ERROR_ACCESS_DENIED: + _set_errno(EACCES); + break; + + default: + _set_errno(ENOLCK); + } + return -1; + } + + return 0; + #else return -1; #endif |