From aaa2584c0498037529a30c985ac8a437ec7d842c Mon Sep 17 00:00:00 2001 From: Andrew Deason Date: Thu, 30 May 2013 17:53:56 -0500 Subject: [PATCH] namei: Create the IH_CREATE_INIT function Create a new function that combines calls to IH_CREATE and IH_INIT into one operation; the new function is called IH_CREATE_INIT. This allows a caller to create a file and then use it, without needing to open() the file twice. This is currently only implemented for the Unix namei backend; other backends result in effectively the same functionality (but can use the same API). Change-Id: I93d531a9892beeb0c1ceac18458cbe0f1e3a0ded Reviewed-on: http://gerrit.openafs.org/9969 Reviewed-by: Derrick Brashear Tested-by: Derrick Brashear --- src/vol/ihandle.c | 17 +++++++++++++ src/vol/ihandle.h | 7 ++++++ src/vol/namei_ops.c | 58 ++++++++++++++++++++++++++++++++++++++++----- src/vol/namei_ops.h | 3 +++ 4 files changed, 79 insertions(+), 6 deletions(-) diff --git a/src/vol/ihandle.c b/src/vol/ihandle.c index c87f43d87..16d233231 100644 --- a/src/vol/ihandle.c +++ b/src/vol/ihandle.c @@ -1051,6 +1051,23 @@ ih_icreate(IHandle_t * ih, int dev, char *part, Inode nI, int p1, int p2, } #endif /* AFS_NAMEI_ENV */ +#if defined(AFS_NT40_ENV) || !defined(AFS_NAMEI_ENV) +/* Unix namei implements its own more efficient IH_CREATE_INIT; this wrapper + * is for everyone else */ +IHandle_t * +ih_icreate_init(IHandle_t *lh, int dev, char *part, Inode nearInode, + afs_uint32 p1, afs_uint32 p2, afs_uint32 p3, afs_uint32 p4) +{ + IHandle_t *ihP; + Inode ino = IH_CREATE(lh, dev, part, nearInode, p1, p2, p3, p4); + if (!VALID_INO(ino)) { + return NULL; + } + IH_INIT(ihP, dev, p1, ino); + return ihP; +} +#endif + afs_sfsize_t ih_size(FD_t fd) { diff --git a/src/vol/ihandle.h b/src/vol/ihandle.h index 8d60e3b70..56223edc6 100644 --- a/src/vol/ihandle.h +++ b/src/vol/ihandle.h @@ -420,6 +420,11 @@ extern int ih_isunlinked(FD_t fd); # define OS_DIRSEPC '/' #endif +#if defined(AFS_NT40_ENV) || !defined(AFS_NAMEI_ENV) +# define IH_CREATE_INIT(H, D, P, N, P1, P2, P3, P4) \ + ih_icreate_init(H, D, P, N, P1, P2, P3, P4) +#endif + #ifdef AFS_NAMEI_ENV # ifdef AFS_NT40_ENV @@ -485,6 +490,8 @@ extern int OS_TRUNC(FD_t FD, OFFT L); # endif /* !O_LARGEFILE */ # define OS_SYNC(FD) fsync(FD) +# define IH_CREATE_INIT(H, D, P, N, P1, P2, P3, P4) \ + namei_icreate_init(H, D, P, P1, P2, P3, P4) /*@=fcnmacros =macrofcndecl@*/ # endif /* AFS_NT40_ENV */ diff --git a/src/vol/namei_ops.c b/src/vol/namei_ops.c index c48c1b2f1..c5ea7ae64 100644 --- a/src/vol/namei_ops.c +++ b/src/vol/namei_ops.c @@ -952,7 +952,8 @@ bad: } #else /* !AFS_NT40_ENV */ Inode -namei_icreate(IHandle_t * lh, char *part, afs_uint32 p1, afs_uint32 p2, afs_uint32 p3, afs_uint32 p4) +icreate(IHandle_t * lh, char *part, afs_uint32 p1, afs_uint32 p2, afs_uint32 p3, afs_uint32 p4, + FD_t *afd, Inode *ainode) { namei_t name; int fd = INVALID_FD; @@ -1042,10 +1043,6 @@ namei_icreate(IHandle_t * lh, char *part, afs_uint32 p1, afs_uint32 p2, afs_uint } bad: - if (fd != INVALID_FD) - OS_CLOSE(fd); - - if (code || (fd == INVALID_FD)) { if (p2 != -1) { fdP = IH_OPEN(lh); @@ -1055,7 +1052,56 @@ namei_icreate(IHandle_t * lh, char *part, afs_uint32 p1, afs_uint32 p2, afs_uint } } } - return (code || (fd == INVALID_FD)) ? (Inode) - 1 : tmp.ih_ino; + + *afd = fd; + *ainode = tmp.ih_ino; + + return code; +} + +Inode +namei_icreate(IHandle_t * lh, char *part, + afs_uint32 p1, afs_uint32 p2, afs_uint32 p3, afs_uint32 p4) +{ + Inode ino = 0; + int fd = INVALID_FD; + int code; + + code = icreate(lh, part, p1, p2, p3, p4, &fd, &ino); + if (fd != INVALID_FD) { + close(fd); + } + return (code || (fd == INVALID_FD)) ? (Inode) - 1 : ino; +} + +IHandle_t * +namei_icreate_init(IHandle_t * lh, int dev, char *part, + afs_uint32 p1, afs_uint32 p2, afs_uint32 p3, afs_uint32 p4) +{ + Inode ino = 0; + int fd = INVALID_FD; + int code; + IHandle_t *ihP; + FdHandle_t *fdP; + + code = icreate(lh, part, p1, p2, p3, p4, &fd, &ino); + if (fd == INVALID_FD) { + return NULL; + } + if (code) { + close(fd); + return NULL; + } + + IH_INIT(ihP, dev, p1, ino); + fdP = ih_attachfd(ihP, fd); + if (!fdP) { + close(fd); + } else { + FDH_CLOSE(fdP); + } + + return ihP; } #endif diff --git a/src/vol/namei_ops.h b/src/vol/namei_ops.h index d3cf996dd..cacb42fd6 100644 --- a/src/vol/namei_ops.h +++ b/src/vol/namei_ops.h @@ -22,6 +22,9 @@ extern int namei_unlink(char *name); extern Inode namei_MakeSpecIno(VolumeId volid, int type); extern Inode namei_icreate(IHandle_t * lh, char *part, afs_uint32 p1, afs_uint32 p2, afs_uint32 p3, afs_uint32 p4); +extern IHandle_t *namei_icreate_init(IHandle_t *lh, int dev, char *part, + afs_uint32 p1, afs_uint32 p2, + afs_uint32 p3, afs_uint32 p4); extern FD_t namei_iopen(IHandle_t * h); extern int namei_irelease(IHandle_t * h); afs_sfsize_t namei_iread(IHandle_t * h, afs_foff_t offset, char *buf, -- 2.39.5