efivars: Improve variable validation
[pandora-kernel.git] / fs / cifs / cifssmb.c
1 /*
2  *   fs/cifs/cifssmb.c
3  *
4  *   Copyright (C) International Business Machines  Corp., 2002,2010
5  *   Author(s): Steve French (sfrench@us.ibm.com)
6  *
7  *   Contains the routines for constructing the SMB PDUs themselves
8  *
9  *   This library is free software; you can redistribute it and/or modify
10  *   it under the terms of the GNU Lesser General Public License as published
11  *   by the Free Software Foundation; either version 2.1 of the License, or
12  *   (at your option) any later version.
13  *
14  *   This library is distributed in the hope that it will be useful,
15  *   but WITHOUT ANY WARRANTY; without even the implied warranty of
16  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See
17  *   the GNU Lesser General Public License for more details.
18  *
19  *   You should have received a copy of the GNU Lesser General Public License
20  *   along with this library; if not, write to the Free Software
21  *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
22  */
23
24  /* SMB/CIFS PDU handling routines here - except for leftovers in connect.c   */
25  /* These are mostly routines that operate on a pathname, or on a tree id     */
26  /* (mounted volume), but there are eight handle based routines which must be */
27  /* treated slightly differently for reconnection purposes since we never     */
28  /* want to reuse a stale file handle and only the caller knows the file info */
29
30 #include <linux/fs.h>
31 #include <linux/kernel.h>
32 #include <linux/vfs.h>
33 #include <linux/slab.h>
34 #include <linux/posix_acl_xattr.h>
35 #include <linux/pagemap.h>
36 #include <linux/swap.h>
37 #include <linux/task_io_accounting_ops.h>
38 #include <asm/uaccess.h>
39 #include "cifspdu.h"
40 #include "cifsglob.h"
41 #include "cifsacl.h"
42 #include "cifsproto.h"
43 #include "cifs_unicode.h"
44 #include "cifs_debug.h"
45 #include "fscache.h"
46
47 #ifdef CONFIG_CIFS_POSIX
48 static struct {
49         int index;
50         char *name;
51 } protocols[] = {
52 #ifdef CONFIG_CIFS_WEAK_PW_HASH
53         {LANMAN_PROT, "\2LM1.2X002"},
54         {LANMAN2_PROT, "\2LANMAN2.1"},
55 #endif /* weak password hashing for legacy clients */
56         {CIFS_PROT, "\2NT LM 0.12"},
57         {POSIX_PROT, "\2POSIX 2"},
58         {BAD_PROT, "\2"}
59 };
60 #else
61 static struct {
62         int index;
63         char *name;
64 } protocols[] = {
65 #ifdef CONFIG_CIFS_WEAK_PW_HASH
66         {LANMAN_PROT, "\2LM1.2X002"},
67         {LANMAN2_PROT, "\2LANMAN2.1"},
68 #endif /* weak password hashing for legacy clients */
69         {CIFS_PROT, "\2NT LM 0.12"},
70         {BAD_PROT, "\2"}
71 };
72 #endif
73
74 /* define the number of elements in the cifs dialect array */
75 #ifdef CONFIG_CIFS_POSIX
76 #ifdef CONFIG_CIFS_WEAK_PW_HASH
77 #define CIFS_NUM_PROT 4
78 #else
79 #define CIFS_NUM_PROT 2
80 #endif /* CIFS_WEAK_PW_HASH */
81 #else /* not posix */
82 #ifdef CONFIG_CIFS_WEAK_PW_HASH
83 #define CIFS_NUM_PROT 3
84 #else
85 #define CIFS_NUM_PROT 1
86 #endif /* CONFIG_CIFS_WEAK_PW_HASH */
87 #endif /* CIFS_POSIX */
88
89 /* Forward declarations */
90 static void cifs_readv_complete(struct work_struct *work);
91
92 /* Mark as invalid, all open files on tree connections since they
93    were closed when session to server was lost */
94 static void mark_open_files_invalid(struct cifs_tcon *pTcon)
95 {
96         struct cifsFileInfo *open_file = NULL;
97         struct list_head *tmp;
98         struct list_head *tmp1;
99
100 /* list all files open on tree connection and mark them invalid */
101         spin_lock(&cifs_file_list_lock);
102         list_for_each_safe(tmp, tmp1, &pTcon->openFileList) {
103                 open_file = list_entry(tmp, struct cifsFileInfo, tlist);
104                 open_file->invalidHandle = true;
105                 open_file->oplock_break_cancelled = true;
106         }
107         spin_unlock(&cifs_file_list_lock);
108         /* BB Add call to invalidate_inodes(sb) for all superblocks mounted
109            to this tcon */
110 }
111
112 /* reconnect the socket, tcon, and smb session if needed */
113 static int
114 cifs_reconnect_tcon(struct cifs_tcon *tcon, int smb_command)
115 {
116         int rc;
117         struct cifs_ses *ses;
118         struct TCP_Server_Info *server;
119         struct nls_table *nls_codepage;
120
121         /*
122          * SMBs NegProt, SessSetup, uLogoff do not have tcon yet so check for
123          * tcp and smb session status done differently for those three - in the
124          * calling routine
125          */
126         if (!tcon)
127                 return 0;
128
129         ses = tcon->ses;
130         server = ses->server;
131
132         /*
133          * only tree disconnect, open, and write, (and ulogoff which does not
134          * have tcon) are allowed as we start force umount
135          */
136         if (tcon->tidStatus == CifsExiting) {
137                 if (smb_command != SMB_COM_WRITE_ANDX &&
138                     smb_command != SMB_COM_OPEN_ANDX &&
139                     smb_command != SMB_COM_TREE_DISCONNECT) {
140                         cFYI(1, "can not send cmd %d while umounting",
141                                 smb_command);
142                         return -ENODEV;
143                 }
144         }
145
146         /*
147          * Give demultiplex thread up to 10 seconds to reconnect, should be
148          * greater than cifs socket timeout which is 7 seconds
149          */
150         while (server->tcpStatus == CifsNeedReconnect) {
151                 wait_event_interruptible_timeout(server->response_q,
152                         (server->tcpStatus != CifsNeedReconnect), 10 * HZ);
153
154                 /* are we still trying to reconnect? */
155                 if (server->tcpStatus != CifsNeedReconnect)
156                         break;
157
158                 /*
159                  * on "soft" mounts we wait once. Hard mounts keep
160                  * retrying until process is killed or server comes
161                  * back on-line
162                  */
163                 if (!tcon->retry) {
164                         cFYI(1, "gave up waiting on reconnect in smb_init");
165                         return -EHOSTDOWN;
166                 }
167         }
168
169         if (!ses->need_reconnect && !tcon->need_reconnect)
170                 return 0;
171
172         nls_codepage = load_nls_default();
173
174         /*
175          * need to prevent multiple threads trying to simultaneously
176          * reconnect the same SMB session
177          */
178         mutex_lock(&ses->session_mutex);
179         rc = cifs_negotiate_protocol(0, ses);
180         if (rc == 0 && ses->need_reconnect)
181                 rc = cifs_setup_session(0, ses, nls_codepage);
182
183         /* do we need to reconnect tcon? */
184         if (rc || !tcon->need_reconnect) {
185                 mutex_unlock(&ses->session_mutex);
186                 goto out;
187         }
188
189         mark_open_files_invalid(tcon);
190         rc = CIFSTCon(0, ses, tcon->treeName, tcon, nls_codepage);
191         mutex_unlock(&ses->session_mutex);
192         cFYI(1, "reconnect tcon rc = %d", rc);
193
194         if (rc)
195                 goto out;
196
197         /*
198          * FIXME: check if wsize needs updated due to negotiated smb buffer
199          *        size shrinking
200          */
201         atomic_inc(&tconInfoReconnectCount);
202
203         /* tell server Unix caps we support */
204         if (ses->capabilities & CAP_UNIX)
205                 reset_cifs_unix_caps(0, tcon, NULL, NULL);
206
207         /*
208          * Removed call to reopen open files here. It is safer (and faster) to
209          * reopen files one at a time as needed in read and write.
210          *
211          * FIXME: what about file locks? don't we need to reclaim them ASAP?
212          */
213
214 out:
215         /*
216          * Check if handle based operation so we know whether we can continue
217          * or not without returning to caller to reset file handle
218          */
219         switch (smb_command) {
220         case SMB_COM_READ_ANDX:
221         case SMB_COM_WRITE_ANDX:
222         case SMB_COM_CLOSE:
223         case SMB_COM_FIND_CLOSE2:
224         case SMB_COM_LOCKING_ANDX:
225                 rc = -EAGAIN;
226         }
227
228         unload_nls(nls_codepage);
229         return rc;
230 }
231
232 /* Allocate and return pointer to an SMB request buffer, and set basic
233    SMB information in the SMB header.  If the return code is zero, this
234    function must have filled in request_buf pointer */
235 static int
236 small_smb_init(int smb_command, int wct, struct cifs_tcon *tcon,
237                 void **request_buf)
238 {
239         int rc;
240
241         rc = cifs_reconnect_tcon(tcon, smb_command);
242         if (rc)
243                 return rc;
244
245         *request_buf = cifs_small_buf_get();
246         if (*request_buf == NULL) {
247                 /* BB should we add a retry in here if not a writepage? */
248                 return -ENOMEM;
249         }
250
251         header_assemble((struct smb_hdr *) *request_buf, smb_command,
252                         tcon, wct);
253
254         if (tcon != NULL)
255                 cifs_stats_inc(&tcon->num_smbs_sent);
256
257         return 0;
258 }
259
260 int
261 small_smb_init_no_tc(const int smb_command, const int wct,
262                      struct cifs_ses *ses, void **request_buf)
263 {
264         int rc;
265         struct smb_hdr *buffer;
266
267         rc = small_smb_init(smb_command, wct, NULL, request_buf);
268         if (rc)
269                 return rc;
270
271         buffer = (struct smb_hdr *)*request_buf;
272         buffer->Mid = GetNextMid(ses->server);
273         if (ses->capabilities & CAP_UNICODE)
274                 buffer->Flags2 |= SMBFLG2_UNICODE;
275         if (ses->capabilities & CAP_STATUS32)
276                 buffer->Flags2 |= SMBFLG2_ERR_STATUS;
277
278         /* uid, tid can stay at zero as set in header assemble */
279
280         /* BB add support for turning on the signing when
281         this function is used after 1st of session setup requests */
282
283         return rc;
284 }
285
286 /* If the return code is zero, this function must fill in request_buf pointer */
287 static int
288 __smb_init(int smb_command, int wct, struct cifs_tcon *tcon,
289                         void **request_buf, void **response_buf)
290 {
291         *request_buf = cifs_buf_get();
292         if (*request_buf == NULL) {
293                 /* BB should we add a retry in here if not a writepage? */
294                 return -ENOMEM;
295         }
296     /* Although the original thought was we needed the response buf for  */
297     /* potential retries of smb operations it turns out we can determine */
298     /* from the mid flags when the request buffer can be resent without  */
299     /* having to use a second distinct buffer for the response */
300         if (response_buf)
301                 *response_buf = *request_buf;
302
303         header_assemble((struct smb_hdr *) *request_buf, smb_command, tcon,
304                         wct);
305
306         if (tcon != NULL)
307                 cifs_stats_inc(&tcon->num_smbs_sent);
308
309         return 0;
310 }
311
312 /* If the return code is zero, this function must fill in request_buf pointer */
313 static int
314 smb_init(int smb_command, int wct, struct cifs_tcon *tcon,
315          void **request_buf, void **response_buf)
316 {
317         int rc;
318
319         rc = cifs_reconnect_tcon(tcon, smb_command);
320         if (rc)
321                 return rc;
322
323         return __smb_init(smb_command, wct, tcon, request_buf, response_buf);
324 }
325
326 static int
327 smb_init_no_reconnect(int smb_command, int wct, struct cifs_tcon *tcon,
328                         void **request_buf, void **response_buf)
329 {
330         if (tcon->ses->need_reconnect || tcon->need_reconnect)
331                 return -EHOSTDOWN;
332
333         return __smb_init(smb_command, wct, tcon, request_buf, response_buf);
334 }
335
336 static int validate_t2(struct smb_t2_rsp *pSMB)
337 {
338         unsigned int total_size;
339
340         /* check for plausible wct */
341         if (pSMB->hdr.WordCount < 10)
342                 goto vt2_err;
343
344         /* check for parm and data offset going beyond end of smb */
345         if (get_unaligned_le16(&pSMB->t2_rsp.ParameterOffset) > 1024 ||
346             get_unaligned_le16(&pSMB->t2_rsp.DataOffset) > 1024)
347                 goto vt2_err;
348
349         total_size = get_unaligned_le16(&pSMB->t2_rsp.ParameterCount);
350         if (total_size >= 512)
351                 goto vt2_err;
352
353         /* check that bcc is at least as big as parms + data, and that it is
354          * less than negotiated smb buffer
355          */
356         total_size += get_unaligned_le16(&pSMB->t2_rsp.DataCount);
357         if (total_size > get_bcc(&pSMB->hdr) ||
358             total_size >= CIFSMaxBufSize + MAX_CIFS_HDR_SIZE)
359                 goto vt2_err;
360
361         return 0;
362 vt2_err:
363         cifs_dump_mem("Invalid transact2 SMB: ", (char *)pSMB,
364                 sizeof(struct smb_t2_rsp) + 16);
365         return -EINVAL;
366 }
367
368 static inline void inc_rfc1001_len(void *pSMB, int count)
369 {
370         struct smb_hdr *hdr = (struct smb_hdr *)pSMB;
371
372         be32_add_cpu(&hdr->smb_buf_length, count);
373 }
374
375 int
376 CIFSSMBNegotiate(unsigned int xid, struct cifs_ses *ses)
377 {
378         NEGOTIATE_REQ *pSMB;
379         NEGOTIATE_RSP *pSMBr;
380         int rc = 0;
381         int bytes_returned;
382         int i;
383         struct TCP_Server_Info *server;
384         u16 count;
385         unsigned int secFlags;
386
387         if (ses->server)
388                 server = ses->server;
389         else {
390                 rc = -EIO;
391                 return rc;
392         }
393         rc = smb_init(SMB_COM_NEGOTIATE, 0, NULL /* no tcon yet */ ,
394                       (void **) &pSMB, (void **) &pSMBr);
395         if (rc)
396                 return rc;
397
398         /* if any of auth flags (ie not sign or seal) are overriden use them */
399         if (ses->overrideSecFlg & (~(CIFSSEC_MUST_SIGN | CIFSSEC_MUST_SEAL)))
400                 secFlags = ses->overrideSecFlg;  /* BB FIXME fix sign flags? */
401         else /* if override flags set only sign/seal OR them with global auth */
402                 secFlags = global_secflags | ses->overrideSecFlg;
403
404         cFYI(1, "secFlags 0x%x", secFlags);
405
406         pSMB->hdr.Mid = GetNextMid(server);
407         pSMB->hdr.Flags2 |= (SMBFLG2_UNICODE | SMBFLG2_ERR_STATUS);
408
409         if ((secFlags & CIFSSEC_MUST_KRB5) == CIFSSEC_MUST_KRB5)
410                 pSMB->hdr.Flags2 |= SMBFLG2_EXT_SEC;
411         else if ((secFlags & CIFSSEC_AUTH_MASK) == CIFSSEC_MAY_KRB5) {
412                 cFYI(1, "Kerberos only mechanism, enable extended security");
413                 pSMB->hdr.Flags2 |= SMBFLG2_EXT_SEC;
414         } else if ((secFlags & CIFSSEC_MUST_NTLMSSP) == CIFSSEC_MUST_NTLMSSP)
415                 pSMB->hdr.Flags2 |= SMBFLG2_EXT_SEC;
416         else if ((secFlags & CIFSSEC_AUTH_MASK) == CIFSSEC_MAY_NTLMSSP) {
417                 cFYI(1, "NTLMSSP only mechanism, enable extended security");
418                 pSMB->hdr.Flags2 |= SMBFLG2_EXT_SEC;
419         }
420
421         count = 0;
422         for (i = 0; i < CIFS_NUM_PROT; i++) {
423                 strncpy(pSMB->DialectsArray+count, protocols[i].name, 16);
424                 count += strlen(protocols[i].name) + 1;
425                 /* null at end of source and target buffers anyway */
426         }
427         inc_rfc1001_len(pSMB, count);
428         pSMB->ByteCount = cpu_to_le16(count);
429
430         rc = SendReceive(xid, ses, (struct smb_hdr *) pSMB,
431                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
432         if (rc != 0)
433                 goto neg_err_exit;
434
435         server->dialect = le16_to_cpu(pSMBr->DialectIndex);
436         cFYI(1, "Dialect: %d", server->dialect);
437         /* Check wct = 1 error case */
438         if ((pSMBr->hdr.WordCount < 13) || (server->dialect == BAD_PROT)) {
439                 /* core returns wct = 1, but we do not ask for core - otherwise
440                 small wct just comes when dialect index is -1 indicating we
441                 could not negotiate a common dialect */
442                 rc = -EOPNOTSUPP;
443                 goto neg_err_exit;
444 #ifdef CONFIG_CIFS_WEAK_PW_HASH
445         } else if ((pSMBr->hdr.WordCount == 13)
446                         && ((server->dialect == LANMAN_PROT)
447                                 || (server->dialect == LANMAN2_PROT))) {
448                 __s16 tmp;
449                 struct lanman_neg_rsp *rsp = (struct lanman_neg_rsp *)pSMBr;
450
451                 if ((secFlags & CIFSSEC_MAY_LANMAN) ||
452                         (secFlags & CIFSSEC_MAY_PLNTXT))
453                         server->secType = LANMAN;
454                 else {
455                         cERROR(1, "mount failed weak security disabled"
456                                    " in /proc/fs/cifs/SecurityFlags");
457                         rc = -EOPNOTSUPP;
458                         goto neg_err_exit;
459                 }
460                 server->sec_mode = (__u8)le16_to_cpu(rsp->SecurityMode);
461                 server->maxReq = min_t(unsigned int,
462                                        le16_to_cpu(rsp->MaxMpxCount),
463                                        cifs_max_pending);
464                 server->oplocks = server->maxReq > 1 ? enable_oplocks : false;
465                 server->maxBuf = le16_to_cpu(rsp->MaxBufSize);
466                 server->max_vcs = le16_to_cpu(rsp->MaxNumberVcs);
467                 /* even though we do not use raw we might as well set this
468                 accurately, in case we ever find a need for it */
469                 if ((le16_to_cpu(rsp->RawMode) & RAW_ENABLE) == RAW_ENABLE) {
470                         server->max_rw = 0xFF00;
471                         server->capabilities = CAP_MPX_MODE | CAP_RAW_MODE;
472                 } else {
473                         server->max_rw = 0;/* do not need to use raw anyway */
474                         server->capabilities = CAP_MPX_MODE;
475                 }
476                 tmp = (__s16)le16_to_cpu(rsp->ServerTimeZone);
477                 if (tmp == -1) {
478                         /* OS/2 often does not set timezone therefore
479                          * we must use server time to calc time zone.
480                          * Could deviate slightly from the right zone.
481                          * Smallest defined timezone difference is 15 minutes
482                          * (i.e. Nepal).  Rounding up/down is done to match
483                          * this requirement.
484                          */
485                         int val, seconds, remain, result;
486                         struct timespec ts, utc;
487                         utc = CURRENT_TIME;
488                         ts = cnvrtDosUnixTm(rsp->SrvTime.Date,
489                                             rsp->SrvTime.Time, 0);
490                         cFYI(1, "SrvTime %d sec since 1970 (utc: %d) diff: %d",
491                                 (int)ts.tv_sec, (int)utc.tv_sec,
492                                 (int)(utc.tv_sec - ts.tv_sec));
493                         val = (int)(utc.tv_sec - ts.tv_sec);
494                         seconds = abs(val);
495                         result = (seconds / MIN_TZ_ADJ) * MIN_TZ_ADJ;
496                         remain = seconds % MIN_TZ_ADJ;
497                         if (remain >= (MIN_TZ_ADJ / 2))
498                                 result += MIN_TZ_ADJ;
499                         if (val < 0)
500                                 result = -result;
501                         server->timeAdj = result;
502                 } else {
503                         server->timeAdj = (int)tmp;
504                         server->timeAdj *= 60; /* also in seconds */
505                 }
506                 cFYI(1, "server->timeAdj: %d seconds", server->timeAdj);
507
508
509                 /* BB get server time for time conversions and add
510                 code to use it and timezone since this is not UTC */
511
512                 if (rsp->EncryptionKeyLength ==
513                                 cpu_to_le16(CIFS_CRYPTO_KEY_SIZE)) {
514                         memcpy(ses->server->cryptkey, rsp->EncryptionKey,
515                                 CIFS_CRYPTO_KEY_SIZE);
516                 } else if (server->sec_mode & SECMODE_PW_ENCRYPT) {
517                         rc = -EIO; /* need cryptkey unless plain text */
518                         goto neg_err_exit;
519                 }
520
521                 cFYI(1, "LANMAN negotiated");
522                 /* we will not end up setting signing flags - as no signing
523                 was in LANMAN and server did not return the flags on */
524                 goto signing_check;
525 #else /* weak security disabled */
526         } else if (pSMBr->hdr.WordCount == 13) {
527                 cERROR(1, "mount failed, cifs module not built "
528                           "with CIFS_WEAK_PW_HASH support");
529                 rc = -EOPNOTSUPP;
530 #endif /* WEAK_PW_HASH */
531                 goto neg_err_exit;
532         } else if (pSMBr->hdr.WordCount != 17) {
533                 /* unknown wct */
534                 rc = -EOPNOTSUPP;
535                 goto neg_err_exit;
536         }
537         /* else wct == 17 NTLM */
538         server->sec_mode = pSMBr->SecurityMode;
539         if ((server->sec_mode & SECMODE_USER) == 0)
540                 cFYI(1, "share mode security");
541
542         if ((server->sec_mode & SECMODE_PW_ENCRYPT) == 0)
543 #ifdef CONFIG_CIFS_WEAK_PW_HASH
544                 if ((secFlags & CIFSSEC_MAY_PLNTXT) == 0)
545 #endif /* CIFS_WEAK_PW_HASH */
546                         cERROR(1, "Server requests plain text password"
547                                   " but client support disabled");
548
549         if ((secFlags & CIFSSEC_MUST_NTLMV2) == CIFSSEC_MUST_NTLMV2)
550                 server->secType = NTLMv2;
551         else if (secFlags & CIFSSEC_MAY_NTLM)
552                 server->secType = NTLM;
553         else if (secFlags & CIFSSEC_MAY_NTLMV2)
554                 server->secType = NTLMv2;
555         else if (secFlags & CIFSSEC_MAY_KRB5)
556                 server->secType = Kerberos;
557         else if (secFlags & CIFSSEC_MAY_NTLMSSP)
558                 server->secType = RawNTLMSSP;
559         else if (secFlags & CIFSSEC_MAY_LANMAN)
560                 server->secType = LANMAN;
561         else {
562                 rc = -EOPNOTSUPP;
563                 cERROR(1, "Invalid security type");
564                 goto neg_err_exit;
565         }
566         /* else ... any others ...? */
567
568         /* one byte, so no need to convert this or EncryptionKeyLen from
569            little endian */
570         server->maxReq = min_t(unsigned int, le16_to_cpu(pSMBr->MaxMpxCount),
571                                cifs_max_pending);
572         server->oplocks = server->maxReq > 1 ? enable_oplocks : false;
573         /* probably no need to store and check maxvcs */
574         server->maxBuf = le32_to_cpu(pSMBr->MaxBufferSize);
575         server->max_rw = le32_to_cpu(pSMBr->MaxRawSize);
576         cFYI(DBG2, "Max buf = %d", ses->server->maxBuf);
577         server->capabilities = le32_to_cpu(pSMBr->Capabilities);
578         server->timeAdj = (int)(__s16)le16_to_cpu(pSMBr->ServerTimeZone);
579         server->timeAdj *= 60;
580         if (pSMBr->EncryptionKeyLength == CIFS_CRYPTO_KEY_SIZE) {
581                 memcpy(ses->server->cryptkey, pSMBr->u.EncryptionKey,
582                        CIFS_CRYPTO_KEY_SIZE);
583         } else if ((pSMBr->hdr.Flags2 & SMBFLG2_EXT_SEC ||
584                         server->capabilities & CAP_EXTENDED_SECURITY) &&
585                                 (pSMBr->EncryptionKeyLength == 0)) {
586                 /* decode security blob */
587                 count = get_bcc(&pSMBr->hdr);
588                 if (count < 16) {
589                         rc = -EIO;
590                         goto neg_err_exit;
591                 }
592                 spin_lock(&cifs_tcp_ses_lock);
593                 if (server->srv_count > 1) {
594                         spin_unlock(&cifs_tcp_ses_lock);
595                         if (memcmp(server->server_GUID,
596                                    pSMBr->u.extended_response.
597                                    GUID, 16) != 0) {
598                                 cFYI(1, "server UID changed");
599                                 memcpy(server->server_GUID,
600                                         pSMBr->u.extended_response.GUID,
601                                         16);
602                         }
603                 } else {
604                         spin_unlock(&cifs_tcp_ses_lock);
605                         memcpy(server->server_GUID,
606                                pSMBr->u.extended_response.GUID, 16);
607                 }
608
609                 if (count == 16) {
610                         server->secType = RawNTLMSSP;
611                 } else {
612                         rc = decode_negTokenInit(pSMBr->u.extended_response.
613                                                  SecurityBlob, count - 16,
614                                                  server);
615                         if (rc == 1)
616                                 rc = 0;
617                         else
618                                 rc = -EINVAL;
619                         if (server->secType == Kerberos) {
620                                 if (!server->sec_kerberos &&
621                                                 !server->sec_mskerberos)
622                                         rc = -EOPNOTSUPP;
623                         } else if (server->secType == RawNTLMSSP) {
624                                 if (!server->sec_ntlmssp)
625                                         rc = -EOPNOTSUPP;
626                         } else
627                                         rc = -EOPNOTSUPP;
628                 }
629         } else if (server->sec_mode & SECMODE_PW_ENCRYPT) {
630                 rc = -EIO; /* no crypt key only if plain text pwd */
631                 goto neg_err_exit;
632         } else
633                 server->capabilities &= ~CAP_EXTENDED_SECURITY;
634
635 #ifdef CONFIG_CIFS_WEAK_PW_HASH
636 signing_check:
637 #endif
638         if ((secFlags & CIFSSEC_MAY_SIGN) == 0) {
639                 /* MUST_SIGN already includes the MAY_SIGN FLAG
640                    so if this is zero it means that signing is disabled */
641                 cFYI(1, "Signing disabled");
642                 if (server->sec_mode & SECMODE_SIGN_REQUIRED) {
643                         cERROR(1, "Server requires "
644                                    "packet signing to be enabled in "
645                                    "/proc/fs/cifs/SecurityFlags.");
646                         rc = -EOPNOTSUPP;
647                 }
648                 server->sec_mode &=
649                         ~(SECMODE_SIGN_ENABLED | SECMODE_SIGN_REQUIRED);
650         } else if ((secFlags & CIFSSEC_MUST_SIGN) == CIFSSEC_MUST_SIGN) {
651                 /* signing required */
652                 cFYI(1, "Must sign - secFlags 0x%x", secFlags);
653                 if ((server->sec_mode &
654                         (SECMODE_SIGN_ENABLED | SECMODE_SIGN_REQUIRED)) == 0) {
655                         cERROR(1, "signing required but server lacks support");
656                         rc = -EOPNOTSUPP;
657                 } else
658                         server->sec_mode |= SECMODE_SIGN_REQUIRED;
659         } else {
660                 /* signing optional ie CIFSSEC_MAY_SIGN */
661                 if ((server->sec_mode & SECMODE_SIGN_REQUIRED) == 0)
662                         server->sec_mode &=
663                                 ~(SECMODE_SIGN_ENABLED | SECMODE_SIGN_REQUIRED);
664         }
665
666 neg_err_exit:
667         cifs_buf_release(pSMB);
668
669         cFYI(1, "negprot rc %d", rc);
670         return rc;
671 }
672
673 int
674 CIFSSMBTDis(const int xid, struct cifs_tcon *tcon)
675 {
676         struct smb_hdr *smb_buffer;
677         int rc = 0;
678
679         cFYI(1, "In tree disconnect");
680
681         /* BB: do we need to check this? These should never be NULL. */
682         if ((tcon->ses == NULL) || (tcon->ses->server == NULL))
683                 return -EIO;
684
685         /*
686          * No need to return error on this operation if tid invalidated and
687          * closed on server already e.g. due to tcp session crashing. Also,
688          * the tcon is no longer on the list, so no need to take lock before
689          * checking this.
690          */
691         if ((tcon->need_reconnect) || (tcon->ses->need_reconnect))
692                 return 0;
693
694         rc = small_smb_init(SMB_COM_TREE_DISCONNECT, 0, tcon,
695                             (void **)&smb_buffer);
696         if (rc)
697                 return rc;
698
699         rc = SendReceiveNoRsp(xid, tcon->ses, smb_buffer, 0);
700         if (rc)
701                 cFYI(1, "Tree disconnect failed %d", rc);
702
703         /* No need to return error on this operation if tid invalidated and
704            closed on server already e.g. due to tcp session crashing */
705         if (rc == -EAGAIN)
706                 rc = 0;
707
708         return rc;
709 }
710
711 /*
712  * This is a no-op for now. We're not really interested in the reply, but
713  * rather in the fact that the server sent one and that server->lstrp
714  * gets updated.
715  *
716  * FIXME: maybe we should consider checking that the reply matches request?
717  */
718 static void
719 cifs_echo_callback(struct mid_q_entry *mid)
720 {
721         struct TCP_Server_Info *server = mid->callback_data;
722
723         DeleteMidQEntry(mid);
724         atomic_dec(&server->inFlight);
725         wake_up(&server->request_q);
726 }
727
728 int
729 CIFSSMBEcho(struct TCP_Server_Info *server)
730 {
731         ECHO_REQ *smb;
732         int rc = 0;
733         struct kvec iov;
734
735         cFYI(1, "In echo request");
736
737         rc = small_smb_init(SMB_COM_ECHO, 0, NULL, (void **)&smb);
738         if (rc)
739                 return rc;
740
741         /* set up echo request */
742         smb->hdr.Tid = 0xffff;
743         smb->hdr.WordCount = 1;
744         put_unaligned_le16(1, &smb->EchoCount);
745         put_bcc(1, &smb->hdr);
746         smb->Data[0] = 'a';
747         inc_rfc1001_len(smb, 3);
748         iov.iov_base = smb;
749         iov.iov_len = be32_to_cpu(smb->hdr.smb_buf_length) + 4;
750
751         rc = cifs_call_async(server, &iov, 1, NULL, cifs_echo_callback,
752                              server, true);
753         if (rc)
754                 cFYI(1, "Echo request failed: %d", rc);
755
756         cifs_small_buf_release(smb);
757
758         return rc;
759 }
760
761 int
762 CIFSSMBLogoff(const int xid, struct cifs_ses *ses)
763 {
764         LOGOFF_ANDX_REQ *pSMB;
765         int rc = 0;
766
767         cFYI(1, "In SMBLogoff for session disconnect");
768
769         /*
770          * BB: do we need to check validity of ses and server? They should
771          * always be valid since we have an active reference. If not, that
772          * should probably be a BUG()
773          */
774         if (!ses || !ses->server)
775                 return -EIO;
776
777         mutex_lock(&ses->session_mutex);
778         if (ses->need_reconnect)
779                 goto session_already_dead; /* no need to send SMBlogoff if uid
780                                               already closed due to reconnect */
781         rc = small_smb_init(SMB_COM_LOGOFF_ANDX, 2, NULL, (void **)&pSMB);
782         if (rc) {
783                 mutex_unlock(&ses->session_mutex);
784                 return rc;
785         }
786
787         pSMB->hdr.Mid = GetNextMid(ses->server);
788
789         if (ses->server->sec_mode &
790                    (SECMODE_SIGN_REQUIRED | SECMODE_SIGN_ENABLED))
791                         pSMB->hdr.Flags2 |= SMBFLG2_SECURITY_SIGNATURE;
792
793         pSMB->hdr.Uid = ses->Suid;
794
795         pSMB->AndXCommand = 0xFF;
796         rc = SendReceiveNoRsp(xid, ses, (struct smb_hdr *) pSMB, 0);
797 session_already_dead:
798         mutex_unlock(&ses->session_mutex);
799
800         /* if session dead then we do not need to do ulogoff,
801                 since server closed smb session, no sense reporting
802                 error */
803         if (rc == -EAGAIN)
804                 rc = 0;
805         return rc;
806 }
807
808 int
809 CIFSPOSIXDelFile(const int xid, struct cifs_tcon *tcon, const char *fileName,
810                  __u16 type, const struct nls_table *nls_codepage, int remap)
811 {
812         TRANSACTION2_SPI_REQ *pSMB = NULL;
813         TRANSACTION2_SPI_RSP *pSMBr = NULL;
814         struct unlink_psx_rq *pRqD;
815         int name_len;
816         int rc = 0;
817         int bytes_returned = 0;
818         __u16 params, param_offset, offset, byte_count;
819
820         cFYI(1, "In POSIX delete");
821 PsxDelete:
822         rc = smb_init(SMB_COM_TRANSACTION2, 15, tcon, (void **) &pSMB,
823                       (void **) &pSMBr);
824         if (rc)
825                 return rc;
826
827         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
828                 name_len =
829                     cifsConvertToUCS((__le16 *) pSMB->FileName, fileName,
830                                      PATH_MAX, nls_codepage, remap);
831                 name_len++;     /* trailing null */
832                 name_len *= 2;
833         } else { /* BB add path length overrun check */
834                 name_len = strnlen(fileName, PATH_MAX);
835                 name_len++;     /* trailing null */
836                 strncpy(pSMB->FileName, fileName, name_len);
837         }
838
839         params = 6 + name_len;
840         pSMB->MaxParameterCount = cpu_to_le16(2);
841         pSMB->MaxDataCount = 0; /* BB double check this with jra */
842         pSMB->MaxSetupCount = 0;
843         pSMB->Reserved = 0;
844         pSMB->Flags = 0;
845         pSMB->Timeout = 0;
846         pSMB->Reserved2 = 0;
847         param_offset = offsetof(struct smb_com_transaction2_spi_req,
848                                 InformationLevel) - 4;
849         offset = param_offset + params;
850
851         /* Setup pointer to Request Data (inode type) */
852         pRqD = (struct unlink_psx_rq *)(((char *)&pSMB->hdr.Protocol) + offset);
853         pRqD->type = cpu_to_le16(type);
854         pSMB->ParameterOffset = cpu_to_le16(param_offset);
855         pSMB->DataOffset = cpu_to_le16(offset);
856         pSMB->SetupCount = 1;
857         pSMB->Reserved3 = 0;
858         pSMB->SubCommand = cpu_to_le16(TRANS2_SET_PATH_INFORMATION);
859         byte_count = 3 /* pad */  + params + sizeof(struct unlink_psx_rq);
860
861         pSMB->DataCount = cpu_to_le16(sizeof(struct unlink_psx_rq));
862         pSMB->TotalDataCount = cpu_to_le16(sizeof(struct unlink_psx_rq));
863         pSMB->ParameterCount = cpu_to_le16(params);
864         pSMB->TotalParameterCount = pSMB->ParameterCount;
865         pSMB->InformationLevel = cpu_to_le16(SMB_POSIX_UNLINK);
866         pSMB->Reserved4 = 0;
867         inc_rfc1001_len(pSMB, byte_count);
868         pSMB->ByteCount = cpu_to_le16(byte_count);
869         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
870                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
871         if (rc)
872                 cFYI(1, "Posix delete returned %d", rc);
873         cifs_buf_release(pSMB);
874
875         cifs_stats_inc(&tcon->num_deletes);
876
877         if (rc == -EAGAIN)
878                 goto PsxDelete;
879
880         return rc;
881 }
882
883 int
884 CIFSSMBDelFile(const int xid, struct cifs_tcon *tcon, const char *fileName,
885                const struct nls_table *nls_codepage, int remap)
886 {
887         DELETE_FILE_REQ *pSMB = NULL;
888         DELETE_FILE_RSP *pSMBr = NULL;
889         int rc = 0;
890         int bytes_returned;
891         int name_len;
892
893 DelFileRetry:
894         rc = smb_init(SMB_COM_DELETE, 1, tcon, (void **) &pSMB,
895                       (void **) &pSMBr);
896         if (rc)
897                 return rc;
898
899         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
900                 name_len =
901                     cifsConvertToUCS((__le16 *) pSMB->fileName, fileName,
902                                      PATH_MAX, nls_codepage, remap);
903                 name_len++;     /* trailing null */
904                 name_len *= 2;
905         } else {                /* BB improve check for buffer overruns BB */
906                 name_len = strnlen(fileName, PATH_MAX);
907                 name_len++;     /* trailing null */
908                 strncpy(pSMB->fileName, fileName, name_len);
909         }
910         pSMB->SearchAttributes =
911             cpu_to_le16(ATTR_READONLY | ATTR_HIDDEN | ATTR_SYSTEM);
912         pSMB->BufferFormat = 0x04;
913         inc_rfc1001_len(pSMB, name_len + 1);
914         pSMB->ByteCount = cpu_to_le16(name_len + 1);
915         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
916                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
917         cifs_stats_inc(&tcon->num_deletes);
918         if (rc)
919                 cFYI(1, "Error in RMFile = %d", rc);
920
921         cifs_buf_release(pSMB);
922         if (rc == -EAGAIN)
923                 goto DelFileRetry;
924
925         return rc;
926 }
927
928 int
929 CIFSSMBRmDir(const int xid, struct cifs_tcon *tcon, const char *dirName,
930              const struct nls_table *nls_codepage, int remap)
931 {
932         DELETE_DIRECTORY_REQ *pSMB = NULL;
933         DELETE_DIRECTORY_RSP *pSMBr = NULL;
934         int rc = 0;
935         int bytes_returned;
936         int name_len;
937
938         cFYI(1, "In CIFSSMBRmDir");
939 RmDirRetry:
940         rc = smb_init(SMB_COM_DELETE_DIRECTORY, 0, tcon, (void **) &pSMB,
941                       (void **) &pSMBr);
942         if (rc)
943                 return rc;
944
945         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
946                 name_len = cifsConvertToUCS((__le16 *) pSMB->DirName, dirName,
947                                          PATH_MAX, nls_codepage, remap);
948                 name_len++;     /* trailing null */
949                 name_len *= 2;
950         } else {                /* BB improve check for buffer overruns BB */
951                 name_len = strnlen(dirName, PATH_MAX);
952                 name_len++;     /* trailing null */
953                 strncpy(pSMB->DirName, dirName, name_len);
954         }
955
956         pSMB->BufferFormat = 0x04;
957         inc_rfc1001_len(pSMB, name_len + 1);
958         pSMB->ByteCount = cpu_to_le16(name_len + 1);
959         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
960                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
961         cifs_stats_inc(&tcon->num_rmdirs);
962         if (rc)
963                 cFYI(1, "Error in RMDir = %d", rc);
964
965         cifs_buf_release(pSMB);
966         if (rc == -EAGAIN)
967                 goto RmDirRetry;
968         return rc;
969 }
970
971 int
972 CIFSSMBMkDir(const int xid, struct cifs_tcon *tcon,
973              const char *name, const struct nls_table *nls_codepage, int remap)
974 {
975         int rc = 0;
976         CREATE_DIRECTORY_REQ *pSMB = NULL;
977         CREATE_DIRECTORY_RSP *pSMBr = NULL;
978         int bytes_returned;
979         int name_len;
980
981         cFYI(1, "In CIFSSMBMkDir");
982 MkDirRetry:
983         rc = smb_init(SMB_COM_CREATE_DIRECTORY, 0, tcon, (void **) &pSMB,
984                       (void **) &pSMBr);
985         if (rc)
986                 return rc;
987
988         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
989                 name_len = cifsConvertToUCS((__le16 *) pSMB->DirName, name,
990                                             PATH_MAX, nls_codepage, remap);
991                 name_len++;     /* trailing null */
992                 name_len *= 2;
993         } else {                /* BB improve check for buffer overruns BB */
994                 name_len = strnlen(name, PATH_MAX);
995                 name_len++;     /* trailing null */
996                 strncpy(pSMB->DirName, name, name_len);
997         }
998
999         pSMB->BufferFormat = 0x04;
1000         inc_rfc1001_len(pSMB, name_len + 1);
1001         pSMB->ByteCount = cpu_to_le16(name_len + 1);
1002         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
1003                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
1004         cifs_stats_inc(&tcon->num_mkdirs);
1005         if (rc)
1006                 cFYI(1, "Error in Mkdir = %d", rc);
1007
1008         cifs_buf_release(pSMB);
1009         if (rc == -EAGAIN)
1010                 goto MkDirRetry;
1011         return rc;
1012 }
1013
1014 int
1015 CIFSPOSIXCreate(const int xid, struct cifs_tcon *tcon, __u32 posix_flags,
1016                 __u64 mode, __u16 *netfid, FILE_UNIX_BASIC_INFO *pRetData,
1017                 __u32 *pOplock, const char *name,
1018                 const struct nls_table *nls_codepage, int remap)
1019 {
1020         TRANSACTION2_SPI_REQ *pSMB = NULL;
1021         TRANSACTION2_SPI_RSP *pSMBr = NULL;
1022         int name_len;
1023         int rc = 0;
1024         int bytes_returned = 0;
1025         __u16 params, param_offset, offset, byte_count, count;
1026         OPEN_PSX_REQ *pdata;
1027         OPEN_PSX_RSP *psx_rsp;
1028
1029         cFYI(1, "In POSIX Create");
1030 PsxCreat:
1031         rc = smb_init(SMB_COM_TRANSACTION2, 15, tcon, (void **) &pSMB,
1032                       (void **) &pSMBr);
1033         if (rc)
1034                 return rc;
1035
1036         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
1037                 name_len =
1038                     cifsConvertToUCS((__le16 *) pSMB->FileName, name,
1039                                      PATH_MAX, nls_codepage, remap);
1040                 name_len++;     /* trailing null */
1041                 name_len *= 2;
1042         } else {        /* BB improve the check for buffer overruns BB */
1043                 name_len = strnlen(name, PATH_MAX);
1044                 name_len++;     /* trailing null */
1045                 strncpy(pSMB->FileName, name, name_len);
1046         }
1047
1048         params = 6 + name_len;
1049         count = sizeof(OPEN_PSX_REQ);
1050         pSMB->MaxParameterCount = cpu_to_le16(2);
1051         pSMB->MaxDataCount = cpu_to_le16(1000); /* large enough */
1052         pSMB->MaxSetupCount = 0;
1053         pSMB->Reserved = 0;
1054         pSMB->Flags = 0;
1055         pSMB->Timeout = 0;
1056         pSMB->Reserved2 = 0;
1057         param_offset = offsetof(struct smb_com_transaction2_spi_req,
1058                                 InformationLevel) - 4;
1059         offset = param_offset + params;
1060         pdata = (OPEN_PSX_REQ *)(((char *)&pSMB->hdr.Protocol) + offset);
1061         pdata->Level = cpu_to_le16(SMB_QUERY_FILE_UNIX_BASIC);
1062         pdata->Permissions = cpu_to_le64(mode);
1063         pdata->PosixOpenFlags = cpu_to_le32(posix_flags);
1064         pdata->OpenFlags =  cpu_to_le32(*pOplock);
1065         pSMB->ParameterOffset = cpu_to_le16(param_offset);
1066         pSMB->DataOffset = cpu_to_le16(offset);
1067         pSMB->SetupCount = 1;
1068         pSMB->Reserved3 = 0;
1069         pSMB->SubCommand = cpu_to_le16(TRANS2_SET_PATH_INFORMATION);
1070         byte_count = 3 /* pad */  + params + count;
1071
1072         pSMB->DataCount = cpu_to_le16(count);
1073         pSMB->ParameterCount = cpu_to_le16(params);
1074         pSMB->TotalDataCount = pSMB->DataCount;
1075         pSMB->TotalParameterCount = pSMB->ParameterCount;
1076         pSMB->InformationLevel = cpu_to_le16(SMB_POSIX_OPEN);
1077         pSMB->Reserved4 = 0;
1078         inc_rfc1001_len(pSMB, byte_count);
1079         pSMB->ByteCount = cpu_to_le16(byte_count);
1080         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
1081                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
1082         if (rc) {
1083                 cFYI(1, "Posix create returned %d", rc);
1084                 goto psx_create_err;
1085         }
1086
1087         cFYI(1, "copying inode info");
1088         rc = validate_t2((struct smb_t2_rsp *)pSMBr);
1089
1090         if (rc || get_bcc(&pSMBr->hdr) < sizeof(OPEN_PSX_RSP)) {
1091                 rc = -EIO;      /* bad smb */
1092                 goto psx_create_err;
1093         }
1094
1095         /* copy return information to pRetData */
1096         psx_rsp = (OPEN_PSX_RSP *)((char *) &pSMBr->hdr.Protocol
1097                         + le16_to_cpu(pSMBr->t2.DataOffset));
1098
1099         *pOplock = le16_to_cpu(psx_rsp->OplockFlags);
1100         if (netfid)
1101                 *netfid = psx_rsp->Fid;   /* cifs fid stays in le */
1102         /* Let caller know file was created so we can set the mode. */
1103         /* Do we care about the CreateAction in any other cases? */
1104         if (cpu_to_le32(FILE_CREATE) == psx_rsp->CreateAction)
1105                 *pOplock |= CIFS_CREATE_ACTION;
1106         /* check to make sure response data is there */
1107         if (psx_rsp->ReturnedLevel != cpu_to_le16(SMB_QUERY_FILE_UNIX_BASIC)) {
1108                 pRetData->Type = cpu_to_le32(-1); /* unknown */
1109                 cFYI(DBG2, "unknown type");
1110         } else {
1111                 if (get_bcc(&pSMBr->hdr) < sizeof(OPEN_PSX_RSP)
1112                                         + sizeof(FILE_UNIX_BASIC_INFO)) {
1113                         cERROR(1, "Open response data too small");
1114                         pRetData->Type = cpu_to_le32(-1);
1115                         goto psx_create_err;
1116                 }
1117                 memcpy((char *) pRetData,
1118                         (char *)psx_rsp + sizeof(OPEN_PSX_RSP),
1119                         sizeof(FILE_UNIX_BASIC_INFO));
1120         }
1121
1122 psx_create_err:
1123         cifs_buf_release(pSMB);
1124
1125         if (posix_flags & SMB_O_DIRECTORY)
1126                 cifs_stats_inc(&tcon->num_posixmkdirs);
1127         else
1128                 cifs_stats_inc(&tcon->num_posixopens);
1129
1130         if (rc == -EAGAIN)
1131                 goto PsxCreat;
1132
1133         return rc;
1134 }
1135
1136 static __u16 convert_disposition(int disposition)
1137 {
1138         __u16 ofun = 0;
1139
1140         switch (disposition) {
1141                 case FILE_SUPERSEDE:
1142                         ofun = SMBOPEN_OCREATE | SMBOPEN_OTRUNC;
1143                         break;
1144                 case FILE_OPEN:
1145                         ofun = SMBOPEN_OAPPEND;
1146                         break;
1147                 case FILE_CREATE:
1148                         ofun = SMBOPEN_OCREATE;
1149                         break;
1150                 case FILE_OPEN_IF:
1151                         ofun = SMBOPEN_OCREATE | SMBOPEN_OAPPEND;
1152                         break;
1153                 case FILE_OVERWRITE:
1154                         ofun = SMBOPEN_OTRUNC;
1155                         break;
1156                 case FILE_OVERWRITE_IF:
1157                         ofun = SMBOPEN_OCREATE | SMBOPEN_OTRUNC;
1158                         break;
1159                 default:
1160                         cFYI(1, "unknown disposition %d", disposition);
1161                         ofun =  SMBOPEN_OAPPEND; /* regular open */
1162         }
1163         return ofun;
1164 }
1165
1166 static int
1167 access_flags_to_smbopen_mode(const int access_flags)
1168 {
1169         int masked_flags = access_flags & (GENERIC_READ | GENERIC_WRITE);
1170
1171         if (masked_flags == GENERIC_READ)
1172                 return SMBOPEN_READ;
1173         else if (masked_flags == GENERIC_WRITE)
1174                 return SMBOPEN_WRITE;
1175
1176         /* just go for read/write */
1177         return SMBOPEN_READWRITE;
1178 }
1179
1180 int
1181 SMBLegacyOpen(const int xid, struct cifs_tcon *tcon,
1182             const char *fileName, const int openDisposition,
1183             const int access_flags, const int create_options, __u16 *netfid,
1184             int *pOplock, FILE_ALL_INFO *pfile_info,
1185             const struct nls_table *nls_codepage, int remap)
1186 {
1187         int rc = -EACCES;
1188         OPENX_REQ *pSMB = NULL;
1189         OPENX_RSP *pSMBr = NULL;
1190         int bytes_returned;
1191         int name_len;
1192         __u16 count;
1193
1194 OldOpenRetry:
1195         rc = smb_init(SMB_COM_OPEN_ANDX, 15, tcon, (void **) &pSMB,
1196                       (void **) &pSMBr);
1197         if (rc)
1198                 return rc;
1199
1200         pSMB->AndXCommand = 0xFF;       /* none */
1201
1202         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
1203                 count = 1;      /* account for one byte pad to word boundary */
1204                 name_len =
1205                    cifsConvertToUCS((__le16 *) (pSMB->fileName + 1),
1206                                     fileName, PATH_MAX, nls_codepage, remap);
1207                 name_len++;     /* trailing null */
1208                 name_len *= 2;
1209         } else {                /* BB improve check for buffer overruns BB */
1210                 count = 0;      /* no pad */
1211                 name_len = strnlen(fileName, PATH_MAX);
1212                 name_len++;     /* trailing null */
1213                 strncpy(pSMB->fileName, fileName, name_len);
1214         }
1215         if (*pOplock & REQ_OPLOCK)
1216                 pSMB->OpenFlags = cpu_to_le16(REQ_OPLOCK);
1217         else if (*pOplock & REQ_BATCHOPLOCK)
1218                 pSMB->OpenFlags = cpu_to_le16(REQ_BATCHOPLOCK);
1219
1220         pSMB->OpenFlags |= cpu_to_le16(REQ_MORE_INFO);
1221         pSMB->Mode = cpu_to_le16(access_flags_to_smbopen_mode(access_flags));
1222         pSMB->Mode |= cpu_to_le16(0x40); /* deny none */
1223         /* set file as system file if special file such
1224            as fifo and server expecting SFU style and
1225            no Unix extensions */
1226
1227         if (create_options & CREATE_OPTION_SPECIAL)
1228                 pSMB->FileAttributes = cpu_to_le16(ATTR_SYSTEM);
1229         else /* BB FIXME BB */
1230                 pSMB->FileAttributes = cpu_to_le16(0/*ATTR_NORMAL*/);
1231
1232         if (create_options & CREATE_OPTION_READONLY)
1233                 pSMB->FileAttributes |= cpu_to_le16(ATTR_READONLY);
1234
1235         /* BB FIXME BB */
1236 /*      pSMB->CreateOptions = cpu_to_le32(create_options &
1237                                                  CREATE_OPTIONS_MASK); */
1238         /* BB FIXME END BB */
1239
1240         pSMB->Sattr = cpu_to_le16(ATTR_HIDDEN | ATTR_SYSTEM | ATTR_DIRECTORY);
1241         pSMB->OpenFunction = cpu_to_le16(convert_disposition(openDisposition));
1242         count += name_len;
1243         inc_rfc1001_len(pSMB, count);
1244
1245         pSMB->ByteCount = cpu_to_le16(count);
1246         /* long_op set to 1 to allow for oplock break timeouts */
1247         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
1248                         (struct smb_hdr *)pSMBr, &bytes_returned, 0);
1249         cifs_stats_inc(&tcon->num_opens);
1250         if (rc) {
1251                 cFYI(1, "Error in Open = %d", rc);
1252         } else {
1253         /* BB verify if wct == 15 */
1254
1255 /*              *pOplock = pSMBr->OplockLevel; */ /* BB take from action field*/
1256
1257                 *netfid = pSMBr->Fid;   /* cifs fid stays in le */
1258                 /* Let caller know file was created so we can set the mode. */
1259                 /* Do we care about the CreateAction in any other cases? */
1260         /* BB FIXME BB */
1261 /*              if (cpu_to_le32(FILE_CREATE) == pSMBr->CreateAction)
1262                         *pOplock |= CIFS_CREATE_ACTION; */
1263         /* BB FIXME END */
1264
1265                 if (pfile_info) {
1266                         pfile_info->CreationTime = 0; /* BB convert CreateTime*/
1267                         pfile_info->LastAccessTime = 0; /* BB fixme */
1268                         pfile_info->LastWriteTime = 0; /* BB fixme */
1269                         pfile_info->ChangeTime = 0;  /* BB fixme */
1270                         pfile_info->Attributes =
1271                                 cpu_to_le32(le16_to_cpu(pSMBr->FileAttributes));
1272                         /* the file_info buf is endian converted by caller */
1273                         pfile_info->AllocationSize =
1274                                 cpu_to_le64(le32_to_cpu(pSMBr->EndOfFile));
1275                         pfile_info->EndOfFile = pfile_info->AllocationSize;
1276                         pfile_info->NumberOfLinks = cpu_to_le32(1);
1277                         pfile_info->DeletePending = 0;
1278                 }
1279         }
1280
1281         cifs_buf_release(pSMB);
1282         if (rc == -EAGAIN)
1283                 goto OldOpenRetry;
1284         return rc;
1285 }
1286
1287 int
1288 CIFSSMBOpen(const int xid, struct cifs_tcon *tcon,
1289             const char *fileName, const int openDisposition,
1290             const int access_flags, const int create_options, __u16 *netfid,
1291             int *pOplock, FILE_ALL_INFO *pfile_info,
1292             const struct nls_table *nls_codepage, int remap)
1293 {
1294         int rc = -EACCES;
1295         OPEN_REQ *pSMB = NULL;
1296         OPEN_RSP *pSMBr = NULL;
1297         int bytes_returned;
1298         int name_len;
1299         __u16 count;
1300
1301 openRetry:
1302         rc = smb_init(SMB_COM_NT_CREATE_ANDX, 24, tcon, (void **) &pSMB,
1303                       (void **) &pSMBr);
1304         if (rc)
1305                 return rc;
1306
1307         pSMB->AndXCommand = 0xFF;       /* none */
1308
1309         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
1310                 count = 1;      /* account for one byte pad to word boundary */
1311                 name_len =
1312                     cifsConvertToUCS((__le16 *) (pSMB->fileName + 1),
1313                                      fileName, PATH_MAX, nls_codepage, remap);
1314                 name_len++;     /* trailing null */
1315                 name_len *= 2;
1316                 pSMB->NameLength = cpu_to_le16(name_len);
1317         } else {                /* BB improve check for buffer overruns BB */
1318                 count = 0;      /* no pad */
1319                 name_len = strnlen(fileName, PATH_MAX);
1320                 name_len++;     /* trailing null */
1321                 pSMB->NameLength = cpu_to_le16(name_len);
1322                 strncpy(pSMB->fileName, fileName, name_len);
1323         }
1324         if (*pOplock & REQ_OPLOCK)
1325                 pSMB->OpenFlags = cpu_to_le32(REQ_OPLOCK);
1326         else if (*pOplock & REQ_BATCHOPLOCK)
1327                 pSMB->OpenFlags = cpu_to_le32(REQ_BATCHOPLOCK);
1328         pSMB->DesiredAccess = cpu_to_le32(access_flags);
1329         pSMB->AllocationSize = 0;
1330         /* set file as system file if special file such
1331            as fifo and server expecting SFU style and
1332            no Unix extensions */
1333         if (create_options & CREATE_OPTION_SPECIAL)
1334                 pSMB->FileAttributes = cpu_to_le32(ATTR_SYSTEM);
1335         else
1336                 pSMB->FileAttributes = cpu_to_le32(ATTR_NORMAL);
1337
1338         /* XP does not handle ATTR_POSIX_SEMANTICS */
1339         /* but it helps speed up case sensitive checks for other
1340         servers such as Samba */
1341         if (tcon->ses->capabilities & CAP_UNIX)
1342                 pSMB->FileAttributes |= cpu_to_le32(ATTR_POSIX_SEMANTICS);
1343
1344         if (create_options & CREATE_OPTION_READONLY)
1345                 pSMB->FileAttributes |= cpu_to_le32(ATTR_READONLY);
1346
1347         pSMB->ShareAccess = cpu_to_le32(FILE_SHARE_ALL);
1348         pSMB->CreateDisposition = cpu_to_le32(openDisposition);
1349         pSMB->CreateOptions = cpu_to_le32(create_options & CREATE_OPTIONS_MASK);
1350         /* BB Expirement with various impersonation levels and verify */
1351         pSMB->ImpersonationLevel = cpu_to_le32(SECURITY_IMPERSONATION);
1352         pSMB->SecurityFlags =
1353             SECURITY_CONTEXT_TRACKING | SECURITY_EFFECTIVE_ONLY;
1354
1355         count += name_len;
1356         inc_rfc1001_len(pSMB, count);
1357
1358         pSMB->ByteCount = cpu_to_le16(count);
1359         /* long_op set to 1 to allow for oplock break timeouts */
1360         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
1361                         (struct smb_hdr *)pSMBr, &bytes_returned, 0);
1362         cifs_stats_inc(&tcon->num_opens);
1363         if (rc) {
1364                 cFYI(1, "Error in Open = %d", rc);
1365         } else {
1366                 *pOplock = pSMBr->OplockLevel; /* 1 byte no need to le_to_cpu */
1367                 *netfid = pSMBr->Fid;   /* cifs fid stays in le */
1368                 /* Let caller know file was created so we can set the mode. */
1369                 /* Do we care about the CreateAction in any other cases? */
1370                 if (cpu_to_le32(FILE_CREATE) == pSMBr->CreateAction)
1371                         *pOplock |= CIFS_CREATE_ACTION;
1372                 if (pfile_info) {
1373                         memcpy((char *)pfile_info, (char *)&pSMBr->CreationTime,
1374                                 36 /* CreationTime to Attributes */);
1375                         /* the file_info buf is endian converted by caller */
1376                         pfile_info->AllocationSize = pSMBr->AllocationSize;
1377                         pfile_info->EndOfFile = pSMBr->EndOfFile;
1378                         pfile_info->NumberOfLinks = cpu_to_le32(1);
1379                         pfile_info->DeletePending = 0;
1380                 }
1381         }
1382
1383         cifs_buf_release(pSMB);
1384         if (rc == -EAGAIN)
1385                 goto openRetry;
1386         return rc;
1387 }
1388
1389 struct cifs_readdata *
1390 cifs_readdata_alloc(unsigned int nr_pages)
1391 {
1392         struct cifs_readdata *rdata;
1393
1394         /* readdata + 1 kvec for each page */
1395         rdata = kzalloc(sizeof(*rdata) +
1396                         sizeof(struct kvec) * nr_pages, GFP_KERNEL);
1397         if (rdata != NULL) {
1398                 INIT_WORK(&rdata->work, cifs_readv_complete);
1399                 INIT_LIST_HEAD(&rdata->pages);
1400         }
1401         return rdata;
1402 }
1403
1404 void
1405 cifs_readdata_free(struct cifs_readdata *rdata)
1406 {
1407         cifsFileInfo_put(rdata->cfile);
1408         kfree(rdata);
1409 }
1410
1411 /*
1412  * Discard any remaining data in the current SMB. To do this, we borrow the
1413  * current bigbuf.
1414  */
1415 static int
1416 cifs_readv_discard(struct TCP_Server_Info *server, struct mid_q_entry *mid)
1417 {
1418         READ_RSP *rsp = (READ_RSP *)server->smallbuf;
1419         unsigned int rfclen = be32_to_cpu(rsp->hdr.smb_buf_length);
1420         int remaining = rfclen + 4 - server->total_read;
1421         struct cifs_readdata *rdata = mid->callback_data;
1422
1423         while (remaining > 0) {
1424                 int length;
1425
1426                 length = cifs_read_from_socket(server, server->bigbuf,
1427                                 min_t(unsigned int, remaining,
1428                                         CIFSMaxBufSize + MAX_CIFS_HDR_SIZE));
1429                 if (length < 0)
1430                         return length;
1431                 server->total_read += length;
1432                 remaining -= length;
1433         }
1434
1435         dequeue_mid(mid, rdata->result);
1436         return 0;
1437 }
1438
1439 static int
1440 cifs_readv_receive(struct TCP_Server_Info *server, struct mid_q_entry *mid)
1441 {
1442         int length, len;
1443         unsigned int data_offset, remaining, data_len;
1444         struct cifs_readdata *rdata = mid->callback_data;
1445         READ_RSP *rsp = (READ_RSP *)server->smallbuf;
1446         unsigned int rfclen = be32_to_cpu(rsp->hdr.smb_buf_length) + 4;
1447         u64 eof;
1448         pgoff_t eof_index;
1449         struct page *page, *tpage;
1450
1451         cFYI(1, "%s: mid=%u offset=%llu bytes=%u", __func__,
1452                 mid->mid, rdata->offset, rdata->bytes);
1453
1454         /*
1455          * read the rest of READ_RSP header (sans Data array), or whatever we
1456          * can if there's not enough data. At this point, we've read down to
1457          * the Mid.
1458          */
1459         len = min_t(unsigned int, rfclen, sizeof(*rsp)) -
1460                         sizeof(struct smb_hdr) + 1;
1461
1462         rdata->iov[0].iov_base = server->smallbuf + sizeof(struct smb_hdr) - 1;
1463         rdata->iov[0].iov_len = len;
1464
1465         length = cifs_readv_from_socket(server, rdata->iov, 1, len);
1466         if (length < 0)
1467                 return length;
1468         server->total_read += length;
1469
1470         /* Was the SMB read successful? */
1471         rdata->result = map_smb_to_linux_error(&rsp->hdr, false);
1472         if (rdata->result != 0) {
1473                 cFYI(1, "%s: server returned error %d", __func__,
1474                         rdata->result);
1475                 return cifs_readv_discard(server, mid);
1476         }
1477
1478         /* Is there enough to get to the rest of the READ_RSP header? */
1479         if (server->total_read < sizeof(READ_RSP)) {
1480                 cFYI(1, "%s: server returned short header. got=%u expected=%zu",
1481                         __func__, server->total_read, sizeof(READ_RSP));
1482                 rdata->result = -EIO;
1483                 return cifs_readv_discard(server, mid);
1484         }
1485
1486         data_offset = le16_to_cpu(rsp->DataOffset) + 4;
1487         if (data_offset < server->total_read) {
1488                 /*
1489                  * win2k8 sometimes sends an offset of 0 when the read
1490                  * is beyond the EOF. Treat it as if the data starts just after
1491                  * the header.
1492                  */
1493                 cFYI(1, "%s: data offset (%u) inside read response header",
1494                         __func__, data_offset);
1495                 data_offset = server->total_read;
1496         } else if (data_offset > MAX_CIFS_SMALL_BUFFER_SIZE) {
1497                 /* data_offset is beyond the end of smallbuf */
1498                 cFYI(1, "%s: data offset (%u) beyond end of smallbuf",
1499                         __func__, data_offset);
1500                 rdata->result = -EIO;
1501                 return cifs_readv_discard(server, mid);
1502         }
1503
1504         cFYI(1, "%s: total_read=%u data_offset=%u", __func__,
1505                 server->total_read, data_offset);
1506
1507         len = data_offset - server->total_read;
1508         if (len > 0) {
1509                 /* read any junk before data into the rest of smallbuf */
1510                 rdata->iov[0].iov_base = server->smallbuf + server->total_read;
1511                 rdata->iov[0].iov_len = len;
1512                 length = cifs_readv_from_socket(server, rdata->iov, 1, len);
1513                 if (length < 0)
1514                         return length;
1515                 server->total_read += length;
1516         }
1517
1518         /* set up first iov for signature check */
1519         rdata->iov[0].iov_base = server->smallbuf;
1520         rdata->iov[0].iov_len = server->total_read;
1521         cFYI(1, "0: iov_base=%p iov_len=%zu",
1522                 rdata->iov[0].iov_base, rdata->iov[0].iov_len);
1523
1524         /* how much data is in the response? */
1525         data_len = le16_to_cpu(rsp->DataLengthHigh) << 16;
1526         data_len += le16_to_cpu(rsp->DataLength);
1527         if (data_offset + data_len > rfclen) {
1528                 /* data_len is corrupt -- discard frame */
1529                 rdata->result = -EIO;
1530                 return cifs_readv_discard(server, mid);
1531         }
1532
1533         /* marshal up the page array */
1534         len = 0;
1535         remaining = data_len;
1536         rdata->nr_iov = 1;
1537
1538         /* determine the eof that the server (probably) has */
1539         eof = CIFS_I(rdata->mapping->host)->server_eof;
1540         eof_index = eof ? (eof - 1) >> PAGE_CACHE_SHIFT : 0;
1541         cFYI(1, "eof=%llu eof_index=%lu", eof, eof_index);
1542
1543         list_for_each_entry_safe(page, tpage, &rdata->pages, lru) {
1544                 if (remaining >= PAGE_CACHE_SIZE) {
1545                         /* enough data to fill the page */
1546                         rdata->iov[rdata->nr_iov].iov_base = kmap(page);
1547                         rdata->iov[rdata->nr_iov].iov_len = PAGE_CACHE_SIZE;
1548                         cFYI(1, "%u: idx=%lu iov_base=%p iov_len=%zu",
1549                                 rdata->nr_iov, page->index,
1550                                 rdata->iov[rdata->nr_iov].iov_base,
1551                                 rdata->iov[rdata->nr_iov].iov_len);
1552                         ++rdata->nr_iov;
1553                         len += PAGE_CACHE_SIZE;
1554                         remaining -= PAGE_CACHE_SIZE;
1555                 } else if (remaining > 0) {
1556                         /* enough for partial page, fill and zero the rest */
1557                         rdata->iov[rdata->nr_iov].iov_base = kmap(page);
1558                         rdata->iov[rdata->nr_iov].iov_len = remaining;
1559                         cFYI(1, "%u: idx=%lu iov_base=%p iov_len=%zu",
1560                                 rdata->nr_iov, page->index,
1561                                 rdata->iov[rdata->nr_iov].iov_base,
1562                                 rdata->iov[rdata->nr_iov].iov_len);
1563                         memset(rdata->iov[rdata->nr_iov].iov_base + remaining,
1564                                 '\0', PAGE_CACHE_SIZE - remaining);
1565                         ++rdata->nr_iov;
1566                         len += remaining;
1567                         remaining = 0;
1568                 } else if (page->index > eof_index) {
1569                         /*
1570                          * The VFS will not try to do readahead past the
1571                          * i_size, but it's possible that we have outstanding
1572                          * writes with gaps in the middle and the i_size hasn't
1573                          * caught up yet. Populate those with zeroed out pages
1574                          * to prevent the VFS from repeatedly attempting to
1575                          * fill them until the writes are flushed.
1576                          */
1577                         zero_user(page, 0, PAGE_CACHE_SIZE);
1578                         list_del(&page->lru);
1579                         lru_cache_add_file(page);
1580                         flush_dcache_page(page);
1581                         SetPageUptodate(page);
1582                         unlock_page(page);
1583                         page_cache_release(page);
1584                 } else {
1585                         /* no need to hold page hostage */
1586                         list_del(&page->lru);
1587                         lru_cache_add_file(page);
1588                         unlock_page(page);
1589                         page_cache_release(page);
1590                 }
1591         }
1592
1593         /* issue the read if we have any iovecs left to fill */
1594         if (rdata->nr_iov > 1) {
1595                 length = cifs_readv_from_socket(server, &rdata->iov[1],
1596                                                 rdata->nr_iov - 1, len);
1597                 if (length < 0)
1598                         return length;
1599                 server->total_read += length;
1600         } else {
1601                 length = 0;
1602         }
1603
1604         rdata->bytes = length;
1605
1606         cFYI(1, "total_read=%u rfclen=%u remaining=%u", server->total_read,
1607                 rfclen, remaining);
1608
1609         /* discard anything left over */
1610         if (server->total_read < rfclen)
1611                 return cifs_readv_discard(server, mid);
1612
1613         dequeue_mid(mid, false);
1614         return length;
1615 }
1616
1617 static void
1618 cifs_readv_complete(struct work_struct *work)
1619 {
1620         struct cifs_readdata *rdata = container_of(work,
1621                                                 struct cifs_readdata, work);
1622         struct page *page, *tpage;
1623
1624         list_for_each_entry_safe(page, tpage, &rdata->pages, lru) {
1625                 list_del(&page->lru);
1626                 lru_cache_add_file(page);
1627
1628                 if (rdata->result == 0) {
1629                         kunmap(page);
1630                         flush_dcache_page(page);
1631                         SetPageUptodate(page);
1632                 }
1633
1634                 unlock_page(page);
1635
1636                 if (rdata->result == 0)
1637                         cifs_readpage_to_fscache(rdata->mapping->host, page);
1638
1639                 page_cache_release(page);
1640         }
1641         cifs_readdata_free(rdata);
1642 }
1643
1644 static void
1645 cifs_readv_callback(struct mid_q_entry *mid)
1646 {
1647         struct cifs_readdata *rdata = mid->callback_data;
1648         struct cifs_tcon *tcon = tlink_tcon(rdata->cfile->tlink);
1649         struct TCP_Server_Info *server = tcon->ses->server;
1650
1651         cFYI(1, "%s: mid=%u state=%d result=%d bytes=%u", __func__,
1652                 mid->mid, mid->midState, rdata->result, rdata->bytes);
1653
1654         switch (mid->midState) {
1655         case MID_RESPONSE_RECEIVED:
1656                 /* result already set, check signature */
1657                 if (server->sec_mode &
1658                     (SECMODE_SIGN_REQUIRED | SECMODE_SIGN_ENABLED)) {
1659                         if (cifs_verify_signature(rdata->iov, rdata->nr_iov,
1660                                           server, mid->sequence_number + 1))
1661                                 cERROR(1, "Unexpected SMB signature");
1662                 }
1663                 /* FIXME: should this be counted toward the initiating task? */
1664                 task_io_account_read(rdata->bytes);
1665                 cifs_stats_bytes_read(tcon, rdata->bytes);
1666                 break;
1667         case MID_REQUEST_SUBMITTED:
1668         case MID_RETRY_NEEDED:
1669                 rdata->result = -EAGAIN;
1670                 break;
1671         default:
1672                 rdata->result = -EIO;
1673         }
1674
1675         queue_work(system_nrt_wq, &rdata->work);
1676         DeleteMidQEntry(mid);
1677         atomic_dec(&server->inFlight);
1678         wake_up(&server->request_q);
1679 }
1680
1681 /* cifs_async_readv - send an async write, and set up mid to handle result */
1682 int
1683 cifs_async_readv(struct cifs_readdata *rdata)
1684 {
1685         int rc;
1686         READ_REQ *smb = NULL;
1687         int wct;
1688         struct cifs_tcon *tcon = tlink_tcon(rdata->cfile->tlink);
1689
1690         cFYI(1, "%s: offset=%llu bytes=%u", __func__,
1691                 rdata->offset, rdata->bytes);
1692
1693         if (tcon->ses->capabilities & CAP_LARGE_FILES)
1694                 wct = 12;
1695         else {
1696                 wct = 10; /* old style read */
1697                 if ((rdata->offset >> 32) > 0)  {
1698                         /* can not handle this big offset for old */
1699                         return -EIO;
1700                 }
1701         }
1702
1703         rc = small_smb_init(SMB_COM_READ_ANDX, wct, tcon, (void **)&smb);
1704         if (rc)
1705                 return rc;
1706
1707         smb->hdr.Pid = cpu_to_le16((__u16)rdata->pid);
1708         smb->hdr.PidHigh = cpu_to_le16((__u16)(rdata->pid >> 16));
1709
1710         smb->AndXCommand = 0xFF;        /* none */
1711         smb->Fid = rdata->cfile->netfid;
1712         smb->OffsetLow = cpu_to_le32(rdata->offset & 0xFFFFFFFF);
1713         if (wct == 12)
1714                 smb->OffsetHigh = cpu_to_le32(rdata->offset >> 32);
1715         smb->Remaining = 0;
1716         smb->MaxCount = cpu_to_le16(rdata->bytes & 0xFFFF);
1717         smb->MaxCountHigh = cpu_to_le32(rdata->bytes >> 16);
1718         if (wct == 12)
1719                 smb->ByteCount = 0;
1720         else {
1721                 /* old style read */
1722                 struct smb_com_readx_req *smbr =
1723                         (struct smb_com_readx_req *)smb;
1724                 smbr->ByteCount = 0;
1725         }
1726
1727         /* 4 for RFC1001 length + 1 for BCC */
1728         rdata->iov[0].iov_base = smb;
1729         rdata->iov[0].iov_len = be32_to_cpu(smb->hdr.smb_buf_length) + 4;
1730
1731         rc = cifs_call_async(tcon->ses->server, rdata->iov, 1,
1732                              cifs_readv_receive, cifs_readv_callback,
1733                              rdata, false);
1734
1735         if (rc == 0)
1736                 cifs_stats_inc(&tcon->num_reads);
1737
1738         cifs_small_buf_release(smb);
1739         return rc;
1740 }
1741
1742 int
1743 CIFSSMBRead(const int xid, struct cifs_io_parms *io_parms, unsigned int *nbytes,
1744             char **buf, int *pbuf_type)
1745 {
1746         int rc = -EACCES;
1747         READ_REQ *pSMB = NULL;
1748         READ_RSP *pSMBr = NULL;
1749         char *pReadData = NULL;
1750         int wct;
1751         int resp_buf_type = 0;
1752         struct kvec iov[1];
1753         __u32 pid = io_parms->pid;
1754         __u16 netfid = io_parms->netfid;
1755         __u64 offset = io_parms->offset;
1756         struct cifs_tcon *tcon = io_parms->tcon;
1757         unsigned int count = io_parms->length;
1758
1759         cFYI(1, "Reading %d bytes on fid %d", count, netfid);
1760         if (tcon->ses->capabilities & CAP_LARGE_FILES)
1761                 wct = 12;
1762         else {
1763                 wct = 10; /* old style read */
1764                 if ((offset >> 32) > 0)  {
1765                         /* can not handle this big offset for old */
1766                         return -EIO;
1767                 }
1768         }
1769
1770         *nbytes = 0;
1771         rc = small_smb_init(SMB_COM_READ_ANDX, wct, tcon, (void **) &pSMB);
1772         if (rc)
1773                 return rc;
1774
1775         pSMB->hdr.Pid = cpu_to_le16((__u16)pid);
1776         pSMB->hdr.PidHigh = cpu_to_le16((__u16)(pid >> 16));
1777
1778         /* tcon and ses pointer are checked in smb_init */
1779         if (tcon->ses->server == NULL)
1780                 return -ECONNABORTED;
1781
1782         pSMB->AndXCommand = 0xFF;       /* none */
1783         pSMB->Fid = netfid;
1784         pSMB->OffsetLow = cpu_to_le32(offset & 0xFFFFFFFF);
1785         if (wct == 12)
1786                 pSMB->OffsetHigh = cpu_to_le32(offset >> 32);
1787
1788         pSMB->Remaining = 0;
1789         pSMB->MaxCount = cpu_to_le16(count & 0xFFFF);
1790         pSMB->MaxCountHigh = cpu_to_le32(count >> 16);
1791         if (wct == 12)
1792                 pSMB->ByteCount = 0;  /* no need to do le conversion since 0 */
1793         else {
1794                 /* old style read */
1795                 struct smb_com_readx_req *pSMBW =
1796                         (struct smb_com_readx_req *)pSMB;
1797                 pSMBW->ByteCount = 0;
1798         }
1799
1800         iov[0].iov_base = (char *)pSMB;
1801         iov[0].iov_len = be32_to_cpu(pSMB->hdr.smb_buf_length) + 4;
1802         rc = SendReceive2(xid, tcon->ses, iov, 1 /* num iovecs */,
1803                          &resp_buf_type, CIFS_LOG_ERROR);
1804         cifs_stats_inc(&tcon->num_reads);
1805         pSMBr = (READ_RSP *)iov[0].iov_base;
1806         if (rc) {
1807                 cERROR(1, "Send error in read = %d", rc);
1808         } else {
1809                 int data_length = le16_to_cpu(pSMBr->DataLengthHigh);
1810                 data_length = data_length << 16;
1811                 data_length += le16_to_cpu(pSMBr->DataLength);
1812                 *nbytes = data_length;
1813
1814                 /*check that DataLength would not go beyond end of SMB */
1815                 if ((data_length > CIFSMaxBufSize)
1816                                 || (data_length > count)) {
1817                         cFYI(1, "bad length %d for count %d",
1818                                  data_length, count);
1819                         rc = -EIO;
1820                         *nbytes = 0;
1821                 } else {
1822                         pReadData = (char *) (&pSMBr->hdr.Protocol) +
1823                                         le16_to_cpu(pSMBr->DataOffset);
1824 /*                      if (rc = copy_to_user(buf, pReadData, data_length)) {
1825                                 cERROR(1, "Faulting on read rc = %d",rc);
1826                                 rc = -EFAULT;
1827                         }*/ /* can not use copy_to_user when using page cache*/
1828                         if (*buf)
1829                                 memcpy(*buf, pReadData, data_length);
1830                 }
1831         }
1832
1833 /*      cifs_small_buf_release(pSMB); */ /* Freed earlier now in SendReceive2 */
1834         if (*buf) {
1835                 if (resp_buf_type == CIFS_SMALL_BUFFER)
1836                         cifs_small_buf_release(iov[0].iov_base);
1837                 else if (resp_buf_type == CIFS_LARGE_BUFFER)
1838                         cifs_buf_release(iov[0].iov_base);
1839         } else if (resp_buf_type != CIFS_NO_BUFFER) {
1840                 /* return buffer to caller to free */
1841                 *buf = iov[0].iov_base;
1842                 if (resp_buf_type == CIFS_SMALL_BUFFER)
1843                         *pbuf_type = CIFS_SMALL_BUFFER;
1844                 else if (resp_buf_type == CIFS_LARGE_BUFFER)
1845                         *pbuf_type = CIFS_LARGE_BUFFER;
1846         } /* else no valid buffer on return - leave as null */
1847
1848         /* Note: On -EAGAIN error only caller can retry on handle based calls
1849                 since file handle passed in no longer valid */
1850         return rc;
1851 }
1852
1853
1854 int
1855 CIFSSMBWrite(const int xid, struct cifs_io_parms *io_parms,
1856              unsigned int *nbytes, const char *buf,
1857              const char __user *ubuf, const int long_op)
1858 {
1859         int rc = -EACCES;
1860         WRITE_REQ *pSMB = NULL;
1861         WRITE_RSP *pSMBr = NULL;
1862         int bytes_returned, wct;
1863         __u32 bytes_sent;
1864         __u16 byte_count;
1865         __u32 pid = io_parms->pid;
1866         __u16 netfid = io_parms->netfid;
1867         __u64 offset = io_parms->offset;
1868         struct cifs_tcon *tcon = io_parms->tcon;
1869         unsigned int count = io_parms->length;
1870
1871         *nbytes = 0;
1872
1873         /* cFYI(1, "write at %lld %d bytes", offset, count);*/
1874         if (tcon->ses == NULL)
1875                 return -ECONNABORTED;
1876
1877         if (tcon->ses->capabilities & CAP_LARGE_FILES)
1878                 wct = 14;
1879         else {
1880                 wct = 12;
1881                 if ((offset >> 32) > 0) {
1882                         /* can not handle big offset for old srv */
1883                         return -EIO;
1884                 }
1885         }
1886
1887         rc = smb_init(SMB_COM_WRITE_ANDX, wct, tcon, (void **) &pSMB,
1888                       (void **) &pSMBr);
1889         if (rc)
1890                 return rc;
1891
1892         pSMB->hdr.Pid = cpu_to_le16((__u16)pid);
1893         pSMB->hdr.PidHigh = cpu_to_le16((__u16)(pid >> 16));
1894
1895         /* tcon and ses pointer are checked in smb_init */
1896         if (tcon->ses->server == NULL)
1897                 return -ECONNABORTED;
1898
1899         pSMB->AndXCommand = 0xFF;       /* none */
1900         pSMB->Fid = netfid;
1901         pSMB->OffsetLow = cpu_to_le32(offset & 0xFFFFFFFF);
1902         if (wct == 14)
1903                 pSMB->OffsetHigh = cpu_to_le32(offset >> 32);
1904
1905         pSMB->Reserved = 0xFFFFFFFF;
1906         pSMB->WriteMode = 0;
1907         pSMB->Remaining = 0;
1908
1909         /* Can increase buffer size if buffer is big enough in some cases ie we
1910         can send more if LARGE_WRITE_X capability returned by the server and if
1911         our buffer is big enough or if we convert to iovecs on socket writes
1912         and eliminate the copy to the CIFS buffer */
1913         if (tcon->ses->capabilities & CAP_LARGE_WRITE_X) {
1914                 bytes_sent = min_t(const unsigned int, CIFSMaxBufSize, count);
1915         } else {
1916                 bytes_sent = (tcon->ses->server->maxBuf - MAX_CIFS_HDR_SIZE)
1917                          & ~0xFF;
1918         }
1919
1920         if (bytes_sent > count)
1921                 bytes_sent = count;
1922         pSMB->DataOffset =
1923                 cpu_to_le16(offsetof(struct smb_com_write_req, Data) - 4);
1924         if (buf)
1925                 memcpy(pSMB->Data, buf, bytes_sent);
1926         else if (ubuf) {
1927                 if (copy_from_user(pSMB->Data, ubuf, bytes_sent)) {
1928                         cifs_buf_release(pSMB);
1929                         return -EFAULT;
1930                 }
1931         } else if (count != 0) {
1932                 /* No buffer */
1933                 cifs_buf_release(pSMB);
1934                 return -EINVAL;
1935         } /* else setting file size with write of zero bytes */
1936         if (wct == 14)
1937                 byte_count = bytes_sent + 1; /* pad */
1938         else /* wct == 12 */
1939                 byte_count = bytes_sent + 5; /* bigger pad, smaller smb hdr */
1940
1941         pSMB->DataLengthLow = cpu_to_le16(bytes_sent & 0xFFFF);
1942         pSMB->DataLengthHigh = cpu_to_le16(bytes_sent >> 16);
1943         inc_rfc1001_len(pSMB, byte_count);
1944
1945         if (wct == 14)
1946                 pSMB->ByteCount = cpu_to_le16(byte_count);
1947         else { /* old style write has byte count 4 bytes earlier
1948                   so 4 bytes pad  */
1949                 struct smb_com_writex_req *pSMBW =
1950                         (struct smb_com_writex_req *)pSMB;
1951                 pSMBW->ByteCount = cpu_to_le16(byte_count);
1952         }
1953
1954         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
1955                          (struct smb_hdr *) pSMBr, &bytes_returned, long_op);
1956         cifs_stats_inc(&tcon->num_writes);
1957         if (rc) {
1958                 cFYI(1, "Send error in write = %d", rc);
1959         } else {
1960                 *nbytes = le16_to_cpu(pSMBr->CountHigh);
1961                 *nbytes = (*nbytes) << 16;
1962                 *nbytes += le16_to_cpu(pSMBr->Count);
1963
1964                 /*
1965                  * Mask off high 16 bits when bytes written as returned by the
1966                  * server is greater than bytes requested by the client. Some
1967                  * OS/2 servers are known to set incorrect CountHigh values.
1968                  */
1969                 if (*nbytes > count)
1970                         *nbytes &= 0xFFFF;
1971         }
1972
1973         cifs_buf_release(pSMB);
1974
1975         /* Note: On -EAGAIN error only caller can retry on handle based calls
1976                 since file handle passed in no longer valid */
1977
1978         return rc;
1979 }
1980
1981 void
1982 cifs_writedata_release(struct kref *refcount)
1983 {
1984         struct cifs_writedata *wdata = container_of(refcount,
1985                                         struct cifs_writedata, refcount);
1986
1987         if (wdata->cfile)
1988                 cifsFileInfo_put(wdata->cfile);
1989
1990         kfree(wdata);
1991 }
1992
1993 /*
1994  * Write failed with a retryable error. Resend the write request. It's also
1995  * possible that the page was redirtied so re-clean the page.
1996  */
1997 static void
1998 cifs_writev_requeue(struct cifs_writedata *wdata)
1999 {
2000         int i, rc;
2001         struct inode *inode = wdata->cfile->dentry->d_inode;
2002
2003         for (i = 0; i < wdata->nr_pages; i++) {
2004                 lock_page(wdata->pages[i]);
2005                 clear_page_dirty_for_io(wdata->pages[i]);
2006         }
2007
2008         do {
2009                 rc = cifs_async_writev(wdata);
2010         } while (rc == -EAGAIN);
2011
2012         for (i = 0; i < wdata->nr_pages; i++) {
2013                 if (rc != 0)
2014                         SetPageError(wdata->pages[i]);
2015                 unlock_page(wdata->pages[i]);
2016         }
2017
2018         mapping_set_error(inode->i_mapping, rc);
2019         kref_put(&wdata->refcount, cifs_writedata_release);
2020 }
2021
2022 static void
2023 cifs_writev_complete(struct work_struct *work)
2024 {
2025         struct cifs_writedata *wdata = container_of(work,
2026                                                 struct cifs_writedata, work);
2027         struct inode *inode = wdata->cfile->dentry->d_inode;
2028         int i = 0;
2029
2030         if (wdata->result == 0) {
2031                 cifs_update_eof(CIFS_I(inode), wdata->offset, wdata->bytes);
2032                 cifs_stats_bytes_written(tlink_tcon(wdata->cfile->tlink),
2033                                          wdata->bytes);
2034         } else if (wdata->sync_mode == WB_SYNC_ALL && wdata->result == -EAGAIN)
2035                 return cifs_writev_requeue(wdata);
2036
2037         for (i = 0; i < wdata->nr_pages; i++) {
2038                 struct page *page = wdata->pages[i];
2039                 if (wdata->result == -EAGAIN)
2040                         __set_page_dirty_nobuffers(page);
2041                 else if (wdata->result < 0)
2042                         SetPageError(page);
2043                 end_page_writeback(page);
2044                 page_cache_release(page);
2045         }
2046         if (wdata->result != -EAGAIN)
2047                 mapping_set_error(inode->i_mapping, wdata->result);
2048         kref_put(&wdata->refcount, cifs_writedata_release);
2049 }
2050
2051 struct cifs_writedata *
2052 cifs_writedata_alloc(unsigned int nr_pages)
2053 {
2054         struct cifs_writedata *wdata;
2055
2056         /* this would overflow */
2057         if (nr_pages == 0) {
2058                 cERROR(1, "%s: called with nr_pages == 0!", __func__);
2059                 return NULL;
2060         }
2061
2062         /* writedata + number of page pointers */
2063         wdata = kzalloc(sizeof(*wdata) +
2064                         sizeof(struct page *) * (nr_pages - 1), GFP_NOFS);
2065         if (wdata != NULL) {
2066                 INIT_WORK(&wdata->work, cifs_writev_complete);
2067                 kref_init(&wdata->refcount);
2068         }
2069         return wdata;
2070 }
2071
2072 /*
2073  * Check the midState and signature on received buffer (if any), and queue the
2074  * workqueue completion task.
2075  */
2076 static void
2077 cifs_writev_callback(struct mid_q_entry *mid)
2078 {
2079         struct cifs_writedata *wdata = mid->callback_data;
2080         struct cifs_tcon *tcon = tlink_tcon(wdata->cfile->tlink);
2081         unsigned int written;
2082         WRITE_RSP *smb = (WRITE_RSP *)mid->resp_buf;
2083
2084         switch (mid->midState) {
2085         case MID_RESPONSE_RECEIVED:
2086                 wdata->result = cifs_check_receive(mid, tcon->ses->server, 0);
2087                 if (wdata->result != 0)
2088                         break;
2089
2090                 written = le16_to_cpu(smb->CountHigh);
2091                 written <<= 16;
2092                 written += le16_to_cpu(smb->Count);
2093                 /*
2094                  * Mask off high 16 bits when bytes written as returned
2095                  * by the server is greater than bytes requested by the
2096                  * client. OS/2 servers are known to set incorrect
2097                  * CountHigh values.
2098                  */
2099                 if (written > wdata->bytes)
2100                         written &= 0xFFFF;
2101
2102                 if (written < wdata->bytes)
2103                         wdata->result = -ENOSPC;
2104                 else
2105                         wdata->bytes = written;
2106                 break;
2107         case MID_REQUEST_SUBMITTED:
2108         case MID_RETRY_NEEDED:
2109                 wdata->result = -EAGAIN;
2110                 break;
2111         default:
2112                 wdata->result = -EIO;
2113                 break;
2114         }
2115
2116         queue_work(system_nrt_wq, &wdata->work);
2117         DeleteMidQEntry(mid);
2118         atomic_dec(&tcon->ses->server->inFlight);
2119         wake_up(&tcon->ses->server->request_q);
2120 }
2121
2122 /* cifs_async_writev - send an async write, and set up mid to handle result */
2123 int
2124 cifs_async_writev(struct cifs_writedata *wdata)
2125 {
2126         int i, rc = -EACCES;
2127         WRITE_REQ *smb = NULL;
2128         int wct;
2129         struct cifs_tcon *tcon = tlink_tcon(wdata->cfile->tlink);
2130         struct inode *inode = wdata->cfile->dentry->d_inode;
2131         struct kvec *iov = NULL;
2132
2133         if (tcon->ses->capabilities & CAP_LARGE_FILES) {
2134                 wct = 14;
2135         } else {
2136                 wct = 12;
2137                 if (wdata->offset >> 32 > 0) {
2138                         /* can not handle big offset for old srv */
2139                         return -EIO;
2140                 }
2141         }
2142
2143         rc = small_smb_init(SMB_COM_WRITE_ANDX, wct, tcon, (void **)&smb);
2144         if (rc)
2145                 goto async_writev_out;
2146
2147         /* 1 iov per page + 1 for header */
2148         iov = kzalloc((wdata->nr_pages + 1) * sizeof(*iov), GFP_NOFS);
2149         if (iov == NULL) {
2150                 rc = -ENOMEM;
2151                 goto async_writev_out;
2152         }
2153
2154         smb->hdr.Pid = cpu_to_le16((__u16)wdata->cfile->pid);
2155         smb->hdr.PidHigh = cpu_to_le16((__u16)(wdata->cfile->pid >> 16));
2156
2157         smb->AndXCommand = 0xFF;        /* none */
2158         smb->Fid = wdata->cfile->netfid;
2159         smb->OffsetLow = cpu_to_le32(wdata->offset & 0xFFFFFFFF);
2160         if (wct == 14)
2161                 smb->OffsetHigh = cpu_to_le32(wdata->offset >> 32);
2162         smb->Reserved = 0xFFFFFFFF;
2163         smb->WriteMode = 0;
2164         smb->Remaining = 0;
2165
2166         smb->DataOffset =
2167             cpu_to_le16(offsetof(struct smb_com_write_req, Data) - 4);
2168
2169         /* 4 for RFC1001 length + 1 for BCC */
2170         iov[0].iov_len = be32_to_cpu(smb->hdr.smb_buf_length) + 4 + 1;
2171         iov[0].iov_base = smb;
2172
2173         /* marshal up the pages into iov array */
2174         wdata->bytes = 0;
2175         for (i = 0; i < wdata->nr_pages; i++) {
2176                 iov[i + 1].iov_len = min(inode->i_size -
2177                                       page_offset(wdata->pages[i]),
2178                                         (loff_t)PAGE_CACHE_SIZE);
2179                 iov[i + 1].iov_base = kmap(wdata->pages[i]);
2180                 wdata->bytes += iov[i + 1].iov_len;
2181         }
2182
2183         cFYI(1, "async write at %llu %u bytes", wdata->offset, wdata->bytes);
2184
2185         smb->DataLengthLow = cpu_to_le16(wdata->bytes & 0xFFFF);
2186         smb->DataLengthHigh = cpu_to_le16(wdata->bytes >> 16);
2187
2188         if (wct == 14) {
2189                 inc_rfc1001_len(&smb->hdr, wdata->bytes + 1);
2190                 put_bcc(wdata->bytes + 1, &smb->hdr);
2191         } else {
2192                 /* wct == 12 */
2193                 struct smb_com_writex_req *smbw =
2194                                 (struct smb_com_writex_req *)smb;
2195                 inc_rfc1001_len(&smbw->hdr, wdata->bytes + 5);
2196                 put_bcc(wdata->bytes + 5, &smbw->hdr);
2197                 iov[0].iov_len += 4; /* pad bigger by four bytes */
2198         }
2199
2200         kref_get(&wdata->refcount);
2201         rc = cifs_call_async(tcon->ses->server, iov, wdata->nr_pages + 1,
2202                              NULL, cifs_writev_callback, wdata, false);
2203
2204         if (rc == 0)
2205                 cifs_stats_inc(&tcon->num_writes);
2206         else
2207                 kref_put(&wdata->refcount, cifs_writedata_release);
2208
2209         /* send is done, unmap pages */
2210         for (i = 0; i < wdata->nr_pages; i++)
2211                 kunmap(wdata->pages[i]);
2212
2213 async_writev_out:
2214         cifs_small_buf_release(smb);
2215         kfree(iov);
2216         return rc;
2217 }
2218
2219 int
2220 CIFSSMBWrite2(const int xid, struct cifs_io_parms *io_parms,
2221               unsigned int *nbytes, struct kvec *iov, int n_vec,
2222               const int long_op)
2223 {
2224         int rc = -EACCES;
2225         WRITE_REQ *pSMB = NULL;
2226         int wct;
2227         int smb_hdr_len;
2228         int resp_buf_type = 0;
2229         __u32 pid = io_parms->pid;
2230         __u16 netfid = io_parms->netfid;
2231         __u64 offset = io_parms->offset;
2232         struct cifs_tcon *tcon = io_parms->tcon;
2233         unsigned int count = io_parms->length;
2234
2235         *nbytes = 0;
2236
2237         cFYI(1, "write2 at %lld %d bytes", (long long)offset, count);
2238
2239         if (tcon->ses->capabilities & CAP_LARGE_FILES) {
2240                 wct = 14;
2241         } else {
2242                 wct = 12;
2243                 if ((offset >> 32) > 0) {
2244                         /* can not handle big offset for old srv */
2245                         return -EIO;
2246                 }
2247         }
2248         rc = small_smb_init(SMB_COM_WRITE_ANDX, wct, tcon, (void **) &pSMB);
2249         if (rc)
2250                 return rc;
2251
2252         pSMB->hdr.Pid = cpu_to_le16((__u16)pid);
2253         pSMB->hdr.PidHigh = cpu_to_le16((__u16)(pid >> 16));
2254
2255         /* tcon and ses pointer are checked in smb_init */
2256         if (tcon->ses->server == NULL)
2257                 return -ECONNABORTED;
2258
2259         pSMB->AndXCommand = 0xFF;       /* none */
2260         pSMB->Fid = netfid;
2261         pSMB->OffsetLow = cpu_to_le32(offset & 0xFFFFFFFF);
2262         if (wct == 14)
2263                 pSMB->OffsetHigh = cpu_to_le32(offset >> 32);
2264         pSMB->Reserved = 0xFFFFFFFF;
2265         pSMB->WriteMode = 0;
2266         pSMB->Remaining = 0;
2267
2268         pSMB->DataOffset =
2269             cpu_to_le16(offsetof(struct smb_com_write_req, Data) - 4);
2270
2271         pSMB->DataLengthLow = cpu_to_le16(count & 0xFFFF);
2272         pSMB->DataLengthHigh = cpu_to_le16(count >> 16);
2273         /* header + 1 byte pad */
2274         smb_hdr_len = be32_to_cpu(pSMB->hdr.smb_buf_length) + 1;
2275         if (wct == 14)
2276                 inc_rfc1001_len(pSMB, count + 1);
2277         else /* wct == 12 */
2278                 inc_rfc1001_len(pSMB, count + 5); /* smb data starts later */
2279         if (wct == 14)
2280                 pSMB->ByteCount = cpu_to_le16(count + 1);
2281         else /* wct == 12 */ /* bigger pad, smaller smb hdr, keep offset ok */ {
2282                 struct smb_com_writex_req *pSMBW =
2283                                 (struct smb_com_writex_req *)pSMB;
2284                 pSMBW->ByteCount = cpu_to_le16(count + 5);
2285         }
2286         iov[0].iov_base = pSMB;
2287         if (wct == 14)
2288                 iov[0].iov_len = smb_hdr_len + 4;
2289         else /* wct == 12 pad bigger by four bytes */
2290                 iov[0].iov_len = smb_hdr_len + 8;
2291
2292
2293         rc = SendReceive2(xid, tcon->ses, iov, n_vec + 1, &resp_buf_type,
2294                           long_op);
2295         cifs_stats_inc(&tcon->num_writes);
2296         if (rc) {
2297                 cFYI(1, "Send error Write2 = %d", rc);
2298         } else if (resp_buf_type == 0) {
2299                 /* presumably this can not happen, but best to be safe */
2300                 rc = -EIO;
2301         } else {
2302                 WRITE_RSP *pSMBr = (WRITE_RSP *)iov[0].iov_base;
2303                 *nbytes = le16_to_cpu(pSMBr->CountHigh);
2304                 *nbytes = (*nbytes) << 16;
2305                 *nbytes += le16_to_cpu(pSMBr->Count);
2306
2307                 /*
2308                  * Mask off high 16 bits when bytes written as returned by the
2309                  * server is greater than bytes requested by the client. OS/2
2310                  * servers are known to set incorrect CountHigh values.
2311                  */
2312                 if (*nbytes > count)
2313                         *nbytes &= 0xFFFF;
2314         }
2315
2316 /*      cifs_small_buf_release(pSMB); */ /* Freed earlier now in SendReceive2 */
2317         if (resp_buf_type == CIFS_SMALL_BUFFER)
2318                 cifs_small_buf_release(iov[0].iov_base);
2319         else if (resp_buf_type == CIFS_LARGE_BUFFER)
2320                 cifs_buf_release(iov[0].iov_base);
2321
2322         /* Note: On -EAGAIN error only caller can retry on handle based calls
2323                 since file handle passed in no longer valid */
2324
2325         return rc;
2326 }
2327
2328 int cifs_lockv(const int xid, struct cifs_tcon *tcon, const __u16 netfid,
2329                const __u8 lock_type, const __u32 num_unlock,
2330                const __u32 num_lock, LOCKING_ANDX_RANGE *buf)
2331 {
2332         int rc = 0;
2333         LOCK_REQ *pSMB = NULL;
2334         struct kvec iov[2];
2335         int resp_buf_type;
2336         __u16 count;
2337
2338         cFYI(1, "cifs_lockv num lock %d num unlock %d", num_lock, num_unlock);
2339
2340         rc = small_smb_init(SMB_COM_LOCKING_ANDX, 8, tcon, (void **) &pSMB);
2341         if (rc)
2342                 return rc;
2343
2344         pSMB->Timeout = 0;
2345         pSMB->NumberOfLocks = cpu_to_le16(num_lock);
2346         pSMB->NumberOfUnlocks = cpu_to_le16(num_unlock);
2347         pSMB->LockType = lock_type;
2348         pSMB->AndXCommand = 0xFF; /* none */
2349         pSMB->Fid = netfid; /* netfid stays le */
2350
2351         count = (num_unlock + num_lock) * sizeof(LOCKING_ANDX_RANGE);
2352         inc_rfc1001_len(pSMB, count);
2353         pSMB->ByteCount = cpu_to_le16(count);
2354
2355         iov[0].iov_base = (char *)pSMB;
2356         iov[0].iov_len = be32_to_cpu(pSMB->hdr.smb_buf_length) + 4 -
2357                          (num_unlock + num_lock) * sizeof(LOCKING_ANDX_RANGE);
2358         iov[1].iov_base = (char *)buf;
2359         iov[1].iov_len = (num_unlock + num_lock) * sizeof(LOCKING_ANDX_RANGE);
2360
2361         cifs_stats_inc(&tcon->num_locks);
2362         rc = SendReceive2(xid, tcon->ses, iov, 2, &resp_buf_type, CIFS_NO_RESP);
2363         if (rc)
2364                 cFYI(1, "Send error in cifs_lockv = %d", rc);
2365
2366         return rc;
2367 }
2368
2369 int
2370 CIFSSMBLock(const int xid, struct cifs_tcon *tcon,
2371             const __u16 smb_file_id, const __u32 netpid, const __u64 len,
2372             const __u64 offset, const __u32 numUnlock,
2373             const __u32 numLock, const __u8 lockType,
2374             const bool waitFlag, const __u8 oplock_level)
2375 {
2376         int rc = 0;
2377         LOCK_REQ *pSMB = NULL;
2378 /*      LOCK_RSP *pSMBr = NULL; */ /* No response data other than rc to parse */
2379         int bytes_returned;
2380         int timeout = 0;
2381         __u16 count;
2382
2383         cFYI(1, "CIFSSMBLock timeout %d numLock %d", (int)waitFlag, numLock);
2384         rc = small_smb_init(SMB_COM_LOCKING_ANDX, 8, tcon, (void **) &pSMB);
2385
2386         if (rc)
2387                 return rc;
2388
2389         if (lockType == LOCKING_ANDX_OPLOCK_RELEASE) {
2390                 timeout = CIFS_ASYNC_OP; /* no response expected */
2391                 pSMB->Timeout = 0;
2392         } else if (waitFlag) {
2393                 timeout = CIFS_BLOCKING_OP; /* blocking operation, no timeout */
2394                 pSMB->Timeout = cpu_to_le32(-1);/* blocking - do not time out */
2395         } else {
2396                 pSMB->Timeout = 0;
2397         }
2398
2399         pSMB->NumberOfLocks = cpu_to_le16(numLock);
2400         pSMB->NumberOfUnlocks = cpu_to_le16(numUnlock);
2401         pSMB->LockType = lockType;
2402         pSMB->OplockLevel = oplock_level;
2403         pSMB->AndXCommand = 0xFF;       /* none */
2404         pSMB->Fid = smb_file_id; /* netfid stays le */
2405
2406         if ((numLock != 0) || (numUnlock != 0)) {
2407                 pSMB->Locks[0].Pid = cpu_to_le16(netpid);
2408                 /* BB where to store pid high? */
2409                 pSMB->Locks[0].LengthLow = cpu_to_le32((u32)len);
2410                 pSMB->Locks[0].LengthHigh = cpu_to_le32((u32)(len>>32));
2411                 pSMB->Locks[0].OffsetLow = cpu_to_le32((u32)offset);
2412                 pSMB->Locks[0].OffsetHigh = cpu_to_le32((u32)(offset>>32));
2413                 count = sizeof(LOCKING_ANDX_RANGE);
2414         } else {
2415                 /* oplock break */
2416                 count = 0;
2417         }
2418         inc_rfc1001_len(pSMB, count);
2419         pSMB->ByteCount = cpu_to_le16(count);
2420
2421         if (waitFlag) {
2422                 rc = SendReceiveBlockingLock(xid, tcon, (struct smb_hdr *) pSMB,
2423                         (struct smb_hdr *) pSMB, &bytes_returned);
2424                 cifs_small_buf_release(pSMB);
2425         } else {
2426                 rc = SendReceiveNoRsp(xid, tcon->ses, (struct smb_hdr *)pSMB,
2427                                       timeout);
2428                 /* SMB buffer freed by function above */
2429         }
2430         cifs_stats_inc(&tcon->num_locks);
2431         if (rc)
2432                 cFYI(1, "Send error in Lock = %d", rc);
2433
2434         /* Note: On -EAGAIN error only caller can retry on handle based calls
2435         since file handle passed in no longer valid */
2436         return rc;
2437 }
2438
2439 int
2440 CIFSSMBPosixLock(const int xid, struct cifs_tcon *tcon,
2441                 const __u16 smb_file_id, const __u32 netpid, const int get_flag,
2442                 const __u64 len, struct file_lock *pLockData,
2443                 const __u16 lock_type, const bool waitFlag)
2444 {
2445         struct smb_com_transaction2_sfi_req *pSMB  = NULL;
2446         struct smb_com_transaction2_sfi_rsp *pSMBr = NULL;
2447         struct cifs_posix_lock *parm_data;
2448         int rc = 0;
2449         int timeout = 0;
2450         int bytes_returned = 0;
2451         int resp_buf_type = 0;
2452         __u16 params, param_offset, offset, byte_count, count;
2453         struct kvec iov[1];
2454
2455         cFYI(1, "Posix Lock");
2456
2457         if (pLockData == NULL)
2458                 return -EINVAL;
2459
2460         rc = small_smb_init(SMB_COM_TRANSACTION2, 15, tcon, (void **) &pSMB);
2461
2462         if (rc)
2463                 return rc;
2464
2465         pSMBr = (struct smb_com_transaction2_sfi_rsp *)pSMB;
2466
2467         params = 6;
2468         pSMB->MaxSetupCount = 0;
2469         pSMB->Reserved = 0;
2470         pSMB->Flags = 0;
2471         pSMB->Reserved2 = 0;
2472         param_offset = offsetof(struct smb_com_transaction2_sfi_req, Fid) - 4;
2473         offset = param_offset + params;
2474
2475         count = sizeof(struct cifs_posix_lock);
2476         pSMB->MaxParameterCount = cpu_to_le16(2);
2477         pSMB->MaxDataCount = cpu_to_le16(1000); /* BB find max SMB from sess */
2478         pSMB->SetupCount = 1;
2479         pSMB->Reserved3 = 0;
2480         if (get_flag)
2481                 pSMB->SubCommand = cpu_to_le16(TRANS2_QUERY_FILE_INFORMATION);
2482         else
2483                 pSMB->SubCommand = cpu_to_le16(TRANS2_SET_FILE_INFORMATION);
2484         byte_count = 3 /* pad */  + params + count;
2485         pSMB->DataCount = cpu_to_le16(count);
2486         pSMB->ParameterCount = cpu_to_le16(params);
2487         pSMB->TotalDataCount = pSMB->DataCount;
2488         pSMB->TotalParameterCount = pSMB->ParameterCount;
2489         pSMB->ParameterOffset = cpu_to_le16(param_offset);
2490         parm_data = (struct cifs_posix_lock *)
2491                         (((char *) &pSMB->hdr.Protocol) + offset);
2492
2493         parm_data->lock_type = cpu_to_le16(lock_type);
2494         if (waitFlag) {
2495                 timeout = CIFS_BLOCKING_OP; /* blocking operation, no timeout */
2496                 parm_data->lock_flags = cpu_to_le16(1);
2497                 pSMB->Timeout = cpu_to_le32(-1);
2498         } else
2499                 pSMB->Timeout = 0;
2500
2501         parm_data->pid = cpu_to_le32(netpid);
2502         parm_data->start = cpu_to_le64(pLockData->fl_start);
2503         parm_data->length = cpu_to_le64(len);  /* normalize negative numbers */
2504
2505         pSMB->DataOffset = cpu_to_le16(offset);
2506         pSMB->Fid = smb_file_id;
2507         pSMB->InformationLevel = cpu_to_le16(SMB_SET_POSIX_LOCK);
2508         pSMB->Reserved4 = 0;
2509         inc_rfc1001_len(pSMB, byte_count);
2510         pSMB->ByteCount = cpu_to_le16(byte_count);
2511         if (waitFlag) {
2512                 rc = SendReceiveBlockingLock(xid, tcon, (struct smb_hdr *) pSMB,
2513                         (struct smb_hdr *) pSMBr, &bytes_returned);
2514         } else {
2515                 iov[0].iov_base = (char *)pSMB;
2516                 iov[0].iov_len = be32_to_cpu(pSMB->hdr.smb_buf_length) + 4;
2517                 rc = SendReceive2(xid, tcon->ses, iov, 1 /* num iovecs */,
2518                                 &resp_buf_type, timeout);
2519                 pSMB = NULL; /* request buf already freed by SendReceive2. Do
2520                                 not try to free it twice below on exit */
2521                 pSMBr = (struct smb_com_transaction2_sfi_rsp *)iov[0].iov_base;
2522         }
2523
2524         if (rc) {
2525                 cFYI(1, "Send error in Posix Lock = %d", rc);
2526         } else if (get_flag) {
2527                 /* lock structure can be returned on get */
2528                 __u16 data_offset;
2529                 __u16 data_count;
2530                 rc = validate_t2((struct smb_t2_rsp *)pSMBr);
2531
2532                 if (rc || get_bcc(&pSMBr->hdr) < sizeof(*parm_data)) {
2533                         rc = -EIO;      /* bad smb */
2534                         goto plk_err_exit;
2535                 }
2536                 data_offset = le16_to_cpu(pSMBr->t2.DataOffset);
2537                 data_count  = le16_to_cpu(pSMBr->t2.DataCount);
2538                 if (data_count < sizeof(struct cifs_posix_lock)) {
2539                         rc = -EIO;
2540                         goto plk_err_exit;
2541                 }
2542                 parm_data = (struct cifs_posix_lock *)
2543                         ((char *)&pSMBr->hdr.Protocol + data_offset);
2544                 if (parm_data->lock_type == __constant_cpu_to_le16(CIFS_UNLCK))
2545                         pLockData->fl_type = F_UNLCK;
2546                 else {
2547                         if (parm_data->lock_type ==
2548                                         __constant_cpu_to_le16(CIFS_RDLCK))
2549                                 pLockData->fl_type = F_RDLCK;
2550                         else if (parm_data->lock_type ==
2551                                         __constant_cpu_to_le16(CIFS_WRLCK))
2552                                 pLockData->fl_type = F_WRLCK;
2553
2554                         pLockData->fl_start = le64_to_cpu(parm_data->start);
2555                         pLockData->fl_end = pLockData->fl_start +
2556                                         le64_to_cpu(parm_data->length) - 1;
2557                         pLockData->fl_pid = le32_to_cpu(parm_data->pid);
2558                 }
2559         }
2560
2561 plk_err_exit:
2562         if (pSMB)
2563                 cifs_small_buf_release(pSMB);
2564
2565         if (resp_buf_type == CIFS_SMALL_BUFFER)
2566                 cifs_small_buf_release(iov[0].iov_base);
2567         else if (resp_buf_type == CIFS_LARGE_BUFFER)
2568                 cifs_buf_release(iov[0].iov_base);
2569
2570         /* Note: On -EAGAIN error only caller can retry on handle based calls
2571            since file handle passed in no longer valid */
2572
2573         return rc;
2574 }
2575
2576
2577 int
2578 CIFSSMBClose(const int xid, struct cifs_tcon *tcon, int smb_file_id)
2579 {
2580         int rc = 0;
2581         CLOSE_REQ *pSMB = NULL;
2582         cFYI(1, "In CIFSSMBClose");
2583
2584 /* do not retry on dead session on close */
2585         rc = small_smb_init(SMB_COM_CLOSE, 3, tcon, (void **) &pSMB);
2586         if (rc == -EAGAIN)
2587                 return 0;
2588         if (rc)
2589                 return rc;
2590
2591         pSMB->FileID = (__u16) smb_file_id;
2592         pSMB->LastWriteTime = 0xFFFFFFFF;
2593         pSMB->ByteCount = 0;
2594         rc = SendReceiveNoRsp(xid, tcon->ses, (struct smb_hdr *) pSMB, 0);
2595         cifs_stats_inc(&tcon->num_closes);
2596         if (rc) {
2597                 if (rc != -EINTR) {
2598                         /* EINTR is expected when user ctl-c to kill app */
2599                         cERROR(1, "Send error in Close = %d", rc);
2600                 }
2601         }
2602
2603         /* Since session is dead, file will be closed on server already */
2604         if (rc == -EAGAIN)
2605                 rc = 0;
2606
2607         return rc;
2608 }
2609
2610 int
2611 CIFSSMBFlush(const int xid, struct cifs_tcon *tcon, int smb_file_id)
2612 {
2613         int rc = 0;
2614         FLUSH_REQ *pSMB = NULL;
2615         cFYI(1, "In CIFSSMBFlush");
2616
2617         rc = small_smb_init(SMB_COM_FLUSH, 1, tcon, (void **) &pSMB);
2618         if (rc)
2619                 return rc;
2620
2621         pSMB->FileID = (__u16) smb_file_id;
2622         pSMB->ByteCount = 0;
2623         rc = SendReceiveNoRsp(xid, tcon->ses, (struct smb_hdr *) pSMB, 0);
2624         cifs_stats_inc(&tcon->num_flushes);
2625         if (rc)
2626                 cERROR(1, "Send error in Flush = %d", rc);
2627
2628         return rc;
2629 }
2630
2631 int
2632 CIFSSMBRename(const int xid, struct cifs_tcon *tcon,
2633               const char *fromName, const char *toName,
2634               const struct nls_table *nls_codepage, int remap)
2635 {
2636         int rc = 0;
2637         RENAME_REQ *pSMB = NULL;
2638         RENAME_RSP *pSMBr = NULL;
2639         int bytes_returned;
2640         int name_len, name_len2;
2641         __u16 count;
2642
2643         cFYI(1, "In CIFSSMBRename");
2644 renameRetry:
2645         rc = smb_init(SMB_COM_RENAME, 1, tcon, (void **) &pSMB,
2646                       (void **) &pSMBr);
2647         if (rc)
2648                 return rc;
2649
2650         pSMB->BufferFormat = 0x04;
2651         pSMB->SearchAttributes =
2652             cpu_to_le16(ATTR_READONLY | ATTR_HIDDEN | ATTR_SYSTEM |
2653                         ATTR_DIRECTORY);
2654
2655         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
2656                 name_len =
2657                     cifsConvertToUCS((__le16 *) pSMB->OldFileName, fromName,
2658                                      PATH_MAX, nls_codepage, remap);
2659                 name_len++;     /* trailing null */
2660                 name_len *= 2;
2661                 pSMB->OldFileName[name_len] = 0x04;     /* pad */
2662         /* protocol requires ASCII signature byte on Unicode string */
2663                 pSMB->OldFileName[name_len + 1] = 0x00;
2664                 name_len2 =
2665                     cifsConvertToUCS((__le16 *)&pSMB->OldFileName[name_len + 2],
2666                                      toName, PATH_MAX, nls_codepage, remap);
2667                 name_len2 += 1 /* trailing null */  + 1 /* Signature word */ ;
2668                 name_len2 *= 2; /* convert to bytes */
2669         } else {        /* BB improve the check for buffer overruns BB */
2670                 name_len = strnlen(fromName, PATH_MAX);
2671                 name_len++;     /* trailing null */
2672                 strncpy(pSMB->OldFileName, fromName, name_len);
2673                 name_len2 = strnlen(toName, PATH_MAX);
2674                 name_len2++;    /* trailing null */
2675                 pSMB->OldFileName[name_len] = 0x04;  /* 2nd buffer format */
2676                 strncpy(&pSMB->OldFileName[name_len + 1], toName, name_len2);
2677                 name_len2++;    /* trailing null */
2678                 name_len2++;    /* signature byte */
2679         }
2680
2681         count = 1 /* 1st signature byte */  + name_len + name_len2;
2682         inc_rfc1001_len(pSMB, count);
2683         pSMB->ByteCount = cpu_to_le16(count);
2684
2685         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
2686                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
2687         cifs_stats_inc(&tcon->num_renames);
2688         if (rc)
2689                 cFYI(1, "Send error in rename = %d", rc);
2690
2691         cifs_buf_release(pSMB);
2692
2693         if (rc == -EAGAIN)
2694                 goto renameRetry;
2695
2696         return rc;
2697 }
2698
2699 int CIFSSMBRenameOpenFile(const int xid, struct cifs_tcon *pTcon,
2700                 int netfid, const char *target_name,
2701                 const struct nls_table *nls_codepage, int remap)
2702 {
2703         struct smb_com_transaction2_sfi_req *pSMB  = NULL;
2704         struct smb_com_transaction2_sfi_rsp *pSMBr = NULL;
2705         struct set_file_rename *rename_info;
2706         char *data_offset;
2707         char dummy_string[30];
2708         int rc = 0;
2709         int bytes_returned = 0;
2710         int len_of_str;
2711         __u16 params, param_offset, offset, count, byte_count;
2712
2713         cFYI(1, "Rename to File by handle");
2714         rc = smb_init(SMB_COM_TRANSACTION2, 15, pTcon, (void **) &pSMB,
2715                         (void **) &pSMBr);
2716         if (rc)
2717                 return rc;
2718
2719         params = 6;
2720         pSMB->MaxSetupCount = 0;
2721         pSMB->Reserved = 0;
2722         pSMB->Flags = 0;
2723         pSMB->Timeout = 0;
2724         pSMB->Reserved2 = 0;
2725         param_offset = offsetof(struct smb_com_transaction2_sfi_req, Fid) - 4;
2726         offset = param_offset + params;
2727
2728         data_offset = (char *) (&pSMB->hdr.Protocol) + offset;
2729         rename_info = (struct set_file_rename *) data_offset;
2730         pSMB->MaxParameterCount = cpu_to_le16(2);
2731         pSMB->MaxDataCount = cpu_to_le16(1000); /* BB find max SMB from sess */
2732         pSMB->SetupCount = 1;
2733         pSMB->Reserved3 = 0;
2734         pSMB->SubCommand = cpu_to_le16(TRANS2_SET_FILE_INFORMATION);
2735         byte_count = 3 /* pad */  + params;
2736         pSMB->ParameterCount = cpu_to_le16(params);
2737         pSMB->TotalParameterCount = pSMB->ParameterCount;
2738         pSMB->ParameterOffset = cpu_to_le16(param_offset);
2739         pSMB->DataOffset = cpu_to_le16(offset);
2740         /* construct random name ".cifs_tmp<inodenum><mid>" */
2741         rename_info->overwrite = cpu_to_le32(1);
2742         rename_info->root_fid  = 0;
2743         /* unicode only call */
2744         if (target_name == NULL) {
2745                 sprintf(dummy_string, "cifs%x", pSMB->hdr.Mid);
2746                 len_of_str = cifsConvertToUCS((__le16 *)rename_info->target_name,
2747                                         dummy_string, 24, nls_codepage, remap);
2748         } else {
2749                 len_of_str = cifsConvertToUCS((__le16 *)rename_info->target_name,
2750                                         target_name, PATH_MAX, nls_codepage,
2751                                         remap);
2752         }
2753         rename_info->target_name_len = cpu_to_le32(2 * len_of_str);
2754         count = 12 /* sizeof(struct set_file_rename) */ + (2 * len_of_str);
2755         byte_count += count;
2756         pSMB->DataCount = cpu_to_le16(count);
2757         pSMB->TotalDataCount = pSMB->DataCount;
2758         pSMB->Fid = netfid;
2759         pSMB->InformationLevel =
2760                 cpu_to_le16(SMB_SET_FILE_RENAME_INFORMATION);
2761         pSMB->Reserved4 = 0;
2762         inc_rfc1001_len(pSMB, byte_count);
2763         pSMB->ByteCount = cpu_to_le16(byte_count);
2764         rc = SendReceive(xid, pTcon->ses, (struct smb_hdr *) pSMB,
2765                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
2766         cifs_stats_inc(&pTcon->num_t2renames);
2767         if (rc)
2768                 cFYI(1, "Send error in Rename (by file handle) = %d", rc);
2769
2770         cifs_buf_release(pSMB);
2771
2772         /* Note: On -EAGAIN error only caller can retry on handle based calls
2773                 since file handle passed in no longer valid */
2774
2775         return rc;
2776 }
2777
2778 int
2779 CIFSSMBCopy(const int xid, struct cifs_tcon *tcon, const char *fromName,
2780             const __u16 target_tid, const char *toName, const int flags,
2781             const struct nls_table *nls_codepage, int remap)
2782 {
2783         int rc = 0;
2784         COPY_REQ *pSMB = NULL;
2785         COPY_RSP *pSMBr = NULL;
2786         int bytes_returned;
2787         int name_len, name_len2;
2788         __u16 count;
2789
2790         cFYI(1, "In CIFSSMBCopy");
2791 copyRetry:
2792         rc = smb_init(SMB_COM_COPY, 1, tcon, (void **) &pSMB,
2793                         (void **) &pSMBr);
2794         if (rc)
2795                 return rc;
2796
2797         pSMB->BufferFormat = 0x04;
2798         pSMB->Tid2 = target_tid;
2799
2800         pSMB->Flags = cpu_to_le16(flags & COPY_TREE);
2801
2802         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
2803                 name_len = cifsConvertToUCS((__le16 *) pSMB->OldFileName,
2804                                             fromName, PATH_MAX, nls_codepage,
2805                                             remap);
2806                 name_len++;     /* trailing null */
2807                 name_len *= 2;
2808                 pSMB->OldFileName[name_len] = 0x04;     /* pad */
2809                 /* protocol requires ASCII signature byte on Unicode string */
2810                 pSMB->OldFileName[name_len + 1] = 0x00;
2811                 name_len2 =
2812                     cifsConvertToUCS((__le16 *)&pSMB->OldFileName[name_len + 2],
2813                                 toName, PATH_MAX, nls_codepage, remap);
2814                 name_len2 += 1 /* trailing null */  + 1 /* Signature word */ ;
2815                 name_len2 *= 2; /* convert to bytes */
2816         } else {        /* BB improve the check for buffer overruns BB */
2817                 name_len = strnlen(fromName, PATH_MAX);
2818                 name_len++;     /* trailing null */
2819                 strncpy(pSMB->OldFileName, fromName, name_len);
2820                 name_len2 = strnlen(toName, PATH_MAX);
2821                 name_len2++;    /* trailing null */
2822                 pSMB->OldFileName[name_len] = 0x04;  /* 2nd buffer format */
2823                 strncpy(&pSMB->OldFileName[name_len + 1], toName, name_len2);
2824                 name_len2++;    /* trailing null */
2825                 name_len2++;    /* signature byte */
2826         }
2827
2828         count = 1 /* 1st signature byte */  + name_len + name_len2;
2829         inc_rfc1001_len(pSMB, count);
2830         pSMB->ByteCount = cpu_to_le16(count);
2831
2832         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
2833                 (struct smb_hdr *) pSMBr, &bytes_returned, 0);
2834         if (rc) {
2835                 cFYI(1, "Send error in copy = %d with %d files copied",
2836                         rc, le16_to_cpu(pSMBr->CopyCount));
2837         }
2838         cifs_buf_release(pSMB);
2839
2840         if (rc == -EAGAIN)
2841                 goto copyRetry;
2842
2843         return rc;
2844 }
2845
2846 int
2847 CIFSUnixCreateSymLink(const int xid, struct cifs_tcon *tcon,
2848                       const char *fromName, const char *toName,
2849                       const struct nls_table *nls_codepage)
2850 {
2851         TRANSACTION2_SPI_REQ *pSMB = NULL;
2852         TRANSACTION2_SPI_RSP *pSMBr = NULL;
2853         char *data_offset;
2854         int name_len;
2855         int name_len_target;
2856         int rc = 0;
2857         int bytes_returned = 0;
2858         __u16 params, param_offset, offset, byte_count;
2859
2860         cFYI(1, "In Symlink Unix style");
2861 createSymLinkRetry:
2862         rc = smb_init(SMB_COM_TRANSACTION2, 15, tcon, (void **) &pSMB,
2863                       (void **) &pSMBr);
2864         if (rc)
2865                 return rc;
2866
2867         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
2868                 name_len =
2869                     cifs_strtoUCS((__le16 *) pSMB->FileName, fromName, PATH_MAX
2870                                   /* find define for this maxpathcomponent */
2871                                   , nls_codepage);
2872                 name_len++;     /* trailing null */
2873                 name_len *= 2;
2874
2875         } else {        /* BB improve the check for buffer overruns BB */
2876                 name_len = strnlen(fromName, PATH_MAX);
2877                 name_len++;     /* trailing null */
2878                 strncpy(pSMB->FileName, fromName, name_len);
2879         }
2880         params = 6 + name_len;
2881         pSMB->MaxSetupCount = 0;
2882         pSMB->Reserved = 0;
2883         pSMB->Flags = 0;
2884         pSMB->Timeout = 0;
2885         pSMB->Reserved2 = 0;
2886         param_offset = offsetof(struct smb_com_transaction2_spi_req,
2887                                 InformationLevel) - 4;
2888         offset = param_offset + params;
2889
2890         data_offset = (char *) (&pSMB->hdr.Protocol) + offset;
2891         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
2892                 name_len_target =
2893                     cifs_strtoUCS((__le16 *) data_offset, toName, PATH_MAX
2894                                   /* find define for this maxpathcomponent */
2895                                   , nls_codepage);
2896                 name_len_target++;      /* trailing null */
2897                 name_len_target *= 2;
2898         } else {        /* BB improve the check for buffer overruns BB */
2899                 name_len_target = strnlen(toName, PATH_MAX);
2900                 name_len_target++;      /* trailing null */
2901                 strncpy(data_offset, toName, name_len_target);
2902         }
2903
2904         pSMB->MaxParameterCount = cpu_to_le16(2);
2905         /* BB find exact max on data count below from sess */
2906         pSMB->MaxDataCount = cpu_to_le16(1000);
2907         pSMB->SetupCount = 1;
2908         pSMB->Reserved3 = 0;
2909         pSMB->SubCommand = cpu_to_le16(TRANS2_SET_PATH_INFORMATION);
2910         byte_count = 3 /* pad */  + params + name_len_target;
2911         pSMB->DataCount = cpu_to_le16(name_len_target);
2912         pSMB->ParameterCount = cpu_to_le16(params);
2913         pSMB->TotalDataCount = pSMB->DataCount;
2914         pSMB->TotalParameterCount = pSMB->ParameterCount;
2915         pSMB->ParameterOffset = cpu_to_le16(param_offset);
2916         pSMB->DataOffset = cpu_to_le16(offset);
2917         pSMB->InformationLevel = cpu_to_le16(SMB_SET_FILE_UNIX_LINK);
2918         pSMB->Reserved4 = 0;
2919         inc_rfc1001_len(pSMB, byte_count);
2920         pSMB->ByteCount = cpu_to_le16(byte_count);
2921         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
2922                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
2923         cifs_stats_inc(&tcon->num_symlinks);
2924         if (rc)
2925                 cFYI(1, "Send error in SetPathInfo create symlink = %d", rc);
2926
2927         cifs_buf_release(pSMB);
2928
2929         if (rc == -EAGAIN)
2930                 goto createSymLinkRetry;
2931
2932         return rc;
2933 }
2934
2935 int
2936 CIFSUnixCreateHardLink(const int xid, struct cifs_tcon *tcon,
2937                        const char *fromName, const char *toName,
2938                        const struct nls_table *nls_codepage, int remap)
2939 {
2940         TRANSACTION2_SPI_REQ *pSMB = NULL;
2941         TRANSACTION2_SPI_RSP *pSMBr = NULL;
2942         char *data_offset;
2943         int name_len;
2944         int name_len_target;
2945         int rc = 0;
2946         int bytes_returned = 0;
2947         __u16 params, param_offset, offset, byte_count;
2948
2949         cFYI(1, "In Create Hard link Unix style");
2950 createHardLinkRetry:
2951         rc = smb_init(SMB_COM_TRANSACTION2, 15, tcon, (void **) &pSMB,
2952                       (void **) &pSMBr);
2953         if (rc)
2954                 return rc;
2955
2956         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
2957                 name_len = cifsConvertToUCS((__le16 *) pSMB->FileName, toName,
2958                                             PATH_MAX, nls_codepage, remap);
2959                 name_len++;     /* trailing null */
2960                 name_len *= 2;
2961
2962         } else {        /* BB improve the check for buffer overruns BB */
2963                 name_len = strnlen(toName, PATH_MAX);
2964                 name_len++;     /* trailing null */
2965                 strncpy(pSMB->FileName, toName, name_len);
2966         }
2967         params = 6 + name_len;
2968         pSMB->MaxSetupCount = 0;
2969         pSMB->Reserved = 0;
2970         pSMB->Flags = 0;
2971         pSMB->Timeout = 0;
2972         pSMB->Reserved2 = 0;
2973         param_offset = offsetof(struct smb_com_transaction2_spi_req,
2974                                 InformationLevel) - 4;
2975         offset = param_offset + params;
2976
2977         data_offset = (char *) (&pSMB->hdr.Protocol) + offset;
2978         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
2979                 name_len_target =
2980                     cifsConvertToUCS((__le16 *) data_offset, fromName, PATH_MAX,
2981                                      nls_codepage, remap);
2982                 name_len_target++;      /* trailing null */
2983                 name_len_target *= 2;
2984         } else {        /* BB improve the check for buffer overruns BB */
2985                 name_len_target = strnlen(fromName, PATH_MAX);
2986                 name_len_target++;      /* trailing null */
2987                 strncpy(data_offset, fromName, name_len_target);
2988         }
2989
2990         pSMB->MaxParameterCount = cpu_to_le16(2);
2991         /* BB find exact max on data count below from sess*/
2992         pSMB->MaxDataCount = cpu_to_le16(1000);
2993         pSMB->SetupCount = 1;
2994         pSMB->Reserved3 = 0;
2995         pSMB->SubCommand = cpu_to_le16(TRANS2_SET_PATH_INFORMATION);
2996         byte_count = 3 /* pad */  + params + name_len_target;
2997         pSMB->ParameterCount = cpu_to_le16(params);
2998         pSMB->TotalParameterCount = pSMB->ParameterCount;
2999         pSMB->DataCount = cpu_to_le16(name_len_target);
3000         pSMB->TotalDataCount = pSMB->DataCount;
3001         pSMB->ParameterOffset = cpu_to_le16(param_offset);
3002         pSMB->DataOffset = cpu_to_le16(offset);
3003         pSMB->InformationLevel = cpu_to_le16(SMB_SET_FILE_UNIX_HLINK);
3004         pSMB->Reserved4 = 0;
3005         inc_rfc1001_len(pSMB, byte_count);
3006         pSMB->ByteCount = cpu_to_le16(byte_count);
3007         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
3008                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
3009         cifs_stats_inc(&tcon->num_hardlinks);
3010         if (rc)
3011                 cFYI(1, "Send error in SetPathInfo (hard link) = %d", rc);
3012
3013         cifs_buf_release(pSMB);
3014         if (rc == -EAGAIN)
3015                 goto createHardLinkRetry;
3016
3017         return rc;
3018 }
3019
3020 int
3021 CIFSCreateHardLink(const int xid, struct cifs_tcon *tcon,
3022                    const char *fromName, const char *toName,
3023                    const struct nls_table *nls_codepage, int remap)
3024 {
3025         int rc = 0;
3026         NT_RENAME_REQ *pSMB = NULL;
3027         RENAME_RSP *pSMBr = NULL;
3028         int bytes_returned;
3029         int name_len, name_len2;
3030         __u16 count;
3031
3032         cFYI(1, "In CIFSCreateHardLink");
3033 winCreateHardLinkRetry:
3034
3035         rc = smb_init(SMB_COM_NT_RENAME, 4, tcon, (void **) &pSMB,
3036                       (void **) &pSMBr);
3037         if (rc)
3038                 return rc;
3039
3040         pSMB->SearchAttributes =
3041             cpu_to_le16(ATTR_READONLY | ATTR_HIDDEN | ATTR_SYSTEM |
3042                         ATTR_DIRECTORY);
3043         pSMB->Flags = cpu_to_le16(CREATE_HARD_LINK);
3044         pSMB->ClusterCount = 0;
3045
3046         pSMB->BufferFormat = 0x04;
3047
3048         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
3049                 name_len =
3050                     cifsConvertToUCS((__le16 *) pSMB->OldFileName, fromName,
3051                                      PATH_MAX, nls_codepage, remap);
3052                 name_len++;     /* trailing null */
3053                 name_len *= 2;
3054
3055                 /* protocol specifies ASCII buffer format (0x04) for unicode */
3056                 pSMB->OldFileName[name_len] = 0x04;
3057                 pSMB->OldFileName[name_len + 1] = 0x00; /* pad */
3058                 name_len2 =
3059                     cifsConvertToUCS((__le16 *)&pSMB->OldFileName[name_len + 2],
3060                                      toName, PATH_MAX, nls_codepage, remap);
3061                 name_len2 += 1 /* trailing null */  + 1 /* Signature word */ ;
3062                 name_len2 *= 2; /* convert to bytes */
3063         } else {        /* BB improve the check for buffer overruns BB */
3064                 name_len = strnlen(fromName, PATH_MAX);
3065                 name_len++;     /* trailing null */
3066                 strncpy(pSMB->OldFileName, fromName, name_len);
3067                 name_len2 = strnlen(toName, PATH_MAX);
3068                 name_len2++;    /* trailing null */
3069                 pSMB->OldFileName[name_len] = 0x04;     /* 2nd buffer format */
3070                 strncpy(&pSMB->OldFileName[name_len + 1], toName, name_len2);
3071                 name_len2++;    /* trailing null */
3072                 name_len2++;    /* signature byte */
3073         }
3074
3075         count = 1 /* string type byte */  + name_len + name_len2;
3076         inc_rfc1001_len(pSMB, count);
3077         pSMB->ByteCount = cpu_to_le16(count);
3078
3079         rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
3080                          (struct smb_hdr *) pSMBr, &bytes_returned, 0);
3081         cifs_stats_inc(&tcon->num_hardlinks);
3082         if (rc)
3083                 cFYI(1, "Send error in hard link (NT rename) = %d", rc);
3084
3085         cifs_buf_release(pSMB);
3086         if (rc == -EAGAIN)
3087                 goto winCreateHardLinkRetry;
3088
3089         return rc;
3090 }
3091
3092 int
3093 CIFSSMBUnixQuerySymLink(const int xid, struct cifs_tcon *tcon,
3094                         const unsigned char *searchName, char **symlinkinfo,
3095                         const struct nls_table *nls_codepage)
3096 {
3097 /* SMB_QUERY_FILE_UNIX_LINK */
3098         TRANSACTION2_QPI_REQ *pSMB = NULL;
3099         TRANSACTION2_QPI_RSP *pSMBr = NULL;
3100         int rc = 0;
3101         int bytes_returned;
3102         int name_len;
3103         __u16 params, byte_count;
3104         char *data_start;
3105
3106         cFYI(1, "In QPathSymLinkInfo (Unix) for path %s", searchName);
3107
3108 querySymLinkRetry:
3109         rc = smb_init(SMB_COM_TRANSACTION2, 15, tcon, (void **) &pSMB,
3110                       (void **) &pSMBr);
3111         if (rc)
3112                 return rc;
3113
3114         if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
3115                 name_len =
3116                     cifs_strtoUCS((__le16 *) pSMB->FileName, searchName,
3117                                   PATH_MAX, nls_codepage);
3118                 name_len++;     /* trailing null */
3119                 name_len *= 2;
3120         } else {        /* BB improve the check for buffer overruns BB */
3121                 name_len = strnlen(searchName, PATH_MAX);
3122                 name_len++;     /* trailing null */
3123                 strncpy(pSMB->FileName, searchName, name_len);