[SCM] Samba Shared Repository - branch v4-0-test updated - release-4-0-0alpha2-1271-g4d40f3a

Stefan Metzmacher metze at samba.org
Wed Mar 12 17:04:47 GMT 2008


The branch, v4-0-test has been updated
       via  4d40f3a02643b4cdacee31f0b7bc9fc77cc9869a (commit)
       via  eeb0b8c349552517b521f1b8d7d9341e0ef630f2 (commit)
       via  e473068bddfaa9028ab8ee49291035313b35fed3 (commit)
       via  3f165d3114519c317b9e7c871bb61d4fcbb8fb09 (commit)
       via  b399f0c872f32bb791da196102a5872c20e62100 (commit)
       via  80f5f9362100b971fa12ffee33705b745131770e (commit)
       via  9db9b6d85d80a8aaa8bd432afaef9bb634d7364d (commit)
       via  b43f1a53dd185cc51a3fb8a18e311abb77c2a7c9 (commit)
       via  40563583f7ef3d8d1a3426c6c12eaecd18af215c (commit)
       via  cd1b8efc5d8dc1eec03fe1bf1eb58dbded9584eb (commit)
       via  3f7fef8b8c567379649611637d69c89d77d11d6c (commit)
       via  eb68a8ed4fa214ad2e858a7fbdf9b5376cda6e04 (commit)
      from  4556fafede8691c6a12670695ff108e9e59aff98 (commit)

http://gitweb.samba.org/?p=samba.git;a=shortlog;h=v4-0-test


- Log -----------------------------------------------------------------
commit 4d40f3a02643b4cdacee31f0b7bc9fc77cc9869a
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Mar 12 14:02:11 2008 +0100

    pvfs_open: retry pvfs_open() after an EGAIN or EWOULDBLOCK from open()
    
    In case a unix application as an oplock or share mode on
    a file we need to retry periodicly as there's no way
    to get a notification from the kernel when the oplock
    is released.
    
    metze

commit eeb0b8c349552517b521f1b8d7d9341e0ef630f2
Author: Stefan Metzmacher <metze at samba.org>
Date:   Mon Mar 10 12:48:02 2008 +0100

    pvfs_open: pass O_NONBLOCK to open() so that we'll not block with kernel oplocks
    
    metze

commit e473068bddfaa9028ab8ee49291035313b35fed3
Author: Stefan Metzmacher <metze at samba.org>
Date:   Fri Mar 7 12:21:11 2008 +0100

    opendb_tdb: use sys_lease to setup kernel oplocks
    
    metze

commit 3f165d3114519c317b9e7c871bb61d4fcbb8fb09
Author: Stefan Metzmacher <metze at samba.org>
Date:   Fri Mar 7 12:19:06 2008 +0100

    ntvfs/sysdep: implement linux kernel oplocks based F_SETLEASE
    
    metze

commit b399f0c872f32bb791da196102a5872c20e62100
Author: Stefan Metzmacher <metze at samba.org>
Date:   Fri Mar 7 12:19:06 2008 +0100

    ntvfs/sysdep: add sys_lease abstraction to later support kernel oplocks
    
    metze

commit 80f5f9362100b971fa12ffee33705b745131770e
Author: Stefan Metzmacher <metze at samba.org>
Date:   Sat Mar 8 09:20:08 2008 +0100

    pvfs_open: pass down &f->handle->fd to odb_open_file()
    
    metze

commit 9db9b6d85d80a8aaa8bd432afaef9bb634d7364d
Author: Stefan Metzmacher <metze at samba.org>
Date:   Sat Mar 8 09:12:09 2008 +0100

    opendb: pass down a pointer to the fd in odb_open_file()
    
    This prepares kernel oplock support.
    
    metze

commit b43f1a53dd185cc51a3fb8a18e311abb77c2a7c9
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Mar 12 17:34:16 2008 +0100

    ntvfs/cifs: fix the fnum on RAW_RENAME_NTTRANS
    
    metze

commit 40563583f7ef3d8d1a3426c6c12eaecd18af215c
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Mar 12 15:12:26 2008 +0100

    pvfs_rename: implement RAW_RENAME_NTTRANS as noop as w2k3
    
    metze

commit cd1b8efc5d8dc1eec03fe1bf1eb58dbded9584eb
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Mar 12 15:10:57 2008 +0100

    RAW-RENAME: w2k3 just ignores a NTTRANS-RENAME!
    
    metze

commit 3f7fef8b8c567379649611637d69c89d77d11d6c
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Mar 12 14:21:50 2008 +0100

    RAW-STREAMS: do a exit on the session after each sub tests
    
    metze

commit eb68a8ed4fa214ad2e858a7fbdf9b5376cda6e04
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Mar 12 14:21:21 2008 +0100

    RAW-STREAMS: do what the comments say
    
    metze

-----------------------------------------------------------------------

Summary of changes:
 source/cluster/ctdb/opendb_ctdb.c     |    2 +-
 source/librpc/idl/opendb.idl          |    1 +
 source/ntvfs/cifs/vfs_cifs.c          |    7 +
 source/ntvfs/common/config.mk         |    5 +-
 source/ntvfs/common/opendb.c          |    4 +-
 source/ntvfs/common/opendb.h          |    2 +-
 source/ntvfs/common/opendb_tdb.c      |   48 ++++++--
 source/ntvfs/posix/pvfs_open.c        |  119 +++++++++++++------
 source/ntvfs/posix/pvfs_rename.c      |   11 ++-
 source/ntvfs/sysdep/config.m4         |   10 ++
 source/ntvfs/sysdep/config.mk         |   18 +++
 source/ntvfs/sysdep/sys_lease.c       |  142 ++++++++++++++++++++++
 source/ntvfs/sysdep/sys_lease.h       |   65 ++++++++++
 source/ntvfs/sysdep/sys_lease_linux.c |  213 +++++++++++++++++++++++++++++++++
 source/torture/raw/oplock.c           |   65 ++++++++---
 source/torture/raw/streams.c          |   10 +-
 16 files changed, 655 insertions(+), 67 deletions(-)
 create mode 100644 source/ntvfs/sysdep/sys_lease.c
 create mode 100644 source/ntvfs/sysdep/sys_lease.h
 create mode 100644 source/ntvfs/sysdep/sys_lease_linux.c


Changeset truncated at 500 lines:

diff --git a/source/cluster/ctdb/opendb_ctdb.c b/source/cluster/ctdb/opendb_ctdb.c
index a7b8ddf..402f3a2 100644
--- a/source/cluster/ctdb/opendb_ctdb.c
+++ b/source/cluster/ctdb/opendb_ctdb.c
@@ -283,7 +283,7 @@ static NTSTATUS odb_oplock_break_send(struct odb_context *odb, struct opendb_ent
 */
 static NTSTATUS odb_ctdb_open_file(struct odb_lock *lck,
 				   void *file_handle, const char *path,
-				   bool allow_level_II_oplock,
+				   int *fd, bool allow_level_II_oplock,
 				   uint32_t oplock_level, uint32_t *oplock_granted)
 
 {
diff --git a/source/librpc/idl/opendb.idl b/source/librpc/idl/opendb.idl
index e3bc2d0..72bf23a 100644
--- a/source/librpc/idl/opendb.idl
+++ b/source/librpc/idl/opendb.idl
@@ -20,6 +20,7 @@ interface opendb
 		uint32 share_access;
 		uint32 access_mask;
 		pointer file_handle;
+		pointer fd;
 		/* we need a per-entry delete on close, as well as a per-file
 		   one, to cope with strange semantics on open */
 		boolean8 delete_on_close;
diff --git a/source/ntvfs/cifs/vfs_cifs.c b/source/ntvfs/cifs/vfs_cifs.c
index 58183b5..3c090b5 100644
--- a/source/ntvfs/cifs/vfs_cifs.c
+++ b/source/ntvfs/cifs/vfs_cifs.c
@@ -595,6 +595,13 @@ static NTSTATUS cvfs_rename(struct ntvfs_module_context *ntvfs,
 
 	SETUP_PID;
 
+	if (ren->nttrans.level == RAW_RENAME_NTTRANS) {
+		struct cvfs_file *f;
+		f = ntvfs_handle_get_backend_data(ren->nttrans.in.file.ntvfs, ntvfs);
+		if (!f) return NT_STATUS_INVALID_HANDLE;
+		ren->nttrans.in.file.fnum = f->fnum;
+	}
+
 	if (!(req->async_states->state & NTVFS_ASYNC_STATE_MAY_ASYNC)) {
 		return smb_raw_rename(private->tree, ren);
 	}
diff --git a/source/ntvfs/common/config.mk b/source/ntvfs/common/config.mk
index 2fc0942..3963ebc 100644
--- a/source/ntvfs/common/config.mk
+++ b/source/ntvfs/common/config.mk
@@ -9,7 +9,10 @@ OBJ_FILES = \
 		opendb.o \
 		opendb_tdb.o \
 		notify.o
-PUBLIC_DEPENDENCIES = NDR_OPENDB NDR_NOTIFY sys_notify share LIBDBWRAP
+PUBLIC_DEPENDENCIES = \
+		NDR_OPENDB NDR_NOTIFY \
+		sys_notify sys_lease \
+		share LIBDBWRAP
 PRIVATE_DEPENDENCIES = brlock_ctdb opendb_ctdb
 # End LIBRARY ntvfs_common
 ################################################
diff --git a/source/ntvfs/common/opendb.c b/source/ntvfs/common/opendb.c
index 1cc0771..676706e 100644
--- a/source/ntvfs/common/opendb.c
+++ b/source/ntvfs/common/opendb.c
@@ -97,11 +97,11 @@ _PUBLIC_ DATA_BLOB odb_get_key(TALLOC_CTX *mem_ctx, struct odb_lock *lck)
 */
 _PUBLIC_ NTSTATUS odb_open_file(struct odb_lock *lck,
 				void *file_handle, const char *path,
-				bool allow_level_II_oplock,
+				int *fd, bool allow_level_II_oplock,
 				uint32_t oplock_level, uint32_t *oplock_granted)
 {
 	return ops->odb_open_file(lck, file_handle, path,
-				  allow_level_II_oplock,
+				  fd, allow_level_II_oplock,
 				  oplock_level, oplock_granted);
 }
 
diff --git a/source/ntvfs/common/opendb.h b/source/ntvfs/common/opendb.h
index fb3223a..0454763 100644
--- a/source/ntvfs/common/opendb.h
+++ b/source/ntvfs/common/opendb.h
@@ -27,7 +27,7 @@ struct opendb_ops {
 	DATA_BLOB (*odb_get_key)(TALLOC_CTX *mem_ctx, struct odb_lock *lck);
 	NTSTATUS (*odb_open_file)(struct odb_lock *lck,
 				  void *file_handle, const char *path,
-				  bool allow_level_II_oplock,
+				  int *fd, bool allow_level_II_oplock,
 				  uint32_t oplock_level, uint32_t *oplock_granted);
 	NTSTATUS (*odb_open_file_pending)(struct odb_lock *lck, void *private);
 	NTSTATUS (*odb_close_file)(struct odb_lock *lck, void *file_handle,
diff --git a/source/ntvfs/common/opendb_tdb.c b/source/ntvfs/common/opendb_tdb.c
index 17fcdfb..be78e09 100644
--- a/source/ntvfs/common/opendb_tdb.c
+++ b/source/ntvfs/common/opendb_tdb.c
@@ -49,11 +49,13 @@
 #include "ntvfs/common/ntvfs_common.h"
 #include "cluster/cluster.h"
 #include "param/param.h"
+#include "ntvfs/sysdep/sys_lease.h"
 
 struct odb_context {
 	struct tdb_wrap *w;
 	struct ntvfs_context *ntvfs_ctx;
 	bool oplocks;
+	struct sys_lease_context *lease_ctx;
 };
 
 /*
@@ -72,6 +74,10 @@ struct odb_lock {
 	} can_open;
 };
 
+static NTSTATUS odb_oplock_break_send(struct messaging_context *msg_ctx,
+				      struct opendb_entry *e,
+				      uint8_t level);
+
 /*
   Open up the openfiles.tdb database. Close it down using
   talloc_free(). We need the messaging_ctx to allow for pending open
@@ -98,6 +104,11 @@ static struct odb_context *odb_tdb_init(TALLOC_CTX *mem_ctx,
 	/* leave oplocks disabled by default until the code is working */
 	odb->oplocks = lp_parm_bool(ntvfs_ctx->lp_ctx, NULL, "opendb", "oplocks", false);
 
+	odb->lease_ctx = sys_lease_context_create(ntvfs_ctx->config, odb,
+						  ntvfs_ctx->event_ctx,
+						  ntvfs_ctx->msg_ctx,
+						  odb_oplock_break_send);
+
 	return odb;
 }
 
@@ -442,7 +453,7 @@ static NTSTATUS odb_tdb_open_can_internal(struct odb_context *odb,
 */
 static NTSTATUS odb_tdb_open_file(struct odb_lock *lck,
 				  void *file_handle, const char *path,
-				  bool allow_level_II_oplock,
+				  int *fd, bool allow_level_II_oplock,
 				  uint32_t oplock_level, uint32_t *oplock_granted)
 {
 	struct odb_context *odb = lck->odb;
@@ -491,22 +502,29 @@ static NTSTATUS odb_tdb_open_file(struct odb_lock *lck,
 		oplock_level	= OPLOCK_NONE;
 	}
 
+	lck->can_open.e->file_handle		= file_handle;
+	lck->can_open.e->fd			= fd;
+	lck->can_open.e->allow_level_II_oplock	= allow_level_II_oplock;
+	lck->can_open.e->oplock_level		= oplock_level;
+
+	if (odb->lease_ctx && fd) {
+		NTSTATUS status;
+		status = sys_lease_setup(odb->lease_ctx, lck->can_open.e);
+		NT_STATUS_NOT_OK_RETURN(status);
+	}
+
 	if (oplock_granted) {
-		if (oplock_level == OPLOCK_EXCLUSIVE) {
+		if (lck->can_open.e->oplock_level == OPLOCK_EXCLUSIVE) {
 			*oplock_granted	= EXCLUSIVE_OPLOCK_RETURN;
-		} else if (oplock_level == OPLOCK_BATCH) {
+		} else if (lck->can_open.e->oplock_level == OPLOCK_BATCH) {
 			*oplock_granted	= BATCH_OPLOCK_RETURN;
-		} else if (oplock_level == OPLOCK_LEVEL_II) {
+		} else if (lck->can_open.e->oplock_level == OPLOCK_LEVEL_II) {
 			*oplock_granted	= LEVEL_II_OPLOCK_RETURN;
 		} else {
 			*oplock_granted	= NO_OPLOCK_RETURN;
 		}
 	}
 
-	lck->can_open.e->file_handle		= file_handle;
-	lck->can_open.e->allow_level_II_oplock	= allow_level_II_oplock;
-	lck->can_open.e->oplock_level		= oplock_level;
-
 	/* it doesn't conflict, so add it to the end */
 	lck->file.entries = talloc_realloc(lck, lck->file.entries,
 					   struct opendb_entry,
@@ -569,6 +587,11 @@ static NTSTATUS odb_tdb_close_file(struct odb_lock *lck, void *file_handle,
 			if (lck->file.entries[i].delete_on_close) {
 				lck->file.delete_on_close = true;
 			}
+			if (odb->lease_ctx && lck->file.entries[i].fd) {
+				NTSTATUS status;
+				status = sys_lease_remove(odb->lease_ctx, &lck->file.entries[i]);
+				NT_STATUS_NOT_OK_RETURN(status);
+			}
 			if (i < lck->file.num_entries-1) {
 				memmove(lck->file.entries+i, lck->file.entries+i+1,
 					(lck->file.num_entries - (i+1)) *
@@ -622,6 +645,13 @@ static NTSTATUS odb_tdb_update_oplock(struct odb_lock *lck, void *file_handle,
 		if (file_handle == lck->file.entries[i].file_handle &&
 		    cluster_id_equal(&odb->ntvfs_ctx->server_id, &lck->file.entries[i].server)) {
 			lck->file.entries[i].oplock_level = oplock_level;
+
+			if (odb->lease_ctx && lck->file.entries[i].fd) {
+				NTSTATUS status;
+				status = sys_lease_update(odb->lease_ctx, &lck->file.entries[i]);
+				NT_STATUS_NOT_OK_RETURN(status);
+			}
+
 			break;
 		}
 	}
@@ -800,6 +830,7 @@ static NTSTATUS odb_tdb_can_open(struct odb_lock *lck,
 
 	lck->can_open.e->server			= odb->ntvfs_ctx->server_id;
 	lck->can_open.e->file_handle		= NULL;
+	lck->can_open.e->fd			= NULL;
 	lck->can_open.e->stream_id		= stream_id;
 	lck->can_open.e->share_access		= share_access;
 	lck->can_open.e->access_mask		= access_mask;
@@ -831,5 +862,6 @@ static const struct opendb_ops opendb_tdb_ops = {
 
 void odb_tdb_init_ops(void)
 {
+	sys_lease_init();
 	odb_set_ops(&opendb_tdb_ops);
 }
diff --git a/source/ntvfs/posix/pvfs_open.c b/source/ntvfs/posix/pvfs_open.c
index 2e757e1..1399f12 100644
--- a/source/ntvfs/posix/pvfs_open.c
+++ b/source/ntvfs/posix/pvfs_open.c
@@ -300,7 +300,7 @@ static NTSTATUS pvfs_open_directory(struct pvfs_state *pvfs,
 
 		/* now really mark the file as open */
 		status = odb_open_file(lck, f->handle, name->full_name,
-				       false, OPLOCK_NONE, NULL);
+				       NULL, false, OPLOCK_NONE, NULL);
 
 		if (!NT_STATUS_IS_OK(status)) {
 			talloc_free(lck);
@@ -360,7 +360,7 @@ static NTSTATUS pvfs_open_directory(struct pvfs_state *pvfs,
 		}
 
 		status = odb_open_file(lck, f->handle, name->full_name,
-				       false, OPLOCK_NONE, NULL);
+				       NULL, false, OPLOCK_NONE, NULL);
 
 		if (!NT_STATUS_IS_OK(status)) {
 			goto cleanup_delete;
@@ -600,7 +600,7 @@ static NTSTATUS pvfs_create_file(struct pvfs_state *pvfs,
 	mode = pvfs_fileperms(pvfs, attrib);
 
 	/* create the file */
-	fd = open(name->full_name, flags | O_CREAT | O_EXCL, mode);
+	fd = open(name->full_name, flags | O_CREAT | O_EXCL| O_NONBLOCK, mode);
 	if (fd == -1) {
 		return pvfs_map_errno(pvfs, errno);
 	}
@@ -688,19 +688,6 @@ static NTSTATUS pvfs_create_file(struct pvfs_state *pvfs,
 		return status;
 	}
 
-	status = odb_open_file(lck, f->handle, name->full_name,
-			       allow_level_II_oplock,
-			       oplock_level, &oplock_granted);
-	talloc_free(lck);
-	if (!NT_STATUS_IS_OK(status)) {
-		/* bad news, we must have hit a race - we don't delete the file
-		   here as the most likely scenario is that someone else created 
-		   the file at the same time */
-		close(fd);
-		return status;
-	}
-
-
 	f->ntvfs             = h;
 	f->pvfs              = pvfs;
 	f->pending_list      = NULL;
@@ -723,6 +710,18 @@ static NTSTATUS pvfs_create_file(struct pvfs_state *pvfs,
 	f->handle->sticky_write_time = false;
 	f->handle->open_completed    = false;
 
+	status = odb_open_file(lck, f->handle, name->full_name,
+			       &f->handle->fd, allow_level_II_oplock,
+			       oplock_level, &oplock_granted);
+	talloc_free(lck);
+	if (!NT_STATUS_IS_OK(status)) {
+		/* bad news, we must have hit a race - we don't delete the file
+		   here as the most likely scenario is that someone else created
+		   the file at the same time */
+		close(fd);
+		return status;
+	}
+
 	DLIST_ADD(pvfs->files.list, f);
 
 	/* setup a destructor to avoid file descriptor leaks on
@@ -859,7 +858,13 @@ NTSTATUS pvfs_odb_retry_setup(struct ntvfs_module_context *ntvfs,
 
 	/* setup a pending lock */
 	status = odb_open_file_pending(lck, r);
-	if (!NT_STATUS_IS_OK(status)) {
+	if (NT_STATUS_EQUAL(NT_STATUS_OBJECT_NAME_NOT_FOUND,status)) {
+		/*
+		 * maybe only a unix application
+		 * has the file open
+		 */
+		data_blob_free(&r->odb_locking_key);
+	} else if (!NT_STATUS_IS_OK(status)) {
 		return status;
 	}
 
@@ -892,8 +897,14 @@ static void pvfs_retry_open_sharing(struct pvfs_odb_retry *r,
 				    enum pvfs_wait_notice reason)
 {
 	union smb_open *io = talloc_get_type(_io, union smb_open);
+	struct timeval *final_timeout = NULL;
 	NTSTATUS status;
 
+	if (private_data) {
+		final_timeout = talloc_get_type(private_data,
+						struct timeval);
+	}
+
 	/* w2k3 ignores SMBntcancel for outstanding open requests. It's probably
 	   just a bug in their server, but we better do the same */
 	if (reason == PVFS_WAIT_CANCEL) {
@@ -901,6 +912,16 @@ static void pvfs_retry_open_sharing(struct pvfs_odb_retry *r,
 	}
 
 	if (reason == PVFS_WAIT_TIMEOUT) {
+		if (final_timeout &&
+		    !timeval_expired(final_timeout)) {
+			/*
+			 * we need to retry periodictly
+			 * after an EAGAIN as there's
+			 * no way the kernel tell us
+			 * an oplock is released.
+			 */
+			goto retry;
+		}
 		/* if it timed out, then give the failure
 		   immediately */
 		talloc_free(r);
@@ -909,6 +930,7 @@ static void pvfs_retry_open_sharing(struct pvfs_odb_retry *r,
 		return;
 	}
 
+retry:
 	talloc_free(r);
 
 	/* try the open again, which could trigger another retry setup
@@ -1028,6 +1050,7 @@ static NTSTATUS pvfs_open_setup_retry(struct ntvfs_module_context *ntvfs,
 	struct pvfs_state *pvfs = ntvfs->private_data;
 	NTSTATUS status;
 	struct timeval end_time;
+	struct timeval *final_timeout = NULL;
 
 	if (io->generic.in.create_options & 
 	    (NTCREATEX_OPTIONS_PRIVATE_DENY_DOS | NTCREATEX_OPTIONS_PRIVATE_DENY_FCB)) {
@@ -1048,12 +1071,28 @@ static NTSTATUS pvfs_open_setup_retry(struct ntvfs_module_context *ntvfs,
 	} else if (NT_STATUS_EQUAL(parent_status, NT_STATUS_OPLOCK_NOT_GRANTED)) {
 		end_time = timeval_add(&req->statistics.request_time,
 				       pvfs->oplock_break_timeout, 0);
+	} else if (NT_STATUS_EQUAL(parent_status, STATUS_MORE_ENTRIES)) {
+		/*
+		 * we got EAGAIN which means a unix application
+		 * has an oplock or share mode
+		 *
+		 * we retry every 4/5 of the sharing violation delay
+		 * to see if the unix application
+		 * has released the oplock or share mode.
+		 */
+		final_timeout = talloc(req, struct timeval);
+		NT_STATUS_HAVE_NO_MEMORY(final_timeout);
+		*final_timeout = timeval_add(&req->statistics.request_time,
+					     pvfs->oplock_break_timeout,
+					     0);
+		end_time = timeval_current_ofs(0, (pvfs->sharing_violation_delay*4)/5);
+		end_time = timeval_min(final_timeout, &end_time);
 	} else {
 		return NT_STATUS_INTERNAL_ERROR;
 	}
 
-	return pvfs_odb_retry_setup(ntvfs, req, lck, end_time, io, NULL,
-				    pvfs_retry_open_sharing);
+	return pvfs_odb_retry_setup(ntvfs, req, lck, end_time, io,
+				    final_timeout, pvfs_retry_open_sharing);
 }
 
 /*
@@ -1297,9 +1336,34 @@ NTSTATUS pvfs_open(struct ntvfs_module_context *ntvfs,
 		return status;
 	}
 
+	if (access_mask & (SEC_FILE_WRITE_DATA | SEC_FILE_APPEND_DATA)) {
+		flags |= O_RDWR;
+	} else {
+		flags |= O_RDONLY;
+	}
+
+	/* do the actual open */
+	fd = open(f->handle->name->full_name, flags | O_NONBLOCK);
+	if (fd == -1) {
+		status = pvfs_map_errno(f->pvfs, errno);
+
+		/*
+		 * STATUS_MORE_ENTRIES is EAGAIN or EWOULDBLOCK
+		 */
+		if (NT_STATUS_EQUAL(status, STATUS_MORE_ENTRIES) &&
+		    (req->async_states->state & NTVFS_ASYNC_STATE_MAY_ASYNC)) {
+			return pvfs_open_setup_retry(ntvfs, req, io, f, lck, status);
+		}
+
+		talloc_free(lck);
+		return status;
+	}
+
+	f->handle->fd = fd;
+
 	/* now really mark the file as open */
 	status = odb_open_file(lck, f->handle, name->full_name,
-			       allow_level_II_oplock,
+			       &f->handle->fd, allow_level_II_oplock,
 			       oplock_level, &oplock_granted);
 
 	if (!NT_STATUS_IS_OK(status)) {
@@ -1319,21 +1383,6 @@ NTSTATUS pvfs_open(struct ntvfs_module_context *ntvfs,
 
 	f->handle->have_opendb_entry = true;
 
-	if (access_mask & (SEC_FILE_WRITE_DATA | SEC_FILE_APPEND_DATA)) {
-		flags |= O_RDWR;
-	} else {
-		flags |= O_RDONLY;
-	}
-
-	/* do the actual open */
-	fd = open(f->handle->name->full_name, flags);
-	if (fd == -1) {
-		talloc_free(lck);
-		return pvfs_map_errno(f->pvfs, errno);
-	}
-
-	f->handle->fd = fd;
-
 	stream_existed = name->stream_exists;
 
 	/* if this was a stream create then create the stream as well */
diff --git a/source/ntvfs/posix/pvfs_rename.c b/source/ntvfs/posix/pvfs_rename.c
index e94de8b..5c2a627 100644
--- a/source/ntvfs/posix/pvfs_rename.c
+++ b/source/ntvfs/posix/pvfs_rename.c
@@ -568,6 +568,9 @@ static NTSTATUS pvfs_rename_nt(struct ntvfs_module_context *ntvfs,
 NTSTATUS pvfs_rename(struct ntvfs_module_context *ntvfs,
 		     struct ntvfs_request *req, union smb_rename *ren)
 {
+	struct pvfs_state *pvfs = ntvfs->private_data;
+	struct pvfs_file *f;
+
 	switch (ren->generic.level) {
 	case RAW_RENAME_RENAME:
 		return pvfs_rename_mv(ntvfs, req, ren);
@@ -576,7 +579,13 @@ NTSTATUS pvfs_rename(struct ntvfs_module_context *ntvfs,
 		return pvfs_rename_nt(ntvfs, req, ren);
 
 	case RAW_RENAME_NTTRANS:
-		return NT_STATUS_NOT_IMPLEMENTED;
+		f = pvfs_find_fd(pvfs, req, ren->nttrans.in.file.ntvfs);
+		if (!f) {
+			return NT_STATUS_INVALID_HANDLE;
+		}
+
+		/* wk23 ignores the request */
+		return NT_STATUS_OK;
 
 	default:
 		break;
diff --git a/source/ntvfs/sysdep/config.m4 b/source/ntvfs/sysdep/config.m4
index f70cac5..6de75a4 100644
--- a/source/ntvfs/sysdep/config.m4
+++ b/source/ntvfs/sysdep/config.m4
@@ -11,3 +11,13 @@ fi
 if test x"$ac_cv_header_linux_inotify_h" = x"yes" -a x"$ac_cv_have___NR_inotify_init_decl" = x"yes"; then
     SMB_ENABLE(sys_notify_inotify, YES)
 fi
+
+AC_HAVE_DECL(F_SETLEASE, [#include <fcntl.h>])
+AC_HAVE_DECL(SA_SIGINFO, [#include <signal.h>])
+
+SMB_ENABLE(sys_lease_linux, NO)
+
+if test x"$ac_cv_have_F_SETLEASE_decl" = x"yes" \
+	-a x"$ac_cv_have_SA_SIGINFO_decl" = x"yes"; then
+    SMB_ENABLE(sys_lease_linux, YES)
+fi
diff --git a/source/ntvfs/sysdep/config.mk b/source/ntvfs/sysdep/config.mk
index dee198c..048226e 100644
--- a/source/ntvfs/sysdep/config.mk
+++ b/source/ntvfs/sysdep/config.mk
@@ -16,3 +16,21 @@ OBJ_FILES = \
 PUBLIC_DEPENDENCIES = 
 # End SUBSYSTEM sys_notify
 ################################################
+
+################################################
+# Start MODULE sys_lease_linux
+[MODULE::sys_lease_linux]
+SUBSYSTEM = sys_lease


-- 
Samba Shared Repository


More information about the samba-cvs mailing list