DTRT when O_NONBLOCK is specified.
MFC after: 3 weeks
This commit is contained in:
parent
9667055264
commit
3dea593400
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=169447
@ -60,6 +60,17 @@ Thus, it is well suited for opening lock files, PID files, spool
|
||||
files, mailboxes and other kinds of files which are used for
|
||||
synchronization between processes.
|
||||
.Pp
|
||||
If
|
||||
.Va flags
|
||||
includes
|
||||
.Dv O_NONBLOCK
|
||||
and the file is already locked,
|
||||
.Fn flopen
|
||||
will fail and set
|
||||
.Va errno
|
||||
to
|
||||
.Dv EWOULDBLOCK .
|
||||
.Pp
|
||||
As with
|
||||
.Fn flopen ,
|
||||
the additional
|
||||
@ -68,7 +79,18 @@ argument is required if
|
||||
.Va flags
|
||||
includes
|
||||
.Dv O_CREAT .
|
||||
.Sh RETURN VALUES
|
||||
If successful,
|
||||
.Fn flopen
|
||||
returns a valid file descriptor.
|
||||
Otherwise, it returns -1, and sets
|
||||
.Va errno
|
||||
as described in
|
||||
.Xr flock 2
|
||||
and
|
||||
.Xr open 2 .
|
||||
.Sh SEE ALSO
|
||||
.Xr errno 2 ,
|
||||
.Xr flock 2 ,
|
||||
.Xr open 2
|
||||
.Sh AUTHORS
|
||||
|
@ -39,29 +39,32 @@ __FBSDID("$FreeBSD$");
|
||||
int
|
||||
flopen(const char *path, int flags, ...)
|
||||
{
|
||||
int fd, operation, serrno;
|
||||
struct stat sb, fsb;
|
||||
mode_t mode;
|
||||
int fd, serrno;
|
||||
|
||||
#ifdef O_EXLOCK
|
||||
flags &= ~O_EXLOCK;
|
||||
#endif
|
||||
|
||||
mode = 0;
|
||||
if (flags & O_CREAT) {
|
||||
va_list ap;
|
||||
|
||||
va_start(ap, flags);
|
||||
mode = va_arg(ap, int); /* mode_t promoted to int */
|
||||
va_end(ap);
|
||||
} else {
|
||||
mode = 0;
|
||||
}
|
||||
|
||||
operation = LOCK_EX;
|
||||
if (flags & O_NONBLOCK)
|
||||
operation |= LOCK_NB;
|
||||
|
||||
for (;;) {
|
||||
if ((fd = open(path, flags, mode)) == -1)
|
||||
/* non-existent or no access */
|
||||
return (-1);
|
||||
if (flock(fd, LOCK_EX) == -1) {
|
||||
if (flock(fd, operation) == -1) {
|
||||
/* unsupported or interrupted */
|
||||
serrno = errno;
|
||||
close(fd);
|
||||
|
Loading…
Reference in New Issue
Block a user