diff options
Diffstat (limited to 'fs/cifs/inode.c')
-rw-r--r-- | fs/cifs/inode.c | 58 |
1 files changed, 35 insertions, 23 deletions
diff --git a/fs/cifs/inode.c b/fs/cifs/inode.c index 39869c3c3efb..589f3e3f6e00 100644 --- a/fs/cifs/inode.c +++ b/fs/cifs/inode.c | |||
@@ -686,13 +686,18 @@ int cifs_get_inode_info(struct inode **pinode, | |||
686 | cFYI(1, "cifs_sfu_type failed: %d", tmprc); | 686 | cFYI(1, "cifs_sfu_type failed: %d", tmprc); |
687 | } | 687 | } |
688 | 688 | ||
689 | #ifdef CONFIG_CIFS_EXPERIMENTAL | 689 | #ifdef CONFIG_CIFS_ACL |
690 | /* fill in 0777 bits from ACL */ | 690 | /* fill in 0777 bits from ACL */ |
691 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_CIFS_ACL) { | 691 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_CIFS_ACL) { |
692 | cFYI(1, "Getting mode bits from ACL"); | 692 | rc = cifs_acl_to_fattr(cifs_sb, &fattr, *pinode, full_path, |
693 | cifs_acl_to_fattr(cifs_sb, &fattr, *pinode, full_path, pfid); | 693 | pfid); |
694 | if (rc) { | ||
695 | cFYI(1, "%s: Getting ACL failed with error: %d", | ||
696 | __func__, rc); | ||
697 | goto cgii_exit; | ||
698 | } | ||
694 | } | 699 | } |
695 | #endif | 700 | #endif /* CONFIG_CIFS_ACL */ |
696 | 701 | ||
697 | /* fill in remaining high mode bits e.g. SUID, VTX */ | 702 | /* fill in remaining high mode bits e.g. SUID, VTX */ |
698 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_UNX_EMUL) | 703 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_UNX_EMUL) |
@@ -723,12 +728,12 @@ static const struct inode_operations cifs_ipc_inode_ops = { | |||
723 | .lookup = cifs_lookup, | 728 | .lookup = cifs_lookup, |
724 | }; | 729 | }; |
725 | 730 | ||
726 | char *cifs_build_path_to_root(struct cifs_sb_info *cifs_sb) | 731 | char *cifs_build_path_to_root(struct cifs_sb_info *cifs_sb, |
732 | struct cifsTconInfo *tcon) | ||
727 | { | 733 | { |
728 | int pplen = cifs_sb->prepathlen; | 734 | int pplen = cifs_sb->prepathlen; |
729 | int dfsplen; | 735 | int dfsplen; |
730 | char *full_path = NULL; | 736 | char *full_path = NULL; |
731 | struct cifsTconInfo *tcon = cifs_sb_master_tcon(cifs_sb); | ||
732 | 737 | ||
733 | /* if no prefix path, simply set path to the root of share to "" */ | 738 | /* if no prefix path, simply set path to the root of share to "" */ |
734 | if (pplen == 0) { | 739 | if (pplen == 0) { |
@@ -870,7 +875,7 @@ struct inode *cifs_root_iget(struct super_block *sb, unsigned long ino) | |||
870 | char *full_path; | 875 | char *full_path; |
871 | struct cifsTconInfo *tcon = cifs_sb_master_tcon(cifs_sb); | 876 | struct cifsTconInfo *tcon = cifs_sb_master_tcon(cifs_sb); |
872 | 877 | ||
873 | full_path = cifs_build_path_to_root(cifs_sb); | 878 | full_path = cifs_build_path_to_root(cifs_sb, tcon); |
874 | if (full_path == NULL) | 879 | if (full_path == NULL) |
875 | return ERR_PTR(-ENOMEM); | 880 | return ERR_PTR(-ENOMEM); |
876 | 881 | ||
@@ -881,8 +886,10 @@ struct inode *cifs_root_iget(struct super_block *sb, unsigned long ino) | |||
881 | rc = cifs_get_inode_info(&inode, full_path, NULL, sb, | 886 | rc = cifs_get_inode_info(&inode, full_path, NULL, sb, |
882 | xid, NULL); | 887 | xid, NULL); |
883 | 888 | ||
884 | if (!inode) | 889 | if (!inode) { |
885 | return ERR_PTR(rc); | 890 | inode = ERR_PTR(rc); |
891 | goto out; | ||
892 | } | ||
886 | 893 | ||
887 | #ifdef CONFIG_CIFS_FSCACHE | 894 | #ifdef CONFIG_CIFS_FSCACHE |
888 | /* populate tcon->resource_id */ | 895 | /* populate tcon->resource_id */ |
@@ -898,13 +905,11 @@ struct inode *cifs_root_iget(struct super_block *sb, unsigned long ino) | |||
898 | inode->i_uid = cifs_sb->mnt_uid; | 905 | inode->i_uid = cifs_sb->mnt_uid; |
899 | inode->i_gid = cifs_sb->mnt_gid; | 906 | inode->i_gid = cifs_sb->mnt_gid; |
900 | } else if (rc) { | 907 | } else if (rc) { |
901 | kfree(full_path); | ||
902 | _FreeXid(xid); | ||
903 | iget_failed(inode); | 908 | iget_failed(inode); |
904 | return ERR_PTR(rc); | 909 | inode = ERR_PTR(rc); |
905 | } | 910 | } |
906 | 911 | ||
907 | 912 | out: | |
908 | kfree(full_path); | 913 | kfree(full_path); |
909 | /* can not call macro FreeXid here since in a void func | 914 | /* can not call macro FreeXid here since in a void func |
910 | * TODO: This is no longer true | 915 | * TODO: This is no longer true |
@@ -1648,6 +1653,7 @@ static bool | |||
1648 | cifs_inode_needs_reval(struct inode *inode) | 1653 | cifs_inode_needs_reval(struct inode *inode) |
1649 | { | 1654 | { |
1650 | struct cifsInodeInfo *cifs_i = CIFS_I(inode); | 1655 | struct cifsInodeInfo *cifs_i = CIFS_I(inode); |
1656 | struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb); | ||
1651 | 1657 | ||
1652 | if (cifs_i->clientCanCacheRead) | 1658 | if (cifs_i->clientCanCacheRead) |
1653 | return false; | 1659 | return false; |
@@ -1658,19 +1664,21 @@ cifs_inode_needs_reval(struct inode *inode) | |||
1658 | if (cifs_i->time == 0) | 1664 | if (cifs_i->time == 0) |
1659 | return true; | 1665 | return true; |
1660 | 1666 | ||
1661 | /* FIXME: the actimeo should be tunable */ | 1667 | if (!time_in_range(jiffies, cifs_i->time, |
1662 | if (time_after_eq(jiffies, cifs_i->time + HZ)) | 1668 | cifs_i->time + cifs_sb->actimeo)) |
1663 | return true; | 1669 | return true; |
1664 | 1670 | ||
1665 | /* hardlinked files w/ noserverino get "special" treatment */ | 1671 | /* hardlinked files w/ noserverino get "special" treatment */ |
1666 | if (!(CIFS_SB(inode->i_sb)->mnt_cifs_flags & CIFS_MOUNT_SERVER_INUM) && | 1672 | if (!(cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SERVER_INUM) && |
1667 | S_ISREG(inode->i_mode) && inode->i_nlink != 1) | 1673 | S_ISREG(inode->i_mode) && inode->i_nlink != 1) |
1668 | return true; | 1674 | return true; |
1669 | 1675 | ||
1670 | return false; | 1676 | return false; |
1671 | } | 1677 | } |
1672 | 1678 | ||
1673 | /* check invalid_mapping flag and zap the cache if it's set */ | 1679 | /* |
1680 | * Zap the cache. Called when invalid_mapping flag is set. | ||
1681 | */ | ||
1674 | static void | 1682 | static void |
1675 | cifs_invalidate_mapping(struct inode *inode) | 1683 | cifs_invalidate_mapping(struct inode *inode) |
1676 | { | 1684 | { |
@@ -2114,11 +2122,16 @@ cifs_setattr_nounix(struct dentry *direntry, struct iattr *attrs) | |||
2114 | 2122 | ||
2115 | if (attrs->ia_valid & ATTR_MODE) { | 2123 | if (attrs->ia_valid & ATTR_MODE) { |
2116 | rc = 0; | 2124 | rc = 0; |
2117 | #ifdef CONFIG_CIFS_EXPERIMENTAL | 2125 | #ifdef CONFIG_CIFS_ACL |
2118 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_CIFS_ACL) | 2126 | if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_CIFS_ACL) { |
2119 | rc = mode_to_acl(inode, full_path, mode); | 2127 | rc = mode_to_cifs_acl(inode, full_path, mode); |
2120 | else | 2128 | if (rc) { |
2121 | #endif | 2129 | cFYI(1, "%s: Setting ACL failed with error: %d", |
2130 | __func__, rc); | ||
2131 | goto cifs_setattr_exit; | ||
2132 | } | ||
2133 | } else | ||
2134 | #endif /* CONFIG_CIFS_ACL */ | ||
2122 | if (((mode & S_IWUGO) == 0) && | 2135 | if (((mode & S_IWUGO) == 0) && |
2123 | (cifsInode->cifsAttrs & ATTR_READONLY) == 0) { | 2136 | (cifsInode->cifsAttrs & ATTR_READONLY) == 0) { |
2124 | 2137 | ||
@@ -2177,7 +2190,6 @@ cifs_setattr_nounix(struct dentry *direntry, struct iattr *attrs) | |||
2177 | 2190 | ||
2178 | setattr_copy(inode, attrs); | 2191 | setattr_copy(inode, attrs); |
2179 | mark_inode_dirty(inode); | 2192 | mark_inode_dirty(inode); |
2180 | return 0; | ||
2181 | 2193 | ||
2182 | cifs_setattr_exit: | 2194 | cifs_setattr_exit: |
2183 | kfree(full_path); | 2195 | kfree(full_path); |