diff options
author | Steve French <sfrench@us.ibm.com> | 2005-12-12 23:53:18 -0500 |
---|---|---|
committer | Steve French <sfrench@us.ibm.com> | 2005-12-12 23:53:18 -0500 |
commit | ec637e3ffb6b978143652477c7c5f96c9519b691 (patch) | |
tree | 32533b8f101e1d85b3499050eef29e78480e5cae /fs/cifs/file.c | |
parent | c89a86bb96307019867d11874ef0b86adaa0598e (diff) |
[CIFS] Avoid extra large buffer allocation (and memcpy) in cifs_readpages
Signed-off-by: Steve French <sfrench@us.ibm.com>
Diffstat (limited to 'fs/cifs/file.c')
-rw-r--r-- | fs/cifs/file.c | 52 |
1 files changed, 32 insertions, 20 deletions
diff --git a/fs/cifs/file.c b/fs/cifs/file.c index b67be3d8c019..c249b628fd1c 100644 --- a/fs/cifs/file.c +++ b/fs/cifs/file.c | |||
@@ -555,13 +555,13 @@ int cifs_closedir(struct inode *inode, struct file *file) | |||
555 | } | 555 | } |
556 | ptmp = pCFileStruct->srch_inf.ntwrk_buf_start; | 556 | ptmp = pCFileStruct->srch_inf.ntwrk_buf_start; |
557 | if (ptmp) { | 557 | if (ptmp) { |
558 | /* BB removeme BB */ cFYI(1, ("freeing smb buf in srch struct in closedir")); | 558 | cFYI(1, ("closedir free smb buf in srch struct")); |
559 | pCFileStruct->srch_inf.ntwrk_buf_start = NULL; | 559 | pCFileStruct->srch_inf.ntwrk_buf_start = NULL; |
560 | cifs_buf_release(ptmp); | 560 | cifs_buf_release(ptmp); |
561 | } | 561 | } |
562 | ptmp = pCFileStruct->search_resume_name; | 562 | ptmp = pCFileStruct->search_resume_name; |
563 | if (ptmp) { | 563 | if (ptmp) { |
564 | /* BB removeme BB */ cFYI(1, ("freeing resume name in closedir")); | 564 | cFYI(1, ("closedir free resume name")); |
565 | pCFileStruct->search_resume_name = NULL; | 565 | pCFileStruct->search_resume_name = NULL; |
566 | kfree(ptmp); | 566 | kfree(ptmp); |
567 | } | 567 | } |
@@ -871,8 +871,8 @@ static ssize_t cifs_write(struct file *file, const char *write_data, | |||
871 | break; | 871 | break; |
872 | } | 872 | } |
873 | /* BB FIXME We can not sign across two buffers yet */ | 873 | /* BB FIXME We can not sign across two buffers yet */ |
874 | if((experimEnabled) && ((pTcon->ses->server->secMode & | 874 | if((pTcon->ses->server->secMode & |
875 | (SECMODE_SIGN_REQUIRED | SECMODE_SIGN_ENABLED)) == 0)) { | 875 | (SECMODE_SIGN_REQUIRED | SECMODE_SIGN_ENABLED)) == 0) { |
876 | struct kvec iov[2]; | 876 | struct kvec iov[2]; |
877 | unsigned int len; | 877 | unsigned int len; |
878 | 878 | ||
@@ -1424,6 +1424,7 @@ ssize_t cifs_user_read(struct file *file, char __user *read_data, | |||
1424 | rc = -EAGAIN; | 1424 | rc = -EAGAIN; |
1425 | smb_read_data = NULL; | 1425 | smb_read_data = NULL; |
1426 | while (rc == -EAGAIN) { | 1426 | while (rc == -EAGAIN) { |
1427 | int buf_type = CIFS_NO_BUFFER; | ||
1427 | if ((open_file->invalidHandle) && | 1428 | if ((open_file->invalidHandle) && |
1428 | (!open_file->closePend)) { | 1429 | (!open_file->closePend)) { |
1429 | rc = cifs_reopen_file(file->f_dentry->d_inode, | 1430 | rc = cifs_reopen_file(file->f_dentry->d_inode, |
@@ -1432,20 +1433,22 @@ ssize_t cifs_user_read(struct file *file, char __user *read_data, | |||
1432 | break; | 1433 | break; |
1433 | } | 1434 | } |
1434 | rc = CIFSSMBRead(xid, pTcon, | 1435 | rc = CIFSSMBRead(xid, pTcon, |
1435 | open_file->netfid, | 1436 | open_file->netfid, |
1436 | current_read_size, *poffset, | 1437 | current_read_size, *poffset, |
1437 | &bytes_read, &smb_read_data); | 1438 | &bytes_read, &smb_read_data, |
1439 | &buf_type); | ||
1438 | pSMBr = (struct smb_com_read_rsp *)smb_read_data; | 1440 | pSMBr = (struct smb_com_read_rsp *)smb_read_data; |
1439 | if (copy_to_user(current_offset, | 1441 | if (copy_to_user(current_offset, |
1440 | smb_read_data + 4 /* RFC1001 hdr */ | 1442 | smb_read_data + 4 /* RFC1001 hdr */ |
1441 | + le16_to_cpu(pSMBr->DataOffset), | 1443 | + le16_to_cpu(pSMBr->DataOffset), |
1442 | bytes_read)) { | 1444 | bytes_read)) { |
1443 | rc = -EFAULT; | 1445 | rc = -EFAULT; |
1444 | FreeXid(xid); | 1446 | } |
1445 | return rc; | ||
1446 | } | ||
1447 | if (smb_read_data) { | 1447 | if (smb_read_data) { |
1448 | cifs_buf_release(smb_read_data); | 1448 | if(buf_type == CIFS_SMALL_BUFFER) |
1449 | cifs_small_buf_release(smb_read_data); | ||
1450 | else if(buf_type == CIFS_LARGE_BUFFER) | ||
1451 | cifs_buf_release(smb_read_data); | ||
1449 | smb_read_data = NULL; | 1452 | smb_read_data = NULL; |
1450 | } | 1453 | } |
1451 | } | 1454 | } |
@@ -1478,6 +1481,7 @@ static ssize_t cifs_read(struct file *file, char *read_data, size_t read_size, | |||
1478 | int xid; | 1481 | int xid; |
1479 | char *current_offset; | 1482 | char *current_offset; |
1480 | struct cifsFileInfo *open_file; | 1483 | struct cifsFileInfo *open_file; |
1484 | int buf_type = CIFS_NO_BUFFER; | ||
1481 | 1485 | ||
1482 | xid = GetXid(); | 1486 | xid = GetXid(); |
1483 | cifs_sb = CIFS_SB(file->f_dentry->d_sb); | 1487 | cifs_sb = CIFS_SB(file->f_dentry->d_sb); |
@@ -1514,9 +1518,10 @@ static ssize_t cifs_read(struct file *file, char *read_data, size_t read_size, | |||
1514 | break; | 1518 | break; |
1515 | } | 1519 | } |
1516 | rc = CIFSSMBRead(xid, pTcon, | 1520 | rc = CIFSSMBRead(xid, pTcon, |
1517 | open_file->netfid, | 1521 | open_file->netfid, |
1518 | current_read_size, *poffset, | 1522 | current_read_size, *poffset, |
1519 | &bytes_read, ¤t_offset); | 1523 | &bytes_read, ¤t_offset, |
1524 | &buf_type); | ||
1520 | } | 1525 | } |
1521 | if (rc || (bytes_read == 0)) { | 1526 | if (rc || (bytes_read == 0)) { |
1522 | if (total_read) { | 1527 | if (total_read) { |
@@ -1614,6 +1619,7 @@ static int cifs_readpages(struct file *file, struct address_space *mapping, | |||
1614 | struct smb_com_read_rsp *pSMBr; | 1619 | struct smb_com_read_rsp *pSMBr; |
1615 | struct pagevec lru_pvec; | 1620 | struct pagevec lru_pvec; |
1616 | struct cifsFileInfo *open_file; | 1621 | struct cifsFileInfo *open_file; |
1622 | int buf_type = CIFS_NO_BUFFER; | ||
1617 | 1623 | ||
1618 | xid = GetXid(); | 1624 | xid = GetXid(); |
1619 | if (file->private_data == NULL) { | 1625 | if (file->private_data == NULL) { |
@@ -1670,14 +1676,17 @@ static int cifs_readpages(struct file *file, struct address_space *mapping, | |||
1670 | } | 1676 | } |
1671 | 1677 | ||
1672 | rc = CIFSSMBRead(xid, pTcon, | 1678 | rc = CIFSSMBRead(xid, pTcon, |
1673 | open_file->netfid, | 1679 | open_file->netfid, |
1674 | read_size, offset, | 1680 | read_size, offset, |
1675 | &bytes_read, &smb_read_data); | 1681 | &bytes_read, &smb_read_data, |
1676 | 1682 | &buf_type); | |
1677 | /* BB more RC checks ? */ | 1683 | /* BB more RC checks ? */ |
1678 | if (rc== -EAGAIN) { | 1684 | if (rc== -EAGAIN) { |
1679 | if (smb_read_data) { | 1685 | if (smb_read_data) { |
1680 | cifs_buf_release(smb_read_data); | 1686 | if(buf_type == CIFS_SMALL_BUFFER) |
1687 | cifs_small_buf_release(smb_read_data); | ||
1688 | else if(buf_type == CIFS_LARGE_BUFFER) | ||
1689 | cifs_buf_release(smb_read_data); | ||
1681 | smb_read_data = NULL; | 1690 | smb_read_data = NULL; |
1682 | } | 1691 | } |
1683 | } | 1692 | } |
@@ -1734,7 +1743,10 @@ static int cifs_readpages(struct file *file, struct address_space *mapping, | |||
1734 | break; | 1743 | break; |
1735 | } | 1744 | } |
1736 | if (smb_read_data) { | 1745 | if (smb_read_data) { |
1737 | cifs_buf_release(smb_read_data); | 1746 | if(buf_type == CIFS_SMALL_BUFFER) |
1747 | cifs_small_buf_release(smb_read_data); | ||
1748 | else if(buf_type == CIFS_LARGE_BUFFER) | ||
1749 | cifs_buf_release(smb_read_data); | ||
1738 | smb_read_data = NULL; | 1750 | smb_read_data = NULL; |
1739 | } | 1751 | } |
1740 | bytes_read = 0; | 1752 | bytes_read = 0; |