Change the type of newsize argument in the smbfs_smb_setfsize() function

from int to int64.
MSDN says that SMB_SET_FILE_END_OF_FILE_INFO uses signed 64-bit integer
to specify offset, but since smbfs_smb_setfsize() has used plain int,
a value was truncated in case when offset was larger than 2G.
	https://msdn.microsoft.com/en-us/library/ff469975.aspx

In particular, now `truncate -s 10G` will work correctly on the mounted
SMB share.

Reported and tested by:	Eugene Grosbein <eugen at grosbein dot net>
MFC after:	1 week
This commit is contained in:
Andrey V. Elsukov 2016-01-11 18:11:06 +00:00
parent adcd1d80b8
commit c829016e85
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=293679
3 changed files with 8 additions and 6 deletions

View File

@ -333,18 +333,18 @@ smbfs_smb_flush(struct smbnode *np, struct smb_cred *scred)
}
int
smbfs_smb_setfsize(struct smbnode *np, int newsize, struct smb_cred *scred)
smbfs_smb_setfsize(struct smbnode *np, int64_t newsize, struct smb_cred *scred)
{
struct smb_share *ssp = np->n_mount->sm_share;
struct smb_rq *rqp;
struct mbchain *mbp;
int error;
if (!smbfs_smb_seteof(np, (int64_t) newsize, scred)) {
if (!smbfs_smb_seteof(np, newsize, scred)) {
np->n_flag |= NFLUSHWIRE;
return (0);
}
/* XXX: We should use SMB_COM_WRITE_ANDX to support large offsets */
error = smb_rq_alloc(SSTOCP(ssp), SMB_COM_WRITE, scred, &rqp);
if (error)
return (error);
@ -352,7 +352,7 @@ smbfs_smb_setfsize(struct smbnode *np, int newsize, struct smb_cred *scred)
smb_rq_wstart(rqp);
mb_put_mem(mbp, (caddr_t)&np->n_fid, 2, MB_MSYSTEM);
mb_put_uint16le(mbp, 0);
mb_put_uint32le(mbp, newsize);
mb_put_uint32le(mbp, (uint32_t)newsize);
mb_put_uint16le(mbp, 0);
smb_rq_wend(rqp);
smb_rq_bstart(rqp);

View File

@ -128,7 +128,8 @@ int smbfs_smb_lock(struct smbnode *np, int op, caddr_t id,
off_t start, off_t end, struct smb_cred *scred);
int smbfs_smb_statfs(struct smb_share *ssp, struct statfs *sbp,
struct smb_cred *scred);
int smbfs_smb_setfsize(struct smbnode *np, int newsize, struct smb_cred *scred);
int smbfs_smb_setfsize(struct smbnode *np, int64_t newsize,
struct smb_cred *scred);
int smbfs_smb_query_info(struct smbnode *np, const char *name, int len,
struct smbfattr *fap, struct smb_cred *scred);

View File

@ -358,7 +358,8 @@ smbfs_setattr(ap)
doclose = 1;
}
if (error == 0)
error = smbfs_smb_setfsize(np, vap->va_size, scred);
error = smbfs_smb_setfsize(np,
(int64_t)vap->va_size, scred);
if (doclose)
smbfs_smb_close(ssp, np->n_fid, NULL, scred);
if (error) {