Merge branch 'for-linus' of git://linux-arm.org/linux-2.6
[linux-2.6] / fs / cifs / inode.c
1 /*
2  *   fs/cifs/inode.c
3  *
4  *   Copyright (C) International Business Machines  Corp., 2002,2008
5  *   Author(s): Steve French (sfrench@us.ibm.com)
6  *
7  *   This library is free software; you can redistribute it and/or modify
8  *   it under the terms of the GNU Lesser General Public License as published
9  *   by the Free Software Foundation; either version 2.1 of the License, or
10  *   (at your option) any later version.
11  *
12  *   This library is distributed in the hope that it will be useful,
13  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
14  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See
15  *   the GNU Lesser General Public License for more details.
16  *
17  *   You should have received a copy of the GNU Lesser General Public License
18  *   along with this library; if not, write to the Free Software
19  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20  */
21 #include <linux/fs.h>
22 #include <linux/stat.h>
23 #include <linux/pagemap.h>
24 #include <asm/div64.h>
25 #include "cifsfs.h"
26 #include "cifspdu.h"
27 #include "cifsglob.h"
28 #include "cifsproto.h"
29 #include "cifs_debug.h"
30 #include "cifs_fs_sb.h"
31
32
33 static void cifs_set_ops(struct inode *inode, const bool is_dfs_referral)
34 {
35         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
36
37         switch (inode->i_mode & S_IFMT) {
38         case S_IFREG:
39                 inode->i_op = &cifs_file_inode_ops;
40                 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_DIRECT_IO) {
41                         if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_NO_BRL)
42                                 inode->i_fop = &cifs_file_direct_nobrl_ops;
43                         else
44                                 inode->i_fop = &cifs_file_direct_ops;
45                 } else if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_NO_BRL)
46                         inode->i_fop = &cifs_file_nobrl_ops;
47                 else { /* not direct, send byte range locks */
48                         inode->i_fop = &cifs_file_ops;
49                 }
50
51
52                 /* check if server can support readpages */
53                 if (cifs_sb->tcon->ses->server->maxBuf <
54                                 PAGE_CACHE_SIZE + MAX_CIFS_HDR_SIZE)
55                         inode->i_data.a_ops = &cifs_addr_ops_smallbuf;
56                 else
57                         inode->i_data.a_ops = &cifs_addr_ops;
58                 break;
59         case S_IFDIR:
60 #ifdef CONFIG_CIFS_DFS_UPCALL
61                 if (is_dfs_referral) {
62                         inode->i_op = &cifs_dfs_referral_inode_operations;
63                 } else {
64 #else /* NO DFS support, treat as a directory */
65                 {
66 #endif
67                         inode->i_op = &cifs_dir_inode_ops;
68                         inode->i_fop = &cifs_dir_ops;
69                 }
70                 break;
71         case S_IFLNK:
72                 inode->i_op = &cifs_symlink_inode_ops;
73                 break;
74         default:
75                 init_special_inode(inode, inode->i_mode, inode->i_rdev);
76                 break;
77         }
78 }
79
80 static void cifs_unix_info_to_inode(struct inode *inode,
81                 FILE_UNIX_BASIC_INFO *info, int force_uid_gid)
82 {
83         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
84         struct cifsInodeInfo *cifsInfo = CIFS_I(inode);
85         __u64 num_of_bytes = le64_to_cpu(info->NumOfBytes);
86         __u64 end_of_file = le64_to_cpu(info->EndOfFile);
87
88         inode->i_atime = cifs_NTtimeToUnix(info->LastAccessTime);
89         inode->i_mtime =
90                 cifs_NTtimeToUnix(info->LastModificationTime);
91         inode->i_ctime = cifs_NTtimeToUnix(info->LastStatusChange);
92         inode->i_mode = le64_to_cpu(info->Permissions);
93
94         /*
95          * Since we set the inode type below we need to mask off
96          * to avoid strange results if bits set above.
97          */
98         inode->i_mode &= ~S_IFMT;
99         switch (le32_to_cpu(info->Type)) {
100         case UNIX_FILE:
101                 inode->i_mode |= S_IFREG;
102                 break;
103         case UNIX_SYMLINK:
104                 inode->i_mode |= S_IFLNK;
105                 break;
106         case UNIX_DIR:
107                 inode->i_mode |= S_IFDIR;
108                 break;
109         case UNIX_CHARDEV:
110                 inode->i_mode |= S_IFCHR;
111                 inode->i_rdev = MKDEV(le64_to_cpu(info->DevMajor),
112                                       le64_to_cpu(info->DevMinor) & MINORMASK);
113                 break;
114         case UNIX_BLOCKDEV:
115                 inode->i_mode |= S_IFBLK;
116                 inode->i_rdev = MKDEV(le64_to_cpu(info->DevMajor),
117                                       le64_to_cpu(info->DevMinor) & MINORMASK);
118                 break;
119         case UNIX_FIFO:
120                 inode->i_mode |= S_IFIFO;
121                 break;
122         case UNIX_SOCKET:
123                 inode->i_mode |= S_IFSOCK;
124                 break;
125         default:
126                 /* safest to call it a file if we do not know */
127                 inode->i_mode |= S_IFREG;
128                 cFYI(1, ("unknown type %d", le32_to_cpu(info->Type)));
129                 break;
130         }
131
132         if ((cifs_sb->mnt_cifs_flags & CIFS_MOUNT_OVERR_UID) &&
133             !force_uid_gid)
134                 inode->i_uid = cifs_sb->mnt_uid;
135         else
136                 inode->i_uid = le64_to_cpu(info->Uid);
137
138         if ((cifs_sb->mnt_cifs_flags & CIFS_MOUNT_OVERR_GID) &&
139             !force_uid_gid)
140                 inode->i_gid = cifs_sb->mnt_gid;
141         else
142                 inode->i_gid = le64_to_cpu(info->Gid);
143
144         inode->i_nlink = le64_to_cpu(info->Nlinks);
145
146         cifsInfo->server_eof = end_of_file;
147         spin_lock(&inode->i_lock);
148         if (is_size_safe_to_change(cifsInfo, end_of_file)) {
149                 /*
150                  * We can not safely change the file size here if the client
151                  * is writing to it due to potential races.
152                  */
153                 i_size_write(inode, end_of_file);
154
155                 /*
156                  * i_blocks is not related to (i_size / i_blksize),
157                  * but instead 512 byte (2**9) size is required for
158                  * calculating num blocks.
159                  */
160                 inode->i_blocks = (512 - 1 + num_of_bytes) >> 9;
161         }
162         spin_unlock(&inode->i_lock);
163 }
164
165
166 /*
167  *      Needed to setup inode data for the directory which is the
168  *      junction to the new submount (ie to setup the fake directory
169  *      which represents a DFS referral)
170  */
171 static void fill_fake_finddataunix(FILE_UNIX_BASIC_INFO *pfnd_dat,
172                                struct super_block *sb)
173 {
174         struct inode *pinode = NULL;
175
176         memset(pfnd_dat, 0, sizeof(FILE_UNIX_BASIC_INFO));
177
178 /*      __le64 pfnd_dat->EndOfFile = cpu_to_le64(0);
179         __le64 pfnd_dat->NumOfBytes = cpu_to_le64(0);
180         __u64 UniqueId = 0;  */
181         pfnd_dat->LastStatusChange =
182                 cpu_to_le64(cifs_UnixTimeToNT(CURRENT_TIME));
183         pfnd_dat->LastAccessTime =
184                 cpu_to_le64(cifs_UnixTimeToNT(CURRENT_TIME));
185         pfnd_dat->LastModificationTime =
186                 cpu_to_le64(cifs_UnixTimeToNT(CURRENT_TIME));
187         pfnd_dat->Type = cpu_to_le32(UNIX_DIR);
188         pfnd_dat->Permissions = cpu_to_le64(S_IXUGO | S_IRWXU);
189         pfnd_dat->Nlinks = cpu_to_le64(2);
190         if (sb->s_root)
191                 pinode = sb->s_root->d_inode;
192         if (pinode == NULL)
193                 return;
194
195         /* fill in default values for the remaining based on root
196            inode since we can not query the server for this inode info */
197         pfnd_dat->DevMajor = cpu_to_le64(MAJOR(pinode->i_rdev));
198         pfnd_dat->DevMinor = cpu_to_le64(MINOR(pinode->i_rdev));
199         pfnd_dat->Uid = cpu_to_le64(pinode->i_uid);
200         pfnd_dat->Gid = cpu_to_le64(pinode->i_gid);
201 }
202
203 /**
204  * cifs_new inode - create new inode, initialize, and hash it
205  * @sb - pointer to superblock
206  * @inum - if valid pointer and serverino is enabled, replace i_ino with val
207  *
208  * Create a new inode, initialize it for CIFS and hash it. Returns the new
209  * inode or NULL if one couldn't be allocated.
210  *
211  * If the share isn't mounted with "serverino" or inum is a NULL pointer then
212  * we'll just use the inode number assigned by new_inode(). Note that this can
213  * mean i_ino collisions since the i_ino assigned by new_inode is not
214  * guaranteed to be unique.
215  */
216 struct inode *
217 cifs_new_inode(struct super_block *sb, __u64 *inum)
218 {
219         struct inode *inode;
220
221         inode = new_inode(sb);
222         if (inode == NULL)
223                 return NULL;
224
225         /*
226          * BB: Is i_ino == 0 legal? Here, we assume that it is. If it isn't we
227          *     stop passing inum as ptr. Are there sanity checks we can use to
228          *     ensure that the server is really filling in that field? Also,
229          *     if serverino is disabled, perhaps we should be using iunique()?
230          */
231         if (inum && (CIFS_SB(sb)->mnt_cifs_flags & CIFS_MOUNT_SERVER_INUM))
232                 inode->i_ino = (unsigned long) *inum;
233
234         /*
235          * must set this here instead of cifs_alloc_inode since VFS will
236          * clobber i_flags
237          */
238         if (sb->s_flags & MS_NOATIME)
239                 inode->i_flags |= S_NOATIME | S_NOCMTIME;
240
241         insert_inode_hash(inode);
242
243         return inode;
244 }
245
246 int cifs_get_inode_info_unix(struct inode **pinode,
247         const unsigned char *full_path, struct super_block *sb, int xid)
248 {
249         int rc = 0;
250         FILE_UNIX_BASIC_INFO find_data;
251         struct cifsTconInfo *pTcon;
252         struct inode *inode;
253         struct cifs_sb_info *cifs_sb = CIFS_SB(sb);
254         bool is_dfs_referral = false;
255         struct cifsInodeInfo *cifsInfo;
256         __u64 num_of_bytes;
257         __u64 end_of_file;
258
259         pTcon = cifs_sb->tcon;
260         cFYI(1, ("Getting info on %s", full_path));
261
262         /* could have done a find first instead but this returns more info */
263         rc = CIFSSMBUnixQPathInfo(xid, pTcon, full_path, &find_data,
264                                   cifs_sb->local_nls, cifs_sb->mnt_cifs_flags &
265                                         CIFS_MOUNT_MAP_SPECIAL_CHR);
266         if (rc == -EREMOTE && !is_dfs_referral) {
267                 is_dfs_referral = true;
268                 cFYI(DBG2, ("DFS ref"));
269                 /* for DFS, server does not give us real inode data */
270                 fill_fake_finddataunix(&find_data, sb);
271                 rc = 0;
272         } else if (rc)
273                 goto cgiiu_exit;
274
275         num_of_bytes = le64_to_cpu(find_data.NumOfBytes);
276         end_of_file = le64_to_cpu(find_data.EndOfFile);
277
278         /* get new inode */
279         if (*pinode == NULL) {
280                 __u64 unique_id = le64_to_cpu(find_data.UniqueId);
281                 *pinode = cifs_new_inode(sb, &unique_id);
282                 if (*pinode == NULL) {
283                         rc = -ENOMEM;
284                         goto cgiiu_exit;
285                 }
286         }
287
288         inode = *pinode;
289         cifsInfo = CIFS_I(inode);
290
291         cFYI(1, ("Old time %ld", cifsInfo->time));
292         cifsInfo->time = jiffies;
293         cFYI(1, ("New time %ld", cifsInfo->time));
294         /* this is ok to set on every inode revalidate */
295         atomic_set(&cifsInfo->inUse, 1);
296
297         cifs_unix_info_to_inode(inode, &find_data, 0);
298
299         if (num_of_bytes < end_of_file)
300                 cFYI(1, ("allocation size less than end of file"));
301         cFYI(1, ("Size %ld and blocks %llu",
302                 (unsigned long) inode->i_size,
303                 (unsigned long long)inode->i_blocks));
304
305         cifs_set_ops(inode, is_dfs_referral);
306 cgiiu_exit:
307         return rc;
308 }
309
310 static int decode_sfu_inode(struct inode *inode, __u64 size,
311                             const unsigned char *path,
312                             struct cifs_sb_info *cifs_sb, int xid)
313 {
314         int rc;
315         int oplock = 0;
316         __u16 netfid;
317         struct cifsTconInfo *pTcon = cifs_sb->tcon;
318         char buf[24];
319         unsigned int bytes_read;
320         char *pbuf;
321
322         pbuf = buf;
323
324         if (size == 0) {
325                 inode->i_mode |= S_IFIFO;
326                 return 0;
327         } else if (size < 8) {
328                 return -EINVAL;  /* EOPNOTSUPP? */
329         }
330
331         rc = CIFSSMBOpen(xid, pTcon, path, FILE_OPEN, GENERIC_READ,
332                          CREATE_NOT_DIR, &netfid, &oplock, NULL,
333                          cifs_sb->local_nls,
334                          cifs_sb->mnt_cifs_flags &
335                                 CIFS_MOUNT_MAP_SPECIAL_CHR);
336         if (rc == 0) {
337                 int buf_type = CIFS_NO_BUFFER;
338                         /* Read header */
339                 rc = CIFSSMBRead(xid, pTcon,
340                                  netfid,
341                                  24 /* length */, 0 /* offset */,
342                                  &bytes_read, &pbuf, &buf_type);
343                 if ((rc == 0) && (bytes_read >= 8)) {
344                         if (memcmp("IntxBLK", pbuf, 8) == 0) {
345                                 cFYI(1, ("Block device"));
346                                 inode->i_mode |= S_IFBLK;
347                                 if (bytes_read == 24) {
348                                         /* we have enough to decode dev num */
349                                         __u64 mjr; /* major */
350                                         __u64 mnr; /* minor */
351                                         mjr = le64_to_cpu(*(__le64 *)(pbuf+8));
352                                         mnr = le64_to_cpu(*(__le64 *)(pbuf+16));
353                                         inode->i_rdev = MKDEV(mjr, mnr);
354                                 }
355                         } else if (memcmp("IntxCHR", pbuf, 8) == 0) {
356                                 cFYI(1, ("Char device"));
357                                 inode->i_mode |= S_IFCHR;
358                                 if (bytes_read == 24) {
359                                         /* we have enough to decode dev num */
360                                         __u64 mjr; /* major */
361                                         __u64 mnr; /* minor */
362                                         mjr = le64_to_cpu(*(__le64 *)(pbuf+8));
363                                         mnr = le64_to_cpu(*(__le64 *)(pbuf+16));
364                                         inode->i_rdev = MKDEV(mjr, mnr);
365                                 }
366                         } else if (memcmp("IntxLNK", pbuf, 7) == 0) {
367                                 cFYI(1, ("Symlink"));
368                                 inode->i_mode |= S_IFLNK;
369                         } else {
370                                 inode->i_mode |= S_IFREG; /* file? */
371                                 rc = -EOPNOTSUPP;
372                         }
373                 } else {
374                         inode->i_mode |= S_IFREG; /* then it is a file */
375                         rc = -EOPNOTSUPP; /* or some unknown SFU type */
376                 }
377                 CIFSSMBClose(xid, pTcon, netfid);
378         }
379         return rc;
380 }
381
382 #define SFBITS_MASK (S_ISVTX | S_ISGID | S_ISUID)  /* SETFILEBITS valid bits */
383
384 static int get_sfu_mode(struct inode *inode,
385                         const unsigned char *path,
386                         struct cifs_sb_info *cifs_sb, int xid)
387 {
388 #ifdef CONFIG_CIFS_XATTR
389         ssize_t rc;
390         char ea_value[4];
391         __u32 mode;
392
393         rc = CIFSSMBQueryEA(xid, cifs_sb->tcon, path, "SETFILEBITS",
394                         ea_value, 4 /* size of buf */, cifs_sb->local_nls,
395                 cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MAP_SPECIAL_CHR);
396         if (rc < 0)
397                 return (int)rc;
398         else if (rc > 3) {
399                 mode = le32_to_cpu(*((__le32 *)ea_value));
400                 inode->i_mode &= ~SFBITS_MASK;
401                 cFYI(1, ("special bits 0%o org mode 0%o", mode, inode->i_mode));
402                 inode->i_mode = (mode &  SFBITS_MASK) | inode->i_mode;
403                 cFYI(1, ("special mode bits 0%o", mode));
404                 return 0;
405         } else {
406                 return 0;
407         }
408 #else
409         return -EOPNOTSUPP;
410 #endif
411 }
412
413 /*
414  *      Needed to setup inode data for the directory which is the
415  *      junction to the new submount (ie to setup the fake directory
416  *      which represents a DFS referral)
417  */
418 static void fill_fake_finddata(FILE_ALL_INFO *pfnd_dat,
419                                struct super_block *sb)
420 {
421         memset(pfnd_dat, 0, sizeof(FILE_ALL_INFO));
422
423 /*      __le64 pfnd_dat->AllocationSize = cpu_to_le64(0);
424         __le64 pfnd_dat->EndOfFile = cpu_to_le64(0);
425         __u8 pfnd_dat->DeletePending = 0;
426         __u8 pfnd_data->Directory = 0;
427         __le32 pfnd_dat->EASize = 0;
428         __u64 pfnd_dat->IndexNumber = 0;
429         __u64 pfnd_dat->IndexNumber1 = 0;  */
430         pfnd_dat->CreationTime =
431                 cpu_to_le64(cifs_UnixTimeToNT(CURRENT_TIME));
432         pfnd_dat->LastAccessTime =
433                 cpu_to_le64(cifs_UnixTimeToNT(CURRENT_TIME));
434         pfnd_dat->LastWriteTime =
435                 cpu_to_le64(cifs_UnixTimeToNT(CURRENT_TIME));
436         pfnd_dat->ChangeTime =
437                 cpu_to_le64(cifs_UnixTimeToNT(CURRENT_TIME));
438         pfnd_dat->Attributes = cpu_to_le32(ATTR_DIRECTORY);
439         pfnd_dat->NumberOfLinks = cpu_to_le32(2);
440 }
441
442 int cifs_get_inode_info(struct inode **pinode,
443         const unsigned char *full_path, FILE_ALL_INFO *pfindData,
444         struct super_block *sb, int xid, const __u16 *pfid)
445 {
446         int rc = 0;
447         __u32 attr;
448         struct cifsInodeInfo *cifsInfo;
449         struct cifsTconInfo *pTcon;
450         struct inode *inode;
451         struct cifs_sb_info *cifs_sb = CIFS_SB(sb);
452         char *buf = NULL;
453         bool adjustTZ = false;
454         bool is_dfs_referral = false;
455         umode_t default_mode;
456
457         pTcon = cifs_sb->tcon;
458         cFYI(1, ("Getting info on %s", full_path));
459
460         if ((pfindData == NULL) && (*pinode != NULL)) {
461                 if (CIFS_I(*pinode)->clientCanCacheRead) {
462                         cFYI(1, ("No need to revalidate cached inode sizes"));
463                         return rc;
464                 }
465         }
466
467         /* if file info not passed in then get it from server */
468         if (pfindData == NULL) {
469                 buf = kmalloc(sizeof(FILE_ALL_INFO), GFP_KERNEL);
470                 if (buf == NULL)
471                         return -ENOMEM;
472                 pfindData = (FILE_ALL_INFO *)buf;
473
474                 /* could do find first instead but this returns more info */
475                 rc = CIFSSMBQPathInfo(xid, pTcon, full_path, pfindData,
476                               0 /* not legacy */,
477                               cifs_sb->local_nls, cifs_sb->mnt_cifs_flags &
478                                 CIFS_MOUNT_MAP_SPECIAL_CHR);
479                 /* BB optimize code so we do not make the above call
480                 when server claims no NT SMB support and the above call
481                 failed at least once - set flag in tcon or mount */
482                 if ((rc == -EOPNOTSUPP) || (rc == -EINVAL)) {
483                         rc = SMBQueryInformation(xid, pTcon, full_path,
484                                         pfindData, cifs_sb->local_nls,
485                                         cifs_sb->mnt_cifs_flags &
486                                           CIFS_MOUNT_MAP_SPECIAL_CHR);
487                         adjustTZ = true;
488                 }
489         }
490         /* dump_mem("\nQPathInfo return data",&findData, sizeof(findData)); */
491         if (rc == -EREMOTE) {
492                 is_dfs_referral = true;
493                 fill_fake_finddata(pfindData, sb);
494                 rc = 0;
495         } else if (rc)
496                 goto cgii_exit;
497
498         attr = le32_to_cpu(pfindData->Attributes);
499
500         /* get new inode */
501         if (*pinode == NULL) {
502                 __u64 inode_num;
503                 __u64 *pinum = &inode_num;
504
505                 /* Is an i_ino of zero legal? Can we use that to check
506                    if the server supports returning inode numbers?  Are
507                    there other sanity checks we can use to ensure that
508                    the server is really filling in that field? */
509
510                 /* We can not use the IndexNumber field by default from
511                    Windows or Samba (in ALL_INFO buf) but we can request
512                    it explicitly.  It may not be unique presumably if
513                    the server has multiple devices mounted under one share */
514
515                 /* There may be higher info levels that work but are
516                    there Windows server or network appliances for which
517                    IndexNumber field is not guaranteed unique? */
518
519                 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SERVER_INUM) {
520                         int rc1 = 0;
521
522                         rc1 = CIFSGetSrvInodeNumber(xid, pTcon,
523                                         full_path, pinum,
524                                         cifs_sb->local_nls,
525                                         cifs_sb->mnt_cifs_flags &
526                                                 CIFS_MOUNT_MAP_SPECIAL_CHR);
527                         if (rc1) {
528                                 cFYI(1, ("GetSrvInodeNum rc %d", rc1));
529                                 pinum = NULL;
530                                 /* BB EOPNOSUPP disable SERVER_INUM? */
531                         }
532                 } else {
533                         pinum = NULL;
534                 }
535
536                 *pinode = cifs_new_inode(sb, pinum);
537                 if (*pinode == NULL) {
538                         rc = -ENOMEM;
539                         goto cgii_exit;
540                 }
541         }
542         inode = *pinode;
543         cifsInfo = CIFS_I(inode);
544         cifsInfo->cifsAttrs = attr;
545         cifsInfo->delete_pending = pfindData->DeletePending ? true : false;
546         cFYI(1, ("Old time %ld", cifsInfo->time));
547         cifsInfo->time = jiffies;
548         cFYI(1, ("New time %ld", cifsInfo->time));
549
550         /* blksize needs to be multiple of two. So safer to default to
551         blksize and blkbits set in superblock so 2**blkbits and blksize
552         will match rather than setting to:
553         (pTcon->ses->server->maxBuf - MAX_CIFS_HDR_SIZE) & 0xFFFFFE00;*/
554
555         /* Linux can not store file creation time so ignore it */
556         if (pfindData->LastAccessTime)
557                 inode->i_atime = cifs_NTtimeToUnix(pfindData->LastAccessTime);
558         else /* do not need to use current_fs_time - time not stored */
559                 inode->i_atime = CURRENT_TIME;
560         inode->i_mtime = cifs_NTtimeToUnix(pfindData->LastWriteTime);
561         inode->i_ctime = cifs_NTtimeToUnix(pfindData->ChangeTime);
562         cFYI(DBG2, ("Attributes came in as 0x%x", attr));
563         if (adjustTZ && (pTcon->ses) && (pTcon->ses->server)) {
564                 inode->i_ctime.tv_sec += pTcon->ses->server->timeAdj;
565                 inode->i_mtime.tv_sec += pTcon->ses->server->timeAdj;
566         }
567
568         /* get default inode mode */
569         if (attr & ATTR_DIRECTORY)
570                 default_mode = cifs_sb->mnt_dir_mode;
571         else
572                 default_mode = cifs_sb->mnt_file_mode;
573
574         /* set permission bits */
575         if (atomic_read(&cifsInfo->inUse) == 0 ||
576             (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_DYNPERM) == 0)
577                 inode->i_mode = default_mode;
578         else {
579                 /* just reenable write bits if !ATTR_READONLY */
580                 if ((inode->i_mode & S_IWUGO) == 0 &&
581                     (attr & ATTR_READONLY) == 0)
582                         inode->i_mode |= (S_IWUGO & default_mode);
583
584                 inode->i_mode &= ~S_IFMT;
585         }
586         /* clear write bits if ATTR_READONLY is set */
587         if (attr & ATTR_READONLY)
588                 inode->i_mode &= ~S_IWUGO;
589
590         /* set inode type */
591         if ((attr & ATTR_SYSTEM) &&
592             (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_UNX_EMUL)) {
593                 /* no need to fix endianness on 0 */
594                 if (pfindData->EndOfFile == 0)
595                         inode->i_mode |= S_IFIFO;
596                 else if (decode_sfu_inode(inode,
597                                 le64_to_cpu(pfindData->EndOfFile),
598                                 full_path, cifs_sb, xid))
599                         cFYI(1, ("unknown SFU file type\n"));
600         } else {
601                 if (attr & ATTR_DIRECTORY)
602                         inode->i_mode |= S_IFDIR;
603                 else
604                         inode->i_mode |= S_IFREG;
605         }
606
607         cifsInfo->server_eof = le64_to_cpu(pfindData->EndOfFile);
608         spin_lock(&inode->i_lock);
609         if (is_size_safe_to_change(cifsInfo, cifsInfo->server_eof)) {
610                 /* can not safely shrink the file size here if the
611                    client is writing to it due to potential races */
612                 i_size_write(inode, cifsInfo->server_eof);
613
614                 /* 512 bytes (2**9) is the fake blocksize that must be
615                    used for this calculation */
616                 inode->i_blocks = (512 - 1 + le64_to_cpu(
617                                    pfindData->AllocationSize)) >> 9;
618         }
619         spin_unlock(&inode->i_lock);
620
621         inode->i_nlink = le32_to_cpu(pfindData->NumberOfLinks);
622
623         /* BB fill in uid and gid here? with help from winbind?
624            or retrieve from NTFS stream extended attribute */
625 #ifdef CONFIG_CIFS_EXPERIMENTAL
626         /* fill in 0777 bits from ACL */
627         if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_CIFS_ACL) {
628                 cFYI(1, ("Getting mode bits from ACL"));
629                 acl_to_uid_mode(cifs_sb, inode, full_path, pfid);
630         }
631 #endif
632         if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_UNX_EMUL) {
633                 /* fill in remaining high mode bits e.g. SUID, VTX */
634                 get_sfu_mode(inode, full_path, cifs_sb, xid);
635         } else if (atomic_read(&cifsInfo->inUse) == 0) {
636                 inode->i_uid = cifs_sb->mnt_uid;
637                 inode->i_gid = cifs_sb->mnt_gid;
638                 /* set so we do not keep refreshing these fields with
639                    bad data after user has changed them in memory */
640                 atomic_set(&cifsInfo->inUse, 1);
641         }
642
643         cifs_set_ops(inode, is_dfs_referral);
644
645
646
647
648 cgii_exit:
649         kfree(buf);
650         return rc;
651 }
652
653 static const struct inode_operations cifs_ipc_inode_ops = {
654         .lookup = cifs_lookup,
655 };
656
657 char *cifs_build_path_to_root(struct cifs_sb_info *cifs_sb)
658 {
659         int pplen = cifs_sb->prepathlen;
660         int dfsplen;
661         char *full_path = NULL;
662
663         /* if no prefix path, simply set path to the root of share to "" */
664         if (pplen == 0) {
665                 full_path = kmalloc(1, GFP_KERNEL);
666                 if (full_path)
667                         full_path[0] = 0;
668                 return full_path;
669         }
670
671         if (cifs_sb->tcon && (cifs_sb->tcon->Flags & SMB_SHARE_IS_IN_DFS))
672                 dfsplen = strnlen(cifs_sb->tcon->treeName, MAX_TREE_SIZE + 1);
673         else
674                 dfsplen = 0;
675
676         full_path = kmalloc(dfsplen + pplen + 1, GFP_KERNEL);
677         if (full_path == NULL)
678                 return full_path;
679
680         if (dfsplen) {
681                 strncpy(full_path, cifs_sb->tcon->treeName, dfsplen);
682                 /* switch slash direction in prepath depending on whether
683                  * windows or posix style path names
684                  */
685                 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_POSIX_PATHS) {
686                         int i;
687                         for (i = 0; i < dfsplen; i++) {
688                                 if (full_path[i] == '\\')
689                                         full_path[i] = '/';
690                         }
691                 }
692         }
693         strncpy(full_path + dfsplen, cifs_sb->prepath, pplen);
694         full_path[dfsplen + pplen] = 0; /* add trailing null */
695         return full_path;
696 }
697
698 /* gets root inode */
699 struct inode *cifs_root_iget(struct super_block *sb, unsigned long ino)
700 {
701         int xid;
702         struct cifs_sb_info *cifs_sb;
703         struct inode *inode;
704         long rc;
705         char *full_path;
706
707         inode = iget_locked(sb, ino);
708         if (!inode)
709                 return ERR_PTR(-ENOMEM);
710         if (!(inode->i_state & I_NEW))
711                 return inode;
712
713         cifs_sb = CIFS_SB(inode->i_sb);
714         full_path = cifs_build_path_to_root(cifs_sb);
715         if (full_path == NULL)
716                 return ERR_PTR(-ENOMEM);
717
718         xid = GetXid();
719         if (cifs_sb->tcon->unix_ext)
720                 rc = cifs_get_inode_info_unix(&inode, full_path, inode->i_sb,
721                                                 xid);
722         else
723                 rc = cifs_get_inode_info(&inode, full_path, NULL, inode->i_sb,
724                                                 xid, NULL);
725         if (rc && cifs_sb->tcon->ipc) {
726                 cFYI(1, ("ipc connection - fake read inode"));
727                 inode->i_mode |= S_IFDIR;
728                 inode->i_nlink = 2;
729                 inode->i_op = &cifs_ipc_inode_ops;
730                 inode->i_fop = &simple_dir_operations;
731                 inode->i_uid = cifs_sb->mnt_uid;
732                 inode->i_gid = cifs_sb->mnt_gid;
733         } else if (rc) {
734                 kfree(full_path);
735                 _FreeXid(xid);
736                 iget_failed(inode);
737                 return ERR_PTR(rc);
738         }
739
740         unlock_new_inode(inode);
741
742         kfree(full_path);
743         /* can not call macro FreeXid here since in a void func
744          * TODO: This is no longer true
745          */
746         _FreeXid(xid);
747         return inode;
748 }
749
750 static int
751 cifs_set_file_info(struct inode *inode, struct iattr *attrs, int xid,
752                     char *full_path, __u32 dosattr)
753 {
754         int rc;
755         int oplock = 0;
756         __u16 netfid;
757         __u32 netpid;
758         bool set_time = false;
759         struct cifsFileInfo *open_file;
760         struct cifsInodeInfo *cifsInode = CIFS_I(inode);
761         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
762         struct cifsTconInfo *pTcon = cifs_sb->tcon;
763         FILE_BASIC_INFO info_buf;
764
765         if (attrs == NULL)
766                 return -EINVAL;
767
768         if (attrs->ia_valid & ATTR_ATIME) {
769                 set_time = true;
770                 info_buf.LastAccessTime =
771                         cpu_to_le64(cifs_UnixTimeToNT(attrs->ia_atime));
772         } else
773                 info_buf.LastAccessTime = 0;
774
775         if (attrs->ia_valid & ATTR_MTIME) {
776                 set_time = true;
777                 info_buf.LastWriteTime =
778                     cpu_to_le64(cifs_UnixTimeToNT(attrs->ia_mtime));
779         } else
780                 info_buf.LastWriteTime = 0;
781
782         /*
783          * Samba throws this field away, but windows may actually use it.
784          * Do not set ctime unless other time stamps are changed explicitly
785          * (i.e. by utimes()) since we would then have a mix of client and
786          * server times.
787          */
788         if (set_time && (attrs->ia_valid & ATTR_CTIME)) {
789                 cFYI(1, ("CIFS - CTIME changed"));
790                 info_buf.ChangeTime =
791                     cpu_to_le64(cifs_UnixTimeToNT(attrs->ia_ctime));
792         } else
793                 info_buf.ChangeTime = 0;
794
795         info_buf.CreationTime = 0;      /* don't change */
796         info_buf.Attributes = cpu_to_le32(dosattr);
797
798         /*
799          * If the file is already open for write, just use that fileid
800          */
801         open_file = find_writable_file(cifsInode);
802         if (open_file) {
803                 netfid = open_file->netfid;
804                 netpid = open_file->pid;
805                 goto set_via_filehandle;
806         }
807
808         /*
809          * NT4 apparently returns success on this call, but it doesn't
810          * really work.
811          */
812         if (!(pTcon->ses->flags & CIFS_SES_NT4)) {
813                 rc = CIFSSMBSetPathInfo(xid, pTcon, full_path,
814                                      &info_buf, cifs_sb->local_nls,
815                                      cifs_sb->mnt_cifs_flags &
816                                         CIFS_MOUNT_MAP_SPECIAL_CHR);
817                 if (rc == 0) {
818                         cifsInode->cifsAttrs = dosattr;
819                         goto out;
820                 } else if (rc != -EOPNOTSUPP && rc != -EINVAL)
821                         goto out;
822         }
823
824         cFYI(1, ("calling SetFileInfo since SetPathInfo for "
825                  "times not supported by this server"));
826         rc = CIFSSMBOpen(xid, pTcon, full_path, FILE_OPEN,
827                          SYNCHRONIZE | FILE_WRITE_ATTRIBUTES,
828                          CREATE_NOT_DIR, &netfid, &oplock,
829                          NULL, cifs_sb->local_nls,
830                          cifs_sb->mnt_cifs_flags &
831                                 CIFS_MOUNT_MAP_SPECIAL_CHR);
832
833         if (rc != 0) {
834                 if (rc == -EIO)
835                         rc = -EINVAL;
836                 goto out;
837         }
838
839         netpid = current->tgid;
840
841 set_via_filehandle:
842         rc = CIFSSMBSetFileInfo(xid, pTcon, &info_buf, netfid, netpid);
843         if (!rc)
844                 cifsInode->cifsAttrs = dosattr;
845
846         if (open_file == NULL)
847                 CIFSSMBClose(xid, pTcon, netfid);
848         else
849                 atomic_dec(&open_file->wrtPending);
850 out:
851         return rc;
852 }
853
854 /*
855  * open the given file (if it isn't already), set the DELETE_ON_CLOSE bit
856  * and rename it to a random name that hopefully won't conflict with
857  * anything else.
858  */
859 static int
860 cifs_rename_pending_delete(char *full_path, struct dentry *dentry, int xid)
861 {
862         int oplock = 0;
863         int rc;
864         __u16 netfid;
865         struct inode *inode = dentry->d_inode;
866         struct cifsInodeInfo *cifsInode = CIFS_I(inode);
867         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
868         struct cifsTconInfo *tcon = cifs_sb->tcon;
869         __u32 dosattr, origattr;
870         FILE_BASIC_INFO *info_buf = NULL;
871
872         rc = CIFSSMBOpen(xid, tcon, full_path, FILE_OPEN,
873                          DELETE|FILE_WRITE_ATTRIBUTES, CREATE_NOT_DIR,
874                          &netfid, &oplock, NULL, cifs_sb->local_nls,
875                          cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MAP_SPECIAL_CHR);
876         if (rc != 0)
877                 goto out;
878
879         origattr = cifsInode->cifsAttrs;
880         if (origattr == 0)
881                 origattr |= ATTR_NORMAL;
882
883         dosattr = origattr & ~ATTR_READONLY;
884         if (dosattr == 0)
885                 dosattr |= ATTR_NORMAL;
886         dosattr |= ATTR_HIDDEN;
887
888         /* set ATTR_HIDDEN and clear ATTR_READONLY, but only if needed */
889         if (dosattr != origattr) {
890                 info_buf = kzalloc(sizeof(*info_buf), GFP_KERNEL);
891                 if (info_buf == NULL) {
892                         rc = -ENOMEM;
893                         goto out_close;
894                 }
895                 info_buf->Attributes = cpu_to_le32(dosattr);
896                 rc = CIFSSMBSetFileInfo(xid, tcon, info_buf, netfid,
897                                         current->tgid);
898                 /* although we would like to mark the file hidden
899                    if that fails we will still try to rename it */
900                 if (rc != 0)
901                         cifsInode->cifsAttrs = dosattr;
902                 else
903                         dosattr = origattr; /* since not able to change them */
904         }
905
906         /* rename the file */
907         rc = CIFSSMBRenameOpenFile(xid, tcon, netfid, NULL, cifs_sb->local_nls,
908                                    cifs_sb->mnt_cifs_flags &
909                                             CIFS_MOUNT_MAP_SPECIAL_CHR);
910         if (rc != 0) {
911                 rc = -ETXTBSY;
912                 goto undo_setattr;
913         }
914
915         /* try to set DELETE_ON_CLOSE */
916         if (!cifsInode->delete_pending) {
917                 rc = CIFSSMBSetFileDisposition(xid, tcon, true, netfid,
918                                                current->tgid);
919                 /*
920                  * some samba versions return -ENOENT when we try to set the
921                  * file disposition here. Likely a samba bug, but work around
922                  * it for now. This means that some cifsXXX files may hang
923                  * around after they shouldn't.
924                  *
925                  * BB: remove this hack after more servers have the fix
926                  */
927                 if (rc == -ENOENT)
928                         rc = 0;
929                 else if (rc != 0) {
930                         rc = -ETXTBSY;
931                         goto undo_rename;
932                 }
933                 cifsInode->delete_pending = true;
934         }
935
936 out_close:
937         CIFSSMBClose(xid, tcon, netfid);
938 out:
939         kfree(info_buf);
940         return rc;
941
942         /*
943          * reset everything back to the original state. Don't bother
944          * dealing with errors here since we can't do anything about
945          * them anyway.
946          */
947 undo_rename:
948         CIFSSMBRenameOpenFile(xid, tcon, netfid, dentry->d_name.name,
949                                 cifs_sb->local_nls, cifs_sb->mnt_cifs_flags &
950                                             CIFS_MOUNT_MAP_SPECIAL_CHR);
951 undo_setattr:
952         if (dosattr != origattr) {
953                 info_buf->Attributes = cpu_to_le32(origattr);
954                 if (!CIFSSMBSetFileInfo(xid, tcon, info_buf, netfid,
955                                         current->tgid))
956                         cifsInode->cifsAttrs = origattr;
957         }
958
959         goto out_close;
960 }
961
962
963 /*
964  * If dentry->d_inode is null (usually meaning the cached dentry
965  * is a negative dentry) then we would attempt a standard SMB delete, but
966  * if that fails we can not attempt the fall back mechanisms on EACESS
967  * but will return the EACESS to the caller.  Note that the VFS does not call
968  * unlink on negative dentries currently.
969  */
970 int cifs_unlink(struct inode *dir, struct dentry *dentry)
971 {
972         int rc = 0;
973         int xid;
974         char *full_path = NULL;
975         struct inode *inode = dentry->d_inode;
976         struct cifsInodeInfo *cifs_inode;
977         struct super_block *sb = dir->i_sb;
978         struct cifs_sb_info *cifs_sb = CIFS_SB(sb);
979         struct cifsTconInfo *tcon = cifs_sb->tcon;
980         struct iattr *attrs = NULL;
981         __u32 dosattr = 0, origattr = 0;
982
983         cFYI(1, ("cifs_unlink, dir=0x%p, dentry=0x%p", dir, dentry));
984
985         xid = GetXid();
986
987         /* Unlink can be called from rename so we can not take the
988          * sb->s_vfs_rename_mutex here */
989         full_path = build_path_from_dentry(dentry);
990         if (full_path == NULL) {
991                 FreeXid(xid);
992                 return -ENOMEM;
993         }
994
995         if ((tcon->ses->capabilities & CAP_UNIX) &&
996                 (CIFS_UNIX_POSIX_PATH_OPS_CAP &
997                         le64_to_cpu(tcon->fsUnixInfo.Capability))) {
998                 rc = CIFSPOSIXDelFile(xid, tcon, full_path,
999                         SMB_POSIX_UNLINK_FILE_TARGET, cifs_sb->local_nls,
1000                         cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MAP_SPECIAL_CHR);
1001                 cFYI(1, ("posix del rc %d", rc));
1002                 if ((rc == 0) || (rc == -ENOENT))
1003                         goto psx_del_no_retry;
1004         }
1005
1006 retry_std_delete:
1007         rc = CIFSSMBDelFile(xid, tcon, full_path, cifs_sb->local_nls,
1008                         cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MAP_SPECIAL_CHR);
1009
1010 psx_del_no_retry:
1011         if (!rc) {
1012                 if (inode)
1013                         drop_nlink(inode);
1014         } else if (rc == -ENOENT) {
1015                 d_drop(dentry);
1016         } else if (rc == -ETXTBSY) {
1017                 rc = cifs_rename_pending_delete(full_path, dentry, xid);
1018                 if (rc == 0)
1019                         drop_nlink(inode);
1020         } else if ((rc == -EACCES) && (dosattr == 0) && inode) {
1021                 attrs = kzalloc(sizeof(*attrs), GFP_KERNEL);
1022                 if (attrs == NULL) {
1023                         rc = -ENOMEM;
1024                         goto out_reval;
1025                 }
1026
1027                 /* try to reset dos attributes */
1028                 cifs_inode = CIFS_I(inode);
1029                 origattr = cifs_inode->cifsAttrs;
1030                 if (origattr == 0)
1031                         origattr |= ATTR_NORMAL;
1032                 dosattr = origattr & ~ATTR_READONLY;
1033                 if (dosattr == 0)
1034                         dosattr |= ATTR_NORMAL;
1035                 dosattr |= ATTR_HIDDEN;
1036
1037                 rc = cifs_set_file_info(inode, attrs, xid, full_path, dosattr);
1038                 if (rc != 0)
1039                         goto out_reval;
1040
1041                 goto retry_std_delete;
1042         }
1043
1044         /* undo the setattr if we errored out and it's needed */
1045         if (rc != 0 && dosattr != 0)
1046                 cifs_set_file_info(inode, attrs, xid, full_path, origattr);
1047
1048 out_reval:
1049         if (inode) {
1050                 cifs_inode = CIFS_I(inode);
1051                 cifs_inode->time = 0;   /* will force revalidate to get info
1052                                            when needed */
1053                 inode->i_ctime = current_fs_time(sb);
1054         }
1055         dir->i_ctime = dir->i_mtime = current_fs_time(sb);
1056         cifs_inode = CIFS_I(dir);
1057         CIFS_I(dir)->time = 0;  /* force revalidate of dir as well */
1058
1059         kfree(full_path);
1060         kfree(attrs);
1061         FreeXid(xid);
1062         return rc;
1063 }
1064
1065 void posix_fill_in_inode(struct inode *tmp_inode,
1066         FILE_UNIX_BASIC_INFO *pData, int isNewInode)
1067 {
1068         struct cifsInodeInfo *cifsInfo = CIFS_I(tmp_inode);
1069         loff_t local_size;
1070         struct timespec local_mtime;
1071
1072         cifsInfo->time = jiffies;
1073         atomic_inc(&cifsInfo->inUse);
1074
1075         /* save mtime and size */
1076         local_mtime = tmp_inode->i_mtime;
1077         local_size  = tmp_inode->i_size;
1078
1079         cifs_unix_info_to_inode(tmp_inode, pData, 1);
1080         cifs_set_ops(tmp_inode, false);
1081
1082         if (!S_ISREG(tmp_inode->i_mode))
1083                 return;
1084
1085         /*
1086          * No sense invalidating pages for new inode
1087          * since we we have not started caching
1088          * readahead file data yet.
1089          */
1090         if (isNewInode)
1091                 return;
1092
1093         if (timespec_equal(&tmp_inode->i_mtime, &local_mtime) &&
1094                 (local_size == tmp_inode->i_size)) {
1095                 cFYI(1, ("inode exists but unchanged"));
1096         } else {
1097                 /* file may have changed on server */
1098                 cFYI(1, ("invalidate inode, readdir detected change"));
1099                 invalidate_remote_inode(tmp_inode);
1100         }
1101 }
1102
1103 int cifs_mkdir(struct inode *inode, struct dentry *direntry, int mode)
1104 {
1105         int rc = 0, tmprc;
1106         int xid;
1107         struct cifs_sb_info *cifs_sb;
1108         struct cifsTconInfo *pTcon;
1109         char *full_path = NULL;
1110         struct inode *newinode = NULL;
1111
1112         cFYI(1, ("In cifs_mkdir, mode = 0x%x inode = 0x%p", mode, inode));
1113
1114         xid = GetXid();
1115
1116         cifs_sb = CIFS_SB(inode->i_sb);
1117         pTcon = cifs_sb->tcon;
1118
1119         full_path = build_path_from_dentry(direntry);
1120         if (full_path == NULL) {
1121                 FreeXid(xid);
1122                 return -ENOMEM;
1123         }
1124
1125         if ((pTcon->ses->capabilities & CAP_UNIX) &&
1126                 (CIFS_UNIX_POSIX_PATH_OPS_CAP &
1127                         le64_to_cpu(pTcon->fsUnixInfo.Capability))) {
1128                 u32 oplock = 0;
1129                 FILE_UNIX_BASIC_INFO *pInfo =
1130                         kzalloc(sizeof(FILE_UNIX_BASIC_INFO), GFP_KERNEL);
1131                 if (pInfo == NULL) {
1132                         rc = -ENOMEM;
1133                         goto mkdir_out;
1134                 }
1135
1136                 mode &= ~current_umask();
1137                 rc = CIFSPOSIXCreate(xid, pTcon, SMB_O_DIRECTORY | SMB_O_CREAT,
1138                                 mode, NULL /* netfid */, pInfo, &oplock,
1139                                 full_path, cifs_sb->local_nls,
1140                                 cifs_sb->mnt_cifs_flags &
1141                                         CIFS_MOUNT_MAP_SPECIAL_CHR);
1142                 if (rc == -EOPNOTSUPP) {
1143                         kfree(pInfo);
1144                         goto mkdir_retry_old;
1145                 } else if (rc) {
1146                         cFYI(1, ("posix mkdir returned 0x%x", rc));
1147                         d_drop(direntry);
1148                 } else {
1149                         __u64 unique_id;
1150                         if (pInfo->Type == cpu_to_le32(-1)) {
1151                                 /* no return info, go query for it */
1152                                 kfree(pInfo);
1153                                 goto mkdir_get_info;
1154                         }
1155 /*BB check (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SET_UID ) to see if need
1156         to set uid/gid */
1157                         inc_nlink(inode);
1158                         if (pTcon->nocase)
1159                                 direntry->d_op = &cifs_ci_dentry_ops;
1160                         else
1161                                 direntry->d_op = &cifs_dentry_ops;
1162
1163                         unique_id = le64_to_cpu(pInfo->UniqueId);
1164                         newinode = cifs_new_inode(inode->i_sb, &unique_id);
1165                         if (newinode == NULL) {
1166                                 kfree(pInfo);
1167                                 goto mkdir_get_info;
1168                         }
1169
1170                         newinode->i_nlink = 2;
1171                         d_instantiate(direntry, newinode);
1172
1173                         /* we already checked in POSIXCreate whether
1174                            frame was long enough */
1175                         posix_fill_in_inode(direntry->d_inode,
1176                                         pInfo, 1 /* NewInode */);
1177 #ifdef CONFIG_CIFS_DEBUG2
1178                         cFYI(1, ("instantiated dentry %p %s to inode %p",
1179                                 direntry, direntry->d_name.name, newinode));
1180
1181                         if (newinode->i_nlink != 2)
1182                                 cFYI(1, ("unexpected number of links %d",
1183                                         newinode->i_nlink));
1184 #endif
1185                 }
1186                 kfree(pInfo);
1187                 goto mkdir_out;
1188         }
1189 mkdir_retry_old:
1190         /* BB add setting the equivalent of mode via CreateX w/ACLs */
1191         rc = CIFSSMBMkDir(xid, pTcon, full_path, cifs_sb->local_nls,
1192                           cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MAP_SPECIAL_CHR);
1193         if (rc) {
1194                 cFYI(1, ("cifs_mkdir returned 0x%x", rc));
1195                 d_drop(direntry);
1196         } else {
1197 mkdir_get_info:
1198                 inc_nlink(inode);
1199                 if (pTcon->unix_ext)
1200                         rc = cifs_get_inode_info_unix(&newinode, full_path,
1201                                                       inode->i_sb, xid);
1202                 else
1203                         rc = cifs_get_inode_info(&newinode, full_path, NULL,
1204                                                  inode->i_sb, xid, NULL);
1205
1206                 if (pTcon->nocase)
1207                         direntry->d_op = &cifs_ci_dentry_ops;
1208                 else
1209                         direntry->d_op = &cifs_dentry_ops;
1210                 d_instantiate(direntry, newinode);
1211                  /* setting nlink not necessary except in cases where we
1212                   * failed to get it from the server or was set bogus */
1213                 if ((direntry->d_inode) && (direntry->d_inode->i_nlink < 2))
1214                                 direntry->d_inode->i_nlink = 2;
1215
1216                 mode &= ~current_umask();
1217                 /* must turn on setgid bit if parent dir has it */
1218                 if (inode->i_mode & S_ISGID)
1219                         mode |= S_ISGID;
1220
1221                 if (pTcon->unix_ext) {
1222                         struct cifs_unix_set_info_args args = {
1223                                 .mode   = mode,
1224                                 .ctime  = NO_CHANGE_64,
1225                                 .atime  = NO_CHANGE_64,
1226                                 .mtime  = NO_CHANGE_64,
1227                                 .device = 0,
1228                         };
1229                         if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SET_UID) {
1230                                 args.uid = (__u64)current_fsuid();
1231                                 if (inode->i_mode & S_ISGID)
1232                                         args.gid = (__u64)inode->i_gid;
1233                                 else
1234                                         args.gid = (__u64)current_fsgid();
1235                         } else {
1236                                 args.uid = NO_CHANGE_64;
1237                                 args.gid = NO_CHANGE_64;
1238                         }
1239                         CIFSSMBUnixSetInfo(xid, pTcon, full_path, &args,
1240                                             cifs_sb->local_nls,
1241                                             cifs_sb->mnt_cifs_flags &
1242                                             CIFS_MOUNT_MAP_SPECIAL_CHR);
1243                 } else {
1244                         if (!(cifs_sb->mnt_cifs_flags & CIFS_MOUNT_CIFS_ACL) &&
1245                             (mode & S_IWUGO) == 0) {
1246                                 FILE_BASIC_INFO pInfo;
1247                                 struct cifsInodeInfo *cifsInode;
1248                                 u32 dosattrs;
1249
1250                                 memset(&pInfo, 0, sizeof(pInfo));
1251                                 cifsInode = CIFS_I(newinode);
1252                                 dosattrs = cifsInode->cifsAttrs|ATTR_READONLY;
1253                                 pInfo.Attributes = cpu_to_le32(dosattrs);
1254                                 tmprc = CIFSSMBSetPathInfo(xid, pTcon,
1255                                                 full_path, &pInfo,
1256                                                 cifs_sb->local_nls,
1257                                                 cifs_sb->mnt_cifs_flags &
1258                                                 CIFS_MOUNT_MAP_SPECIAL_CHR);
1259                                 if (tmprc == 0)
1260                                         cifsInode->cifsAttrs = dosattrs;
1261                         }
1262                         if (direntry->d_inode) {
1263                                 if (cifs_sb->mnt_cifs_flags &
1264                                      CIFS_MOUNT_DYNPERM)
1265                                         direntry->d_inode->i_mode =
1266                                                 (mode | S_IFDIR);
1267
1268                                 if (cifs_sb->mnt_cifs_flags &
1269                                      CIFS_MOUNT_SET_UID) {
1270                                         direntry->d_inode->i_uid =
1271                                                 current_fsuid();
1272                                         if (inode->i_mode & S_ISGID)
1273                                                 direntry->d_inode->i_gid =
1274                                                         inode->i_gid;
1275                                         else
1276                                                 direntry->d_inode->i_gid =
1277                                                         current_fsgid();
1278                                 }
1279                         }
1280                 }
1281         }
1282 mkdir_out:
1283         kfree(full_path);
1284         FreeXid(xid);
1285         return rc;
1286 }
1287
1288 int cifs_rmdir(struct inode *inode, struct dentry *direntry)
1289 {
1290         int rc = 0;
1291         int xid;
1292         struct cifs_sb_info *cifs_sb;
1293         struct cifsTconInfo *pTcon;
1294         char *full_path = NULL;
1295         struct cifsInodeInfo *cifsInode;
1296
1297         cFYI(1, ("cifs_rmdir, inode = 0x%p", inode));
1298
1299         xid = GetXid();
1300
1301         cifs_sb = CIFS_SB(inode->i_sb);
1302         pTcon = cifs_sb->tcon;
1303
1304         full_path = build_path_from_dentry(direntry);
1305         if (full_path == NULL) {
1306                 FreeXid(xid);
1307                 return -ENOMEM;
1308         }
1309
1310         rc = CIFSSMBRmDir(xid, pTcon, full_path, cifs_sb->local_nls,
1311                           cifs_sb->mnt_cifs_flags & CIFS_MOUNT_MAP_SPECIAL_CHR);
1312
1313         if (!rc) {
1314                 drop_nlink(inode);
1315                 spin_lock(&direntry->d_inode->i_lock);
1316                 i_size_write(direntry->d_inode, 0);
1317                 clear_nlink(direntry->d_inode);
1318                 spin_unlock(&direntry->d_inode->i_lock);
1319         }
1320
1321         cifsInode = CIFS_I(direntry->d_inode);
1322         cifsInode->time = 0;    /* force revalidate to go get info when
1323                                    needed */
1324
1325         cifsInode = CIFS_I(inode);
1326         cifsInode->time = 0;    /* force revalidate to get parent dir info
1327                                    since cached search results now invalid */
1328
1329         direntry->d_inode->i_ctime = inode->i_ctime = inode->i_mtime =
1330                 current_fs_time(inode->i_sb);
1331
1332         kfree(full_path);
1333         FreeXid(xid);
1334         return rc;
1335 }
1336
1337 static int
1338 cifs_do_rename(int xid, struct dentry *from_dentry, const char *fromPath,
1339                 struct dentry *to_dentry, const char *toPath)
1340 {
1341         struct cifs_sb_info *cifs_sb = CIFS_SB(from_dentry->d_sb);
1342         struct cifsTconInfo *pTcon = cifs_sb->tcon;
1343         __u16 srcfid;
1344         int oplock, rc;
1345
1346         /* try path-based rename first */
1347         rc = CIFSSMBRename(xid, pTcon, fromPath, toPath, cifs_sb->local_nls,
1348                            cifs_sb->mnt_cifs_flags &
1349                                 CIFS_MOUNT_MAP_SPECIAL_CHR);
1350
1351         /*
1352          * don't bother with rename by filehandle unless file is busy and
1353          * source Note that cross directory moves do not work with
1354          * rename by filehandle to various Windows servers.
1355          */
1356         if (rc == 0 || rc != -ETXTBSY)
1357                 return rc;
1358
1359         /* open the file to be renamed -- we need DELETE perms */
1360         rc = CIFSSMBOpen(xid, pTcon, fromPath, FILE_OPEN, DELETE,
1361                          CREATE_NOT_DIR, &srcfid, &oplock, NULL,
1362                          cifs_sb->local_nls, cifs_sb->mnt_cifs_flags &
1363                                 CIFS_MOUNT_MAP_SPECIAL_CHR);
1364
1365         if (rc == 0) {
1366                 rc = CIFSSMBRenameOpenFile(xid, pTcon, srcfid,
1367                                 (const char *) to_dentry->d_name.name,
1368                                 cifs_sb->local_nls, cifs_sb->mnt_cifs_flags &
1369                                         CIFS_MOUNT_MAP_SPECIAL_CHR);
1370
1371                 CIFSSMBClose(xid, pTcon, srcfid);
1372         }
1373
1374         return rc;
1375 }
1376
1377 int cifs_rename(struct inode *source_dir, struct dentry *source_dentry,
1378         struct inode *target_dir, struct dentry *target_dentry)
1379 {
1380         char *fromName = NULL;
1381         char *toName = NULL;
1382         struct cifs_sb_info *cifs_sb_source;
1383         struct cifs_sb_info *cifs_sb_target;
1384         struct cifsTconInfo *tcon;
1385         FILE_UNIX_BASIC_INFO *info_buf_source = NULL;
1386         FILE_UNIX_BASIC_INFO *info_buf_target;
1387         int xid, rc, tmprc;
1388
1389         cifs_sb_target = CIFS_SB(target_dir->i_sb);
1390         cifs_sb_source = CIFS_SB(source_dir->i_sb);
1391         tcon = cifs_sb_source->tcon;
1392
1393         xid = GetXid();
1394
1395         /*
1396          * BB: this might be allowed if same server, but different share.
1397          * Consider adding support for this
1398          */
1399         if (tcon != cifs_sb_target->tcon) {
1400                 rc = -EXDEV;
1401                 goto cifs_rename_exit;
1402         }
1403
1404         /*
1405          * we already have the rename sem so we do not need to
1406          * grab it again here to protect the path integrity
1407          */
1408         fromName = build_path_from_dentry(source_dentry);
1409         if (fromName == NULL) {
1410                 rc = -ENOMEM;
1411                 goto cifs_rename_exit;
1412         }
1413
1414         toName = build_path_from_dentry(target_dentry);
1415         if (toName == NULL) {
1416                 rc = -ENOMEM;
1417                 goto cifs_rename_exit;
1418         }
1419
1420         rc = cifs_do_rename(xid, source_dentry, fromName,
1421                             target_dentry, toName);
1422
1423         if (rc == -EEXIST && tcon->unix_ext) {
1424                 /*
1425                  * Are src and dst hardlinks of same inode? We can
1426                  * only tell with unix extensions enabled
1427                  */
1428                 info_buf_source =
1429                         kmalloc(2 * sizeof(FILE_UNIX_BASIC_INFO),
1430                                         GFP_KERNEL);
1431                 if (info_buf_source == NULL) {
1432                         rc = -ENOMEM;
1433                         goto cifs_rename_exit;
1434                 }
1435
1436                 info_buf_target = info_buf_source + 1;
1437                 tmprc = CIFSSMBUnixQPathInfo(xid, tcon, fromName,
1438                                         info_buf_source,
1439                                         cifs_sb_source->local_nls,
1440                                         cifs_sb_source->mnt_cifs_flags &
1441                                         CIFS_MOUNT_MAP_SPECIAL_CHR);
1442                 if (tmprc != 0)
1443                         goto unlink_target;
1444
1445                 tmprc = CIFSSMBUnixQPathInfo(xid, tcon,
1446                                         toName, info_buf_target,
1447                                         cifs_sb_target->local_nls,
1448                                         /* remap based on source sb */
1449                                         cifs_sb_source->mnt_cifs_flags &
1450                                         CIFS_MOUNT_MAP_SPECIAL_CHR);
1451
1452                 if (tmprc == 0 && (info_buf_source->UniqueId ==
1453                                    info_buf_target->UniqueId)) {
1454                         /* same file, POSIX says that this is a noop */
1455                         rc = 0;
1456                         goto cifs_rename_exit;
1457                 }
1458         } /* else ... BB we could add the same check for Windows by
1459                      checking the UniqueId via FILE_INTERNAL_INFO */
1460
1461 unlink_target:
1462         /* Try unlinking the target dentry if it's not negative */
1463         if (target_dentry->d_inode && (rc == -EACCES || rc == -EEXIST)) {
1464                 tmprc = cifs_unlink(target_dir, target_dentry);
1465                 if (tmprc)
1466                         goto cifs_rename_exit;
1467
1468                 rc = cifs_do_rename(xid, source_dentry, fromName,
1469                                     target_dentry, toName);
1470         }
1471
1472 cifs_rename_exit:
1473         kfree(info_buf_source);
1474         kfree(fromName);
1475         kfree(toName);
1476         FreeXid(xid);
1477         return rc;
1478 }
1479
1480 int cifs_revalidate(struct dentry *direntry)
1481 {
1482         int xid;
1483         int rc = 0, wbrc = 0;
1484         char *full_path;
1485         struct cifs_sb_info *cifs_sb;
1486         struct cifsInodeInfo *cifsInode;
1487         loff_t local_size;
1488         struct timespec local_mtime;
1489         bool invalidate_inode = false;
1490
1491         if (direntry->d_inode == NULL)
1492                 return -ENOENT;
1493
1494         cifsInode = CIFS_I(direntry->d_inode);
1495
1496         if (cifsInode == NULL)
1497                 return -ENOENT;
1498
1499         /* no sense revalidating inode info on file that no one can write */
1500         if (CIFS_I(direntry->d_inode)->clientCanCacheRead)
1501                 return rc;
1502
1503         xid = GetXid();
1504
1505         cifs_sb = CIFS_SB(direntry->d_sb);
1506
1507         /* can not safely grab the rename sem here if rename calls revalidate
1508            since that would deadlock */
1509         full_path = build_path_from_dentry(direntry);
1510         if (full_path == NULL) {
1511                 FreeXid(xid);
1512                 return -ENOMEM;
1513         }
1514         cFYI(1, ("Revalidate: %s inode 0x%p count %d dentry: 0x%p d_time %ld "
1515                  "jiffies %ld", full_path, direntry->d_inode,
1516                  direntry->d_inode->i_count.counter, direntry,
1517                  direntry->d_time, jiffies));
1518
1519         if (cifsInode->time == 0) {
1520                 /* was set to zero previously to force revalidate */
1521         } else if (time_before(jiffies, cifsInode->time + HZ) &&
1522                    lookupCacheEnabled) {
1523                 if ((S_ISREG(direntry->d_inode->i_mode) == 0) ||
1524                     (direntry->d_inode->i_nlink == 1)) {
1525                         kfree(full_path);
1526                         FreeXid(xid);
1527                         return rc;
1528                 } else {
1529                         cFYI(1, ("Have to revalidate file due to hardlinks"));
1530                 }
1531         }
1532
1533         /* save mtime and size */
1534         local_mtime = direntry->d_inode->i_mtime;
1535         local_size = direntry->d_inode->i_size;
1536
1537         if (cifs_sb->tcon->unix_ext) {
1538                 rc = cifs_get_inode_info_unix(&direntry->d_inode, full_path,
1539                                               direntry->d_sb, xid);
1540                 if (rc) {
1541                         cFYI(1, ("error on getting revalidate info %d", rc));
1542 /*                      if (rc != -ENOENT)
1543                                 rc = 0; */      /* BB should we cache info on
1544                                                    certain errors? */
1545                 }
1546         } else {
1547                 rc = cifs_get_inode_info(&direntry->d_inode, full_path, NULL,
1548                                          direntry->d_sb, xid, NULL);
1549                 if (rc) {
1550                         cFYI(1, ("error on getting revalidate info %d", rc));
1551 /*                      if (rc != -ENOENT)
1552                                 rc = 0; */      /* BB should we cache info on
1553                                                    certain errors? */
1554                 }
1555         }
1556         /* should we remap certain errors, access denied?, to zero */
1557
1558         /* if not oplocked, we invalidate inode pages if mtime or file size
1559            had changed on server */
1560
1561         if (timespec_equal(&local_mtime, &direntry->d_inode->i_mtime) &&
1562             (local_size == direntry->d_inode->i_size)) {
1563                 cFYI(1, ("cifs_revalidate - inode unchanged"));
1564         } else {
1565                 /* file may have changed on server */
1566                 if (cifsInode->clientCanCacheRead) {
1567                         /* no need to invalidate inode pages since we were the
1568                            only ones who could have modified the file and the
1569                            server copy is staler than ours */
1570                 } else {
1571                         invalidate_inode = true;
1572                 }
1573         }
1574
1575         /* can not grab this sem since kernel filesys locking documentation
1576            indicates i_mutex may be taken by the kernel on lookup and rename
1577            which could deadlock if we grab the i_mutex here as well */
1578 /*      mutex_lock(&direntry->d_inode->i_mutex);*/
1579         /* need to write out dirty pages here  */
1580         if (direntry->d_inode->i_mapping) {
1581                 /* do we need to lock inode until after invalidate completes
1582                    below? */
1583                 wbrc = filemap_fdatawrite(direntry->d_inode->i_mapping);
1584                 if (wbrc)
1585                         CIFS_I(direntry->d_inode)->write_behind_rc = wbrc;
1586         }
1587         if (invalidate_inode) {
1588         /* shrink_dcache not necessary now that cifs dentry ops
1589         are exported for negative dentries */
1590 /*              if (S_ISDIR(direntry->d_inode->i_mode))
1591                         shrink_dcache_parent(direntry); */
1592                 if (S_ISREG(direntry->d_inode->i_mode)) {
1593                         if (direntry->d_inode->i_mapping) {
1594                                 wbrc = filemap_fdatawait(direntry->d_inode->i_mapping);
1595                                 if (wbrc)
1596                                         CIFS_I(direntry->d_inode)->write_behind_rc = wbrc;
1597                         }
1598                         /* may eventually have to do this for open files too */
1599                         if (list_empty(&(cifsInode->openFileList))) {
1600                                 /* changed on server - flush read ahead pages */
1601                                 cFYI(1, ("Invalidating read ahead data on "
1602                                          "closed file"));
1603                                 invalidate_remote_inode(direntry->d_inode);
1604                         }
1605                 }
1606         }
1607 /*      mutex_unlock(&direntry->d_inode->i_mutex); */
1608
1609         kfree(full_path);
1610         FreeXid(xid);
1611         return rc;
1612 }
1613
1614 int cifs_getattr(struct vfsmount *mnt, struct dentry *dentry,
1615         struct kstat *stat)
1616 {
1617         int err = cifs_revalidate(dentry);
1618         if (!err) {
1619                 generic_fillattr(dentry->d_inode, stat);
1620                 stat->blksize = CIFS_MAX_MSGSIZE;
1621         }
1622         return err;
1623 }
1624
1625 static int cifs_truncate_page(struct address_space *mapping, loff_t from)
1626 {
1627         pgoff_t index = from >> PAGE_CACHE_SHIFT;
1628         unsigned offset = from & (PAGE_CACHE_SIZE - 1);
1629         struct page *page;
1630         int rc = 0;
1631
1632         page = grab_cache_page(mapping, index);
1633         if (!page)
1634                 return -ENOMEM;
1635
1636         zero_user_segment(page, offset, PAGE_CACHE_SIZE);
1637         unlock_page(page);
1638         page_cache_release(page);
1639         return rc;
1640 }
1641
1642 static int cifs_vmtruncate(struct inode *inode, loff_t offset)
1643 {
1644         struct address_space *mapping = inode->i_mapping;
1645         unsigned long limit;
1646
1647         spin_lock(&inode->i_lock);
1648         if (inode->i_size < offset)
1649                 goto do_expand;
1650         /*
1651          * truncation of in-use swapfiles is disallowed - it would cause
1652          * subsequent swapout to scribble on the now-freed blocks.
1653          */
1654         if (IS_SWAPFILE(inode)) {
1655                 spin_unlock(&inode->i_lock);
1656                 goto out_busy;
1657         }
1658         i_size_write(inode, offset);
1659         spin_unlock(&inode->i_lock);
1660         /*
1661          * unmap_mapping_range is called twice, first simply for efficiency
1662          * so that truncate_inode_pages does fewer single-page unmaps. However
1663          * after this first call, and before truncate_inode_pages finishes,
1664          * it is possible for private pages to be COWed, which remain after
1665          * truncate_inode_pages finishes, hence the second unmap_mapping_range
1666          * call must be made for correctness.
1667          */
1668         unmap_mapping_range(mapping, offset + PAGE_SIZE - 1, 0, 1);
1669         truncate_inode_pages(mapping, offset);
1670         unmap_mapping_range(mapping, offset + PAGE_SIZE - 1, 0, 1);
1671         goto out_truncate;
1672
1673 do_expand:
1674         limit = current->signal->rlim[RLIMIT_FSIZE].rlim_cur;
1675         if (limit != RLIM_INFINITY && offset > limit) {
1676                 spin_unlock(&inode->i_lock);
1677                 goto out_sig;
1678         }
1679         if (offset > inode->i_sb->s_maxbytes) {
1680                 spin_unlock(&inode->i_lock);
1681                 goto out_big;
1682         }
1683         i_size_write(inode, offset);
1684         spin_unlock(&inode->i_lock);
1685 out_truncate:
1686         if (inode->i_op->truncate)
1687                 inode->i_op->truncate(inode);
1688         return 0;
1689 out_sig:
1690         send_sig(SIGXFSZ, current, 0);
1691 out_big:
1692         return -EFBIG;
1693 out_busy:
1694         return -ETXTBSY;
1695 }
1696
1697 static int
1698 cifs_set_file_size(struct inode *inode, struct iattr *attrs,
1699                    int xid, char *full_path)
1700 {
1701         int rc;
1702         struct cifsFileInfo *open_file;
1703         struct cifsInodeInfo *cifsInode = CIFS_I(inode);
1704         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
1705         struct cifsTconInfo *pTcon = cifs_sb->tcon;
1706
1707         /*
1708          * To avoid spurious oplock breaks from server, in the case of
1709          * inodes that we already have open, avoid doing path based
1710          * setting of file size if we can do it by handle.
1711          * This keeps our caching token (oplock) and avoids timeouts
1712          * when the local oplock break takes longer to flush
1713          * writebehind data than the SMB timeout for the SetPathInfo
1714          * request would allow
1715          */
1716         open_file = find_writable_file(cifsInode);
1717         if (open_file) {
1718                 __u16 nfid = open_file->netfid;
1719                 __u32 npid = open_file->pid;
1720                 rc = CIFSSMBSetFileSize(xid, pTcon, attrs->ia_size, nfid,
1721                                         npid, false);
1722                 atomic_dec(&open_file->wrtPending);
1723                 cFYI(1, ("SetFSize for attrs rc = %d", rc));
1724                 if ((rc == -EINVAL) || (rc == -EOPNOTSUPP)) {
1725                         unsigned int bytes_written;
1726                         rc = CIFSSMBWrite(xid, pTcon, nfid, 0, attrs->ia_size,
1727                                           &bytes_written, NULL, NULL, 1);
1728                         cFYI(1, ("Wrt seteof rc %d", rc));
1729                 }
1730         } else
1731                 rc = -EINVAL;
1732
1733         if (rc != 0) {
1734                 /* Set file size by pathname rather than by handle
1735                    either because no valid, writeable file handle for
1736                    it was found or because there was an error setting
1737                    it by handle */
1738                 rc = CIFSSMBSetEOF(xid, pTcon, full_path, attrs->ia_size,
1739                                    false, cifs_sb->local_nls,
1740                                    cifs_sb->mnt_cifs_flags &
1741                                         CIFS_MOUNT_MAP_SPECIAL_CHR);
1742                 cFYI(1, ("SetEOF by path (setattrs) rc = %d", rc));
1743                 if ((rc == -EINVAL) || (rc == -EOPNOTSUPP)) {
1744                         __u16 netfid;
1745                         int oplock = 0;
1746
1747                         rc = SMBLegacyOpen(xid, pTcon, full_path,
1748                                 FILE_OPEN, GENERIC_WRITE,
1749                                 CREATE_NOT_DIR, &netfid, &oplock, NULL,
1750                                 cifs_sb->local_nls,
1751                                 cifs_sb->mnt_cifs_flags &
1752                                         CIFS_MOUNT_MAP_SPECIAL_CHR);
1753                         if (rc == 0) {
1754                                 unsigned int bytes_written;
1755                                 rc = CIFSSMBWrite(xid, pTcon, netfid, 0,
1756                                                   attrs->ia_size,
1757                                                   &bytes_written, NULL,
1758                                                   NULL, 1);
1759                                 cFYI(1, ("wrt seteof rc %d", rc));
1760                                 CIFSSMBClose(xid, pTcon, netfid);
1761                         }
1762                 }
1763         }
1764
1765         if (rc == 0) {
1766                 cifsInode->server_eof = attrs->ia_size;
1767                 rc = cifs_vmtruncate(inode, attrs->ia_size);
1768                 cifs_truncate_page(inode->i_mapping, inode->i_size);
1769         }
1770
1771         return rc;
1772 }
1773
1774 static int
1775 cifs_setattr_unix(struct dentry *direntry, struct iattr *attrs)
1776 {
1777         int rc;
1778         int xid;
1779         char *full_path = NULL;
1780         struct inode *inode = direntry->d_inode;
1781         struct cifsInodeInfo *cifsInode = CIFS_I(inode);
1782         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
1783         struct cifsTconInfo *pTcon = cifs_sb->tcon;
1784         struct cifs_unix_set_info_args *args = NULL;
1785
1786         cFYI(1, ("setattr_unix on file %s attrs->ia_valid=0x%x",
1787                  direntry->d_name.name, attrs->ia_valid));
1788
1789         xid = GetXid();
1790
1791         if ((cifs_sb->mnt_cifs_flags & CIFS_MOUNT_NO_PERM) == 0) {
1792                 /* check if we have permission to change attrs */
1793                 rc = inode_change_ok(inode, attrs);
1794                 if (rc < 0)
1795                         goto out;
1796                 else
1797                         rc = 0;
1798         }
1799
1800         full_path = build_path_from_dentry(direntry);
1801         if (full_path == NULL) {
1802                 rc = -ENOMEM;
1803                 goto out;
1804         }
1805
1806         /*
1807          * Attempt to flush data before changing attributes. We need to do
1808          * this for ATTR_SIZE and ATTR_MTIME for sure, and if we change the
1809          * ownership or mode then we may also need to do this. Here, we take
1810          * the safe way out and just do the flush on all setattr requests. If
1811          * the flush returns error, store it to report later and continue.
1812          *
1813          * BB: This should be smarter. Why bother flushing pages that
1814          * will be truncated anyway? Also, should we error out here if
1815          * the flush returns error?
1816          */
1817         rc = filemap_write_and_wait(inode->i_mapping);
1818         if (rc != 0) {
1819                 cifsInode->write_behind_rc = rc;
1820                 rc = 0;
1821         }
1822
1823         if (attrs->ia_valid & ATTR_SIZE) {
1824                 rc = cifs_set_file_size(inode, attrs, xid, full_path);
1825                 if (rc != 0)
1826                         goto out;
1827         }
1828
1829         /* skip mode change if it's just for clearing setuid/setgid */
1830         if (attrs->ia_valid & (ATTR_KILL_SUID|ATTR_KILL_SGID))
1831                 attrs->ia_valid &= ~ATTR_MODE;
1832
1833         args = kmalloc(sizeof(*args), GFP_KERNEL);
1834         if (args == NULL) {
1835                 rc = -ENOMEM;
1836                 goto out;
1837         }
1838
1839         /* set up the struct */
1840         if (attrs->ia_valid & ATTR_MODE)
1841                 args->mode = attrs->ia_mode;
1842         else
1843                 args->mode = NO_CHANGE_64;
1844
1845         if (attrs->ia_valid & ATTR_UID)
1846                 args->uid = attrs->ia_uid;
1847         else
1848                 args->uid = NO_CHANGE_64;
1849
1850         if (attrs->ia_valid & ATTR_GID)
1851                 args->gid = attrs->ia_gid;
1852         else
1853                 args->gid = NO_CHANGE_64;
1854
1855         if (attrs->ia_valid & ATTR_ATIME)
1856                 args->atime = cifs_UnixTimeToNT(attrs->ia_atime);
1857         else
1858                 args->atime = NO_CHANGE_64;
1859
1860         if (attrs->ia_valid & ATTR_MTIME)
1861                 args->mtime = cifs_UnixTimeToNT(attrs->ia_mtime);
1862         else
1863                 args->mtime = NO_CHANGE_64;
1864
1865         if (attrs->ia_valid & ATTR_CTIME)
1866                 args->ctime = cifs_UnixTimeToNT(attrs->ia_ctime);
1867         else
1868                 args->ctime = NO_CHANGE_64;
1869
1870         args->device = 0;
1871         rc = CIFSSMBUnixSetInfo(xid, pTcon, full_path, args,
1872                                 cifs_sb->local_nls,
1873                                 cifs_sb->mnt_cifs_flags &
1874                                 CIFS_MOUNT_MAP_SPECIAL_CHR);
1875
1876         if (!rc)
1877                 rc = inode_setattr(inode, attrs);
1878 out:
1879         kfree(args);
1880         kfree(full_path);
1881         FreeXid(xid);
1882         return rc;
1883 }
1884
1885 static int
1886 cifs_setattr_nounix(struct dentry *direntry, struct iattr *attrs)
1887 {
1888         int xid;
1889         struct inode *inode = direntry->d_inode;
1890         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
1891         struct cifsInodeInfo *cifsInode = CIFS_I(inode);
1892         char *full_path = NULL;
1893         int rc = -EACCES;
1894         __u32 dosattr = 0;
1895         __u64 mode = NO_CHANGE_64;
1896
1897         xid = GetXid();
1898
1899         cFYI(1, ("setattr on file %s attrs->iavalid 0x%x",
1900                  direntry->d_name.name, attrs->ia_valid));
1901
1902         if ((cifs_sb->mnt_cifs_flags & CIFS_MOUNT_NO_PERM) == 0) {
1903                 /* check if we have permission to change attrs */
1904                 rc = inode_change_ok(inode, attrs);
1905                 if (rc < 0) {
1906                         FreeXid(xid);
1907                         return rc;
1908                 } else
1909                         rc = 0;
1910         }
1911
1912         full_path = build_path_from_dentry(direntry);
1913         if (full_path == NULL) {
1914                 FreeXid(xid);
1915                 return -ENOMEM;
1916         }
1917
1918         /*
1919          * Attempt to flush data before changing attributes. We need to do
1920          * this for ATTR_SIZE and ATTR_MTIME for sure, and if we change the
1921          * ownership or mode then we may also need to do this. Here, we take
1922          * the safe way out and just do the flush on all setattr requests. If
1923          * the flush returns error, store it to report later and continue.
1924          *
1925          * BB: This should be smarter. Why bother flushing pages that
1926          * will be truncated anyway? Also, should we error out here if
1927          * the flush returns error?
1928          */
1929         rc = filemap_write_and_wait(inode->i_mapping);
1930         if (rc != 0) {
1931                 cifsInode->write_behind_rc = rc;
1932                 rc = 0;
1933         }
1934
1935         if (attrs->ia_valid & ATTR_SIZE) {
1936                 rc = cifs_set_file_size(inode, attrs, xid, full_path);
1937                 if (rc != 0)
1938                         goto cifs_setattr_exit;
1939         }
1940
1941         /*
1942          * Without unix extensions we can't send ownership changes to the
1943          * server, so silently ignore them. This is consistent with how
1944          * local DOS/Windows filesystems behave (VFAT, NTFS, etc). With
1945          * CIFSACL support + proper Windows to Unix idmapping, we may be
1946          * able to support this in the future.
1947          */
1948         if (!(cifs_sb->mnt_cifs_flags & CIFS_MOUNT_SET_UID))
1949                 attrs->ia_valid &= ~(ATTR_UID | ATTR_GID);
1950
1951         /* skip mode change if it's just for clearing setuid/setgid */
1952         if (attrs->ia_valid & (ATTR_KILL_SUID|ATTR_KILL_SGID))
1953                 attrs->ia_valid &= ~ATTR_MODE;
1954
1955         if (attrs->ia_valid & ATTR_MODE) {
1956                 cFYI(1, ("Mode changed to 0%o", attrs->ia_mode));
1957                 mode = attrs->ia_mode;
1958         }
1959
1960         if (attrs->ia_valid & ATTR_MODE) {
1961                 rc = 0;
1962 #ifdef CONFIG_CIFS_EXPERIMENTAL
1963                 if (cifs_sb->mnt_cifs_flags & CIFS_MOUNT_CIFS_ACL)
1964                         rc = mode_to_acl(inode, full_path, mode);
1965                 else
1966 #endif
1967                 if (((mode & S_IWUGO) == 0) &&
1968                     (cifsInode->cifsAttrs & ATTR_READONLY) == 0) {
1969
1970                         dosattr = cifsInode->cifsAttrs | ATTR_READONLY;
1971
1972                         /* fix up mode if we're not using dynperm */
1973                         if ((cifs_sb->mnt_cifs_flags & CIFS_MOUNT_DYNPERM) == 0)
1974                                 attrs->ia_mode = inode->i_mode & ~S_IWUGO;
1975                 } else if ((mode & S_IWUGO) &&
1976                            (cifsInode->cifsAttrs & ATTR_READONLY)) {
1977
1978                         dosattr = cifsInode->cifsAttrs & ~ATTR_READONLY;
1979                         /* Attributes of 0 are ignored */
1980                         if (dosattr == 0)
1981                                 dosattr |= ATTR_NORMAL;
1982
1983                         /* reset local inode permissions to normal */
1984                         if (!(cifs_sb->mnt_cifs_flags & CIFS_MOUNT_DYNPERM)) {
1985                                 attrs->ia_mode &= ~(S_IALLUGO);
1986                                 if (S_ISDIR(inode->i_mode))
1987                                         attrs->ia_mode |=
1988                                                 cifs_sb->mnt_dir_mode;
1989                                 else
1990                                         attrs->ia_mode |=
1991                                                 cifs_sb->mnt_file_mode;
1992                         }
1993                 } else if (!(cifs_sb->mnt_cifs_flags & CIFS_MOUNT_DYNPERM)) {
1994                         /* ignore mode change - ATTR_READONLY hasn't changed */
1995                         attrs->ia_valid &= ~ATTR_MODE;
1996                 }
1997         }
1998
1999         if (attrs->ia_valid & (ATTR_MTIME|ATTR_ATIME|ATTR_CTIME) ||
2000             ((attrs->ia_valid & ATTR_MODE) && dosattr)) {
2001                 rc = cifs_set_file_info(inode, attrs, xid, full_path, dosattr);
2002                 /* BB: check for rc = -EOPNOTSUPP and switch to legacy mode */
2003
2004                 /* Even if error on time set, no sense failing the call if
2005                 the server would set the time to a reasonable value anyway,
2006                 and this check ensures that we are not being called from
2007                 sys_utimes in which case we ought to fail the call back to
2008                 the user when the server rejects the call */
2009                 if ((rc) && (attrs->ia_valid &
2010                                 (ATTR_MODE | ATTR_GID | ATTR_UID | ATTR_SIZE)))
2011                         rc = 0;
2012         }
2013
2014         /* do not need local check to inode_check_ok since the server does
2015            that */
2016         if (!rc)
2017                 rc = inode_setattr(inode, attrs);
2018 cifs_setattr_exit:
2019         kfree(full_path);
2020         FreeXid(xid);
2021         return rc;
2022 }
2023
2024 int
2025 cifs_setattr(struct dentry *direntry, struct iattr *attrs)
2026 {
2027         struct inode *inode = direntry->d_inode;
2028         struct cifs_sb_info *cifs_sb = CIFS_SB(inode->i_sb);
2029         struct cifsTconInfo *pTcon = cifs_sb->tcon;
2030
2031         if (pTcon->unix_ext)
2032                 return cifs_setattr_unix(direntry, attrs);
2033
2034         return cifs_setattr_nounix(direntry, attrs);
2035
2036         /* BB: add cifs_setattr_legacy for really old servers */
2037 }
2038
2039 #if 0
2040 void cifs_delete_inode(struct inode *inode)
2041 {
2042         cFYI(1, ("In cifs_delete_inode, inode = 0x%p", inode));
2043         /* may have to add back in if and when safe distributed caching of
2044            directories added e.g. via FindNotify */
2045 }
2046 #endif