ensure that we honor SMB2 read min_count properly
authorAndrew Tridgell <tridge@samba.org>
Tue, 27 May 2008 08:20:23 +0000 (18:20 +1000)
committerAndrew Tridgell <tridge@samba.org>
Tue, 27 May 2008 08:20:23 +0000 (18:20 +1000)
(This used to be commit 318038d6f670efffa96d8b0db63f46b3752e1cd3)

source4/libcli/raw/interfaces.h
source4/ntvfs/ntvfs_generic.c
source4/ntvfs/posix/pvfs_read.c

index 68ebc19bdbb3c8c32089657e3da4ea4aabf38026..17c85138ac1377610936bedcce5ea7b6634d41d2 100644 (file)
@@ -1647,7 +1647,7 @@ union smb_read {
                struct {
                        union smb_handle file;
                        uint64_t offset;
-                       uint16_t mincnt;
+                       uint32_t mincnt; /* enforced on SMB2, 16 bit on SMB */
                        uint32_t maxcnt;
                        uint16_t remaining;
                        bool read_for_execute;
index 3d92c0be3391ead1903b5df3da689005deb1e8be..06d89a717bead710e83c62398a815f81b0839df8 100644 (file)
@@ -1295,16 +1295,6 @@ static NTSTATUS ntvfs_map_read_finish(struct ntvfs_module_context *ntvfs,
                rd->smb2.out.data.length= rd2->generic.out.nread;
                rd->smb2.out.remaining  = 0;
                rd->smb2.out.reserved   = 0;
-               if (NT_STATUS_IS_OK(status) &&
-                   rd->smb2.out.data.length == 0) {
-                       status = NT_STATUS_END_OF_FILE;
-               }
-               /* SMB2 does honor the min_count field, SMB does not */
-               if (NT_STATUS_IS_OK(status) && 
-                   rd->smb2.in.min_count > rd->smb2.out.data.length) {
-                       rd->smb2.out.data.length = 0;
-                       status = NT_STATUS_END_OF_FILE;                 
-               }
                break;
        default:
                return NT_STATUS_INVALID_LEVEL;
@@ -1396,7 +1386,7 @@ NTSTATUS ntvfs_map_read(struct ntvfs_module_context *ntvfs,
        case RAW_READ_SMB2:
                rd2->readx.in.file.ntvfs= rd->smb2.in.file.ntvfs;
                rd2->readx.in.offset    = rd->smb2.in.offset;
-               rd2->readx.in.mincnt    = rd->smb2.in.length;
+               rd2->readx.in.mincnt    = rd->smb2.in.min_count;
                rd2->readx.in.maxcnt    = rd->smb2.in.length;
                rd2->readx.in.remaining = 0;
                rd2->readx.out.data     = rd->smb2.out.data.data;
index 418b7e09fb073bcf038a8e8d03da5d7c336f298a..a01a8a57e3b800595ebe434d9aed4a54ba76cab4 100644 (file)
@@ -93,6 +93,14 @@ NTSTATUS pvfs_read(struct ntvfs_module_context *ntvfs,
                return pvfs_map_errno(pvfs, errno);
        }
 
+       /* only SMB2 honors mincnt */
+       if (req->ctx->protocol == PROTOCOL_SMB2) {
+               if (rd->readx.in.mincnt > ret ||
+                   (ret == 0 && maxcnt > 0)) {
+                       return NT_STATUS_END_OF_FILE;
+               }
+       }
+
        f->handle->position = f->handle->seek_offset = rd->readx.in.offset + ret;
 
        rd->readx.out.nread = ret;