Commit 6035c8a5 authored by Steve French's avatar Steve French

POSIX protocol extensions part 1

parent a7c47e51
......@@ -1687,6 +1687,83 @@ struct data_blob {
void (*free) (struct data_blob * data_blob);
};
#ifdef CIFS_POSIX
/*
For better POSIX semantics from Linux client, (even better
than the existing CIFS Unix Extensions) we need updated PDUs for:
1) PosixCreateX - to set and return the mode, inode#, device info and
perhaps add a CreateDevice - to create Pipes and other special .inodes
Also note POSIX open flags
2) Close - to return the last write time to do cache across close more safely
3) PosixQFSInfo - to return statfs info
4) FindFirst return unique inode number - what about resume key, two forms short (matches readdir) and full (enough info to cache inodes)
5) Mkdir - set mode
And under consideration:
6) FindClose2 (return nanosecond timestamp ??)
7) Use nanosecond timestamps throughout all time fields if
corresponding attribute flag is set
8) sendfile - handle based copy
9) Direct i/o
10) "POSIX ACL" support
11) Misc fcntls?
what about fixing 64 bit alignment
There are also various legacy SMB/CIFS requests used as is
From existing Lanman and NTLM dialects:
--------------------------------------
NEGOTIATE
SESSION_SETUP_ANDX (BB which?)
TREE_CONNECT_ANDX (BB which wct?)
TREE_DISCONNECT (BB add volume timestamp on response)
LOGOFF_ANDX
DELETE (note delete open file behavior)
DELETE_DIRECTORY
READ_AND_X
WRITE_AND_X
LOCKING_AND_X (note posix lock semantics)
RENAME (note rename across dirs and open file rename posix behaviors)
NT_RENAME (for hardlinks) Is this good enough for all features?
FIND_CLOSE2
TRANSACTION2 (18 cases)
SMB_SET_FILE_END_OF_FILE_INFO2 SMB_SET_PATH_END_OF_FILE_INFO2
(BB verify that never need to set allocation size)
SMB_SET_FILE_BASIC_INFO2 (setting times - BB can it be done via Unix ext?)
COPY (note support for copy across directories) - FUTURE, OPTIONAL
setting/getting OS/2 EAs - FUTURE (BB can this handle
setting Linux xattrs perfectly) - OPTIONAL
dnotify - FUTURE, OPTIONAL
quota - FUTURE, OPTIONAL
Note that various requests implemented for NT interop such as
NT_TRANSACT (IOCTL) QueryReparseInfo
are unneeded to servers compliant with the CIFS POSIX extensions
From CIFS Unix Extensions:
-------------------------
T2 SET_PATH_INFO (SMB_SET_FILE_UNIX_LINK) for symlinks
T2 SET_PATH_INFO (SMB_SET_FILE_BASIC_INFO2)
T2 QUERY_PATH_INFO (SMB_QUERY_FILE_UNIX_LINK)
T2 QUERY_PATH_INFO (SMB_QUERY_FILE_UNIX_BASIC) - BB check for missing inode fields
Actually need QUERY_FILE_UNIX_INFO since has inode num
BB what about a) blksize/blkbits/blocks
b) i_version
c) i_rdev
d) notify mask?
e) generation
f) size_seqcount
T2 FIND_FIRST/FIND_NEXT FIND_FILE_UNIX
TRANS2_GET_DFS_REFERRAL - OPTIONAL but recommended
T2_QFS_INFO QueryDevice/AttributeInfo - OPTIONAL
*/
#endif
#pragma pack() /* resume default structure packing */
#endif /* _CIFSPDU_H */
......@@ -37,13 +37,24 @@
#include "cifs_unicode.h"
#include "cifs_debug.h"
#ifdef CIFS_POSIX
static struct {
int index;
char *name;
} protocols[] = {
{CIFS_PROT, "\2NT LM 0.12"},
{CIFS_PROT, "\2POSIX 2"},
{BAD_PROT, "\2"}
};
#else
static struct {
int index;
char *name;
} protocols[] = {
{CIFS_PROT, "\2NT LM 0.12"},
{BAD_PROT, "\2"}
};
#endif
/* Mark as invalid, all open files on tree connections since they
......@@ -987,60 +998,59 @@ int CIFSSMBRenameOpenFile(const int xid,struct cifsTconInfo *pTcon,
int
CIFSSMBCopy(const int xid, struct cifsTconInfo *tcon, const char * fromName,
const __u16 target_tid, const char *toName, const int flags,
const struct nls_table *nls_codepage)
const __u16 target_tid, const char *toName, const int flags,
const struct nls_table *nls_codepage)
{
int rc = 0;
COPY_REQ *pSMB = NULL;
COPY_RSP *pSMBr = NULL;
int bytes_returned;
int name_len, name_len2;
int rc = 0;
COPY_REQ *pSMB = NULL;
COPY_RSP *pSMBr = NULL;
int bytes_returned;
int name_len, name_len2;
cFYI(1, ("In CIFSSMBCopy"));
cFYI(1, ("In CIFSSMBCopy"));
copyRetry:
rc = smb_init(SMB_COM_COPY, 1, tcon, (void **) &pSMB,
(void **) &pSMBr);
if (rc)
return rc;
rc = smb_init(SMB_COM_COPY, 1, tcon, (void **) &pSMB,
(void **) &pSMBr);
if (rc)
return rc;
pSMB->BufferFormat = 0x04;
pSMB->BufferFormat = 0x04;
pSMB->Tid2 = target_tid;
if(flags & COPY_TREE)
pSMB->Flags |= COPY_TREE;
pSMB->Flags = cpu_to_le16(pSMB->Flags);
if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
name_len =
cifs_strtoUCS((wchar_t *) pSMB->OldFileName, fromName, 530
/* find define for this maxpathcomponent */
, nls_codepage);
name_len++; /* trailing null */
name_len *= 2;
pSMB->OldFileName[name_len] = 0x04; /* pad */
/* protocol requires ASCII signature byte on Unicode string */
pSMB->OldFileName[name_len + 1] = 0x00;
name_len2 =
cifs_strtoUCS((wchar_t *) & pSMB->
OldFileName[name_len + 2], toName, 530,
nls_codepage);
name_len2 += 1 /* trailing null */ + 1 /* Signature word */ ;
name_len2 *= 2; /* convert to bytes */
} else { /* BB improve the check for buffer overruns BB */
name_len = strnlen(fromName, 530);
name_len++; /* trailing null */
strncpy(pSMB->OldFileName, fromName, name_len);
name_len2 = strnlen(toName, 530);
name_len2++; /* trailing null */
pSMB->OldFileName[name_len] = 0x04; /* 2nd buffer format */
strncpy(&pSMB->OldFileName[name_len + 1], toName, name_len2);
name_len2++; /* trailing null */
name_len2++; /* signature byte */
}
pSMB->ByteCount = 1 /* 1st signature byte */ + name_len + name_len2;
pSMB->hdr.smb_buf_length += pSMB->ByteCount;
pSMB->ByteCount = cpu_to_le16(pSMB->ByteCount);
if (pSMB->hdr.Flags2 & SMBFLG2_UNICODE) {
name_len = cifs_strtoUCS((wchar_t *) pSMB->OldFileName,
fromName,
530 /* find define for this maxpathcomponent */,
nls_codepage);
name_len++; /* trailing null */
name_len *= 2;
pSMB->OldFileName[name_len] = 0x04; /* pad */
/* protocol requires ASCII signature byte on Unicode string */
pSMB->OldFileName[name_len + 1] = 0x00;
name_len2 = cifs_strtoUCS((wchar_t *) & pSMB->
OldFileName[name_len + 2], toName, 530,
nls_codepage);
name_len2 += 1 /* trailing null */ + 1 /* Signature word */ ;
name_len2 *= 2; /* convert to bytes */
} else { /* BB improve the check for buffer overruns BB */
name_len = strnlen(fromName, 530);
name_len++; /* trailing null */
strncpy(pSMB->OldFileName, fromName, name_len);
name_len2 = strnlen(toName, 530);
name_len2++; /* trailing null */
pSMB->OldFileName[name_len] = 0x04; /* 2nd buffer format */
strncpy(&pSMB->OldFileName[name_len + 1], toName, name_len2);
name_len2++; /* trailing null */
name_len2++; /* signature byte */
}
pSMB->ByteCount = 1 /* 1st signature byte */ + name_len + name_len2;
pSMB->hdr.smb_buf_length += pSMB->ByteCount;
pSMB->ByteCount = cpu_to_le16(pSMB->ByteCount);
rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
(struct smb_hdr *) pSMBr, &bytes_returned, 0);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment