Commit 1ba4886d authored by Steve French's avatar Steve French Committed by Steve French

fix rename of open files

parent d1b8ea55
......@@ -94,9 +94,14 @@ int cifs_verify_signature(struct smb_hdr * cifs_pdu, const char * mac_key,
if (cifs_pdu->Command == SMB_COM_NEGOTIATE)
return 0;
if (cifs_pdu->Command == SMB_COM_LOCKING_ANDX) {
struct smb_com_lock_req * pSMB = (struct smb_com_lock_req *)cifs_pdu;
if(pSMB->LockType & LOCKING_ANDX_OPLOCK_RELEASE)
return 0;
}
/* BB what if signatures are supposed to be on for session but server does not
send one? BB */
/* BB also do not verify oplock breaks for signature */
/* Do not need to verify session setups with signature "BSRSPYL " */
if(memcmp(cifs_pdu->Signature.SecuritySignature,"BSRSPYL ",8)==0)
......
......@@ -170,8 +170,8 @@ extern int CIFSSMBDelFile(const int xid, struct cifsTconInfo *tcon,
extern int CIFSSMBRename(const int xid, struct cifsTconInfo *tcon,
const char *fromName, const char *toName,
const struct nls_table *nls_codepage);
extern int CIFSSMBDummyRenameOpenFile(const int xid,struct cifsTconInfo *pTcon,
int netfid, const struct nls_table *nls_codepage);
extern int CIFSSMBRenameOpenFile(const int xid,struct cifsTconInfo *pTcon,
int netfid, char * target_name, const struct nls_table *nls_codepage);
extern int CIFSCreateHardLink(const int xid,
struct cifsTconInfo *tcon,
const char *fromName, const char *toName,
......
......@@ -639,8 +639,9 @@ CIFSSMBLock(const int xid, struct cifsTconInfo *tcon,
if (rc)
return rc;
if(lockType == LOCKING_ANDX_OPLOCK_RELEASE)
if(lockType == LOCKING_ANDX_OPLOCK_RELEASE) {
timeout = -1; /* no response expected */
}
pSMB->NumberOfLocks = cpu_to_le32(numLock);
pSMB->NumberOfUnlocks = cpu_to_le32(numUnlock);
......@@ -754,7 +755,7 @@ CIFSSMBRename(const int xid, struct cifsTconInfo *tcon,
rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
(struct smb_hdr *) pSMBr, &bytes_returned, 0);
if (rc) {
cFYI(1, ("Send error in RMDir = %d", rc));
cFYI(1, ("Send error in rename = %d", rc));
}
if (pSMB)
buf_release(pSMB);
......@@ -762,18 +763,19 @@ CIFSSMBRename(const int xid, struct cifsTconInfo *tcon,
return rc;
}
int CIFSSMBDummyRenameOpenFile(const int xid,struct cifsTconInfo *pTcon,
int netfid, const struct nls_table * nls_codepage)
int CIFSSMBRenameOpenFile(const int xid,struct cifsTconInfo *pTcon,
int netfid, char * target_name, const struct nls_table * nls_codepage)
{
struct smb_com_transaction2_sfi_req *pSMB = NULL;
struct smb_com_transaction2_sfi_rsp *pSMBr = NULL;
struct set_file_rename * rename_info;
char *data_offset;
char dummy_string[30];
int rc = 0;
int bytes_returned = 0;
int len_of_str;
cFYI(1, ("Rename to Dummy Random File Name"));
cFYI(1, ("Rename to File by handle"));
rc = smb_init(SMB_COM_TRANSACTION2, 15, pTcon, (void **) &pSMB,
(void **) &pSMBr);
......@@ -805,12 +807,19 @@ int CIFSSMBDummyRenameOpenFile(const int xid,struct cifsTconInfo *pTcon,
/* construct random name ".cifs_tmp<inodenum><mid>" */
rename_info->overwrite = cpu_to_le32(1);
rename_info->root_fid = 0;
len_of_str = cifs_strtoUCS((wchar_t *) rename_info->target_name, ".cifs", 12, nls_codepage);
/* unicode only call */
if(target_name == NULL) {
sprintf(dummy_string,"cifs%x",pSMB->hdr.Mid);
len_of_str = cifs_strtoUCS((wchar_t *) rename_info->target_name, dummy_string, 24, nls_codepage);
} else {
len_of_str = cifs_strtoUCS((wchar_t *) rename_info->target_name, target_name, 530, nls_codepage);
}
cFYI(1,("len of str: %d", len_of_str)); /* BB removeme BB */
rename_info->target_name_len = cpu_to_le32(2 * len_of_str);
pSMB->DataCount = 12 /* sizeof(struct set_file_rename) */ + (2 * len_of_str);
pSMB->ByteCount += pSMB->DataCount;
pSMB->DataCount = cpu_to_le16(pSMB->DataCount);
pSMB->Fid = netfid;
/* should we check the passthrough bit ? */
pSMB->InformationLevel =
cpu_to_le16(SMB_SET_FILE_RENAME_INFORMATION);
pSMB->Reserved4 = 0;
......@@ -819,7 +828,7 @@ int CIFSSMBDummyRenameOpenFile(const int xid,struct cifsTconInfo *pTcon,
rc = SendReceive(xid, pTcon->ses, (struct smb_hdr *) pSMB,
(struct smb_hdr *) pSMBr, &bytes_returned, 0);
if (rc) {
cFYI(1,("Send error in DummyRename = %d", rc));
cFYI(1,("Send error in Rename (by file handle) = %d", rc));
}
if (pSMB)
......
......@@ -102,7 +102,7 @@ cifs_reconnect(struct TCP_Server_Info *server)
}
list_for_each(tmp, &GlobalTreeConnectionList) {
tcon = list_entry(tmp, struct cifsTconInfo, cifsConnectionList);
if(tcon->ses->server == server) {
if((tcon) && (tcon->ses) && (tcon->ses->server == server)) {
tcon->tidStatus = CifsNeedReconnect;
}
}
......@@ -728,6 +728,7 @@ ipv4_connect(struct sockaddr_in *psin_server, struct socket **csocket)
*csocket = NULL;
return rc;
} else {
/* BB other socket options to set KEEPALIVE, timeouts? NODELAY? */
cFYI(1,("Socket created"));
}
}
......@@ -783,6 +784,7 @@ ipv6_connect(struct sockaddr_in6 *psin_server, struct socket **csocket)
(struct sockaddr *) psin_server,
sizeof (struct sockaddr_in6),0);
if (rc >= 0) {
/* BB other socket options to set KEEPALIVE, timeouts? NODELAY? */
return rc;
}
}
......
......@@ -353,8 +353,8 @@ cifs_unlink(struct inode *inode, struct dentry *direntry)
CREATE_NOT_DIR | CREATE_DELETE_ON_CLOSE,
&netfid, &oplock, NULL, cifs_sb->local_nls);
if(rc==0) {
CIFSSMBDummyRenameOpenFile(xid,pTcon,netfid,
cifs_sb->local_nls);
CIFSSMBRenameOpenFile(xid,pTcon,netfid,
NULL, cifs_sb->local_nls);
CIFSSMBClose(xid, pTcon, netfid);
direntry->d_inode->i_nlink--;
}
......@@ -381,7 +381,7 @@ cifs_unlink(struct inode *inode, struct dentry *direntry)
CREATE_NOT_DIR | CREATE_DELETE_ON_CLOSE,
&netfid, &oplock, NULL, cifs_sb->local_nls);
if(rc==0) {
CIFSSMBDummyRenameOpenFile(xid,pTcon,netfid,cifs_sb->local_nls);
CIFSSMBRenameOpenFile(xid,pTcon,netfid,NULL,cifs_sb->local_nls);
CIFSSMBClose(xid, pTcon, netfid);
direntry->d_inode->i_nlink--;
}
......@@ -526,6 +526,20 @@ cifs_rename(struct inode *source_inode, struct dentry *source_direntry,
rc = CIFSSMBRename(xid, pTcon, fromName, toName,
cifs_sb_source->local_nls);
}
if((rc == -EIO)||(rc == -EEXIST)) {
int oplock = FALSE;
__u16 netfid;
rc = CIFSSMBOpen(xid, pTcon, fromName, FILE_OPEN, GENERIC_READ,
CREATE_NOT_DIR,
&netfid, &oplock, NULL, cifs_sb_source->local_nls);
if(rc==0) {
CIFSSMBRenameOpenFile(xid,pTcon,netfid,
toName, cifs_sb_source->local_nls);
CIFSSMBClose(xid, pTcon, netfid);
}
}
if (fromName)
kfree(fromName);
if (toName)
......
......@@ -169,7 +169,10 @@ smb_send(struct socket *ssocket, struct smb_hdr *smb_buffer,
temp_fs = get_fs(); /* we must turn off socket api parm checking */
set_fs(get_ds());
rc = sock_sendmsg(ssocket, &smb_msg, smb_buf_length + 4);
while(rc == -ENOSPC) {
schedule_timeout(HZ/2);
rc = sock_sendmsg(ssocket, &smb_msg, smb_buf_length + 4);
}
set_fs(temp_fs);
if (rc < 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