[linux-cifs-client] [PATCH] F_GETLK request - returning value

Pavel Shilovsky piastry at etersoft.ru
Sat Mar 28 11:27:11 GMT 2009


Previous patch only added right behaviour without option forcemand. Here 
is another path that works right with forcemand and without it.

diff --git a/fs/cifs/cifssmb.c b/fs/cifs/cifssmb.c
index 8f0f86d..aa26a3a 100644
--- a/fs/cifs/cifssmb.c
+++ b/fs/cifs/cifssmb.c
@@ -1882,6 +1882,16 @@ CIFSSMBPosixLock(const int xid, struct 
cifsTconInfo *tcon,
             ((char *)&pSMBr->hdr.Protocol + data_offset);
         if (parm_data->lock_type == cpu_to_le16(CIFS_UNLCK))
             pLockData->fl_type = F_UNLCK;
+        else {
+            if (parm_data->lock_type == cpu_to_le16(CIFS_RDLCK))
+                pLockData->fl_type = F_RDLCK;
+            else if (parm_data->lock_type == cpu_to_le16(CIFS_WRLCK))
+                pLockData->fl_type = F_WRLCK;
+
+            pLockData->fl_start = parm_data->start;
+            pLockData->fl_end = parm_data->start + parm_data->length - 1;
+            pLockData->fl_pid = parm_data->pid;
+        }
     }
 
 plk_err_exit:
diff --git a/fs/cifs/file.c b/fs/cifs/file.c
index 6851043..7e333c2 100644
--- a/fs/cifs/file.c
+++ b/fs/cifs/file.c
@@ -898,6 +898,25 @@ int cifs_lock(struct file *file, int cmd, struct 
file_lock *pfLock)
             /* if rc == ERR_SHARING_VIOLATION ? */
             rc = 0;    /* do not change lock type to unlock
                    since range in use */
+            if (lockType | LOCKING_ANDX_SHARED_LOCK) {
+                pfLock->fl_type = F_WRLCK;
+            } else {
+                rc = CIFSSMBLock(xid, pTcon, netfid, length, 
pfLock->fl_start,
+                     0, 1, lockType | LOCKING_ANDX_SHARED_LOCK, 0 /* 
wait flag */ );
+                if (rc == 0) {
+                    rc = CIFSSMBLock(xid, pTcon, netfid, length,
+                         pfLock->fl_start, 1 /* numUnlock */ ,
+                         0 /* numLock */ , lockType | 
LOCKING_ANDX_SHARED_LOCK,
+                         0 /* wait flag */ );
+                    pfLock->fl_type = F_RDLCK;
+                    if (rc != 0)
+                        cERROR(1, ("Error unlocking previously locked "
+                           "range %d during test of lock", rc));
+                    rc = 0;
+                } else {
+                    pfLock->fl_type = F_WRLCK;
+                }
+            }
         }
 
         FreeXid(xid);

 Signed-off-by: Pavel Shilovsky <piastryyy at gmail.com>

--
Best regards,
Pavel Shilovsky.


More information about the linux-cifs-client mailing list