s3:smbd/close remove filesystem lock before removing sharemode
authorChristian Ambach <ambi@samba.org>
Thu, 13 Jun 2013 13:23:07 +0000 (15:23 +0200)
committerChristian Ambach <ambi@samba.org>
Tue, 25 Jun 2013 12:48:44 +0000 (14:48 +0200)
otherwise we are open for a race condition:

opener 1 opens file and closes it
- during the close, the share mode entry will be removed from
  locking.tdb, but share mode in the file system will be dropped later
  after delete_on_close and write time updates have been done

opener 2 requests open of same file with file overwrite
- locking.tdb does not list original entry, but file system share mode
  is still around
- VFS_FTRUNCATE will fail and error was converted to STATUS_ACCESS_DENIED

Signed-off-by: Christian Ambach <ambi@samba.org>
Reviewed-by: Volker Lendecke <vl@samba.org>
Autobuild-User(master): Christian Ambach <ambi@samba.org>
Autobuild-Date(master): Tue Jun 25 14:48:44 CEST 2013 on sn-devel-104

source3/smbd/close.c

index 093bb9f7ed84c61ec8364ca0be0091979094523e..2bd588b176190e3e008266b79969f70e569c7d1c 100644 (file)
@@ -246,6 +246,7 @@ static NTSTATUS close_remove_share_mode(files_struct *fsp,
        const struct security_token *del_nt_token = NULL;
        bool got_tokens = false;
        bool normal_close;
+       int ret_flock;
 
        /* Ensure any pending write time updates are done. */
        if (fsp->update_write_time_event) {
@@ -469,6 +470,14 @@ static NTSTATUS close_remove_share_mode(files_struct *fsp,
                pop_sec_ctx();
        }
 
+       /* remove filesystem sharemodes */
+       ret_flock = SMB_VFS_KERNEL_FLOCK(fsp, 0, 0);
+       if (ret_flock == -1) {
+               DEBUG(2, ("close_remove_share_mode: removing kernel flock for "
+                                       "%s failed: %s\n", fsp_str_dbg(fsp),
+                                       strerror(errno)));
+       }
+
        if (!del_share_mode(lck, fsp)) {
                DEBUG(0, ("close_remove_share_mode: Could not delete share "
                          "entry for file %s\n", fsp_str_dbg(fsp)));