Date: Fri, 4 Aug 2017 14:24:24 +0000 (UTC) From: Mariusz Zaborski <oshogbo@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r322054 - head/lib/libutil Message-ID: <201708041424.v74EOOcm067800@repo.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: oshogbo Date: Fri Aug 4 14:24:24 2017 New Revision: 322054 URL: https://svnweb.freebsd.org/changeset/base/322054 Log: Introduce the flopenat(3) function. Reviewed by: des, emaste Differential Revision: https://reviews.freebsd.org/D11690 Modified: head/lib/libutil/Makefile head/lib/libutil/flopen.3 head/lib/libutil/flopen.c head/lib/libutil/libutil.h Modified: head/lib/libutil/Makefile ============================================================================== --- head/lib/libutil/Makefile Fri Aug 4 13:08:45 2017 (r322053) +++ head/lib/libutil/Makefile Fri Aug 4 14:24:24 2017 (r322054) @@ -35,6 +35,7 @@ MAN+= expand_number.3 flopen.3 fparseln.3 hexdump.3 \ property.3 pty.3 quotafile.3 realhostname.3 realhostname_sa.3 \ _secure_path.3 trimdomain.3 uucplock.3 pw_util.3 MAN+= login.conf.5 +MLINKS+=flopen.3 flopenat.3 MLINKS+=kld.3 kld_isloaded.3 kld.3 kld_load.3 MLINKS+=login_auth.3 auth_cat.3 login_auth.3 auth_checknologin.3 MLINKS+=login_cap.3 login_close.3 login_cap.3 login_getcapbool.3 \ Modified: head/lib/libutil/flopen.3 ============================================================================== --- head/lib/libutil/flopen.3 Fri Aug 4 13:08:45 2017 (r322053) +++ head/lib/libutil/flopen.3 Fri Aug 4 14:24:24 2017 (r322054) @@ -25,11 +25,12 @@ .\" .\" $FreeBSD$ .\" -.Dd June 6, 2009 +.Dd July 28, 2017 .Dt FLOPEN 3 .Os .Sh NAME -.Nm flopen +.Nm flopen , +.Nm flopenat .Nd "Reliably open and lock a file" .Sh LIBRARY .Lb libutil @@ -40,6 +41,10 @@ .Fn flopen "const char *path" "int flags" .Ft int .Fn flopen "const char *path" "int flags" "mode_t mode" +.Ft int +.Fn flopenat "int fd" "const char *path" "int flags" +.Ft int +.Fn flopenat "int fd" "const char *path" "int flags" "mode_t mode" .Sh DESCRIPTION The .Fn flopen @@ -79,6 +84,27 @@ argument is required if .Va flags includes .Dv O_CREAT . +.Pp +The +.Fn flopenat +function is equivalent to the +.Fn flopen +function except in the case where the +.Fa path +specifies a relative path. +In this case the file to be opened is determined relative to the directory +associated with the file descriptor +.Fa fd +instead of the current working directory. +If +.Fn flopenat +is passed the special value +.Dv AT_FDCWD +in the +.Fa fd +parameter, the current working directory is used +and the behavior is identical to a call to +.Fn flopen . .Sh RETURN VALUES If successful, .Fn flopen Modified: head/lib/libutil/flopen.c ============================================================================== --- head/lib/libutil/flopen.c Fri Aug 4 13:08:45 2017 (r322053) +++ head/lib/libutil/flopen.c Fri Aug 4 14:24:24 2017 (r322054) @@ -45,8 +45,8 @@ __FBSDID("$FreeBSD$"); * code's apparent simplicity; there would be no need for this function if it * was easy to get right. */ -int -flopen(const char *path, int flags, ...) +static int +vflopenat(int dirfd, const char *path, int flags, va_list ap) { int fd, operation, serrno, trunc; struct stat sb, fsb; @@ -58,11 +58,7 @@ flopen(const char *path, int flags, ...) mode = 0; if (flags & O_CREAT) { - va_list ap; - - va_start(ap, flags); mode = (mode_t)va_arg(ap, int); /* mode_t promoted to int */ - va_end(ap); } operation = LOCK_EX; @@ -73,7 +69,7 @@ flopen(const char *path, int flags, ...) flags &= ~O_TRUNC; for (;;) { - if ((fd = open(path, flags, mode)) == -1) + if ((fd = openat(dirfd, path, flags, mode)) == -1) /* non-existent or no access */ return (-1); if (flock(fd, operation) == -1) { @@ -83,7 +79,7 @@ flopen(const char *path, int flags, ...) errno = serrno; return (-1); } - if (stat(path, &sb) == -1) { + if (fstatat(dirfd, path, &sb, 0) == -1) { /* disappeared from under our feet */ (void)close(fd); continue; @@ -122,4 +118,28 @@ flopen(const char *path, int flags, ...) #endif return (fd); } +} + +int +flopen(const char *path, int flags, ...) +{ + va_list ap; + int ret; + + va_start(ap, flags); + ret = vflopenat(AT_FDCWD, path, flags, ap); + va_end(ap); + return (ret); +} + +int +flopenat(int dirfd, const char *path, int flags, ...) +{ + va_list ap; + int ret; + + va_start(ap, flags); + ret = vflopenat(dirfd, path, flags, ap); + va_end(ap); + return (ret); } Modified: head/lib/libutil/libutil.h ============================================================================== --- head/lib/libutil/libutil.h Fri Aug 4 13:08:45 2017 (r322053) +++ head/lib/libutil/libutil.h Fri Aug 4 14:24:24 2017 (r322054) @@ -93,6 +93,7 @@ int expand_number(const char *_buf, uint64_t *_num); int extattr_namespace_to_string(int _attrnamespace, char **_string); int extattr_string_to_namespace(const char *_string, int *_attrnamespace); int flopen(const char *_path, int _flags, ...); +int flopenat(int _dirfd, const char *_path, int _flags, ...); int forkpty(int *_amaster, char *_name, struct termios *_termp, struct winsize *_winp); void hexdump(const void *_ptr, int _length, const char *_hdr, int _flags);
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201708041424.v74EOOcm067800>