[cifs-protocol] Clarification on expected behavior with SMB2 short reads/writes. [120051422002815]

Obaid Farooqi obaidf at microsoft.com
Thu May 14 18:15:50 UTC 2020

Hi Jeremy:
Thanks for contacting Microsoft. I have created a case to track this issue. A member of the open specifications team will be in touch soon.

Obaid Farooqi
Escalatiion Engineer | Microsoft

-----Original Message-----
From: Jeremy Allison <jra at samba.org> 
Sent: Thursday, May 14, 2020 12:32 PM
To: cifs-protocol <cifs-protocol at lists.samba.org>; Interoperability Documentation Help <dochelp at microsoft.com>; Stefan Metzmacher <metze at samba.org>; jra at samba.org; Obaid Farooqi <obaidf at microsoft.com>; Bradley Suinn <suinn at apple.com>; Steve French <smfrench at gmail.com>
Subject: [EXTERNAL] Clarification on expected behavior with SMB2 short reads/writes.

Hi Dochelp,

We recently noticed a problem with the Windows (and MacOSX) clients when the server returns short reads.

The MS-SMB2 description of SMB2_READ has the following field inside the read request:

MinimumCount (4 bytes): The minimum number of bytes to be read for this operation to be successful. If fewer than the minimum number of bytes are read by the server, the server MUST return an error rather than the bytes read.

Windows sets this to zero, implying that for a read request of X bytes, a server may optionally return less than X bytes, so long as the number of bytes returned is greater than MinimumCount.

This is expected at end-of-file, when
the server has run out of available bytes to return.

However, the Windows client misbehaves
if this is returned for an SMB2_READ at
an offset in the middle of a file.

The Windows client pipelines reads at
(around) 1MB byte boundaries, and issues as many async simultaneous reads as it has credits for. So for a 1GB file it can simultaneously send (note this is an example only, I have wireshark traces of real behavior):

1). SMB2_READ offset 0 length 1MB
2). SMB2_READ offset 1MB length 1MB
3). SMB2_READ offset 2MB length 1MB
X). SMB2_READ offset (X-1)MB length 1MB

Consider if the server returns a read
return value of 1MB-2 bytes for the
(1) read (the one at offset 0).

Linux cifsfs and the libsmbclient Samba
library check the short read return value, and will re-issue a read at offset 1MB-2 length 2 bytes to fill in the missing data.

The Windows client doesn't treat the short read reply at (1) as EOF, and doesn't re-issue a read for the missing 2 bytes, ending up with data corruption in the copied file.

If this is expected behavior, I think either the protocol doc needs updating to prohibit short reads (and probably writes too) or a Windows behavior note adding explaining that Windows clients cannot cope with short SMB2_READ / SMB2_WRITE replies (execpt for EOF/EIO or DISK_FULL/EIO cases).


Jeremy Allison,
Samba Team.

More information about the cifs-protocol mailing list