summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJeremy Allison <jra@samba.org>2007-12-07 09:57:19 -0800
committerJeremy Allison <jra@samba.org>2007-12-07 09:57:19 -0800
commit5b3459e34017b2eea1d82233a07bef8a418613f4 (patch)
treeba4e758b1f484d1472e4bc9325f67bf62673ed2b
parent9e03d6117a2c3049bdb3e2a7226e7b91283bbc23 (diff)
parentd3b4b69a270efd85728ac77fe23a0fb39d9dce10 (diff)
downloadsamba-5b3459e34017b2eea1d82233a07bef8a418613f4.tar.gz
samba-5b3459e34017b2eea1d82233a07bef8a418613f4.tar.bz2
samba-5b3459e34017b2eea1d82233a07bef8a418613f4.zip
Merge branch 'v3-2-test' of ssh://jra@git.samba.org/data/git/samba into v3-2-test
(This used to be commit 0c21c5fa84e18d78801ab79abd726e5588902476)
-rw-r--r--source3/include/nterr.h1
-rw-r--r--source3/librpc/gen_ndr/ndr_wkssvc.c2
-rw-r--r--source3/libsmb/nterr.c1
-rw-r--r--source3/rpcclient/cmd_wkssvc.c82
-rw-r--r--source3/smbd/nttrans.c82
-rw-r--r--source3/smbd/open.c70
6 files changed, 176 insertions, 62 deletions
diff --git a/source3/include/nterr.h b/source3/include/nterr.h
index da9fab3aca..5749c4efbf 100644
--- a/source3/include/nterr.h
+++ b/source3/include/nterr.h
@@ -563,6 +563,7 @@
#define NT_STATUS_FILE_IS_OFFLINE NT_STATUS(0xC0000000 | 0x0267)
#define NT_STATUS_DS_NO_MORE_RIDS NT_STATUS(0xC0000000 | 0x02a8)
#define NT_STATUS_NOT_A_REPARSE_POINT NT_STATUS(0xC0000000 | 0x0275)
+#define NT_STATUS_DOWNGRADE_DETECTED NT_STATUS(0xC0000000 | 0x0388)
#define NT_STATUS_NO_SUCH_JOB NT_STATUS(0xC0000000 | 0xEDE) /* scheduler */
#define NT_STATUS_RPC_PROTSEQ_NOT_SUPPORTED NT_STATUS(0xC0000000 | 0x20004)
diff --git a/source3/librpc/gen_ndr/ndr_wkssvc.c b/source3/librpc/gen_ndr/ndr_wkssvc.c
index c3a1f706cd..3599fef352 100644
--- a/source3/librpc/gen_ndr/ndr_wkssvc.c
+++ b/source3/librpc/gen_ndr/ndr_wkssvc.c
@@ -8606,7 +8606,6 @@ static enum ndr_err_code ndr_pull_wkssvc_NetrGetJoinableOus(struct ndr_pull *ndr
TALLOC_CTX *_mem_save_unknown_0;
TALLOC_CTX *_mem_save_num_ous_0;
TALLOC_CTX *_mem_save_ous_1;
- TALLOC_CTX *_mem_save_ous_2;
if (flags & NDR_IN) {
ZERO_STRUCT(r->out);
@@ -9488,7 +9487,6 @@ static enum ndr_err_code ndr_pull_wkssvc_NetrGetJoinableOus2(struct ndr_pull *nd
TALLOC_CTX *_mem_save_EncryptedPassword_0;
TALLOC_CTX *_mem_save_num_ous_0;
TALLOC_CTX *_mem_save_ous_1;
- TALLOC_CTX *_mem_save_ous_2;
if (flags & NDR_IN) {
ZERO_STRUCT(r->out);
diff --git a/source3/libsmb/nterr.c b/source3/libsmb/nterr.c
index cf443f2339..608fe9db20 100644
--- a/source3/libsmb/nterr.c
+++ b/source3/libsmb/nterr.c
@@ -534,6 +534,7 @@ static const nt_err_code_struct nt_errs[] =
{ "NT_STATUS_FILE_IS_OFFLINE", NT_STATUS_FILE_IS_OFFLINE },
{ "NT_STATUS_DS_NO_MORE_RIDS", NT_STATUS_DS_NO_MORE_RIDS },
{ "NT_STATUS_NOT_A_REPARSE_POINT", NT_STATUS_NOT_A_REPARSE_POINT },
+ { "NT_STATUS_DOWNGRADE_DETECTED", NT_STATUS_DOWNGRADE_DETECTED },
{ "NT_STATUS_NO_MORE_ENTRIES", NT_STATUS_NO_MORE_ENTRIES },
{ "STATUS_MORE_ENTRIES", STATUS_MORE_ENTRIES },
{ "STATUS_SOME_UNMAPPED", STATUS_SOME_UNMAPPED },
diff --git a/source3/rpcclient/cmd_wkssvc.c b/source3/rpcclient/cmd_wkssvc.c
index f3ff8113e9..d136cd0d45 100644
--- a/source3/rpcclient/cmd_wkssvc.c
+++ b/source3/rpcclient/cmd_wkssvc.c
@@ -32,6 +32,15 @@ static WERROR cmd_wkssvc_wkstagetinfo(struct rpc_pipe_client *cli,
union wkssvc_NetWkstaInfo info;
const char *server_name;
+ if (argc > 2) {
+ printf("usage: %s <level>\n", argv[0]);
+ return WERR_OK;
+ }
+
+ if (argc > 1) {
+ level = atoi(argv[1]);
+ }
+
server_name = cli->cli->desthost;
status = rpccli_wkssvc_NetWkstaGetInfo(cli, mem_ctx,
@@ -46,9 +55,80 @@ static WERROR cmd_wkssvc_wkstagetinfo(struct rpc_pipe_client *cli,
return werr;
}
+static WERROR cmd_wkssvc_getjoininformation(struct rpc_pipe_client *cli,
+ TALLOC_CTX *mem_ctx,
+ int argc,
+ const char **argv)
+{
+ const char *server_name;
+ const char *name_buffer;
+ enum wkssvc_NetJoinStatus name_type;
+ NTSTATUS status;
+ WERROR werr;
+
+ server_name = cli->cli->desthost;
+ name_buffer = "";
+
+ status = rpccli_wkssvc_NetrGetJoinInformation(cli, mem_ctx,
+ server_name,
+ &name_buffer,
+ &name_type,
+ &werr);
+ if (!NT_STATUS_IS_OK(status)) {
+ return ntstatus_to_werror(status);
+ }
+
+ if (W_ERROR_IS_OK(werr)) {
+ printf("%s (%d)\n", name_buffer, name_type);
+ }
+
+ return werr;
+}
+
+static WERROR cmd_wkssvc_messagebuffersend(struct rpc_pipe_client *cli,
+ TALLOC_CTX *mem_ctx,
+ int argc,
+ const char **argv)
+{
+ const char *server_name = cli->cli->desthost;
+ const char *message_name = cli->cli->desthost;
+ const char *message_sender_name = cli->cli->desthost;
+ smb_ucs2_t *message_buffer = NULL;
+ size_t message_size = 0;
+ const char *message = "my message";
+ NTSTATUS status;
+ WERROR werr;
+
+ if (argc > 1) {
+ message = argv[1];
+ }
+
+ message_size = push_ucs2_talloc(mem_ctx,
+ &message_buffer,
+ message);
+ if (message_size == -1) {
+ return WERR_NOMEM;
+ }
+
+ status = rpccli_wkssvc_NetrMessageBufferSend(cli, mem_ctx,
+ server_name,
+ message_name,
+ message_sender_name,
+ (uint8_t *)message_buffer,
+ message_size,
+ &werr);
+ if (!NT_STATUS_IS_OK(status)) {
+ return ntstatus_to_werror(status);
+ }
+
+ return werr;
+}
+
struct cmd_set wkssvc_commands[] = {
{ "WKSSVC" },
- { "wkstagetinfo", RPC_RTYPE_WERROR, NULL, cmd_wkssvc_wkstagetinfo, PI_WKSSVC, NULL, "Query WKSSVC Workstation Information", "" },
+ { "wkssvc_wkstagetinfo", RPC_RTYPE_WERROR, NULL, cmd_wkssvc_wkstagetinfo, PI_WKSSVC, NULL, "Query WKSSVC Workstation Information", "" },
+ { "wkssvc_getjoininformation", RPC_RTYPE_WERROR, NULL, cmd_wkssvc_getjoininformation, PI_WKSSVC, NULL, "Query WKSSVC Join Information", "" },
+ { "wkssvc_messagebuffersend", RPC_RTYPE_WERROR, NULL, cmd_wkssvc_messagebuffersend, PI_WKSSVC, NULL, "Send WKSSVC message", "" },
{ NULL }
};
diff --git a/source3/smbd/nttrans.c b/source3/smbd/nttrans.c
index fb85a67d0a..99b2bf65bb 100644
--- a/source3/smbd/nttrans.c
+++ b/source3/smbd/nttrans.c
@@ -433,6 +433,7 @@ void reply_ntcreate_and_X(connection_struct *conn, struct smb_request *req)
struct timespec a_timespec;
struct timespec m_timespec;
NTSTATUS status;
+ int oplock_request;
uint8_t oplock_granted = NO_OPLOCK_RETURN;
TALLOC_CTX *ctx = talloc_tos();
@@ -497,11 +498,16 @@ void reply_ntcreate_and_X(connection_struct *conn, struct smb_request *req)
}
}
- status = create_file(conn, req, root_dir_fid, fname, flags,
- access_mask, file_attributes, share_access,
- create_disposition, create_options,
- allocation_size, NULL, NULL,
- &fsp, &info, &oplock_granted, &sbuf);
+ oplock_request = (flags & REQUEST_OPLOCK) ? EXCLUSIVE_OPLOCK : 0;
+ if (oplock_request) {
+ oplock_request |= (flags & REQUEST_BATCH_OPLOCK)
+ ? BATCH_OPLOCK : 0;
+ }
+
+ status = create_file(conn, req, root_dir_fid, fname,
+ access_mask, share_access, create_disposition,
+ create_options, file_attributes, oplock_request,
+ allocation_size, NULL, NULL, &fsp, &info, &sbuf);
if (!NT_STATUS_IS_OK(status)) {
if (open_was_deferred(req->mid)) {
@@ -519,6 +525,31 @@ void reply_ntcreate_and_X(connection_struct *conn, struct smb_request *req)
return;
}
+ /*
+ * If the caller set the extended oplock request bit
+ * and we granted one (by whatever means) - set the
+ * correct bit for extended oplock reply.
+ */
+
+ if (oplock_request &&
+ (lp_fake_oplocks(SNUM(conn))
+ || EXCLUSIVE_OPLOCK_TYPE(fsp->oplock_type))) {
+
+ /*
+ * Exclusive oplock granted
+ */
+
+ if (flags & REQUEST_BATCH_OPLOCK) {
+ oplock_granted = BATCH_OPLOCK_RETURN;
+ } else {
+ oplock_granted = EXCLUSIVE_OPLOCK_RETURN;
+ }
+ } else if (fsp->oplock_type == LEVEL_II_OPLOCK) {
+ oplock_granted = LEVEL_II_OPLOCK_RETURN;
+ } else {
+ oplock_granted = NO_OPLOCK_RETURN;
+ }
+
file_len = sbuf.st_size;
fattr = dos_mode(conn,fname,&sbuf);
if (fattr == 0) {
@@ -834,6 +865,7 @@ static void call_nt_transact_create(connection_struct *conn,
NTSTATUS status;
size_t param_len;
SMB_BIG_UINT allocation_size;
+ int oplock_request;
uint8_t oplock_granted;
TALLOC_CTX *ctx = talloc_tos();
@@ -941,11 +973,16 @@ static void call_nt_transact_create(connection_struct *conn,
return;
}
- status = create_file(conn, req, root_dir_fid, fname, flags,
- access_mask, file_attributes, share_access,
- create_disposition, create_options,
- allocation_size, sd, ea_list,
- &fsp, &info, &oplock_granted, &sbuf);
+ oplock_request = (flags & REQUEST_OPLOCK) ? EXCLUSIVE_OPLOCK : 0;
+ if (oplock_request) {
+ oplock_request |= (flags & REQUEST_BATCH_OPLOCK)
+ ? BATCH_OPLOCK : 0;
+ }
+
+ status = create_file(conn, req, root_dir_fid, fname,
+ access_mask, share_access, create_disposition,
+ create_options, file_attributes, oplock_request,
+ allocation_size, sd, ea_list, &fsp, &info, &sbuf);
if(!NT_STATUS_IS_OK(status)) {
if (open_was_deferred(req->mid)) {
@@ -961,6 +998,31 @@ static void call_nt_transact_create(connection_struct *conn,
return;
}
+ /*
+ * If the caller set the extended oplock request bit
+ * and we granted one (by whatever means) - set the
+ * correct bit for extended oplock reply.
+ */
+
+ if (oplock_request &&
+ (lp_fake_oplocks(SNUM(conn))
+ || EXCLUSIVE_OPLOCK_TYPE(fsp->oplock_type))) {
+
+ /*
+ * Exclusive oplock granted
+ */
+
+ if (flags & REQUEST_BATCH_OPLOCK) {
+ oplock_granted = BATCH_OPLOCK_RETURN;
+ } else {
+ oplock_granted = EXCLUSIVE_OPLOCK_RETURN;
+ }
+ } else if (fsp->oplock_type == LEVEL_II_OPLOCK) {
+ oplock_granted = LEVEL_II_OPLOCK_RETURN;
+ } else {
+ oplock_granted = NO_OPLOCK_RETURN;
+ }
+
file_len = sbuf.st_size;
fattr = dos_mode(conn,fname,&sbuf);
if (fattr == 0) {
diff --git a/source3/smbd/open.c b/source3/smbd/open.c
index 66ceb8dac7..b156dbbce1 100644
--- a/source3/smbd/open.c
+++ b/source3/smbd/open.c
@@ -2447,20 +2447,19 @@ static struct case_semantics_state *set_posix_case_semantics(TALLOC_CTX *mem_ctx
NTSTATUS create_file(connection_struct *conn,
struct smb_request *req,
uint16_t root_dir_fid,
- char *fname,
- uint32_t flags,
+ const char *fname,
uint32_t access_mask,
- uint32_t file_attributes,
uint32_t share_access,
uint32_t create_disposition,
uint32_t create_options,
+ uint32_t file_attributes,
+ uint32_t oplock_request,
SMB_BIG_UINT allocation_size,
struct security_descriptor *sd,
struct ea_list *ea_list,
files_struct **result,
int *pinfo,
- uint8_t *poplock_granted,
SMB_STRUCT_STAT *psbuf)
{
TALLOC_CTX *frame = talloc_stackframe();
@@ -2468,21 +2467,20 @@ NTSTATUS create_file(connection_struct *conn,
SMB_STRUCT_STAT sbuf;
int info = FILE_WAS_OPENED;
files_struct *fsp = NULL;
- uint8_t oplock_granted = NO_OPLOCK_RETURN;
- int oplock_request;
NTSTATUS status;
- DEBUG(10,("create_file: flags = 0x%x, access_mask = 0x%x "
+ DEBUG(10,("create_file: access_mask = 0x%x "
"file_attributes = 0x%x, share_access = 0x%x, "
"create_disposition = 0x%x create_options = 0x%x "
+ "oplock_request = 0x%x "
"root_dir_fid = 0x%x, ea_list = 0x%p, sd = 0x%p, "
"fname = %s\n",
- (unsigned int)flags,
(unsigned int)access_mask,
(unsigned int)file_attributes,
(unsigned int)share_access,
(unsigned int)create_disposition,
(unsigned int)create_options,
+ (unsigned int)oplock_request,
(unsigned int)root_dir_fid,
ea_list, sd, fname));
@@ -2613,18 +2611,15 @@ NTSTATUS create_file(connection_struct *conn,
}
}
- oplock_request = (flags & REQUEST_OPLOCK) ? EXCLUSIVE_OPLOCK : 0;
- if (oplock_request) {
- oplock_request |= (flags & REQUEST_BATCH_OPLOCK)
- ? BATCH_OPLOCK : 0;
- }
-
if (req == NULL) {
oplock_request |= INTERNAL_OPEN_ONLY;
}
if ((req != NULL) && (req->flags2 & FLAGS2_DFS_PATHNAMES)) {
- status = resolve_dfspath(talloc_tos(), conn, true, fname, &fname);
+ char *resolved_fname;
+
+ status = resolve_dfspath(talloc_tos(), conn, true, fname,
+ &resolved_fname);
if (!NT_STATUS_IS_OK(status)) {
/*
@@ -2635,6 +2630,7 @@ NTSTATUS create_file(connection_struct *conn,
*/
goto fail;
}
+ fname = resolved_fname;
}
/*
@@ -2646,10 +2642,15 @@ NTSTATUS create_file(connection_struct *conn,
file_attributes &= ~FILE_FLAG_POSIX_SEMANTICS;
}
- status = unix_convert(talloc_tos(), conn, fname, False, &fname, NULL,
- &sbuf);
- if (!NT_STATUS_IS_OK(status)) {
- goto fail;
+ {
+ char *converted_fname;
+
+ status = unix_convert(talloc_tos(), conn, fname, False,
+ &converted_fname, NULL, &sbuf);
+ if (!NT_STATUS_IS_OK(status)) {
+ goto fail;
+ }
+ fname = converted_fname;
}
/* All file access must go through check_name() */
@@ -2826,42 +2827,13 @@ NTSTATUS create_file(connection_struct *conn,
}
}
- /*
- * If the caller set the extended oplock request bit
- * and we granted one (by whatever means) - set the
- * correct bit for extended oplock reply.
- */
-
- if (oplock_request &&
- (lp_fake_oplocks(SNUM(conn))
- || EXCLUSIVE_OPLOCK_TYPE(fsp->oplock_type))) {
-
- /*
- * Exclusive oplock granted
- */
-
- if (flags & REQUEST_BATCH_OPLOCK) {
- oplock_granted = BATCH_OPLOCK_RETURN;
- } else {
- oplock_granted = EXCLUSIVE_OPLOCK_RETURN;
- }
- } else if (fsp->oplock_type == LEVEL_II_OPLOCK) {
- oplock_granted = LEVEL_II_OPLOCK_RETURN;
- } else {
- oplock_granted = NO_OPLOCK_RETURN;
- }
-
done:
- DEBUG(10, ("create_file: info=%d, oplock_granted=%d\n",
- info, (int)oplock_granted));
+ DEBUG(10, ("create_file: info=%d\n", info));
*result = fsp;
if (pinfo != NULL) {
*pinfo = info;
}
- if (poplock_granted != NULL) {
- *poplock_granted = oplock_granted;
- }
if (psbuf != NULL) {
*psbuf = sbuf;
}