int rc = -EACCES;
        WRITE_REQ *pSMB = NULL;
        WRITE_RSP *pSMBr = NULL;
-       int bytes_returned;
+       int bytes_returned, wct;
        __u32 bytes_sent;
        __u16 byte_count;
 
        /* cFYI(1,("write at %lld %d bytes",offset,count));*/
-       rc = smb_init(SMB_COM_WRITE_ANDX, 14, tcon, (void **) &pSMB,
+       if(tcon->ses == NULL)
+               return -ECONNABORTED;
+
+       if(tcon->ses->capabilities & CAP_LARGE_FILES)
+               wct = 14;
+       else
+               wct = 12;
+
+       rc = smb_init(SMB_COM_WRITE_ANDX, wct, tcon, (void **) &pSMB,
                      (void **) &pSMBr);
        if (rc)
                return rc;
        pSMB->AndXCommand = 0xFF;       /* none */
        pSMB->Fid = netfid;
        pSMB->OffsetLow = cpu_to_le32(offset & 0xFFFFFFFF);
-       pSMB->OffsetHigh = cpu_to_le32(offset >> 32);
+       if(wct == 14) 
+               pSMB->OffsetHigh = cpu_to_le32(offset >> 32);
+       else if((offset >> 32) > 0) /* can not handle this big offset for old */
+               return -EIO;
+       
        pSMB->Reserved = 0xFFFFFFFF;
        pSMB->WriteMode = 0;
        pSMB->Remaining = 0;
        pSMB->DataLengthLow = cpu_to_le16(bytes_sent & 0xFFFF);
        pSMB->DataLengthHigh = cpu_to_le16(bytes_sent >> 16);
        pSMB->hdr.smb_buf_length += bytes_sent+1;
-       pSMB->ByteCount = cpu_to_le16(byte_count);
+
+       if(wct == 14)
+               pSMB->ByteCount = cpu_to_le16(byte_count);
+       else { /* old style write has byte count 4 bytes earlier */
+               struct smb_com_writex_req * pSMBW = 
+                       (struct smb_com_writex_req *)pSMB;
+               pSMBW->ByteCount = cpu_to_le16(byte_count);
+       }
 
        rc = SendReceive(xid, tcon->ses, (struct smb_hdr *) pSMB,
                         (struct smb_hdr *) pSMBr, &bytes_returned, long_op);
 
        char *smb_read_data;
        char __user *current_offset;
        struct smb_com_read_rsp *pSMBr;
+       int use_old_read = FALSE;
 
        xid = GetXid();
        cifs_sb = CIFS_SB(file->f_dentry->d_sb);
        pTcon = cifs_sb->tcon;
 
+       if(pTcon->ses)
+               if((pTcon->ses->capabilities & CAP_LARGE_FILES) == 0)
+                       use_old_read = TRUE;
+
        if (file->private_data == NULL) {
                FreeXid(xid);
                return -EBADF;
                                if (rc != 0)
                                        break;
                        }
-
-                       rc = CIFSSMBRead(xid, pTcon,
-                                open_file->netfid,
-                                current_read_size, *poffset,
-                                &bytes_read, &smb_read_data);
-                       if(rc == -EINVAL) {
+                       if(use_old_read)
                                rc = SMBLegacyRead(xid, pTcon,
                                        open_file->netfid,
                                        current_read_size, *poffset,
                                        &bytes_read, &smb_read_data);
+                       else {
+                               rc = CIFSSMBRead(xid, pTcon,
+                                       open_file->netfid,
+                                       current_read_size, *poffset,
+                                       &bytes_read, &smb_read_data);
+                               if(rc == -EINVAL) {
+                                       use_old_read = TRUE;
+                                       rc = -EAGAIN;
+                                       continue;
+                               }
                        }
                        pSMBr = (struct smb_com_read_rsp *)smb_read_data;
                        if (copy_to_user(current_offset, 
        int xid;
        char *current_offset;
        struct cifsFileInfo *open_file;
+       int use_old_read = FALSE;
 
        xid = GetXid();
        cifs_sb = CIFS_SB(file->f_dentry->d_sb);
                return -EBADF;
        }
        open_file = (struct cifsFileInfo *)file->private_data;
+       if(pTcon->ses)
+               if((pTcon->ses->capabilities & CAP_LARGE_FILES) == 0)
+                       use_old_read = TRUE;
 
        if ((file->f_flags & O_ACCMODE) == O_WRONLY)
                cFYI(1, ("attempting read on write only file instance"));
                                if (rc != 0)
                                        break;
                        }
-
-                       rc = CIFSSMBRead(xid, pTcon,
-                                open_file->netfid,
-                                current_read_size, *poffset,
-                                &bytes_read, ¤t_offset);
-                       if(rc == -EINVAL) {
+                       if(use_old_read) 
                                rc = SMBLegacyRead(xid, pTcon,
+                                        open_file->netfid,
+                                        current_read_size, *poffset,
+                                        &bytes_read, ¤t_offset);
+                       else {
+                               rc = CIFSSMBRead(xid, pTcon,
                                        open_file->netfid,
                                        current_read_size, *poffset,
                                        &bytes_read, ¤t_offset);
+                               /* check if server disavows support for
+                                  64 bit offsets */
+                               if(rc == -EINVAL) {
+                                       rc = -EAGAIN;
+                                       use_old_read = TRUE;
+                                       continue;
+                               }
                        }
                }
                if (rc || (bytes_read == 0)) {
        struct smb_com_read_rsp *pSMBr;
        struct pagevec lru_pvec;
        struct cifsFileInfo *open_file;
+       int use_old_read = FALSE;
 
        xid = GetXid();
        if (file->private_data == NULL) {
        open_file = (struct cifsFileInfo *)file->private_data;
        cifs_sb = CIFS_SB(file->f_dentry->d_sb);
        pTcon = cifs_sb->tcon;
-
+       if(pTcon->ses)
+               if((pTcon->ses->capabilities & CAP_LARGE_FILES) == 0)
+                       use_old_read = TRUE;
        pagevec_init(&lru_pvec, 0);
 
        for (i = 0; i < num_pages; ) {
                                        break;
                        }
 
-                       rc = CIFSSMBRead(xid, pTcon,
-                               open_file->netfid,
-                               read_size, offset,
-                               &bytes_read, &smb_read_data);
-                       if (rc == -EINVAL) {
+                       if(use_old_read)
                                rc = SMBLegacyRead(xid, pTcon,
                                        open_file->netfid,
                                        read_size, offset,
                                        &bytes_read, &smb_read_data);
+                       else {
+                               rc = CIFSSMBRead(xid, pTcon,
+                                       open_file->netfid,
+                                       read_size, offset,
+                                       &bytes_read, &smb_read_data);
+                               if(rc == -EINVAL) {
+                                       use_old_read = TRUE;
+                                       rc = -EAGAIN;
+                                       continue;
+                               }
                        }
 
                        /* BB more RC checks ? */