diff options
author | Jeremy Allison <jra@samba.org> | 2001-08-22 00:29:40 +0000 |
---|---|---|
committer | Jeremy Allison <jra@samba.org> | 2001-08-22 00:29:40 +0000 |
commit | fe4aa720181a43f7a636ca029680fab0c836b968 (patch) | |
tree | 14ba095f2278198e00a7d79b2248c5efd6403cee /source/smbd/open.c | |
parent | feb9bf86723bce7dd1e81250b92191c370228a45 (diff) | |
download | samba-fe4aa720181a43f7a636ca029680fab0c836b968.tar.gz samba-fe4aa720181a43f7a636ca029680fab0c836b968.tar.xz samba-fe4aa720181a43f7a636ca029680fab0c836b968.zip |
Fixed the (incorrect) paranioa fix I put in for the fcntl lock spin.
Don't delete a share mode that failed to remove the oplock (doh!),
just set the oplock entry to zero....
Jeremy.
Diffstat (limited to 'source/smbd/open.c')
-rw-r--r-- | source/smbd/open.c | 44 |
1 files changed, 35 insertions, 9 deletions
diff --git a/source/smbd/open.c b/source/smbd/open.c index 143aa934a68..633cf718179 100644 --- a/source/smbd/open.c +++ b/source/smbd/open.c @@ -527,17 +527,42 @@ dev = %x, inode = %.0f\n", old_shares[i].op_type, fname, (unsigned int)dev, (dou if(broke_oplock) { free((char *)old_shares); - if (del_share_entry(dev, inode, &broken_entry, NULL) == -1) { - DEBUG(0,("open_mode_check: cannot delete entry when breaking oplock (%x) on file %s, \ -dev = %x, inode = %.0f\n", broken_entry.op_type, fname, (unsigned int)dev, (double)inode)); - errno = EACCES; - unix_ERR_class = ERRDOS; - unix_ERR_code = ERRbadshare; - return -1; - } num_share_modes = get_share_modes(conn, dev, inode, &old_shares); oplock_contention_count++; - } + + /* Paranoia check that this is no longer an exlusive entry. */ + for(i = 0; i < num_share_modes; i++) { + share_mode_entry *share_entry = &old_shares[i]; + + if (share_modes_identical(&broken_entry, share_entry) && + EXCLUSIVE_OPLOCK_TYPE(share_entry->op_type) ) { + + /* + * This should not happen. The target left this oplock + * as exlusive.... The process *must* be dead.... + */ + + DEBUG(0,("open_mode_check: exlusive oplock left after break ! For file %s, +dev = %x, inode = %.0f\n", fname, (unsigned int)dev, (double)inode)); + + if (process_exists(broken_entry.pid)) { + pstring errmsg; + slprintf(errmsg, sizeof(errmsg)-1, + "open_mode_check: Existant process %d left active oplock.\n", + broken_entry.pid ); + smb_panic(errmsg); + } + + if (!clear_share_entry(dev, inode, &broken_entry)) { + errno = EACCES; + unix_ERR_class = ERRDOS; + unix_ERR_code = ERRbadshare; + return -1; + } + } + } /* end for paranoia... */ + } /* end if broke_oplock */ + } while(broke_oplock); if(old_shares != 0) @@ -570,6 +595,7 @@ static void kernel_flock(files_struct *fsp, int deny_mode) else if (deny_mode == DENY_ALL) kernel_mode = LOCK_MAND; if (kernel_mode) flock(fsp->fd, kernel_mode); #endif + ;; } |