@@ -644,32 +644,16 @@ xfs_ialloc_iget(
*/
int
xfs_dir_ialloc(
- xfs_trans_t **tpp, /* input: current transaction;
- output: may be a new transaction. */
- xfs_inode_t *dp, /* directory within whose allocate
- the inode. */
- umode_t mode,
- xfs_nlink_t nlink,
- dev_t rdev,
- prid_t prid, /* project id */
- xfs_inode_t **ipp) /* pointer to inode; it will be
- locked. */
+ struct xfs_trans **tpp,
+ const struct xfs_ialloc_args *args,
+ struct xfs_inode **ipp)
{
- struct xfs_ialloc_args args = {
- .pip = dp,
- .uid = xfs_kuid_to_uid(current_fsuid()),
- .gid = xfs_kgid_to_gid(current_fsgid()),
- .prid = prid,
- .nlink = nlink,
- .rdev = rdev,
- .mode = mode,
- };
- xfs_trans_t *tp;
- xfs_inode_t *ip;
- xfs_buf_t *ialloc_context = NULL;
- int code;
- void *dqinfo;
- uint tflags;
+ struct xfs_trans *tp;
+ struct xfs_inode *ip;
+ struct xfs_buf *ialloc_context = NULL;
+ void *dqinfo;
+ uint tflags;
+ int code;
tp = *tpp;
ASSERT(tp->t_flags & XFS_TRANS_PERM_LOG_RES);
@@ -689,7 +673,7 @@ xfs_dir_ialloc(
* transaction commit so that no other process can steal
* the inode(s) that we've just allocated.
*/
- code = xfs_ialloc(tp, &args, &ialloc_context, &ip);
+ code = xfs_ialloc(tp, args, &ialloc_context, &ip);
/*
* Return an error if we were unable to allocate a new inode.
@@ -758,7 +742,7 @@ xfs_dir_ialloc(
* other allocations in this allocation group,
* this call should always succeed.
*/
- code = xfs_ialloc(tp, &args, &ialloc_context, &ip);
+ code = xfs_ialloc(tp, args, &ialloc_context, &ip);
/*
* If we get an error at this point, return to the caller
@@ -817,38 +801,34 @@ xfs_bumplink(
int
xfs_create(
- xfs_inode_t *dp,
- struct xfs_name *name,
- umode_t mode,
- dev_t rdev,
- xfs_inode_t **ipp)
-{
- int is_dir = S_ISDIR(mode);
- struct xfs_mount *mp = dp->i_mount;
- struct xfs_inode *ip = NULL;
- struct xfs_trans *tp = NULL;
- int error;
- bool unlock_dp_on_error = false;
- prid_t prid;
- struct xfs_dquot *udqp = NULL;
- struct xfs_dquot *gdqp = NULL;
- struct xfs_dquot *pdqp = NULL;
- struct xfs_trans_res *tres;
- bool cleared_space = false;
- uint resblks;
-
+ struct xfs_inode *dp,
+ struct xfs_name *name,
+ const struct xfs_ialloc_args *args,
+ struct xfs_inode **ipp)
+{
+ struct xfs_mount *mp = dp->i_mount;
+ struct xfs_inode *ip = NULL;
+ struct xfs_trans *tp = NULL;
+ struct xfs_dquot *udqp = NULL;
+ struct xfs_dquot *gdqp = NULL;
+ struct xfs_dquot *pdqp = NULL;
+ struct xfs_trans_res *tres;
+ uint resblks;
+ bool unlock_dp_on_error = false;
+ bool is_dir = S_ISDIR(args->mode);
+ bool cleared_space = false;
+ int error;
+
+ ASSERT(args->pip == dp);
trace_xfs_create(dp, name);
if (XFS_FORCED_SHUTDOWN(mp))
return -EIO;
- prid = xfs_get_initial_prid(dp);
-
/*
* Make sure that we have allocated dquot(s) on disk.
*/
- error = xfs_qm_vop_dqalloc(dp, xfs_kuid_to_uid(current_fsuid()),
- xfs_kgid_to_gid(current_fsgid()), prid,
+ error = xfs_qm_vop_dqalloc(dp, args->uid, args->gid, args->prid,
XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT,
&udqp, &gdqp, &pdqp);
if (error)
@@ -917,7 +897,7 @@ xfs_create(
* entry pointing to them, but a directory also the "." entry
* pointing to itself.
*/
- error = xfs_dir_ialloc(&tp, dp, mode, is_dir ? 2 : 1, rdev, prid, &ip);
+ error = xfs_dir_ialloc(&tp, args, &ip);
if (error)
goto out_trans_cancel;
@@ -999,31 +979,30 @@ xfs_create(
int
xfs_create_tmpfile(
- struct xfs_inode *dp,
- umode_t mode,
- struct xfs_inode **ipp)
-{
- struct xfs_mount *mp = dp->i_mount;
- struct xfs_inode *ip = NULL;
- struct xfs_trans *tp = NULL;
- int error;
- prid_t prid;
- struct xfs_dquot *udqp = NULL;
- struct xfs_dquot *gdqp = NULL;
- struct xfs_dquot *pdqp = NULL;
- struct xfs_trans_res *tres;
- uint resblks;
+ struct xfs_inode *dp,
+ const struct xfs_ialloc_args *args,
+ struct xfs_inode **ipp)
+{
+ struct xfs_mount *mp = dp->i_mount;
+ struct xfs_inode *ip = NULL;
+ struct xfs_trans *tp = NULL;
+ struct xfs_dquot *udqp = NULL;
+ struct xfs_dquot *gdqp = NULL;
+ struct xfs_dquot *pdqp = NULL;
+ struct xfs_trans_res *tres;
+ uint resblks;
+ int error;
+
+ ASSERT(args->nlink == 0);
+ ASSERT(args->pip == dp);
if (XFS_FORCED_SHUTDOWN(mp))
return -EIO;
- prid = xfs_get_initial_prid(dp);
-
/*
* Make sure that we have allocated dquot(s) on disk.
*/
- error = xfs_qm_vop_dqalloc(dp, xfs_kuid_to_uid(current_fsuid()),
- xfs_kgid_to_gid(current_fsgid()), prid,
+ error = xfs_qm_vop_dqalloc(dp, args->uid, args->gid, args->prid,
XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT,
&udqp, &gdqp, &pdqp);
if (error)
@@ -1041,7 +1020,7 @@ xfs_create_tmpfile(
if (error)
goto out_trans_cancel;
- error = xfs_dir_ialloc(&tp, dp, mode, 0, 0, prid, &ip);
+ error = xfs_dir_ialloc(&tp, args, &ip);
if (error)
goto out_trans_cancel;
@@ -3086,10 +3065,18 @@ xfs_rename_alloc_whiteout(
struct xfs_inode *dp,
struct xfs_inode **wip)
{
+ struct xfs_ialloc_args args = {
+ .pip = dp,
+ .uid = xfs_kuid_to_uid(current_fsuid()),
+ .gid = xfs_kgid_to_gid(current_fsgid()),
+ .prid = xfs_get_initial_prid(dp),
+ .nlink = 0,
+ .mode = S_IFCHR | WHITEOUT_MODE,
+ };
struct xfs_inode *tmpfile;
int error;
- error = xfs_create_tmpfile(dp, S_IFCHR | WHITEOUT_MODE, &tmpfile);
+ error = xfs_create_tmpfile(dp, &args, &tmpfile);
if (error)
return error;
@@ -405,8 +405,10 @@ void xfs_inactive(struct xfs_inode *ip);
int xfs_lookup(struct xfs_inode *dp, struct xfs_name *name,
struct xfs_inode **ipp, struct xfs_name *ci_name);
int xfs_create(struct xfs_inode *dp, struct xfs_name *name,
- umode_t mode, dev_t rdev, struct xfs_inode **ipp);
-int xfs_create_tmpfile(struct xfs_inode *dp, umode_t mode,
+ const struct xfs_ialloc_args *iargs,
+ struct xfs_inode **ipp);
+int xfs_create_tmpfile(struct xfs_inode *dp,
+ const struct xfs_ialloc_args *iargs,
struct xfs_inode **ipp);
int xfs_remove(struct xfs_inode *dp, struct xfs_name *name,
struct xfs_inode *ip);
@@ -438,8 +440,8 @@ int xfs_iflush(struct xfs_inode *, struct xfs_buf **);
void xfs_lock_two_inodes(struct xfs_inode *ip0, uint ip0_mode,
struct xfs_inode *ip1, uint ip1_mode);
-int xfs_dir_ialloc(struct xfs_trans **, struct xfs_inode *, umode_t,
- xfs_nlink_t, dev_t, prid_t,
+int xfs_dir_ialloc(struct xfs_trans **,
+ const struct xfs_ialloc_args *,
struct xfs_inode **);
static inline int
@@ -123,42 +123,52 @@ xfs_cleanup_inode(
STATIC int
xfs_generic_create(
- struct inode *dir,
- struct dentry *dentry,
- umode_t mode,
- dev_t rdev,
- bool tmpfile) /* unnamed file */
+ struct inode *dir,
+ struct dentry *dentry,
+ umode_t mode,
+ dev_t rdev,
+ bool tmpfile) /* unnamed file */
{
- struct inode *inode;
- struct xfs_inode *ip = NULL;
- struct posix_acl *default_acl, *acl;
- struct xfs_name name;
- int error;
+ struct xfs_ialloc_args args = {
+ .pip = XFS_I(dir),
+ .uid = xfs_kuid_to_uid(current_fsuid()),
+ .gid = xfs_kgid_to_gid(current_fsgid()),
+ .prid = xfs_get_initial_prid(XFS_I(dir)),
+ .nlink = tmpfile ? 0 : (S_ISDIR(mode) ? 2 : 1),
+ .rdev = rdev,
+ .mode = mode,
+ };
+ struct inode *inode;
+ struct xfs_inode *ip = NULL;
+ struct posix_acl *default_acl, *acl;
+ struct xfs_name name;
+ int error;
/*
* Irix uses Missed'em'V split, but doesn't want to see
* the upper 5 bits of (14bit) major.
*/
- if (S_ISCHR(mode) || S_ISBLK(mode)) {
- if (unlikely(!sysv_valid_dev(rdev) || MAJOR(rdev) & ~0x1ff))
+ if (S_ISCHR(args.mode) || S_ISBLK(args.mode)) {
+ if (unlikely(!sysv_valid_dev(args.rdev) ||
+ MAJOR(args.rdev) & ~0x1ff))
return -EINVAL;
} else {
- rdev = 0;
+ args.rdev = 0;
}
- error = posix_acl_create(dir, &mode, &default_acl, &acl);
+ error = posix_acl_create(dir, &args.mode, &default_acl, &acl);
if (error)
return error;
/* Verify mode is valid also for tmpfile case */
- error = xfs_dentry_mode_to_name(&name, dentry, mode);
+ error = xfs_dentry_mode_to_name(&name, dentry, args.mode);
if (unlikely(error))
goto out_free_acl;
if (!tmpfile) {
- error = xfs_create(XFS_I(dir), &name, mode, rdev, &ip);
+ error = xfs_create(XFS_I(dir), &name, &args, &ip);
} else {
- error = xfs_create_tmpfile(XFS_I(dir), mode, &ip);
+ error = xfs_create_tmpfile(XFS_I(dir), &args, &ip);
}
if (unlikely(error))
goto out_free_acl;
@@ -757,6 +757,10 @@ xfs_qm_qino_alloc(
xfs_inode_t **ip,
uint flags)
{
+ struct xfs_ialloc_args args = {
+ .nlink = 1,
+ .mode = S_IFREG,
+ };
xfs_trans_t *tp;
int error;
bool need_alloc = true;
@@ -806,7 +810,7 @@ xfs_qm_qino_alloc(
return error;
if (need_alloc) {
- error = xfs_dir_ialloc(&tp, NULL, S_IFREG, 1, 0, 0, ip);
+ error = xfs_dir_ialloc(&tp, &args, ip);
if (error) {
xfs_trans_cancel(tp);
return error;
@@ -235,6 +235,14 @@ xfs_symlink(
umode_t mode,
struct xfs_inode **ipp)
{
+ struct xfs_ialloc_args args = {
+ .pip = dp,
+ .uid = xfs_kuid_to_uid(current_fsuid()),
+ .gid = xfs_kgid_to_gid(current_fsgid()),
+ .prid = xfs_get_initial_prid(dp),
+ .nlink = 1,
+ .mode = S_IFLNK | (mode & ~S_IFMT),
+ };
struct xfs_mount *mp = dp->i_mount;
struct xfs_trans *tp = NULL;
struct xfs_inode *ip = NULL;
@@ -242,7 +250,6 @@ xfs_symlink(
int pathlen;
bool unlock_dp_on_error = false;
xfs_filblks_t fs_blocks;
- prid_t prid;
struct xfs_dquot *udqp = NULL;
struct xfs_dquot *gdqp = NULL;
struct xfs_dquot *pdqp = NULL;
@@ -264,14 +271,11 @@ xfs_symlink(
ASSERT(pathlen > 0);
udqp = gdqp = NULL;
- prid = xfs_get_initial_prid(dp);
/*
* Make sure that we have allocated dquot(s) on disk.
*/
- error = xfs_qm_vop_dqalloc(dp,
- xfs_kuid_to_uid(current_fsuid()),
- xfs_kgid_to_gid(current_fsgid()), prid,
+ error = xfs_qm_vop_dqalloc(dp, args.uid, args.gid, args.prid,
XFS_QMOPT_QUOTALL | XFS_QMOPT_INHERIT,
&udqp, &gdqp, &pdqp);
if (error)
@@ -313,8 +317,7 @@ xfs_symlink(
/*
* Allocate an inode for the symlink.
*/
- error = xfs_dir_ialloc(&tp, dp, S_IFLNK | (mode & ~S_IFMT), 1, 0,
- prid, &ip);
+ error = xfs_dir_ialloc(&tp, &args, &ip);
if (error)
goto out_trans_cancel;