svn commit: samba r15961 - in trunk/source: include smbd
jra at samba.org
jra at samba.org
Tue May 30 18:39:04 GMT 2006
Author: jra
Date: 2006-05-30 18:39:04 +0000 (Tue, 30 May 2006)
New Revision: 15961
WebSVN: http://websvn.samba.org/cgi-bin/viewcvs.cgi?view=rev&root=samba&rev=15961
Log:
Bring HEAD up to date with the RAW-OPLOCK test fixes.
Jeremy.
Modified:
trunk/source/include/smb.h
trunk/source/smbd/nttrans.c
trunk/source/smbd/open.c
trunk/source/smbd/oplock.c
trunk/source/smbd/trans2.c
Changeset:
Modified: trunk/source/include/smb.h
===================================================================
--- trunk/source/include/smb.h 2006-05-30 18:38:10 UTC (rev 15960)
+++ trunk/source/include/smb.h 2006-05-30 18:39:04 UTC (rev 15961)
@@ -1538,19 +1538,26 @@
/*
* Bits we test with.
+ * Note these must fit into 16-bits.
*/
-
+
#define NO_OPLOCK 0
#define EXCLUSIVE_OPLOCK 1
#define BATCH_OPLOCK 2
#define LEVEL_II_OPLOCK 4
+
+/* The following are Samba-private. */
#define INTERNAL_OPEN_ONLY 8
#define FAKE_LEVEL_II_OPLOCK 16 /* Client requested no_oplock, but we have to
* inform potential level2 holders on
* write. */
#define DEFERRED_OPEN_ENTRY 32
#define UNUSED_SHARE_MODE_ENTRY 64
+#define FORCE_OPLOCK_BREAK_TO_NONE 128
+/* None of the following should ever appear in fsp->oplock_request. */
+#define SAMBA_PRIVATE_OPLOCK_MASK (INTERNAL_OPEN_ONLY|DEFERRED_OPEN_ENTRY|UNUSED_SHARE_MODE_ENTRY|FORCE_OPLOCK_BREAK_TO_NONE)
+
#define EXCLUSIVE_OPLOCK_TYPE(lck) ((lck) & ((unsigned int)EXCLUSIVE_OPLOCK|(unsigned int)BATCH_OPLOCK))
#define BATCH_OPLOCK_TYPE(lck) ((lck) & (unsigned int)BATCH_OPLOCK)
#define LEVEL_II_OPLOCK_TYPE(lck) ((lck) & ((unsigned int)LEVEL_II_OPLOCK|(unsigned int)FAKE_LEVEL_II_OPLOCK))
Modified: trunk/source/smbd/nttrans.c
===================================================================
--- trunk/source/smbd/nttrans.c 2006-05-30 18:38:10 UTC (rev 15960)
+++ trunk/source/smbd/nttrans.c 2006-05-30 18:39:04 UTC (rev 15961)
@@ -1658,11 +1658,11 @@
status = open_file_ntcreate(conn,oldname,&sbuf1,
FILE_READ_DATA, /* Read-only. */
- 0, /* No sharing. */
+ FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
FILE_OPEN,
0, /* No create options. */
FILE_ATTRIBUTE_NORMAL,
- INTERNAL_OPEN_ONLY,
+ NO_OPLOCK,
&info, &fsp1);
if (!NT_STATUS_IS_OK(status)) {
@@ -1671,11 +1671,11 @@
status = open_file_ntcreate(conn,newname,&sbuf2,
FILE_WRITE_DATA, /* Read-only. */
- 0, /* No sharing. */
+ FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
FILE_CREATE,
0, /* No create options. */
fattr,
- INTERNAL_OPEN_ONLY,
+ NO_OPLOCK,
&info, &fsp2);
if (!NT_STATUS_IS_OK(status)) {
Modified: trunk/source/smbd/open.c
===================================================================
--- trunk/source/smbd/open.c 2006-05-30 18:38:10 UTC (rev 15960)
+++ trunk/source/smbd/open.c 2006-05-30 18:39:04 UTC (rev 15961)
@@ -599,7 +599,7 @@
}
/*
- * 1) No files open at all: Grant whatever the client wants.
+ * 1) No files open at all or internal open: Grant whatever the client wants.
*
* 2) Exclusive (or batch) oplock around: If the requested access is a delete
* request, break if the oplock around is a batch oplock. If it's another
@@ -608,7 +608,10 @@
* 3) Only level2 around: Grant level2 and do nothing else.
*/
-static BOOL delay_for_oplocks(struct share_mode_lock *lck, files_struct *fsp, int pass_number)
+static BOOL delay_for_oplocks(struct share_mode_lock *lck,
+ files_struct *fsp,
+ int pass_number,
+ int oplock_request)
{
int i;
struct share_mode_entry *exclusive = NULL;
@@ -616,7 +619,7 @@
BOOL delay_it = False;
BOOL have_level2 = False;
- if (is_stat_open(fsp->access_mask)) {
+ if ((oplock_request & INTERNAL_OPEN_ONLY) || is_stat_open(fsp->access_mask)) {
fsp->oplock_type = NO_OPLOCK;
return False;
}
@@ -683,8 +686,19 @@
procid_str_static(&exclusive->pid)));
exclusive->op_mid = get_current_mid();
+ if (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE) {
+ /* Send the message with this bit set. */
+ exclusive->op_type |= FORCE_OPLOCK_BREAK_TO_NONE;
+ }
+
+ /* Create the message. */
share_mode_entry_to_message(msg, exclusive);
+ /* And remove it again - we don't want this stored. */
+ if (oplock_request & FORCE_OPLOCK_BREAK_TO_NONE) {
+ exclusive->op_type &= ~FORCE_OPLOCK_BREAK_TO_NONE;
+ }
+
become_root();
ret = message_send_pid(exclusive->pid, MSG_SMB_BREAK_REQUEST,
msg, MSG_SMB_SHARE_MODE_ENTRY_SIZE, True);
@@ -692,7 +706,6 @@
if (!ret) {
DEBUG(3, ("Could not send oplock break message\n"));
}
- file_free(fsp);
}
return delay_it;
@@ -1088,7 +1101,6 @@
int flags2=0;
BOOL file_existed = VALID_STAT(*psbuf);
BOOL def_acl = False;
- BOOL internal_only_open = False;
SMB_DEV_T dev = 0;
SMB_INO_T inode = 0;
NTSTATUS fsp_open = NT_STATUS_ACCESS_DENIED;
@@ -1131,11 +1143,6 @@
create_disposition, create_options, unx_mode,
oplock_request));
- if (oplock_request == INTERNAL_OPEN_ONLY) {
- internal_only_open = True;
- oplock_request = 0;
- }
-
if ((pml = get_open_deferred_message(mid)) != NULL) {
struct deferred_open_record *state =
(struct deferred_open_record *)pml->private_data.data;
@@ -1172,7 +1179,8 @@
/* ignore any oplock requests if oplocks are disabled */
if (!lp_oplocks(SNUM(conn)) || global_client_failed_oplock_break ||
IS_VETO_OPLOCK_PATH(conn, fname)) {
- oplock_request = 0;
+ /* Mask off everything except the private Samba bits. */
+ oplock_request &= SAMBA_PRIVATE_OPLOCK_MASK;
}
/* this is for OS/2 long file names - say we don't support them */
@@ -1344,7 +1352,8 @@
fsp->share_access = share_access;
fsp->fh->private_options = create_options;
fsp->access_mask = access_mask;
- fsp->oplock_type = oplock_request;
+ /* Ensure no SAMBA_PRIVATE bits can be set. */
+ fsp->oplock_type = (oplock_request & ~SAMBA_PRIVATE_OPLOCK_MASK);
if (timeval_is_zero(&request_time)) {
request_time = fsp->open_time;
@@ -1359,14 +1368,16 @@
fname);
if (lck == NULL) {
+ file_free(fsp);
DEBUG(0, ("Could not get share mode lock\n"));
return NT_STATUS_SHARING_VIOLATION;
}
/* First pass - send break only on batch oplocks. */
- if (delay_for_oplocks(lck, fsp, 1)) {
+ if (delay_for_oplocks(lck, fsp, 1, oplock_request)) {
schedule_defer_open(lck, request_time);
TALLOC_FREE(lck);
+ file_free(fsp);
return NT_STATUS_SHARING_VIOLATION;
}
@@ -1377,9 +1388,10 @@
if (NT_STATUS_IS_OK(status)) {
/* We might be going to allow this open. Check oplock status again. */
/* Second pass - send break for both batch or exclusive oplocks. */
- if (delay_for_oplocks(lck, fsp, 2)) {
+ if (delay_for_oplocks(lck, fsp, 2, oplock_request)) {
schedule_defer_open(lck, request_time);
TALLOC_FREE(lck);
+ file_free(fsp);
return NT_STATUS_SHARING_VIOLATION;
}
}
@@ -1453,7 +1465,7 @@
* cope with the braindead 1 second delay.
*/
- if (!internal_only_open &&
+ if (!(oplock_request & INTERNAL_OPEN_ONLY) &&
lp_defer_sharing_violations()) {
struct timeval timeout;
struct deferred_open_record state;
Modified: trunk/source/smbd/oplock.c
===================================================================
--- trunk/source/smbd/oplock.c 2006-05-30 18:38:10 UTC (rev 15960)
+++ trunk/source/smbd/oplock.c 2006-05-30 18:39:04 UTC (rev 15961)
@@ -540,6 +540,7 @@
}
if ((global_client_caps & CAP_LEVEL_II_OPLOCKS) &&
+ !(msg.op_type & FORCE_OPLOCK_BREAK_TO_NONE) &&
!koplocks && /* NOTE: we force levelII off for kernel oplocks -
* this will change when it is supported */
lp_level2_oplocks(SNUM(fsp->conn))) {
Modified: trunk/source/smbd/trans2.c
===================================================================
--- trunk/source/smbd/trans2.c 2006-05-30 18:38:10 UTC (rev 15960)
+++ trunk/source/smbd/trans2.c 2006-05-30 18:39:04 UTC (rev 15961)
@@ -4020,15 +4020,19 @@
status = open_file_ntcreate(conn, fname, &sbuf,
FILE_WRITE_DATA,
- FILE_SHARE_READ|FILE_SHARE_WRITE,
+ FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
FILE_OPEN,
0,
FILE_ATTRIBUTE_NORMAL,
- INTERNAL_OPEN_ONLY,
+ FORCE_OPLOCK_BREAK_TO_NONE,
NULL, &new_fsp);
if (!NT_STATUS_IS_OK(status)) {
- return(UNIXERROR(ERRDOS,ERRbadpath));
+ if (open_was_deferred(SVAL(inbuf,smb_mid))) {
+ /* We have re-scheduled this call. */
+ return -1;
+ }
+ return(UNIXERROR(ERRDOS,ERRnoaccess));
}
ret = vfs_allocate_file_space(new_fsp, allocation_size);
if (SMB_VFS_FSTAT(new_fsp,new_fsp->fh->fd,&new_sbuf) != 0) {
@@ -4561,7 +4565,6 @@
POSIX_LOCK,
&my_lock_ctx);
- /* TODO: Deal with rescheduling blocking lock fail here... */
if (lp_blocking_locks(SNUM(conn)) && ERROR_WAS_LOCK_DENIED(status)) {
/*
* A blocking lock was requested. Package up
@@ -4660,15 +4663,19 @@
status = open_file_ntcreate(conn, fname, &sbuf,
FILE_WRITE_DATA,
- FILE_SHARE_READ|FILE_SHARE_WRITE,
+ FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
FILE_OPEN,
0,
FILE_ATTRIBUTE_NORMAL,
- INTERNAL_OPEN_ONLY,
+ FORCE_OPLOCK_BREAK_TO_NONE,
NULL, &new_fsp);
if (!NT_STATUS_IS_OK(status)) {
- return(UNIXERROR(ERRDOS,ERRbadpath));
+ if (open_was_deferred(SVAL(inbuf,smb_mid))) {
+ /* We have re-scheduled this call. */
+ return -1;
+ }
+ return(UNIXERROR(ERRDOS,ERRnoaccess));
}
ret = vfs_set_filelen(new_fsp, size);
close_file(new_fsp,NORMAL_CLOSE);
More information about the samba-cvs
mailing list