[SCM] Samba Shared Repository - branch v3-5-test updated

Karolin Seeger kseeger at samba.org
Thu Aug 18 12:45:53 MDT 2011


The branch, v3-5-test has been updated
       via  8e9dfd0 s3: Add a fallback for missing open&x support in OS/X Lion
       via  aa0c6eb s3: Make map_open_params_to_ntcreate() available in lib/
       via  612361b s3: Make is_executable() available in lib/
       via  1fa4b36 s3: We only need base_name in map_open_params_to_ntcreate
      from  552ccc6 s3/swat: use strlcat instead of strncat to fix build on old Linux distros

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


- Log -----------------------------------------------------------------
commit 8e9dfd04fac5353fb12270647209ac45d19a1ad2
Author: Volker Lendecke <vl at samba.org>
Date:   Fri Jul 29 15:43:46 2011 -0700

    s3: Add a fallback for missing open&x support in OS/X Lion
    
    The last 4 patches address bug #8338 (MAC Lion - smbclient "Open AndX
    Request->STATUS_NOT_SUPPORTED).

commit aa0c6eb76a6e16652a2ef46560eaffb881792cf6
Author: Volker Lendecke <vl at samba.org>
Date:   Fri Jul 29 15:03:03 2011 -0700

    s3: Make map_open_params_to_ntcreate() available in lib/

commit 612361bdcaf4256eb54913423e127d0628b35356
Author: Volker Lendecke <vl at samba.org>
Date:   Fri Jul 29 14:41:10 2011 -0700

    s3: Make is_executable() available in lib/

commit 1fa4b369d2fabbf34cda576d91d8aa9baa4e8b68
Author: Volker Lendecke <vl at samba.org>
Date:   Fri Jul 29 14:26:58 2011 -0700

    s3: We only need base_name in map_open_params_to_ntcreate

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

Summary of changes:
 source3/include/proto.h  |   14 ++--
 source3/lib/util.c       |  158 ++++++++++++++++++++++++++++++++++++++++++++++
 source3/libsmb/clifile.c |   91 +++++++++++++++++++++------
 source3/smbd/open.c      |  158 ----------------------------------------------
 source3/smbd/reply.c     |    8 ++-
 source3/smbd/trans2.c    |    3 +-
 6 files changed, 243 insertions(+), 189 deletions(-)


Changeset truncated at 500 lines:

diff --git a/source3/include/proto.h b/source3/include/proto.h
index d560ee5..c5065e2 100644
--- a/source3/include/proto.h
+++ b/source3/include/proto.h
@@ -1242,6 +1242,13 @@ const char *strip_hostname(const char *s);
 bool tevent_req_poll_ntstatus(struct tevent_req *req,
 			      struct tevent_context *ev,
 			      NTSTATUS *status);
+bool is_executable(const char *fname);
+bool map_open_params_to_ntcreate(const char *smb_base_fname,
+				 int deny_mode, int open_func,
+				 uint32 *paccess_mask,
+				 uint32 *pshare_mode,
+				 uint32 *pcreate_disposition,
+				 uint32 *pcreate_options);
 
 /* The following definitions come from lib/util_file.c  */
 
@@ -6608,7 +6615,6 @@ NTSTATUS change_dir_owner_to_parent(connection_struct *conn,
 				    const char *inherit_from_dir,
 				    const char *fname,
 				    SMB_STRUCT_STAT *psbuf);
-bool is_executable(const char *fname);
 bool is_stat_open(uint32 access_mask);
 bool request_timed_out(struct timeval request_time,
 		       struct timeval timeout);
@@ -6628,12 +6634,6 @@ NTSTATUS fcb_or_dos_open(struct smb_request *req,
 			 uint32 access_mask,
 			 uint32 share_access,
 			 uint32 create_options);
-bool map_open_params_to_ntcreate(const struct smb_filename *smb_fname,
-				 int deny_mode, int open_func,
-				 uint32 *paccess_mask,
-				 uint32 *pshare_mode,
-				 uint32 *pcreate_disposition,
-				 uint32 *pcreate_options);
 NTSTATUS open_file_fchmod(connection_struct *conn,
 			  struct smb_filename *smb_fname,
 			  files_struct **result);
diff --git a/source3/lib/util.c b/source3/lib/util.c
index 238981d..c7dfa28 100644
--- a/source3/lib/util.c
+++ b/source3/lib/util.c
@@ -3075,3 +3075,161 @@ bool tevent_req_poll_ntstatus(struct tevent_req *req,
 	}
 	return ret;
 }
+
+/*******************************************************************
+ Return True if the filename is one of the special executable types.
+********************************************************************/
+
+bool is_executable(const char *fname)
+{
+	if ((fname = strrchr_m(fname,'.'))) {
+		if (strequal(fname,".com") ||
+		    strequal(fname,".dll") ||
+		    strequal(fname,".exe") ||
+		    strequal(fname,".sym")) {
+			return True;
+		}
+	}
+	return False;
+}
+
+/****************************************************************************
+ Open a file with a share mode - old openX method - map into NTCreate.
+****************************************************************************/
+
+bool map_open_params_to_ntcreate(const char *smb_base_fname,
+				 int deny_mode, int open_func,
+				 uint32 *paccess_mask,
+				 uint32 *pshare_mode,
+				 uint32 *pcreate_disposition,
+				 uint32 *pcreate_options)
+{
+	uint32 access_mask;
+	uint32 share_mode;
+	uint32 create_disposition;
+	uint32 create_options = FILE_NON_DIRECTORY_FILE;
+
+	DEBUG(10,("map_open_params_to_ntcreate: fname = %s, deny_mode = 0x%x, "
+		  "open_func = 0x%x\n",
+		  smb_base_fname, (unsigned int)deny_mode,
+		  (unsigned int)open_func ));
+
+	/* Create the NT compatible access_mask. */
+	switch (GET_OPENX_MODE(deny_mode)) {
+		case DOS_OPEN_EXEC: /* Implies read-only - used to be FILE_READ_DATA */
+		case DOS_OPEN_RDONLY:
+			access_mask = FILE_GENERIC_READ;
+			break;
+		case DOS_OPEN_WRONLY:
+			access_mask = FILE_GENERIC_WRITE;
+			break;
+		case DOS_OPEN_RDWR:
+		case DOS_OPEN_FCB:
+			access_mask = FILE_GENERIC_READ|FILE_GENERIC_WRITE;
+			break;
+		default:
+			DEBUG(10,("map_open_params_to_ntcreate: bad open mode = 0x%x\n",
+				  (unsigned int)GET_OPENX_MODE(deny_mode)));
+			return False;
+	}
+
+	/* Create the NT compatible create_disposition. */
+	switch (open_func) {
+		case OPENX_FILE_EXISTS_FAIL|OPENX_FILE_CREATE_IF_NOT_EXIST:
+			create_disposition = FILE_CREATE;
+			break;
+
+		case OPENX_FILE_EXISTS_OPEN:
+			create_disposition = FILE_OPEN;
+			break;
+
+		case OPENX_FILE_EXISTS_OPEN|OPENX_FILE_CREATE_IF_NOT_EXIST:
+			create_disposition = FILE_OPEN_IF;
+			break;
+
+		case OPENX_FILE_EXISTS_TRUNCATE:
+			create_disposition = FILE_OVERWRITE;
+			break;
+
+		case OPENX_FILE_EXISTS_TRUNCATE|OPENX_FILE_CREATE_IF_NOT_EXIST:
+			create_disposition = FILE_OVERWRITE_IF;
+			break;
+
+		default:
+			/* From samba4 - to be confirmed. */
+			if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_EXEC) {
+				create_disposition = FILE_CREATE;
+				break;
+			}
+			DEBUG(10,("map_open_params_to_ntcreate: bad "
+				  "open_func 0x%x\n", (unsigned int)open_func));
+			return False;
+	}
+
+	/* Create the NT compatible share modes. */
+	switch (GET_DENY_MODE(deny_mode)) {
+		case DENY_ALL:
+			share_mode = FILE_SHARE_NONE;
+			break;
+
+		case DENY_WRITE:
+			share_mode = FILE_SHARE_READ;
+			break;
+
+		case DENY_READ:
+			share_mode = FILE_SHARE_WRITE;
+			break;
+
+		case DENY_NONE:
+			share_mode = FILE_SHARE_READ|FILE_SHARE_WRITE;
+			break;
+
+		case DENY_DOS:
+			create_options |= NTCREATEX_OPTIONS_PRIVATE_DENY_DOS;
+	                if (is_executable(smb_base_fname)) {
+				share_mode = FILE_SHARE_READ|FILE_SHARE_WRITE;
+			} else {
+				if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_RDONLY) {
+					share_mode = FILE_SHARE_READ;
+				} else {
+					share_mode = FILE_SHARE_NONE;
+				}
+			}
+			break;
+
+		case DENY_FCB:
+			create_options |= NTCREATEX_OPTIONS_PRIVATE_DENY_FCB;
+			share_mode = FILE_SHARE_NONE;
+			break;
+
+		default:
+			DEBUG(10,("map_open_params_to_ntcreate: bad deny_mode 0x%x\n",
+				(unsigned int)GET_DENY_MODE(deny_mode) ));
+			return False;
+	}
+
+	DEBUG(10,("map_open_params_to_ntcreate: file %s, access_mask = 0x%x, "
+		  "share_mode = 0x%x, create_disposition = 0x%x, "
+		  "create_options = 0x%x\n",
+		  smb_base_fname,
+		  (unsigned int)access_mask,
+		  (unsigned int)share_mode,
+		  (unsigned int)create_disposition,
+		  (unsigned int)create_options ));
+
+	if (paccess_mask) {
+		*paccess_mask = access_mask;
+	}
+	if (pshare_mode) {
+		*pshare_mode = share_mode;
+	}
+	if (pcreate_disposition) {
+		*pcreate_disposition = create_disposition;
+	}
+	if (pcreate_options) {
+		*pcreate_options = create_options;
+	}
+
+	return True;
+
+}
diff --git a/source3/libsmb/clifile.c b/source3/libsmb/clifile.c
index 5eb8bd4..9a33db4 100644
--- a/source3/libsmb/clifile.c
+++ b/source3/libsmb/clifile.c
@@ -2149,12 +2149,19 @@ NTSTATUS cli_ntcreate(struct cli_state *cli,
 ****************************************************************************/
 
 struct cli_open_state {
+	struct tevent_context *ev;
+	struct cli_state *cli;
+	const char *fname;
 	uint16_t vwv[15];
 	uint16_t fnum;
+	unsigned openfn;
+	unsigned dos_deny;
+	uint8_t additional_flags;
 	struct iovec bytes;
 };
 
 static void cli_open_done(struct tevent_req *subreq);
+static void cli_open_ntcreate_done(struct tevent_req *subreq);
 
 struct tevent_req *cli_open_create(TALLOC_CTX *mem_ctx,
 				   struct event_context *ev,
@@ -2164,64 +2171,61 @@ struct tevent_req *cli_open_create(TALLOC_CTX *mem_ctx,
 {
 	struct tevent_req *req, *subreq;
 	struct cli_open_state *state;
-	unsigned openfn;
-	unsigned accessmode;
-	uint8_t additional_flags;
 	uint8_t *bytes;
 
 	req = tevent_req_create(mem_ctx, &state, struct cli_open_state);
 	if (req == NULL) {
 		return NULL;
 	}
+	state->ev = ev;
+	state->cli = cli;
+	state->fname = fname;
 
-	openfn = 0;
 	if (flags & O_CREAT) {
-		openfn |= (1<<4);
+		state->openfn |= (1<<4);
 	}
 	if (!(flags & O_EXCL)) {
 		if (flags & O_TRUNC)
-			openfn |= (1<<1);
+			state->openfn |= (1<<1);
 		else
-			openfn |= (1<<0);
+			state->openfn |= (1<<0);
 	}
 
-	accessmode = (share_mode<<4);
+	state->dos_deny = (share_mode<<4);
 
 	if ((flags & O_ACCMODE) == O_RDWR) {
-		accessmode |= 2;
+		state->dos_deny |= 2;
 	} else if ((flags & O_ACCMODE) == O_WRONLY) {
-		accessmode |= 1;
+		state->dos_deny |= 1;
 	}
 
 #if defined(O_SYNC)
 	if ((flags & O_SYNC) == O_SYNC) {
-		accessmode |= (1<<14);
+		state->dos_deny |= (1<<14);
 	}
 #endif /* O_SYNC */
 
 	if (share_mode == DENY_FCB) {
-		accessmode = 0xFF;
+		state->dos_deny = 0xFF;
 	}
 
 	SCVAL(state->vwv + 0, 0, 0xFF);
 	SCVAL(state->vwv + 0, 1, 0);
 	SSVAL(state->vwv + 1, 0, 0);
 	SSVAL(state->vwv + 2, 0, 0);  /* no additional info */
-	SSVAL(state->vwv + 3, 0, accessmode);
+	SSVAL(state->vwv + 3, 0, state->dos_deny);
 	SSVAL(state->vwv + 4, 0, aSYSTEM | aHIDDEN);
 	SSVAL(state->vwv + 5, 0, 0);
 	SIVAL(state->vwv + 6, 0, 0);
-	SSVAL(state->vwv + 8, 0, openfn);
+	SSVAL(state->vwv + 8, 0, state->openfn);
 	SIVAL(state->vwv + 9, 0, 0);
 	SIVAL(state->vwv + 11, 0, 0);
 	SIVAL(state->vwv + 13, 0, 0);
 
-	additional_flags = 0;
-
 	if (cli->use_oplocks) {
 		/* if using oplocks then ask for a batch oplock via
                    core and extended methods */
-		additional_flags =
+		state->additional_flags =
 			FLAG_REQUEST_OPLOCK|FLAG_REQUEST_BATCH_OPLOCK;
 		SSVAL(state->vwv+2, 0, SVAL(state->vwv+2, 0) | 6);
 	}
@@ -2237,7 +2241,8 @@ struct tevent_req *cli_open_create(TALLOC_CTX *mem_ctx,
 	state->bytes.iov_base = (void *)bytes;
 	state->bytes.iov_len = talloc_get_size(bytes);
 
-	subreq = cli_smb_req_create(state, ev, cli, SMBopenX, additional_flags,
+	subreq = cli_smb_req_create(state, ev, cli, SMBopenX,
+				    state->additional_flags,
 				    15, state->vwv, 1, &state->bytes);
 	if (subreq == NULL) {
 		TALLOC_FREE(req);
@@ -2278,14 +2283,60 @@ static void cli_open_done(struct tevent_req *subreq)
 	uint8_t wct;
 	uint16_t *vwv;
 	NTSTATUS status;
+	uint32_t access_mask, share_mode, create_disposition, create_options;
 
 	status = cli_smb_recv(subreq, 3, &wct, &vwv, NULL, NULL);
+	TALLOC_FREE(subreq);
+
+	if (NT_STATUS_IS_OK(status)) {
+		state->fnum = SVAL(vwv+2, 0);
+		tevent_req_done(req);
+		return;
+	}
+
+	if (!NT_STATUS_EQUAL(status, NT_STATUS_NOT_SUPPORTED)) {
+		tevent_req_nterror(req, status);
+		return;
+	}
+
+	/*
+	 * For the new shiny OS/X Lion SMB server, try a ntcreate
+	 * fallback.
+	 */
+
+	if (!map_open_params_to_ntcreate(state->fname, state->dos_deny,
+					state->openfn, &access_mask,
+					&share_mode, &create_disposition,
+					&create_options)) {
+		tevent_req_nterror(req, NT_STATUS_NOT_SUPPORTED);
+		return;
+	}
+
+	subreq = cli_ntcreate_send(state, state->ev, state->cli,
+				state->fname, 0, access_mask,
+				0, share_mode, create_disposition,
+				create_options, 0);
+	if (tevent_req_nomem(subreq, req)) {
+		return;
+	}
+	tevent_req_set_callback(subreq, cli_open_ntcreate_done, req);
+}
+
+static void cli_open_ntcreate_done(struct tevent_req *subreq)
+{
+	struct tevent_req *req = tevent_req_callback_data(
+		subreq, struct tevent_req);
+	struct cli_open_state *state = tevent_req_data(
+		req, struct cli_open_state);
+	NTSTATUS status;
+
+	status = cli_ntcreate_recv(subreq, &state->fnum);
+	TALLOC_FREE(subreq);
+
 	if (!NT_STATUS_IS_OK(status)) {
-		TALLOC_FREE(subreq);
 		tevent_req_nterror(req, status);
 		return;
 	}
-	state->fnum = SVAL(vwv+2, 0);
 	tevent_req_done(req);
 }
 
diff --git a/source3/smbd/open.c b/source3/smbd/open.c
index f0b9271..9048d6b 100644
--- a/source3/smbd/open.c
+++ b/source3/smbd/open.c
@@ -660,23 +660,6 @@ static NTSTATUS open_file(files_struct *fsp,
 	return NT_STATUS_OK;
 }
 
-/*******************************************************************
- Return True if the filename is one of the special executable types.
-********************************************************************/
-
-bool is_executable(const char *fname)
-{
-	if ((fname = strrchr_m(fname,'.'))) {
-		if (strequal(fname,".com") ||
-		    strequal(fname,".dll") ||
-		    strequal(fname,".exe") ||
-		    strequal(fname,".sym")) {
-			return True;
-		}
-	}
-	return False;
-}
-
 /****************************************************************************
  Check if we can open a file with a share mode.
  Returns True if conflict, False if not.
@@ -1222,147 +1205,6 @@ NTSTATUS fcb_or_dos_open(struct smb_request *req,
 			    create_options, fsp_to_dup_into);
 }
 
-/****************************************************************************
- Open a file with a share mode - old openX method - map into NTCreate.
-****************************************************************************/
-
-bool map_open_params_to_ntcreate(const struct smb_filename *smb_fname,
-				 int deny_mode, int open_func,
-				 uint32 *paccess_mask,
-				 uint32 *pshare_mode,
-				 uint32 *pcreate_disposition,
-				 uint32 *pcreate_options)
-{
-	uint32 access_mask;
-	uint32 share_mode;
-	uint32 create_disposition;
-	uint32 create_options = FILE_NON_DIRECTORY_FILE;
-
-	DEBUG(10,("map_open_params_to_ntcreate: fname = %s, deny_mode = 0x%x, "
-		  "open_func = 0x%x\n",
-		  smb_fname_str_dbg(smb_fname), (unsigned int)deny_mode,
-		  (unsigned int)open_func ));
-
-	/* Create the NT compatible access_mask. */
-	switch (GET_OPENX_MODE(deny_mode)) {
-		case DOS_OPEN_EXEC: /* Implies read-only - used to be FILE_READ_DATA */
-		case DOS_OPEN_RDONLY:
-			access_mask = FILE_GENERIC_READ;
-			break;
-		case DOS_OPEN_WRONLY:
-			access_mask = FILE_GENERIC_WRITE;
-			break;
-		case DOS_OPEN_RDWR:
-		case DOS_OPEN_FCB:
-			access_mask = FILE_GENERIC_READ|FILE_GENERIC_WRITE;
-			break;
-		default:
-			DEBUG(10,("map_open_params_to_ntcreate: bad open mode = 0x%x\n",
-				  (unsigned int)GET_OPENX_MODE(deny_mode)));
-			return False;
-	}
-
-	/* Create the NT compatible create_disposition. */
-	switch (open_func) {
-		case OPENX_FILE_EXISTS_FAIL|OPENX_FILE_CREATE_IF_NOT_EXIST:
-			create_disposition = FILE_CREATE;
-			break;
-
-		case OPENX_FILE_EXISTS_OPEN:
-			create_disposition = FILE_OPEN;
-			break;
-
-		case OPENX_FILE_EXISTS_OPEN|OPENX_FILE_CREATE_IF_NOT_EXIST:
-			create_disposition = FILE_OPEN_IF;
-			break;
-       
-		case OPENX_FILE_EXISTS_TRUNCATE:
-			create_disposition = FILE_OVERWRITE;
-			break;
-
-		case OPENX_FILE_EXISTS_TRUNCATE|OPENX_FILE_CREATE_IF_NOT_EXIST:
-			create_disposition = FILE_OVERWRITE_IF;
-			break;
-
-		default:
-			/* From samba4 - to be confirmed. */
-			if (GET_OPENX_MODE(deny_mode) == DOS_OPEN_EXEC) {
-				create_disposition = FILE_CREATE;
-				break;
-			}
-			DEBUG(10,("map_open_params_to_ntcreate: bad "
-				  "open_func 0x%x\n", (unsigned int)open_func));
-			return False;
-	}
- 
-	/* Create the NT compatible share modes. */
-	switch (GET_DENY_MODE(deny_mode)) {
-		case DENY_ALL:
-			share_mode = FILE_SHARE_NONE;
-			break;
-
-		case DENY_WRITE:
-			share_mode = FILE_SHARE_READ;
-			break;
-
-		case DENY_READ:
-			share_mode = FILE_SHARE_WRITE;
-			break;
-


-- 
Samba Shared Repository


More information about the samba-cvs mailing list