summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJelmer Vernooij <jelmer@samba.org>2009-02-12 16:00:46 +0100
committerJelmer Vernooij <jelmer@samba.org>2009-02-12 16:00:46 +0100
commit082ba6a1ad3a68aff118d96f855a2aa65eaeb359 (patch)
treed70b7e8012e787a11ea1c12224318643cdd552c3
parent762fdc8c5c2db304f3dc4536c19d69366d1399df (diff)
parent4f6d1728254c8503e71c6fdd008fb7264dec26c5 (diff)
downloadsamba-082ba6a1ad3a68aff118d96f855a2aa65eaeb359.tar.gz
samba-082ba6a1ad3a68aff118d96f855a2aa65eaeb359.tar.bz2
samba-082ba6a1ad3a68aff118d96f855a2aa65eaeb359.zip
Merge branch 'master' of ssh://git.samba.org/data/git/samba
-rw-r--r--lib/replace/libreplace_network.m41
-rw-r--r--libcli/util/ntstatus.h3
-rw-r--r--librpc/gen_ndr/cli_spoolss.c48
-rw-r--r--librpc/gen_ndr/cli_spoolss.h26
-rw-r--r--librpc/gen_ndr/ndr_spoolss.c248
-rw-r--r--librpc/gen_ndr/ndr_spoolss.h15
-rw-r--r--librpc/gen_ndr/spoolss.h32
-rw-r--r--librpc/gen_ndr/srv_spoolss.c57
-rw-r--r--librpc/gen_ndr/srv_spoolss.h8
-rw-r--r--librpc/idl/spoolss.idl37
-rw-r--r--nsswitch/libwbclient/wbc_pwd.c39
-rw-r--r--nsswitch/libwbclient/wbc_sid.c139
-rw-r--r--nsswitch/libwbclient/wbclient.h24
-rw-r--r--nsswitch/wbinfo.c101
-rw-r--r--nsswitch/winbind_struct_protocol.h12
-rwxr-xr-xpackaging/bin/fill-templates10
-rw-r--r--source3/Makefile.in9
-rw-r--r--source3/auth/auth_util.c61
-rw-r--r--source3/configure.in315
-rw-r--r--source3/include/includes.h5
-rw-r--r--source3/include/proto.h30
-rw-r--r--source3/include/rpc_spoolss.h15
-rw-r--r--source3/lib/time.c66
-rw-r--r--source3/lib/winbind_util.c131
-rw-r--r--source3/modules/onefs_acl.c6
-rw-r--r--source3/modules/onefs_open.c5
-rw-r--r--source3/passdb/passdb.c19
-rw-r--r--source3/rpc_server/srv_spoolss_nt.c22
-rw-r--r--source3/winbindd/winbindd.c3
-rw-r--r--source3/winbindd/winbindd_async.c90
-rw-r--r--source3/winbindd/winbindd_domain.c4
-rw-r--r--source3/winbindd/winbindd_group.c115
-rw-r--r--source3/winbindd/winbindd_proto.h4
-rw-r--r--source3/winbindd/winbindd_user.c28
-rw-r--r--source4/rpc_server/spoolss/dcesrv_spoolss.c12
-rw-r--r--source4/torture/basic/locking.c2
-rw-r--r--source4/torture/ndr/spoolss.c8
-rw-r--r--source4/torture/raw/lock.c573
-rw-r--r--source4/torture/smbtorture.c2
39 files changed, 1688 insertions, 637 deletions
diff --git a/lib/replace/libreplace_network.m4 b/lib/replace/libreplace_network.m4
index 30be30f4ab..78fb1abaf0 100644
--- a/lib/replace/libreplace_network.m4
+++ b/lib/replace/libreplace_network.m4
@@ -353,6 +353,7 @@ AC_CACHE_CHECK([for ipv6 support],libreplace_cv_HAVE_IPV6,[
#include <sys/socket.h>
#include <sys/types.h>
#include <netdb.h>
+#include <netinet/in.h>
],
[
struct sockaddr_storage sa_store;
diff --git a/libcli/util/ntstatus.h b/libcli/util/ntstatus.h
index 139562d8c2..1608e2874f 100644
--- a/libcli/util/ntstatus.h
+++ b/libcli/util/ntstatus.h
@@ -60,6 +60,9 @@ typedef uint32_t NTSTATUS;
#define ERROR_INSUFFICIENT_BUFFER NT_STATUS(0x007a)
#define ERROR_INVALID_DATATYPE NT_STATUS(0x070c)
+/* XXX Win7 Status code: Name unknown. */
+#define NT_STATUS_WIN7_INVALID_RANGE NT_STATUS(0xC0000000 | 0x01a1)
+
/* Win32 Error codes extracted using a loop in smbclient then printing a
netmon sniff to a file. */
diff --git a/librpc/gen_ndr/cli_spoolss.c b/librpc/gen_ndr/cli_spoolss.c
index 492f2c2a71..2f15cb30bb 100644
--- a/librpc/gen_ndr/cli_spoolss.c
+++ b/librpc/gen_ndr/cli_spoolss.c
@@ -3107,23 +3107,34 @@ NTSTATUS rpccli_spoolss_RemoteFindFirstPrinterChangeNotifyEx(struct rpc_pipe_cli
return werror_to_ntstatus(r.out.result);
}
-NTSTATUS rpccli_spoolss_RouterRefreshPrinterChangeNotification(struct rpc_pipe_client *cli,
- TALLOC_CTX *mem_ctx,
- WERROR *werror)
+NTSTATUS rpccli_spoolss_RouterReplyPrinterEx(struct rpc_pipe_client *cli,
+ TALLOC_CTX *mem_ctx,
+ struct policy_handle *handle /* [in] [ref] */,
+ uint32_t color /* [in] */,
+ uint32_t flags /* [in] */,
+ uint32_t *reply_result /* [out] [ref] */,
+ uint32_t reply_type /* [in] */,
+ union spoolss_ReplyPrinterInfo info /* [in] [switch_is(reply_type)] */,
+ WERROR *werror)
{
- struct spoolss_RouterRefreshPrinterChangeNotification r;
+ struct spoolss_RouterReplyPrinterEx r;
NTSTATUS status;
/* In parameters */
+ r.in.handle = handle;
+ r.in.color = color;
+ r.in.flags = flags;
+ r.in.reply_type = reply_type;
+ r.in.info = info;
if (DEBUGLEVEL >= 10) {
- NDR_PRINT_IN_DEBUG(spoolss_RouterRefreshPrinterChangeNotification, &r);
+ NDR_PRINT_IN_DEBUG(spoolss_RouterReplyPrinterEx, &r);
}
status = cli->dispatch(cli,
mem_ctx,
&ndr_table_spoolss,
- NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFICATION,
+ NDR_SPOOLSS_ROUTERREPLYPRINTEREX,
&r);
if (!NT_STATUS_IS_OK(status)) {
@@ -3131,7 +3142,7 @@ NTSTATUS rpccli_spoolss_RouterRefreshPrinterChangeNotification(struct rpc_pipe_c
}
if (DEBUGLEVEL >= 10) {
- NDR_PRINT_OUT_DEBUG(spoolss_RouterRefreshPrinterChangeNotification, &r);
+ NDR_PRINT_OUT_DEBUG(spoolss_RouterReplyPrinterEx, &r);
}
if (NT_STATUS_IS_ERR(status)) {
@@ -3139,6 +3150,7 @@ NTSTATUS rpccli_spoolss_RouterRefreshPrinterChangeNotification(struct rpc_pipe_c
}
/* Return variables */
+ *reply_result = *r.out.reply_result;
/* Return result */
if (werror) {
@@ -3148,15 +3160,15 @@ NTSTATUS rpccli_spoolss_RouterRefreshPrinterChangeNotification(struct rpc_pipe_c
return werror_to_ntstatus(r.out.result);
}
-NTSTATUS rpccli_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct rpc_pipe_client *cli,
- TALLOC_CTX *mem_ctx,
- struct policy_handle *handle /* [in] [ref] */,
- uint32_t change_low /* [in] */,
- struct spoolss_NotifyOptionsContainer *container /* [in] [unique] */,
- struct spoolss_NotifyInfo **info /* [out] [ref] */,
- WERROR *werror)
+NTSTATUS rpccli_spoolss_RouterRefreshPrinterChangeNotify(struct rpc_pipe_client *cli,
+ TALLOC_CTX *mem_ctx,
+ struct policy_handle *handle /* [in] [ref] */,
+ uint32_t change_low /* [in] */,
+ struct spoolss_NotifyOptionsContainer *container /* [in] [unique] */,
+ struct spoolss_NotifyInfo **info /* [out] [ref] */,
+ WERROR *werror)
{
- struct spoolss_RemoteFindNextPrinterChangeNotifyEx r;
+ struct spoolss_RouterRefreshPrinterChangeNotify r;
NTSTATUS status;
/* In parameters */
@@ -3165,13 +3177,13 @@ NTSTATUS rpccli_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct rpc_pipe_clie
r.in.container = container;
if (DEBUGLEVEL >= 10) {
- NDR_PRINT_IN_DEBUG(spoolss_RemoteFindNextPrinterChangeNotifyEx, &r);
+ NDR_PRINT_IN_DEBUG(spoolss_RouterRefreshPrinterChangeNotify, &r);
}
status = cli->dispatch(cli,
mem_ctx,
&ndr_table_spoolss,
- NDR_SPOOLSS_REMOTEFINDNEXTPRINTERCHANGENOTIFYEX,
+ NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFY,
&r);
if (!NT_STATUS_IS_OK(status)) {
@@ -3179,7 +3191,7 @@ NTSTATUS rpccli_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct rpc_pipe_clie
}
if (DEBUGLEVEL >= 10) {
- NDR_PRINT_OUT_DEBUG(spoolss_RemoteFindNextPrinterChangeNotifyEx, &r);
+ NDR_PRINT_OUT_DEBUG(spoolss_RouterRefreshPrinterChangeNotify, &r);
}
if (NT_STATUS_IS_ERR(status)) {
diff --git a/librpc/gen_ndr/cli_spoolss.h b/librpc/gen_ndr/cli_spoolss.h
index 25000a4cc4..6903aa6909 100644
--- a/librpc/gen_ndr/cli_spoolss.h
+++ b/librpc/gen_ndr/cli_spoolss.h
@@ -382,16 +382,22 @@ NTSTATUS rpccli_spoolss_RemoteFindFirstPrinterChangeNotifyEx(struct rpc_pipe_cli
uint32_t printer_local /* [in] */,
struct spoolss_NotifyOptionsContainer *t1 /* [in] [unique] */,
WERROR *werror);
-NTSTATUS rpccli_spoolss_RouterRefreshPrinterChangeNotification(struct rpc_pipe_client *cli,
- TALLOC_CTX *mem_ctx,
- WERROR *werror);
-NTSTATUS rpccli_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct rpc_pipe_client *cli,
- TALLOC_CTX *mem_ctx,
- struct policy_handle *handle /* [in] [ref] */,
- uint32_t change_low /* [in] */,
- struct spoolss_NotifyOptionsContainer *container /* [in] [unique] */,
- struct spoolss_NotifyInfo **info /* [out] [ref] */,
- WERROR *werror);
+NTSTATUS rpccli_spoolss_RouterReplyPrinterEx(struct rpc_pipe_client *cli,
+ TALLOC_CTX *mem_ctx,
+ struct policy_handle *handle /* [in] [ref] */,
+ uint32_t color /* [in] */,
+ uint32_t flags /* [in] */,
+ uint32_t *reply_result /* [out] [ref] */,
+ uint32_t reply_type /* [in] */,
+ union spoolss_ReplyPrinterInfo info /* [in] [switch_is(reply_type)] */,
+ WERROR *werror);
+NTSTATUS rpccli_spoolss_RouterRefreshPrinterChangeNotify(struct rpc_pipe_client *cli,
+ TALLOC_CTX *mem_ctx,
+ struct policy_handle *handle /* [in] [ref] */,
+ uint32_t change_low /* [in] */,
+ struct spoolss_NotifyOptionsContainer *container /* [in] [unique] */,
+ struct spoolss_NotifyInfo **info /* [out] [ref] */,
+ WERROR *werror);
NTSTATUS rpccli_spoolss_44(struct rpc_pipe_client *cli,
TALLOC_CTX *mem_ctx,
WERROR *werror);
diff --git a/librpc/gen_ndr/ndr_spoolss.c b/librpc/gen_ndr/ndr_spoolss.c
index 9ef5d37336..5525ad4586 100644
--- a/librpc/gen_ndr/ndr_spoolss.c
+++ b/librpc/gen_ndr/ndr_spoolss.c
@@ -10602,6 +10602,124 @@ _PUBLIC_ void ndr_print_spoolss_NotifyInfo(struct ndr_print *ndr, const char *na
ndr->depth--;
}
+static enum ndr_err_code ndr_push_spoolss_ReplyPrinterInfo(struct ndr_push *ndr, int ndr_flags, const union spoolss_ReplyPrinterInfo *r)
+{
+ if (ndr_flags & NDR_SCALARS) {
+ int level = ndr_push_get_switch_value(ndr, r);
+ NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, level));
+ switch (level) {
+ case 0: {
+ NDR_CHECK(ndr_push_unique_ptr(ndr, r->info0));
+ break; }
+
+ default:
+ return ndr_push_error(ndr, NDR_ERR_BAD_SWITCH, "Bad switch value %u", level);
+ }
+ }
+ if (ndr_flags & NDR_BUFFERS) {
+ int level = ndr_push_get_switch_value(ndr, r);
+ switch (level) {
+ case 0:
+ if (r->info0) {
+ NDR_CHECK(ndr_push_spoolss_NotifyInfo(ndr, NDR_SCALARS|NDR_BUFFERS, r->info0));
+ }
+ break;
+
+ default:
+ return ndr_push_error(ndr, NDR_ERR_BAD_SWITCH, "Bad switch value %u", level);
+ }
+ }
+ return NDR_ERR_SUCCESS;
+}
+
+static enum ndr_err_code ndr_pull_spoolss_ReplyPrinterInfo(struct ndr_pull *ndr, int ndr_flags, union spoolss_ReplyPrinterInfo *r)
+{
+ int level;
+ uint32_t _level;
+ TALLOC_CTX *_mem_save_info0_0;
+ level = ndr_pull_get_switch_value(ndr, r);
+ if (ndr_flags & NDR_SCALARS) {
+ NDR_CHECK(ndr_pull_uint32(ndr, NDR_SCALARS, &_level));
+ if (_level != level) {
+ return ndr_pull_error(ndr, NDR_ERR_BAD_SWITCH, "Bad switch value %u for r", _level);
+ }
+ switch (level) {
+ case 0: {
+ uint32_t _ptr_info0;
+ NDR_CHECK(ndr_pull_generic_ptr(ndr, &_ptr_info0));
+ if (_ptr_info0) {
+ NDR_PULL_ALLOC(ndr, r->info0);
+ } else {
+ r->info0 = NULL;
+ }
+ break; }
+
+ default:
+ return ndr_pull_error(ndr, NDR_ERR_BAD_SWITCH, "Bad switch value %u", level);
+ }
+ }
+ if (ndr_flags & NDR_BUFFERS) {
+ switch (level) {
+ case 0:
+ if (r->info0) {
+ _mem_save_info0_0 = NDR_PULL_GET_MEM_CTX(ndr);
+ NDR_PULL_SET_MEM_CTX(ndr, r->info0, 0);
+ NDR_CHECK(ndr_pull_spoolss_NotifyInfo(ndr, NDR_SCALARS|NDR_BUFFERS, r->info0));
+ NDR_PULL_SET_MEM_CTX(ndr, _mem_save_info0_0, 0);
+ }
+ break;
+
+ default:
+ return ndr_pull_error(ndr, NDR_ERR_BAD_SWITCH, "Bad switch value %u", level);
+ }
+ }
+ return NDR_ERR_SUCCESS;
+}
+
+_PUBLIC_ void ndr_print_spoolss_ReplyPrinterInfo(struct ndr_print *ndr, const char *name, const union spoolss_ReplyPrinterInfo *r)
+{
+ int level;
+ level = ndr_print_get_switch_value(ndr, r);
+ ndr_print_union(ndr, name, level, "spoolss_ReplyPrinterInfo");
+ switch (level) {
+ case 0:
+ ndr_print_ptr(ndr, "info0", r->info0);
+ ndr->depth++;
+ if (r->info0) {
+ ndr_print_spoolss_NotifyInfo(ndr, "info0", r->info0);
+ }
+ ndr->depth--;
+ break;
+
+ default:
+ ndr_print_bad_level(ndr, name, level);
+ }
+}
+
+static enum ndr_err_code ndr_push_spoolss_PrinterNotifyFlags(struct ndr_push *ndr, int ndr_flags, uint32_t r)
+{
+ NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, r));
+ return NDR_ERR_SUCCESS;
+}
+
+static enum ndr_err_code ndr_pull_spoolss_PrinterNotifyFlags(struct ndr_pull *ndr, int ndr_flags, uint32_t *r)
+{
+ uint32_t v;
+ NDR_CHECK(ndr_pull_uint32(ndr, NDR_SCALARS, &v));
+ *r = v;
+ return NDR_ERR_SUCCESS;
+}
+
+_PUBLIC_ void ndr_print_spoolss_PrinterNotifyFlags(struct ndr_print *ndr, const char *name, uint32_t r)
+{
+ ndr_print_uint32(ndr, name, r);
+ ndr->depth++;
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "PRINTER_NOTIFY_INFO_DISCARDED", PRINTER_NOTIFY_INFO_DISCARDED, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "PRINTER_NOTIFY_INFO_DISCARDNOTED", PRINTER_NOTIFY_INFO_DISCARDNOTED, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "PRINTER_NOTIFY_INFO_COLOR_MISMATCH", PRINTER_NOTIFY_INFO_COLOR_MISMATCH, r);
+ ndr->depth--;
+}
+
static enum ndr_err_code ndr_push_spoolss_UserLevel1(struct ndr_push *ndr, int ndr_flags, const struct spoolss_UserLevel1 *r)
{
if (ndr_flags & NDR_SCALARS) {
@@ -10828,6 +10946,35 @@ _PUBLIC_ void ndr_print_spoolss_DeleteDriverFlags(struct ndr_print *ndr, const c
ndr->depth--;
}
+static enum ndr_err_code ndr_push_spoolss_AddPrinterDriverExFlags(struct ndr_push *ndr, int ndr_flags, uint32_t r)
+{
+ NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, r));
+ return NDR_ERR_SUCCESS;
+}
+
+static enum ndr_err_code ndr_pull_spoolss_AddPrinterDriverExFlags(struct ndr_pull *ndr, int ndr_flags, uint32_t *r)
+{
+ uint32_t v;
+ NDR_CHECK(ndr_pull_uint32(ndr, NDR_SCALARS, &v));
+ *r = v;
+ return NDR_ERR_SUCCESS;
+}
+
+_PUBLIC_ void ndr_print_spoolss_AddPrinterDriverExFlags(struct ndr_print *ndr, const char *name, uint32_t r)
+{
+ ndr_print_uint32(ndr, name, r);
+ ndr->depth++;
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "APD_STRICT_UPGRADE", APD_STRICT_UPGRADE, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "APD_STRICT_DOWNGRADE", APD_STRICT_DOWNGRADE, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "APD_COPY_ALL_FILES", APD_COPY_ALL_FILES, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "APD_COPY_NEW_FILES", APD_COPY_NEW_FILES, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "APD_COPY_FROM_DIRECTORY", APD_COPY_FROM_DIRECTORY, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "APD_DONT_COPY_FILES_TO_CLUSTER", APD_DONT_COPY_FILES_TO_CLUSTER, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "APD_COPY_TO_ALL_SPOOLERS", APD_COPY_TO_ALL_SPOOLERS, r);
+ ndr_print_bitmap_flag(ndr, sizeof(uint32_t), "APD_RETURN_BLOCKING_STATUS_CODE", APD_RETURN_BLOCKING_STATUS_CODE, r);
+ ndr->depth--;
+}
+
_PUBLIC_ enum ndr_err_code ndr_push__spoolss_EnumPrinters(struct ndr_push *ndr, int flags, const struct _spoolss_EnumPrinters *r)
{
if (flags & NDR_IN) {
@@ -16638,48 +16785,99 @@ _PUBLIC_ void ndr_print_spoolss_RemoteFindFirstPrinterChangeNotifyEx(struct ndr_
ndr->depth--;
}
-static enum ndr_err_code ndr_push_spoolss_RouterRefreshPrinterChangeNotification(struct ndr_push *ndr, int flags, const struct spoolss_RouterRefreshPrinterChangeNotification *r)
+static enum ndr_err_code ndr_push_spoolss_RouterReplyPrinterEx(struct ndr_push *ndr, int flags, const struct spoolss_RouterReplyPrinterEx *r)
{
if (flags & NDR_IN) {
+ if (r->in.handle == NULL) {
+ return ndr_push_error(ndr, NDR_ERR_INVALID_POINTER, "NULL [ref] pointer");
+ }
+ NDR_CHECK(ndr_push_policy_handle(ndr, NDR_SCALARS, r->in.handle));
+ NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, r->in.color));
+ NDR_CHECK(ndr_push_spoolss_PrinterChangeFlags(ndr, NDR_SCALARS, r->in.flags));
+ NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, r->in.reply_type));
+ NDR_CHECK(ndr_push_set_switch_value(ndr, &r->in.info, r->in.reply_type));
+ NDR_CHECK(ndr_push_spoolss_ReplyPrinterInfo(ndr, NDR_SCALARS|NDR_BUFFERS, &r->in.info));
}
if (flags & NDR_OUT) {
+ if (r->out.reply_result == NULL) {
+ return ndr_push_error(ndr, NDR_ERR_INVALID_POINTER, "NULL [ref] pointer");
+ }
+ NDR_CHECK(ndr_push_spoolss_PrinterNotifyFlags(ndr, NDR_SCALARS, *r->out.reply_result));
NDR_CHECK(ndr_push_WERROR(ndr, NDR_SCALARS, r->out.result));
}
return NDR_ERR_SUCCESS;
}
-static enum ndr_err_code ndr_pull_spoolss_RouterRefreshPrinterChangeNotification(struct ndr_pull *ndr, int flags, struct spoolss_RouterRefreshPrinterChangeNotification *r)
+static enum ndr_err_code ndr_pull_spoolss_RouterReplyPrinterEx(struct ndr_pull *ndr, int flags, struct spoolss_RouterReplyPrinterEx *r)
{
+ TALLOC_CTX *_mem_save_handle_0;
+ TALLOC_CTX *_mem_save_reply_result_0;
if (flags & NDR_IN) {
+ ZERO_STRUCT(r->out);
+
+ if (ndr->flags & LIBNDR_FLAG_REF_ALLOC) {
+ NDR_PULL_ALLOC(ndr, r->in.handle);
+ }
+ _mem_save_handle_0 = NDR_PULL_GET_MEM_CTX(ndr);
+ NDR_PULL_SET_MEM_CTX(ndr, r->in.handle, LIBNDR_FLAG_REF_ALLOC);
+ NDR_CHECK(ndr_pull_policy_handle(ndr, NDR_SCALARS, r->in.handle));
+ NDR_PULL_SET_MEM_CTX(ndr, _mem_save_handle_0, LIBNDR_FLAG_REF_ALLOC);
+ NDR_CHECK(ndr_pull_uint32(ndr, NDR_SCALARS, &r->in.color));
+ NDR_CHECK(ndr_pull_spoolss_PrinterChangeFlags(ndr, NDR_SCALARS, &r->in.flags));
+ NDR_CHECK(ndr_pull_uint32(ndr, NDR_SCALARS, &r->in.reply_type));
+ NDR_CHECK(ndr_pull_set_switch_value(ndr, &r->in.info, r->in.reply_type));
+ NDR_CHECK(ndr_pull_spoolss_ReplyPrinterInfo(ndr, NDR_SCALARS|NDR_BUFFERS, &r->in.info));
+ NDR_PULL_ALLOC(ndr, r->out.reply_result);
+ ZERO_STRUCTP(r->out.reply_result);
}
if (flags & NDR_OUT) {
+ if (ndr->flags & LIBNDR_FLAG_REF_ALLOC) {
+ NDR_PULL_ALLOC(ndr, r->out.reply_result);
+ }
+ _mem_save_reply_result_0 = NDR_PULL_GET_MEM_CTX(ndr);
+ NDR_PULL_SET_MEM_CTX(ndr, r->out.reply_result, LIBNDR_FLAG_REF_ALLOC);
+ NDR_CHECK(ndr_pull_spoolss_PrinterNotifyFlags(ndr, NDR_SCALARS, r->out.reply_result));
+ NDR_PULL_SET_MEM_CTX(ndr, _mem_save_reply_result_0, LIBNDR_FLAG_REF_ALLOC);
NDR_CHECK(ndr_pull_WERROR(ndr, NDR_SCALARS, &r->out.result));
}
return NDR_ERR_SUCCESS;
}
-_PUBLIC_ void ndr_print_spoolss_RouterRefreshPrinterChangeNotification(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RouterRefreshPrinterChangeNotification *r)
+_PUBLIC_ void ndr_print_spoolss_RouterReplyPrinterEx(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RouterReplyPrinterEx *r)
{
- ndr_print_struct(ndr, name, "spoolss_RouterRefreshPrinterChangeNotification");
+ ndr_print_struct(ndr, name, "spoolss_RouterReplyPrinterEx");
ndr->depth++;
if (flags & NDR_SET_VALUES) {
ndr->flags |= LIBNDR_PRINT_SET_VALUES;
}
if (flags & NDR_IN) {
- ndr_print_struct(ndr, "in", "spoolss_RouterRefreshPrinterChangeNotification");
+ ndr_print_struct(ndr, "in", "spoolss_RouterReplyPrinterEx");
ndr->depth++;
+ ndr_print_ptr(ndr, "handle", r->in.handle);
+ ndr->depth++;
+ ndr_print_policy_handle(ndr, "handle", r->in.handle);
+ ndr->depth--;
+ ndr_print_uint32(ndr, "color", r->in.color);
+ ndr_print_spoolss_PrinterChangeFlags(ndr, "flags", r->in.flags);
+ ndr_print_uint32(ndr, "reply_type", r->in.reply_type);
+ ndr_print_set_switch_value(ndr, &r->in.info, r->in.reply_type);
+ ndr_print_spoolss_ReplyPrinterInfo(ndr, "info", &r->in.info);
ndr->depth--;
}
if (flags & NDR_OUT) {
- ndr_print_struct(ndr, "out", "spoolss_RouterRefreshPrinterChangeNotification");
+ ndr_print_struct(ndr, "out", "spoolss_RouterReplyPrinterEx");
+ ndr->depth++;
+ ndr_print_ptr(ndr, "reply_result", r->out.reply_result);
ndr->depth++;
+ ndr_print_spoolss_PrinterNotifyFlags(ndr, "reply_result", *r->out.reply_result);
+ ndr->depth--;
ndr_print_WERROR(ndr, "result", r->out.result);
ndr->depth--;
}
ndr->depth--;
}
-_PUBLIC_ enum ndr_err_code ndr_push_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct ndr_push *ndr, int flags, const struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r)
+_PUBLIC_ enum ndr_err_code ndr_push_spoolss_RouterRefreshPrinterChangeNotify(struct ndr_push *ndr, int flags, const struct spoolss_RouterRefreshPrinterChangeNotify *r)
{
if (flags & NDR_IN) {
if (r->in.handle == NULL) {
@@ -16705,7 +16903,7 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_RemoteFindNextPrinterChangeNotifyEx(
return NDR_ERR_SUCCESS;
}
-_PUBLIC_ enum ndr_err_code ndr_pull_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct ndr_pull *ndr, int flags, struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r)
+_PUBLIC_ enum ndr_err_code ndr_pull_spoolss_RouterRefreshPrinterChangeNotify(struct ndr_pull *ndr, int flags, struct spoolss_RouterRefreshPrinterChangeNotify *r)
{
uint32_t _ptr_container;
uint32_t _ptr_info;
@@ -16763,15 +16961,15 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_RemoteFindNextPrinterChangeNotifyEx(
return NDR_ERR_SUCCESS;
}
-_PUBLIC_ void ndr_print_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r)
+_PUBLIC_ void ndr_print_spoolss_RouterRefreshPrinterChangeNotify(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RouterRefreshPrinterChangeNotify *r)
{
- ndr_print_struct(ndr, name, "spoolss_RemoteFindNextPrinterChangeNotifyEx");
+ ndr_print_struct(ndr, name, "spoolss_RouterRefreshPrinterChangeNotify");
ndr->depth++;
if (flags & NDR_SET_VALUES) {
ndr->flags |= LIBNDR_PRINT_SET_VALUES;
}
if (flags & NDR_IN) {
- ndr_print_struct(ndr, "in", "spoolss_RemoteFindNextPrinterChangeNotifyEx");
+ ndr_print_struct(ndr, "in", "spoolss_RouterRefreshPrinterChangeNotify");
ndr->depth++;
ndr_print_ptr(ndr, "handle", r->in.handle);
ndr->depth++;
@@ -16787,7 +16985,7 @@ _PUBLIC_ void ndr_print_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct ndr_p
ndr->depth--;
}
if (flags & NDR_OUT) {
- ndr_print_struct(ndr, "out", "spoolss_RemoteFindNextPrinterChangeNotifyEx");
+ ndr_print_struct(ndr, "out", "spoolss_RouterRefreshPrinterChangeNotify");
ndr->depth++;
ndr_print_ptr(ndr, "info", r->out.info);
ndr->depth++;
@@ -18580,7 +18778,7 @@ _PUBLIC_ enum ndr_err_code ndr_push_spoolss_AddPrinterDriverEx(struct ndr_push *
NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, r->in.level));
NDR_CHECK(ndr_push_set_switch_value(ndr, &r->in.info, r->in.level));
NDR_CHECK(ndr_push_spoolss_AddDriverInfo(ndr, NDR_SCALARS|NDR_BUFFERS, &r->in.info));
- NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, r->in.flags));
+ NDR_CHECK(ndr_push_spoolss_AddPrinterDriverExFlags(ndr, NDR_SCALARS, r->in.flags));
}
if (flags & NDR_OUT) {
NDR_CHECK(ndr_push_WERROR(ndr, NDR_SCALARS, r->out.result));
@@ -18601,7 +18799,7 @@ _PUBLIC_ enum ndr_err_code ndr_pull_spoolss_AddPrinterDriverEx(struct ndr_pull *
NDR_CHECK(ndr_pull_uint32(ndr, NDR_SCALARS, &r->in.level));
NDR_CHECK(ndr_pull_set_switch_value(ndr, &r->in.info, r->in.level));
NDR_CHECK(ndr_pull_spoolss_AddDriverInfo(ndr, NDR_SCALARS|NDR_BUFFERS, &r->in.info));
- NDR_CHECK(ndr_pull_uint32(ndr, NDR_SCALARS, &r->in.flags));
+ NDR_CHECK(ndr_pull_spoolss_AddPrinterDriverExFlags(ndr, NDR_SCALARS, &r->in.flags));
}
if (flags & NDR_OUT) {
NDR_CHECK(ndr_pull_WERROR(ndr, NDR_SCALARS, &r->out.result));
@@ -18626,7 +18824,7 @@ _PUBLIC_ void ndr_print_spoolss_AddPrinterDriverEx(struct ndr_print *ndr, const
ndr_print_uint32(ndr, "level", r->in.level);
ndr_print_set_switch_value(ndr, &r->in.info, r->in.level);
ndr_print_spoolss_AddDriverInfo(ndr, "info", &r->in.info);
- ndr_print_uint32(ndr, "flags", r->in.flags);
+ ndr_print_spoolss_AddPrinterDriverExFlags(ndr, "flags", r->in.flags);
ndr->depth--;
}
if (flags & NDR_OUT) {
@@ -19414,19 +19612,19 @@ static const struct ndr_interface_call spoolss_calls[] = {
false,
},
{
- "spoolss_RouterRefreshPrinterChangeNotification",
- sizeof(struct spoolss_RouterRefreshPrinterChangeNotification),
- (ndr_push_flags_fn_t) ndr_push_spoolss_RouterRefreshPrinterChangeNotification,
- (ndr_pull_flags_fn_t) ndr_pull_spoolss_RouterRefreshPrinterChangeNotification,
- (ndr_print_function_t) ndr_print_spoolss_RouterRefreshPrinterChangeNotification,
+ "spoolss_RouterReplyPrinterEx",
+ sizeof(struct spoolss_RouterReplyPrinterEx),
+ (ndr_push_flags_fn_t) ndr_push_spoolss_RouterReplyPrinterEx,
+ (ndr_pull_flags_fn_t) ndr_pull_spoolss_RouterReplyPrinterEx,
+ (ndr_print_function_t) ndr_print_spoolss_RouterReplyPrinterEx,
false,
},
{
- "spoolss_RemoteFindNextPrinterChangeNotifyEx",
- sizeof(struct spoolss_RemoteFindNextPrinterChangeNotifyEx),
- (ndr_push_flags_fn_t) ndr_push_spoolss_RemoteFindNextPrinterChangeNotifyEx,
- (ndr_pull_flags_fn_t) ndr_pull_spoolss_RemoteFindNextPrinterChangeNotifyEx,
- (ndr_print_function_t) ndr_print_spoolss_RemoteFindNextPrinterChangeNotifyEx,
+ "spoolss_RouterRefreshPrinterChangeNotify",
+ sizeof(struct spoolss_RouterRefreshPrinterChangeNotify),
+ (ndr_push_flags_fn_t) ndr_push_spoolss_RouterRefreshPrinterChangeNotify,
+ (ndr_pull_flags_fn_t) ndr_pull_spoolss_RouterRefreshPrinterChangeNotify,
+ (ndr_print_function_t) ndr_print_spoolss_RouterRefreshPrinterChangeNotify,
false,
},
{
diff --git a/librpc/gen_ndr/ndr_spoolss.h b/librpc/gen_ndr/ndr_spoolss.h
index 6240290e4c..ef97a01ecd 100644
--- a/librpc/gen_ndr/ndr_spoolss.h
+++ b/librpc/gen_ndr/ndr_spoolss.h
@@ -144,9 +144,9 @@ extern const struct ndr_interface_table ndr_table_spoolss;
#define NDR_SPOOLSS_REMOTEFINDFIRSTPRINTERCHANGENOTIFYEX (0x41)
-#define NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFICATION (0x42)
+#define NDR_SPOOLSS_ROUTERREPLYPRINTEREX (0x42)
-#define NDR_SPOOLSS_REMOTEFINDNEXTPRINTERCHANGENOTIFYEX (0x43)
+#define NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFY (0x43)
#define NDR_SPOOLSS_44 (0x44)
@@ -315,11 +315,14 @@ void ndr_print_spoolss_NotifyBlob(struct ndr_print *ndr, const char *name, const
void ndr_print_spoolss_NotifyData(struct ndr_print *ndr, const char *name, const union spoolss_NotifyData *r);
void ndr_print_spoolss_Notify(struct ndr_print *ndr, const char *name, const struct spoolss_Notify *r);
void ndr_print_spoolss_NotifyInfo(struct ndr_print *ndr, const char *name, const struct spoolss_NotifyInfo *r);
+void ndr_print_spoolss_ReplyPrinterInfo(struct ndr_print *ndr, const char *name, const union spoolss_ReplyPrinterInfo *r);
+void ndr_print_spoolss_PrinterNotifyFlags(struct ndr_print *ndr, const char *name, uint32_t r);
void ndr_print_spoolss_UserLevel1(struct ndr_print *ndr, const char *name, const struct spoolss_UserLevel1 *r);
void ndr_print_spoolss_UserLevel(struct ndr_print *ndr, const char *name, const union spoolss_UserLevel *r);
enum ndr_err_code ndr_push_spoolss_DeleteDriverFlags(struct ndr_push *ndr, int ndr_flags, uint32_t r);
enum ndr_err_code ndr_pull_spoolss_DeleteDriverFlags(struct ndr_pull *ndr, int ndr_flags, uint32_t *r);
void ndr_print_spoolss_DeleteDriverFlags(struct ndr_print *ndr, const char *name, uint32_t r);
+void ndr_print_spoolss_AddPrinterDriverExFlags(struct ndr_print *ndr, const char *name, uint32_t r);
enum ndr_err_code ndr_push__spoolss_EnumPrinters(struct ndr_push *ndr, int flags, const struct _spoolss_EnumPrinters *r);
enum ndr_err_code ndr_pull__spoolss_EnumPrinters(struct ndr_pull *ndr, int flags, struct _spoolss_EnumPrinters *r);
void ndr_print__spoolss_EnumPrinters(struct ndr_print *ndr, const char *name, int flags, const struct _spoolss_EnumPrinters *r);
@@ -473,10 +476,10 @@ void ndr_print_spoolss_ResetPrinterEx(struct ndr_print *ndr, const char *name, i
enum ndr_err_code ndr_push_spoolss_RemoteFindFirstPrinterChangeNotifyEx(struct ndr_push *ndr, int flags, const struct spoolss_RemoteFindFirstPrinterChangeNotifyEx *r);
enum ndr_err_code ndr_pull_spoolss_RemoteFindFirstPrinterChangeNotifyEx(struct ndr_pull *ndr, int flags, struct spoolss_RemoteFindFirstPrinterChangeNotifyEx *r);
void ndr_print_spoolss_RemoteFindFirstPrinterChangeNotifyEx(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RemoteFindFirstPrinterChangeNotifyEx *r);
-void ndr_print_spoolss_RouterRefreshPrinterChangeNotification(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RouterRefreshPrinterChangeNotification *r);
-enum ndr_err_code ndr_push_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct ndr_push *ndr, int flags, const struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r);
-enum ndr_err_code ndr_pull_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct ndr_pull *ndr, int flags, struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r);
-void ndr_print_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r);
+void ndr_print_spoolss_RouterReplyPrinterEx(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RouterReplyPrinterEx *r);
+enum ndr_err_code ndr_push_spoolss_RouterRefreshPrinterChangeNotify(struct ndr_push *ndr, int flags, const struct spoolss_RouterRefreshPrinterChangeNotify *r);
+enum ndr_err_code ndr_pull_spoolss_RouterRefreshPrinterChangeNotify(struct ndr_pull *ndr, int flags, struct spoolss_RouterRefreshPrinterChangeNotify *r);
+void ndr_print_spoolss_RouterRefreshPrinterChangeNotify(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_RouterRefreshPrinterChangeNotify *r);
void ndr_print_spoolss_44(struct ndr_print *ndr, const char *name, int flags, const struct spoolss_44 *r);
enum ndr_err_code ndr_push_spoolss_OpenPrinterEx(struct ndr_push *ndr, int flags, const struct spoolss_OpenPrinterEx *r);
enum ndr_err_code ndr_pull_spoolss_OpenPrinterEx(struct ndr_pull *ndr, int flags, struct spoolss_OpenPrinterEx *r);
diff --git a/librpc/gen_ndr/spoolss.h b/librpc/gen_ndr/spoolss.h
index 4e854db009..3554d37b39 100644
--- a/librpc/gen_ndr/spoolss.h
+++ b/librpc/gen_ndr/spoolss.h
@@ -877,6 +877,15 @@ struct spoolss_NotifyInfo {
struct spoolss_Notify *notifies;/* [size_is(count)] */
};
+union spoolss_ReplyPrinterInfo {
+ struct spoolss_NotifyInfo *info0;/* [unique,case(0)] */
+}/* [switch_type(uint32)] */;
+
+/* bitmap spoolss_PrinterNotifyFlags */
+#define PRINTER_NOTIFY_INFO_DISCARDED ( 0x00000001 )
+#define PRINTER_NOTIFY_INFO_DISCARDNOTED ( 0x00010000 )
+#define PRINTER_NOTIFY_INFO_COLOR_MISMATCH ( 0x00080000 )
+
struct spoolss_UserLevel1 {
uint32_t size;
const char *client;/* [unique,charset(UTF16)] */
@@ -903,6 +912,16 @@ union spoolss_UserLevel {
#define DPD_DELETE_SPECIFIC_VERSION ( 0x00000002 )
#define DPD_DELETE_ALL_FILES ( 0x00000004 )
+/* bitmap spoolss_AddPrinterDriverExFlags */
+#define APD_STRICT_UPGRADE ( 0x00000001 )
+#define APD_STRICT_DOWNGRADE ( 0x00000002 )
+#define APD_COPY_ALL_FILES ( 0x00000004 )
+#define APD_COPY_NEW_FILES ( 0x00000008 )
+#define APD_COPY_FROM_DIRECTORY ( 0x00000010 )
+#define APD_DONT_COPY_FILES_TO_CLUSTER ( 0x00001000 )
+#define APD_COPY_TO_ALL_SPOOLERS ( 0x00002000 )
+#define APD_RETURN_BLOCKING_STATUS_CODE ( 0x00010000 )
+
struct _spoolss_EnumPrinters {
struct {
@@ -2017,15 +2036,24 @@ struct spoolss_RemoteFindFirstPrinterChangeNotifyEx {
};
-struct spoolss_RouterRefreshPrinterChangeNotification {
+struct spoolss_RouterReplyPrinterEx {
+ struct {
+ struct policy_handle *handle;/* [ref] */
+ uint32_t color;
+ uint32_t flags;
+ uint32_t reply_type;
+ union spoolss_ReplyPrinterInfo info;/* [switch_is(reply_type)] */
+ } in;
+
struct {
+ uint32_t *reply_result;/* [ref] */
WERROR result;
} out;
};
-struct spoolss_RemoteFindNextPrinterChangeNotifyEx {
+struct spoolss_RouterRefreshPrinterChangeNotify {
struct {
struct policy_handle *handle;/* [ref] */
uint32_t change_low;
diff --git a/librpc/gen_ndr/srv_spoolss.c b/librpc/gen_ndr/srv_spoolss.c
index c6f5d62b32..1f8c89a53f 100644
--- a/librpc/gen_ndr/srv_spoolss.c
+++ b/librpc/gen_ndr/srv_spoolss.c
@@ -5058,18 +5058,18 @@ static bool api_spoolss_RemoteFindFirstPrinterChangeNotifyEx(pipes_struct *p)
return true;
}
-static bool api_spoolss_RouterRefreshPrinterChangeNotification(pipes_struct *p)
+static bool api_spoolss_RouterReplyPrinterEx(pipes_struct *p)
{
const struct ndr_interface_call *call;
struct ndr_pull *pull;
struct ndr_push *push;
enum ndr_err_code ndr_err;
DATA_BLOB blob;
- struct spoolss_RouterRefreshPrinterChangeNotification *r;
+ struct spoolss_RouterReplyPrinterEx *r;
- call = &ndr_table_spoolss.calls[NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFICATION];
+ call = &ndr_table_spoolss.calls[NDR_SPOOLSS_ROUTERREPLYPRINTEREX];
- r = talloc(talloc_tos(), struct spoolss_RouterRefreshPrinterChangeNotification);
+ r = talloc(talloc_tos(), struct spoolss_RouterReplyPrinterEx);
if (r == NULL) {
return false;
}
@@ -5093,10 +5093,17 @@ static bool api_spoolss_RouterRefreshPrinterChangeNotification(pipes_struct *p)
}
if (DEBUGLEVEL >= 10) {
- NDR_PRINT_IN_DEBUG(spoolss_RouterRefreshPrinterChangeNotification, r);
+ NDR_PRINT_IN_DEBUG(spoolss_RouterReplyPrinterEx, r);
}
- r->out.result = _spoolss_RouterRefreshPrinterChangeNotification(p, r);
+ ZERO_STRUCT(r->out);
+ r->out.reply_result = talloc_zero(r, uint32_t);
+ if (r->out.reply_result == NULL) {
+ talloc_free(r);
+ return false;
+ }
+
+ r->out.result = _spoolss_RouterReplyPrinterEx(p, r);
if (p->rng_fault_state) {
talloc_free(r);
@@ -5105,7 +5112,7 @@ static bool api_spoolss_RouterRefreshPrinterChangeNotification(pipes_struct *p)
}
if (DEBUGLEVEL >= 10) {
- NDR_PRINT_OUT_DEBUG(spoolss_RouterRefreshPrinterChangeNotification, r);
+ NDR_PRINT_OUT_DEBUG(spoolss_RouterReplyPrinterEx, r);
}
push = ndr_push_init_ctx(r, NULL);
@@ -5131,18 +5138,18 @@ static bool api_spoolss_RouterRefreshPrinterChangeNotification(pipes_struct *p)
return true;
}
-static bool api_spoolss_RemoteFindNextPrinterChangeNotifyEx(pipes_struct *p)
+static bool api_spoolss_RouterRefreshPrinterChangeNotify(pipes_struct *p)
{
const struct ndr_interface_call *call;
struct ndr_pull *pull;
struct ndr_push *push;
enum ndr_err_code ndr_err;
DATA_BLOB blob;
- struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r;
+ struct spoolss_RouterRefreshPrinterChangeNotify *r;
- call = &ndr_table_spoolss.calls[NDR_SPOOLSS_REMOTEFINDNEXTPRINTERCHANGENOTIFYEX];
+ call = &ndr_table_spoolss.calls[NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFY];
- r = talloc(talloc_tos(), struct spoolss_RemoteFindNextPrinterChangeNotifyEx);
+ r = talloc(talloc_tos(), struct spoolss_RouterRefreshPrinterChangeNotify);
if (r == NULL) {
return false;
}
@@ -5166,7 +5173,7 @@ static bool api_spoolss_RemoteFindNextPrinterChangeNotifyEx(pipes_struct *p)
}
if (DEBUGLEVEL >= 10) {
- NDR_PRINT_IN_DEBUG(spoolss_RemoteFindNextPrinterChangeNotifyEx, r);
+ NDR_PRINT_IN_DEBUG(spoolss_RouterRefreshPrinterChangeNotify, r);
}
ZERO_STRUCT(r->out);
@@ -5176,7 +5183,7 @@ static bool api_spoolss_RemoteFindNextPrinterChangeNotifyEx(pipes_struct *p)
return false;
}
- r->out.result = _spoolss_RemoteFindNextPrinterChangeNotifyEx(p, r);
+ r->out.result = _spoolss_RouterRefreshPrinterChangeNotify(p, r);
if (p->rng_fault_state) {
talloc_free(r);
@@ -5185,7 +5192,7 @@ static bool api_spoolss_RemoteFindNextPrinterChangeNotifyEx(pipes_struct *p)
}
if (DEBUGLEVEL >= 10) {
- NDR_PRINT_OUT_DEBUG(spoolss_RemoteFindNextPrinterChangeNotifyEx, r);
+ NDR_PRINT_OUT_DEBUG(spoolss_RouterRefreshPrinterChangeNotify, r);
}
push = ndr_push_init_ctx(r, NULL);
@@ -7428,8 +7435,8 @@ static struct api_struct api_spoolss_cmds[] =
{"SPOOLSS_SPOOLERINIT", NDR_SPOOLSS_SPOOLERINIT, api_spoolss_SpoolerInit},
{"SPOOLSS_RESETPRINTEREX", NDR_SPOOLSS_RESETPRINTEREX, api_spoolss_ResetPrinterEx},
{"SPOOLSS_REMOTEFINDFIRSTPRINTERCHANGENOTIFYEX", NDR_SPOOLSS_REMOTEFINDFIRSTPRINTERCHANGENOTIFYEX, api_spoolss_RemoteFindFirstPrinterChangeNotifyEx},
- {"SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFICATION", NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFICATION, api_spoolss_RouterRefreshPrinterChangeNotification},
- {"SPOOLSS_REMOTEFINDNEXTPRINTERCHANGENOTIFYEX", NDR_SPOOLSS_REMOTEFINDNEXTPRINTERCHANGENOTIFYEX, api_spoolss_RemoteFindNextPrinterChangeNotifyEx},
+ {"SPOOLSS_ROUTERREPLYPRINTEREX", NDR_SPOOLSS_ROUTERREPLYPRINTEREX, api_spoolss_RouterReplyPrinterEx},
+ {"SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFY", NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFY, api_spoolss_RouterRefreshPrinterChangeNotify},
{"SPOOLSS_44", NDR_SPOOLSS_44, api_spoolss_44},
{"SPOOLSS_OPENPRINTEREX", NDR_SPOOLSS_OPENPRINTEREX, api_spoolss_OpenPrinterEx},
{"SPOOLSS_ADDPRINTEREX", NDR_SPOOLSS_ADDPRINTEREX, api_spoolss_AddPrinterEx},
@@ -8069,21 +8076,27 @@ NTSTATUS rpc_spoolss_dispatch(struct rpc_pipe_client *cli, TALLOC_CTX *mem_ctx,
return NT_STATUS_OK;
}
- case NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFICATION: {
- struct spoolss_RouterRefreshPrinterChangeNotification *r = (struct spoolss_RouterRefreshPrinterChangeNotification *)_r;
- r->out.result = _spoolss_RouterRefreshPrinterChangeNotification(cli->pipes_struct, r);
+ case NDR_SPOOLSS_ROUTERREPLYPRINTEREX: {
+ struct spoolss_RouterReplyPrinterEx *r = (struct spoolss_RouterReplyPrinterEx *)_r;
+ ZERO_STRUCT(r->out);
+ r->out.reply_result = talloc_zero(mem_ctx, uint32_t);
+ if (r->out.reply_result == NULL) {
+ return NT_STATUS_NO_MEMORY;
+ }
+
+ r->out.result = _spoolss_RouterReplyPrinterEx(cli->pipes_struct, r);
return NT_STATUS_OK;
}
- case NDR_SPOOLSS_REMOTEFINDNEXTPRINTERCHANGENOTIFYEX: {
- struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r = (struct spoolss_RemoteFindNextPrinterChangeNotifyEx *)_r;
+ case NDR_SPOOLSS_ROUTERREFRESHPRINTERCHANGENOTIFY: {
+ struct spoolss_RouterRefreshPrinterChangeNotify *r = (struct spoolss_RouterRefreshPrinterChangeNotify *)_r;
ZERO_STRUCT(r->out);
r->out.info = talloc_zero(mem_ctx, struct spoolss_NotifyInfo *);
if (r->out.info == NULL) {
return NT_STATUS_NO_MEMORY;
}
- r->out.result = _spoolss_RemoteFindNextPrinterChangeNotifyEx(cli->pipes_struct, r);
+ r->out.result = _spoolss_RouterRefreshPrinterChangeNotify(cli->pipes_struct, r);
return NT_STATUS_OK;
}
diff --git a/librpc/gen_ndr/srv_spoolss.h b/librpc/gen_ndr/srv_spoolss.h
index 82e9faf993..da31eb78b6 100644
--- a/librpc/gen_ndr/srv_spoolss.h
+++ b/librpc/gen_ndr/srv_spoolss.h
@@ -67,8 +67,8 @@ WERROR _spoolss_RouterFindFirstPrinterChangeNotification(pipes_struct *p, struct
WERROR _spoolss_SpoolerInit(pipes_struct *p, struct spoolss_SpoolerInit *r);
WERROR _spoolss_ResetPrinterEx(pipes_struct *p, struct spoolss_ResetPrinterEx *r);
WERROR _spoolss_RemoteFindFirstPrinterChangeNotifyEx(pipes_struct *p, struct spoolss_RemoteFindFirstPrinterChangeNotifyEx *r);
-WERROR _spoolss_RouterRefreshPrinterChangeNotification(pipes_struct *p, struct spoolss_RouterRefreshPrinterChangeNotification *r);
-WERROR _spoolss_RemoteFindNextPrinterChangeNotifyEx(pipes_struct *p, struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r);
+WERROR _spoolss_RouterReplyPrinterEx(pipes_struct *p, struct spoolss_RouterReplyPrinterEx *r);
+WERROR _spoolss_RouterRefreshPrinterChangeNotify(pipes_struct *p, struct spoolss_RouterRefreshPrinterChangeNotify *r);
WERROR _spoolss_44(pipes_struct *p, struct spoolss_44 *r);
WERROR _spoolss_OpenPrinterEx(pipes_struct *p, struct spoolss_OpenPrinterEx *r);
WERROR _spoolss_AddPrinterEx(pipes_struct *p, struct spoolss_AddPrinterEx *r);
@@ -165,8 +165,8 @@ WERROR _spoolss_RouterFindFirstPrinterChangeNotification(pipes_struct *p, struct
WERROR _spoolss_SpoolerInit(pipes_struct *p, struct spoolss_SpoolerInit *r);
WERROR _spoolss_ResetPrinterEx(pipes_struct *p, struct spoolss_ResetPrinterEx *r);
WERROR _spoolss_RemoteFindFirstPrinterChangeNotifyEx(pipes_struct *p, struct spoolss_RemoteFindFirstPrinterChangeNotifyEx *r);
-WERROR _spoolss_RouterRefreshPrinterChangeNotification(pipes_struct *p, struct spoolss_RouterRefreshPrinterChangeNotification *r);
-WERROR _spoolss_RemoteFindNextPrinterChangeNotifyEx(pipes_struct *p, struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r);
+WERROR _spoolss_RouterReplyPrinterEx(pipes_struct *p, struct spoolss_RouterReplyPrinterEx *r);
+WERROR _spoolss_RouterRefreshPrinterChangeNotify(pipes_struct *p, struct spoolss_RouterRefreshPrinterChangeNotify *r);
WERROR _spoolss_44(pipes_struct *p, struct spoolss_44 *r);
WERROR _spoolss_OpenPrinterEx(pipes_struct *p, struct spoolss_OpenPrinterEx *r);
WERROR _spoolss_AddPrinterEx(pipes_struct *p, struct spoolss_AddPrinterEx *r);
diff --git a/librpc/idl/spoolss.idl b/librpc/idl/spoolss.idl
index 294ab50aaf..3e1d6620f7 100644
--- a/librpc/idl/spoolss.idl
+++ b/librpc/idl/spoolss.idl
@@ -1442,8 +1442,6 @@ import "misc.idl", "security.idl", "winreg.idl";
/******************/
/* Function: 0x42 */
- [todo] WERROR spoolss_RouterRefreshPrinterChangeNotification(
- );
typedef struct {
uint32 size;
@@ -1487,9 +1485,28 @@ import "misc.idl", "security.idl", "winreg.idl";
[size_is(count)] spoolss_Notify notifies[];
} spoolss_NotifyInfo;
+ typedef [switch_type(uint32)] union {
+ [case(0)] spoolss_NotifyInfo *info0;
+ } spoolss_ReplyPrinterInfo;
+
+ typedef [bitmap32bit] bitmap {
+ PRINTER_NOTIFY_INFO_DISCARDED = 0x00000001,
+ PRINTER_NOTIFY_INFO_DISCARDNOTED = 0x00010000,
+ PRINTER_NOTIFY_INFO_COLOR_MISMATCH = 0x00080000
+ } spoolss_PrinterNotifyFlags;
+
+ WERROR spoolss_RouterReplyPrinterEx(
+ [in,ref] policy_handle *handle,
+ [in] uint32 color,
+ [in] spoolss_PrinterChangeFlags flags,
+ [out,ref] spoolss_PrinterNotifyFlags *reply_result,
+ [in] uint32 reply_type,
+ [in,switch_is(reply_type)] spoolss_ReplyPrinterInfo info
+ );
+
/******************/
/* Function: 0x43 */
- [public] WERROR spoolss_RemoteFindNextPrinterChangeNotifyEx(
+ [public] WERROR spoolss_RouterRefreshPrinterChangeNotify(
[in,ref] policy_handle *handle,
[in] uint32 change_low,
[in,unique] spoolss_NotifyOptionsContainer *container,
@@ -1751,11 +1768,23 @@ import "misc.idl", "security.idl", "winreg.idl";
/******************/
/* Function: 0x59 */
+
+ typedef [bitmap32bit] bitmap {
+ APD_STRICT_UPGRADE = 0x00000001,
+ APD_STRICT_DOWNGRADE = 0x00000002,
+ APD_COPY_ALL_FILES = 0x00000004,
+ APD_COPY_NEW_FILES = 0x00000008,
+ APD_COPY_FROM_DIRECTORY = 0x00000010,
+ APD_DONT_COPY_FILES_TO_CLUSTER = 0x00001000,
+ APD_COPY_TO_ALL_SPOOLERS = 0x00002000,
+ APD_RETURN_BLOCKING_STATUS_CODE = 0x00010000
+ } spoolss_AddPrinterDriverExFlags;
+
[public] WERROR spoolss_AddPrinterDriverEx(
[in] [string,charset(UTF16)] uint16 *servername,
[in] uint32 level,
[in,switch_is(level)] spoolss_AddDriverInfo info,
- [in] uint32 flags
+ [in] spoolss_AddPrinterDriverExFlags flags
);
/******************/
diff --git a/nsswitch/libwbclient/wbc_pwd.c b/nsswitch/libwbclient/wbc_pwd.c
index cd945996c8..dacd9499dd 100644
--- a/nsswitch/libwbclient/wbc_pwd.c
+++ b/nsswitch/libwbclient/wbc_pwd.c
@@ -190,6 +190,45 @@ wbcErr wbcGetpwuid(uid_t uid, struct passwd **pwd)
return wbc_status;
}
+/* Fill in a struct passwd* for a domain user based on sid */
+wbcErr wbcGetpwsid(struct wbcDomainSid *sid, struct passwd **pwd)
+{
+ wbcErr wbc_status = WBC_ERR_UNKNOWN_FAILURE;
+ struct winbindd_request request;
+ struct winbindd_response response;
+ char * sid_string = NULL;
+
+ if (!pwd) {
+ wbc_status = WBC_ERR_INVALID_PARAM;
+ BAIL_ON_WBC_ERROR(wbc_status);
+ }
+
+ wbc_status = wbcSidToString(sid, &sid_string);
+ BAIL_ON_WBC_ERROR(wbc_status);
+
+ /* Initialize request */
+
+ ZERO_STRUCT(request);
+ ZERO_STRUCT(response);
+
+ strncpy(request.data.sid, sid_string, sizeof(request.data.sid));
+
+ wbc_status = wbcRequestResponse(WINBINDD_GETPWSID,
+ &request,
+ &response);
+ BAIL_ON_WBC_ERROR(wbc_status);
+
+ *pwd = copy_passwd_entry(&response.data.pw);
+ BAIL_ON_PTR_ERROR(*pwd, wbc_status);
+
+ done:
+ if (sid_string) {
+ wbcFreeMemory(sid_string);
+ }
+
+ return wbc_status;
+}
+
/* Fill in a struct passwd* for a domain user based on username */
wbcErr wbcGetgrnam(const char *name, struct group **grp)
{
diff --git a/nsswitch/libwbclient/wbc_sid.c b/nsswitch/libwbclient/wbc_sid.c
index e2157b9609..46c59a9513 100644
--- a/nsswitch/libwbclient/wbc_sid.c
+++ b/nsswitch/libwbclient/wbc_sid.c
@@ -491,6 +491,145 @@ wbcErr wbcLookupUserSids(const struct wbcDomainSid *user_sid,
return wbc_status;
}
+static inline
+wbcErr _sid_to_rid(struct wbcDomainSid *sid, uint32_t *rid)
+{
+ if (sid->num_auths < 1) {
+ return WBC_ERR_INVALID_RESPONSE;
+ }
+ *rid = sid->sub_auths[sid->num_auths - 1];
+
+ return WBC_ERR_SUCCESS;
+}
+
+/* Get alias membership for sids */
+wbcErr wbcGetSidAliases(const struct wbcDomainSid *dom_sid,
+ struct wbcDomainSid *sids,
+ uint32_t num_sids,
+ uint32_t **alias_rids,
+ uint32_t *num_alias_rids)
+{
+ uint32_t i;
+ const char *s;
+ struct winbindd_request request;
+ struct winbindd_response response;
+ char *sid_string = NULL;
+ ssize_t sid_len;
+ ssize_t extra_data_len = 0;
+ char * extra_data = NULL;
+ ssize_t buflen = 0;
+ struct wbcDomainSid sid;
+ wbcErr wbc_status = WBC_ERR_UNKNOWN_FAILURE;
+ uint32_t * rids = NULL;
+
+ /* Initialise request */
+
+ ZERO_STRUCT(request);
+ ZERO_STRUCT(response);
+
+ if (!dom_sid) {
+ wbc_status = WBC_ERR_INVALID_PARAM;
+ BAIL_ON_WBC_ERROR(wbc_status);
+ }
+
+ wbc_status = wbcSidToString(dom_sid, &sid_string);
+ BAIL_ON_WBC_ERROR(wbc_status);
+
+ strncpy(request.data.sid, sid_string, sizeof(request.data.sid)-1);
+ wbcFreeMemory(sid_string);
+ sid_string = NULL;
+
+ /* Lets assume each sid is around 54 characters
+ * S-1-5-AAAAAAAAAAA-BBBBBBBBBBB-CCCCCCCCCCC-DDDDDDDDDDD\n */
+ buflen = 54 * num_sids;
+ extra_data = talloc_array(NULL, char, buflen);
+ if (!extra_data) {
+ wbc_status = WBC_ERR_NO_MEMORY;
+ BAIL_ON_WBC_ERROR(wbc_status);
+ }
+
+ /* Build the sid list */
+ for (i=0; i<num_sids; i++) {
+ if (sid_string) {
+ wbcFreeMemory(sid_string);
+ sid_string = NULL;
+ }
+ wbc_status = wbcSidToString(&sids[i], &sid_string);
+ BAIL_ON_WBC_ERROR(wbc_status);
+
+ sid_len = strlen(sid_string);
+
+ if (buflen < extra_data_len + sid_len + 2) {
+ buflen *= 2;
+ extra_data = talloc_realloc(NULL, extra_data,
+ char, buflen);
+ if (!extra_data) {
+ wbc_status = WBC_ERR_NO_MEMORY;
+ BAIL_ON_WBC_ERROR(wbc_status);
+ }
+ }
+
+ strncpy(&extra_data[extra_data_len], sid_string,
+ buflen - extra_data_len);
+ extra_data_len += sid_len;
+ extra_data[extra_data_len++] = '\n';
+ extra_data[extra_data_len] = '\0';
+ }
+
+ request.extra_data.data = extra_data;
+ request.extra_len = extra_data_len;
+
+ wbc_status = wbcRequestResponse(WINBINDD_GETSIDALIASES,
+ &request,
+ &response);
+ BAIL_ON_WBC_ERROR(wbc_status);
+
+ if (response.data.num_entries &&
+ !response.extra_data.data) {
+ wbc_status = WBC_ERR_INVALID_RESPONSE;
+ BAIL_ON_WBC_ERROR(wbc_status);
+ }
+
+ rids = talloc_array(NULL, uint32_t,
+ response.data.num_entries);
+ BAIL_ON_PTR_ERROR(sids, wbc_status);
+
+ s = (const char *)response.extra_data.data;
+ for (i = 0; i < response.data.num_entries; i++) {
+ char *n = strchr(s, '\n');
+ if (n) {
+ *n = '\0';
+ }
+ wbc_status = wbcStringToSid(s, &sid);
+ BAIL_ON_WBC_ERROR(wbc_status);
+ wbc_status = _sid_to_rid(&sid, &rids[i]);
+ BAIL_ON_WBC_ERROR(wbc_status);
+ s += strlen(s) + 1;
+ }
+
+ *num_alias_rids = response.data.num_entries;
+ *alias_rids = rids;
+ rids = NULL;
+ wbc_status = WBC_ERR_SUCCESS;
+
+ done:
+ if (sid_string) {
+ wbcFreeMemory(sid_string);
+ }
+ if (extra_data) {
+ talloc_free(extra_data);
+ }
+ if (response.extra_data.data) {
+ free(response.extra_data.data);
+ }
+ if (rids) {
+ talloc_free(rids);
+ }
+
+ return wbc_status;
+}
+
+
/* Lists Users */
wbcErr wbcListUsers(const char *domain_name,
uint32_t *_num_users,
diff --git a/nsswitch/libwbclient/wbclient.h b/nsswitch/libwbclient/wbclient.h
index 990cc52df7..9d29951ae5 100644
--- a/nsswitch/libwbclient/wbclient.h
+++ b/nsswitch/libwbclient/wbclient.h
@@ -60,9 +60,11 @@ const char *wbcErrorString(wbcErr error);
* 0.1: Initial version
* 0.2: Added wbcRemoveUidMapping()
* Added wbcRemoveGidMapping()
+ * 0.3: Added wbcGetpwsid()
+ * Added wbcGetSidAliases()
**/
#define WBCLIENT_MAJOR_VERSION 0
-#define WBCLIENT_MINOR_VERSION 2
+#define WBCLIENT_MINOR_VERSION 3
#define WBCLIENT_VENDOR_VERSION "Samba libwbclient"
struct wbcLibraryDetails {
uint16_t major_version;
@@ -615,6 +617,15 @@ wbcErr wbcLookupUserSids(const struct wbcDomainSid *user_sid,
uint32_t *num_sids,
struct wbcDomainSid **sids);
+/*
+ * @brief Get alias membership for sids
+ **/
+wbcErr wbcGetSidAliases(const struct wbcDomainSid *dom_sid,
+ struct wbcDomainSid *sids,
+ uint32_t num_sids,
+ uint32_t **alias_rids,
+ uint32_t *num_alias_rids);
+
/**
* @brief Lists Users
**/
@@ -838,6 +849,17 @@ wbcErr wbcGetpwuid(uid_t uid, struct passwd **pwd);
/**
* @brief Fill in a struct passwd* for a domain user based
+ * on sid
+ *
+ * @param sid Sid to lookup
+ * @param **pwd Pointer to resulting struct passwd* from the query.
+ *
+ * @return #wbcErr
+ **/
+wbcErr wbcGetpwsid(struct wbcDomainSid * sid, struct passwd **pwd);
+
+/**
+ * @brief Fill in a struct passwd* for a domain user based
* on username
*
* @param *name Username to lookup
diff --git a/nsswitch/wbinfo.c b/nsswitch/wbinfo.c
index ce53cadc58..4d935f5239 100644
--- a/nsswitch/wbinfo.c
+++ b/nsswitch/wbinfo.c
@@ -202,6 +202,31 @@ static bool wbinfo_get_uidinfo(int uid)
return true;
}
+static bool wbinfo_get_user_sidinfo(const char *sid_str)
+{
+ wbcErr wbc_status = WBC_ERR_UNKNOWN_FAILURE;
+ struct passwd *pwd = NULL;
+ struct wbcDomainSid sid;
+
+ wbc_status = wbcStringToSid(sid_str, &sid);
+ wbc_status = wbcGetpwsid(&sid, &pwd);
+ if (!WBC_ERROR_IS_OK(wbc_status)) {
+ return false;
+ }
+
+ d_printf("%s:%s:%d:%d:%s:%s:%s\n",
+ pwd->pw_name,
+ pwd->pw_passwd,
+ pwd->pw_uid,
+ pwd->pw_gid,
+ pwd->pw_gecos,
+ pwd->pw_dir,
+ pwd->pw_shell);
+
+ return true;
+}
+
+
/* pull grent for a given group */
static bool wbinfo_get_groupinfo(const char *group)
{
@@ -341,6 +366,64 @@ static bool wbinfo_get_userdomgroups(const char *user_sid_str)
return true;
}
+static bool wbinfo_get_sidaliases(const char *domain,
+ const char *user_sid_str)
+{
+ wbcErr wbc_status = WBC_ERR_UNKNOWN_FAILURE;
+ struct wbcDomainInfo *dinfo = NULL;
+ uint32_t i;
+ struct wbcDomainSid user_sid;
+ uint32_t *alias_rids = NULL;
+ uint32_t num_alias_rids;
+ char *domain_sid_str = NULL;
+
+ /* Send request */
+ if ((domain == NULL) || (strequal(domain, ".")) ||
+ (domain[0] == '\0')) {
+ domain = get_winbind_domain();
+ }
+
+ /* Send request */
+
+ wbc_status = wbcDomainInfo(domain, &dinfo);
+ if (!WBC_ERROR_IS_OK(wbc_status)) {
+ d_printf("wbcDomainInfo(%s) failed: %s\n", domain,
+ wbcErrorString(wbc_status));
+ goto done;
+ }
+ wbc_status = wbcStringToSid(user_sid_str, &user_sid);
+ if (!WBC_ERROR_IS_OK(wbc_status)) {
+ goto done;
+ }
+
+ wbc_status = wbcGetSidAliases(&dinfo->sid, &user_sid, 1,
+ &alias_rids, &num_alias_rids);
+ if (!WBC_ERROR_IS_OK(wbc_status)) {
+ goto done;
+ }
+
+ wbc_status = wbcSidToString(&dinfo->sid, &domain_sid_str);
+ if (!WBC_ERROR_IS_OK(wbc_status)) {
+ goto done;
+ }
+
+ for (i = 0; i < num_alias_rids; i++) {
+ d_printf("%s-%d\n", domain_sid_str, alias_rids[i]);
+ }
+
+ wbcFreeMemory(alias_rids);
+
+done:
+ if (domain_sid_str) {
+ wbcFreeMemory(domain_sid_str);
+ }
+ if (dinfo) {
+ wbcFreeMemory(dinfo);
+ }
+ return (WBC_ERR_SUCCESS == wbc_status);
+}
+
+
/* Convert NetBIOS name to IP */
static bool wbinfo_wins_byname(const char *name)
@@ -1553,6 +1636,7 @@ enum {
OPT_GETDCNAME,
OPT_DSGETDCNAME,
OPT_USERDOMGROUPS,
+ OPT_SIDALIASES,
OPT_USERSIDS,
OPT_ALLOCATE_UID,
OPT_ALLOCATE_GID,
@@ -1564,6 +1648,7 @@ enum {
OPT_LIST_ALL_DOMAINS,
OPT_LIST_OWN_DOMAIN,
OPT_UID_INFO,
+ OPT_USER_SIDINFO,
OPT_GROUP_INFO,
OPT_GID_INFO,
OPT_VERBOSE,
@@ -1622,10 +1707,12 @@ int main(int argc, char **argv, char **envp)
{ "user-info", 'i', POPT_ARG_STRING, &string_arg, 'i', "Get user info", "USER" },
{ "uid-info", 0, POPT_ARG_INT, &int_arg, OPT_UID_INFO, "Get user info from uid", "UID" },
{ "group-info", 0, POPT_ARG_STRING, &string_arg, OPT_GROUP_INFO, "Get group info", "GROUP" },
+ { "user-sidinfo", 0, POPT_ARG_STRING, &string_arg, OPT_USER_SIDINFO, "Get user info from sid", "SID" },
{ "gid-info", 0, POPT_ARG_INT, &int_arg, OPT_GID_INFO, "Get group info from gid", "GID" },
{ "user-groups", 'r', POPT_ARG_STRING, &string_arg, 'r', "Get user groups", "USER" },
{ "user-domgroups", 0, POPT_ARG_STRING, &string_arg,
OPT_USERDOMGROUPS, "Get user domain groups", "SID" },
+ { "sid-aliases", 0, POPT_ARG_STRING, &string_arg, OPT_SIDALIASES, "Get sid aliases", "SID" },
{ "user-sids", 0, POPT_ARG_STRING, &string_arg, OPT_USERSIDS, "Get user group sids for user SID", "SID" },
{ "authenticate", 'a', POPT_ARG_STRING, &string_arg, 'a', "authenticate user", "user%password" },
{ "set-auth-user", 0, POPT_ARG_STRING, &string_arg, OPT_SET_AUTH_USER, "Store user and password used by winbindd (root only)", "user%password" },
@@ -1860,6 +1947,13 @@ int main(int argc, char **argv, char **envp)
goto done;
}
break;
+ case OPT_USER_SIDINFO:
+ if ( !wbinfo_get_user_sidinfo(string_arg)) {
+ d_fprintf(stderr, "Could not get info for user sid %s\n",
+ string_arg);
+ goto done;
+ }
+ break;
case OPT_UID_INFO:
if ( !wbinfo_get_uidinfo(int_arg)) {
d_fprintf(stderr, "Could not get info for uid "
@@ -1902,6 +1996,13 @@ int main(int argc, char **argv, char **envp)
goto done;
}
break;
+ case OPT_SIDALIASES:
+ if (!wbinfo_get_sidaliases(opt_domain_name, string_arg)) {
+ d_fprintf(stderr, "Could not get sid aliases "
+ "for user SID %s\n", string_arg);
+ goto done;
+ }
+ break;
case 'a': {
bool got_error = false;
diff --git a/nsswitch/winbind_struct_protocol.h b/nsswitch/winbind_struct_protocol.h
index 0b3e74492c..11b2069c3a 100644
--- a/nsswitch/winbind_struct_protocol.h
+++ b/nsswitch/winbind_struct_protocol.h
@@ -39,9 +39,11 @@
#define WINBINDD_DONT_ENV "_NO_WINBINDD"
#define WINBINDD_LOCATOR_KDC_ADDRESS "WINBINDD_LOCATOR_KDC_ADDRESS"
-/* Update this when you change the interface. */
-
-#define WINBIND_INTERFACE_VERSION 20
+/* Update this when you change the interface.
+ * 21: added WINBINDD_GETPWSID
+ * added WINBINDD_GETSIDALIASES
+ */
+#define WINBIND_INTERFACE_VERSION 21
/* Have to deal with time_t being 4 or 8 bytes due to structure alignment.
On a 64bit Linux box, we have to support a constant structure size
@@ -60,6 +62,7 @@ enum winbindd_cmd {
WINBINDD_GETPWNAM,
WINBINDD_GETPWUID,
+ WINBINDD_GETPWSID,
WINBINDD_GETGRNAM,
WINBINDD_GETGRGID,
WINBINDD_GETGROUPS,
@@ -140,6 +143,9 @@ enum winbindd_cmd {
/* Various group queries */
WINBINDD_GETUSERDOMGROUPS,
+ /* lookup local groups */
+ WINBINDD_GETSIDALIASES,
+
/* Initialize connection in a child */
WINBINDD_INIT_CONNECTION,
diff --git a/packaging/bin/fill-templates b/packaging/bin/fill-templates
index e74020fb69..204003c53b 100755
--- a/packaging/bin/fill-templates
+++ b/packaging/bin/fill-templates
@@ -13,7 +13,7 @@
# License: GPL
DIRNAME=$(dirname $0)
-TOPDIR=${DIRNAME}/../../
+TOPDIR=${DIRNAME}/../..
SRCDIR=${TOPDIR}/source3
VERSION_H=${SRCDIR}/include/version.h
@@ -26,14 +26,14 @@ if [ ! -f ${VERSION_H} ] ; then
exit 1
fi
-VERSION=`grep SAMBA_VERSION_OFFICIAL_STRING ${VERSION_H} | awk '{print $3}'`
+VERSION=`grep "define SAMBA_VERSION_OFFICIAL_STRING" ${VERSION_H} | awk '{print $3}'`
-vendor_version=`grep SAMBA_VERSION_VENDOR_SUFFIX ${VERSION_H} | awk '{print $3}'`
+vendor_version=`grep "define SAMBA_VERSION_VENDOR_SUFFIX" ${VERSION_H} | awk '{print $3}'`
if test "x${vendor_version}" != "x" ; then
VERSION="${VERSION}-${vendor_version}"
fi
-vendor_patch=`grep SAMBA_VERSION_VENDOR_PATCH ${VERSION_H} | awk '{print $3}'`
+vendor_patch=`grep "define SAMBA_VERSION_VENDOR_PATCH" ${VERSION_H} | awk '{print $3}'`
if test "x${vendor_patch}" != "x" ; then
VERSION="${VERSION}-${vendor_patch}"
fi
@@ -43,5 +43,5 @@ VERSION=`echo ${VERSION} | sed 's/\"//g'`
echo "VERSION: ${VERSION}"
pushd ${TOPDIR}/packaging > /dev/null 2>&1
-${TOPDIR}/packaging/bin/update-pkginfo "${VERSION}" 1 ""
+./bin/update-pkginfo "${VERSION}" 1 ""
popd > /dev/null 2>&1
diff --git a/source3/Makefile.in b/source3/Makefile.in
index 2d2d9a0c6d..948403248d 100644
--- a/source3/Makefile.in
+++ b/source3/Makefile.in
@@ -2813,7 +2813,8 @@ TOPFILES=dynconfig.o localedir.o
cleanlibs::
-rm -f ../lib/*/*.o ../lib/*/*/*.o \
- ../libcli/*.o ../libcli/*/*.o
+ ../libcli/*.o ../libcli/*/*.o \
+ ../librpc/*/*.o
clean:: cleanlibs
-rm -f include/build_env.h
@@ -2822,15 +2823,13 @@ clean:: cleanlibs
-rm -f core */*~ *~ \
*/*.o */*/*.o */*/*/*.o \
../testsuite/*/*.o \
+ ../nsswitch/*.o ../nsswitch/*/*.o ../nsswitch/*.@SHLIBEXT@ \
*/*.@SHLIBEXT@ */*/*.@SHLIBEXT@ */*/*/*.@SHLIBEXT@ \
$(TOPFILES) $(BIN_PROGS) $(SBIN_PROGS) $(ROOT_SBIN_PROGS) \
$(MODULES) $(TORTURE_PROGS) \
$(EVERYTHING_PROGS) \
bin/timelimit \
- .headers.stamp */src/*.o \
- ../lib/*/*.o \
- ../libcli/*.o ../libcli/*/*.o \
- ../librpc/*/*.o
+ .headers.stamp */src/*.o
-rm -rf t_dir
include/build_env.h: script/build_env.sh
diff --git a/source3/auth/auth_util.c b/source3/auth/auth_util.c
index e3677c41a4..f942b2e50a 100644
--- a/source3/auth/auth_util.c
+++ b/source3/auth/auth_util.c
@@ -186,13 +186,15 @@ static NTSTATUS make_user_info(auth_usersupplied_info **user_info,
Create an auth_usersupplied_data structure after appropriate mapping.
****************************************************************************/
-NTSTATUS make_user_info_map(auth_usersupplied_info **user_info,
- const char *smb_name,
- const char *client_domain,
- const char *wksta_name,
- DATA_BLOB *lm_pwd, DATA_BLOB *nt_pwd,
- DATA_BLOB *lm_interactive_pwd, DATA_BLOB *nt_interactive_pwd,
- DATA_BLOB *plaintext,
+NTSTATUS make_user_info_map(auth_usersupplied_info **user_info,
+ const char *smb_name,
+ const char *client_domain,
+ const char *wksta_name,
+ DATA_BLOB *lm_pwd,
+ DATA_BLOB *nt_pwd,
+ DATA_BLOB *lm_interactive_pwd,
+ DATA_BLOB *nt_interactive_pwd,
+ DATA_BLOB *plaintext,
bool encrypted)
{
const char *domain;
@@ -200,12 +202,12 @@ NTSTATUS make_user_info_map(auth_usersupplied_info **user_info,
bool was_mapped;
fstring internal_username;
fstrcpy(internal_username, smb_name);
- was_mapped = map_username(internal_username);
-
- DEBUG(5, ("make_user_info_map: Mapping user [%s]\\[%s] from workstation [%s]\n",
- client_domain, smb_name, wksta_name));
-
- /* don't allow "" as a domain, fixes a Win9X bug
+ was_mapped = map_username(internal_username);
+
+ DEBUG(5, ("Mapping user [%s]\\[%s] from workstation [%s]\n",
+ client_domain, smb_name, wksta_name));
+
+ /* don't allow "" as a domain, fixes a Win9X bug
where it doens't supply a domain for logon script
'net use' commands. */
@@ -214,16 +216,27 @@ NTSTATUS make_user_info_map(auth_usersupplied_info **user_info,
else
domain = lp_workgroup();
- /* do what win2k does. Always map unknown domains to our own
- and let the "passdb backend" handle unknown users. */
+ /* If you connect to a Windows domain member using a bogus domain name,
+ * the Windows box will map the BOGUS\user to SAMNAME\user. Thus, if
+ * the Windows box is a DC the name will become DOMAIN\user and be
+ * authenticated against AD, if the Windows box is a member server but
+ * not a DC the name will become WORKSTATION\user. A standalone
+ * non-domain member box will also map to WORKSTATION\user. */
- if ( !is_trusted_domain(domain) && !strequal(domain, get_global_sam_name()) )
- domain = my_sam_name();
-
- /* we know that it is a trusted domain (and we are allowing them) or it is our domain */
-
- result = make_user_info(user_info, smb_name, internal_username,
- client_domain, domain, wksta_name,
+ if (!is_trusted_domain(domain) &&
+ !strequal(domain, get_global_sam_name()) )
+ {
+ domain = get_global_sam_name();
+ DEBUG(5, ("Mapped domain from [%s] to [%s] for user [%s] on "
+ "workstation [%s]\n",
+ client_domain, domain, smb_name, wksta_name));
+ }
+
+ /* we know that it is a trusted domain (and we are allowing them) or it
+ * is our domain */
+
+ result = make_user_info(user_info, smb_name, internal_username,
+ client_domain, domain, wksta_name,
lm_pwd, nt_pwd,
lm_interactive_pwd, nt_interactive_pwd,
plaintext, encrypted);
@@ -573,8 +586,6 @@ NTSTATUS make_server_info_sam(auth_serversupplied_info **server_info,
}
result->sam_account = sampass;
- /* Ensure that the sampass will be freed with the result */
- talloc_steal(result, sampass);
result->unix_name = pwd->pw_name;
/* Ensure that we keep pwd->pw_name, because we will free pwd below */
talloc_steal(result, pwd->pw_name);
@@ -665,6 +676,8 @@ NTSTATUS make_server_info_sam(auth_serversupplied_info **server_info,
pdb_get_username(sampass), result->unix_name));
*server_info = result;
+ /* Ensure that the sampass will be freed with the result */
+ talloc_steal(result, sampass);
return NT_STATUS_OK;
}
diff --git a/source3/configure.in b/source3/configure.in
index 10ce6f6e5e..d11ece1b53 100644
--- a/source3/configure.in
+++ b/source3/configure.in
@@ -703,18 +703,6 @@ CPPFLAGS="$old_CPPFLAGS"
# subdirectory of headers.
AC_CHECK_HEADERS(valgrind.h valgrind/valgrind.h valgrind/memcheck.h)
-# check for linux on amd64 since valgrind is not quite there yet
-case "$host_os" in
- *linux*)
- case "$UNAME_P" in
- *x86_64*)
- AC_DEFINE(HAVE_64BIT_LINUX,1,[Whether we are running on 64bit linux])
- ;;
- esac
- ;;
-esac
-
-
#
# HPUX has a bug in that including shadow.h causes a re-definition of MAXINT.
# This causes configure to fail to detect it. Check for shadow separately on HPUX.
@@ -1041,8 +1029,7 @@ AC_CHECK_FUNCS(getdents64)
AC_CHECK_FUNCS(setenv strcasecmp fcvt fcvtl)
AC_CHECK_FUNCS(syslog vsyslog timegm)
AC_CHECK_FUNCS(setlocale nl_langinfo)
-AC_CHECK_FUNCS(nanosleep)
-AC_CHECK_LIB_EXT(rt, LIBS, nanosleep)
+AC_CHECK_FUNCS(nanosleep,,[AC_CHECK_LIB_EXT(rt, LIBS, nanosleep)])
AC_CHECK_FUNCS(mlock munlock mlockall munlockall)
AC_CHECK_FUNCS(memalign posix_memalign hstrerror)
AC_CHECK_HEADERS(sys/mman.h)
@@ -1311,301 +1298,29 @@ fi
#################################################
# Check whether struct stat has timestamps with sub-second resolution.
-# At least IRIX and Solaris have these. FREEBSD does as well,
-# but with different members
-#
-# We check that
-# all of st_mtim, st_atim and st_ctim exist
-# all of the members are in fact of type struct timespec
#
-# There is some conflicting standards weirdness about whether we should use
-# "struct timespec" or "timespec_t". Linux doesn't have timespec_t, so we
-# prefer struct timespec.
-AC_CACHE_CHECK([whether struct stat has timespec timestamps],
- samba_cv_stat_timespec_hires,
- [
- AC_TRY_COMPILE(
- [
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
-#endif
-#ifdef HAVE_SYS_STAT_H
-#include <sys/stat.h>
-#endif
- ],
- [
- struct timespec t;
- struct stat s = {0};
- t = s.st_mtimespec;
- t = s.st_ctimespec;
- t = s.st_atimespec;
- ],
- samba_cv_stat_timespec_hires=yes, samba_cv_stat_timespec_hires=no)
- ])
-
-if test x"$samba_cv_stat_timespec_hires" = x"yes" ; then
- AC_DEFINE(HAVE_STAT_ST_MTIMESPEC, 1, [whether struct stat contains st_mtimepec])
- AC_DEFINE(HAVE_STAT_ST_ATIMESPEC, 1, [whether struct stat contains st_atimespec])
- AC_DEFINE(HAVE_STAT_ST_CTIMESPEC, 1, [whether struct stat contains st_ctimespec])
- AC_DEFINE(HAVE_STAT_HIRES_TIMESTAMPS, 1, [whether struct stat has sub-second timestamps])
-fi
-
-
-AC_CACHE_CHECK([whether struct stat has sub-second timestamps], samba_cv_stat_hires,
- [
- AC_TRY_COMPILE(
- [
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
-#endif
-#ifdef HAVE_SYS_STAT_H
-#include <sys/stat.h>
-#endif
- ],
- [
- struct timespec t;
- struct stat s = {0};
- t.tv_sec = s.st_mtim.tv_sec;
- t.tv_nsec = s.st_mtim.tv_nsec;
- t.tv_sec = s.st_ctim.tv_sec;
- t.tv_nsec = s.st_ctim.tv_nsec;
- t.tv_sec = s.st_atim.tv_sec;
- t.tv_nsec = s.st_atim.tv_nsec;
- ],
- samba_cv_stat_hires=yes, samba_cv_stat_hires=no)
- ])
+samba_cv_stat_hires=no
+AC_CHECK_MEMBERS([struct stat.st_mtim.tv_nsec], # Linux, Solaris
+ [samba_cv_stat_hires=yes])
+AC_CHECK_MEMBERS([struct stat.st_mtimensec], # BSD, if defined _POSIX_SOURCE
+ [samba_cv_stat_hires=yes])
+AC_CHECK_MEMBERS([struct stat.st_mtimespec.tv_nsec], # BSD, if not defined _POSIX_SOURCE
+ [samba_cv_stat_hires=yes])
+AC_CHECK_MEMBERS([struct stat.st_mtime_n], # AIX
+ [samba_cv_stat_hires=yes])
+AC_CHECK_MEMBERS([struct stat.st_umtime], # Tru64
+ [samba_cv_stat_hires=yes])
if test x"$samba_cv_stat_hires" = x"yes" ; then
- AC_DEFINE(HAVE_STAT_ST_MTIM, 1, [whether struct stat contains st_mtim])
- AC_DEFINE(HAVE_STAT_ST_ATIM, 1, [whether struct stat contains st_atim])
- AC_DEFINE(HAVE_STAT_ST_CTIM, 1, [whether struct stat contains st_ctim])
AC_DEFINE(HAVE_STAT_HIRES_TIMESTAMPS, 1,
[whether struct stat has sub-second timestamps])
fi
-AC_CACHE_CHECK([whether struct stat has sub-second timestamps without struct timespec suffixed nsec], samba_cv_stat_hires_notimespec,
- [
- AC_TRY_COMPILE(
- [
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
-#endif
-#ifdef HAVE_SYS_STAT_H
-#include <sys/stat.h>
-#endif
- ],
- [
- struct timespec t;
- struct stat s = {0};
- t.tv_sec = s.st_mtime;
- t.tv_nsec = s.st_mtimensec;
- t.tv_sec = s.st_ctime;
- t.tv_nsec = s.st_ctimensec;
- t.tv_sec = s.st_atime;
- t.tv_nsec = s.st_atimensec;
- ],
- samba_cv_stat_hires_notimespec=yes, samba_cv_stat_hires_notimespec=no)
- ])
-
-if test x"$samba_cv_stat_hires_notimespec" = x"yes" ; then
- AC_DEFINE(HAVE_STAT_ST_MTIMENSEC, 1, [whether struct stat contains st_mtimensec])
- AC_DEFINE(HAVE_STAT_ST_ATIMENSEC, 1, [whether struct stat contains st_atimensec])
- AC_DEFINE(HAVE_STAT_ST_CTIMENSEC, 1, [whether struct stat contains st_ctimensec])
- AC_DEFINE(HAVE_STAT_HIRES_TIMESTAMPS, 1,
- [whether struct stat has sub-second timestamps without struct timespec suffixed nsec])
-fi
-
-dnl AIX stype sub-second timestamps:
-AC_CACHE_CHECK([whether struct stat has sub-second timestamps without struct timespec suffixed _n], samba_cv_stat_hires_notimespec_n,
- [
- AC_TRY_COMPILE(
- [
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
-#endif
-#ifdef HAVE_SYS_STAT_H
-#include <sys/stat.h>
-#endif
- ],
- [
- struct timespec t;
- struct stat s = {0};
- t.tv_sec = s.st_mtime;
- t.tv_nsec = s.st_mtime_n;
- t.tv_sec = s.st_ctime;
- t.tv_nsec = s.st_ctime_n;
- t.tv_sec = s.st_atime;
- t.tv_nsec = s.st_atime_n;
- ],
- samba_cv_stat_hires_notimespec_n=yes, samba_cv_stat_hires_notimespec_n=no)
- ])
-
-if test x"$samba_cv_stat_hires_notimespec_n" = x"yes" ; then
- AC_DEFINE(HAVE_STAT_ST_MTIME_N, 1, [whether struct stat contains st_mtime_n])
- AC_DEFINE(HAVE_STAT_ST_ATIME_N, 1, [whether struct stat contains st_atime_n])
- AC_DEFINE(HAVE_STAT_ST_CTIME_N, 1, [whether struct stat contains st_ctime_n])
- AC_DEFINE(HAVE_STAT_HIRES_TIMESTAMPS, 1,
- [whether struct stat has sub-second timestamps without struct timespec suffixed _n])
-fi
-
-dnl Tru64 has _micro_second_ resolution:
-AC_CACHE_CHECK([whether struct stat has sub-second timestamps in st_uXtime], samba_cv_stat_hires_uxtime,
- [
- AC_TRY_COMPILE(
- [
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
-#endif
-#ifdef HAVE_SYS_STAT_H
-#include <sys/stat.h>
-#endif
- ],
- [
- struct timespec t;
- struct stat s = {0};
- t.tv_sec = s.st_mtime;
- t.tv_nsec = s.st_umtime * 1000;
- t.tv_sec = s.st_ctime;
- t.tv_nsec = s.st_uctime * 1000;
- t.tv_sec = s.st_atime;
- t.tv_nsec = s.st_uatime * 1000;
- ],
- samba_cv_stat_hires_uxtime=yes, samba_cv_stat_hires_uxtime=no)
- ])
-
-if test x"$samba_cv_stat_hires_uxtime" = x"yes" ; then
- AC_DEFINE(HAVE_STAT_ST_UMTIME, 1, [whether struct stat contains st_umtime])
- AC_DEFINE(HAVE_STAT_ST_UATIME, 1, [whether struct stat contains st_uatime])
- AC_DEFINE(HAVE_STAT_ST_UCTIME, 1, [whether struct stat contains st_uctime])
- AC_DEFINE(HAVE_STAT_HIRES_TIMESTAMPS, 1,
- [whether struct stat has sub-second timestamps in st_uXtime])
-fi
-
-AC_CACHE_CHECK([whether struct stat has st_birthtimespec], samba_cv_stat_st_birthtimespec,
- [
- AC_TRY_COMPILE(
- [
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
-#endif
-#ifdef HAVE_SYS_STAT_H
-#include <sys/stat.h>
-#endif
- ],
- [
- struct timespec t;
- struct stat s = {0};
- t = s.st_birthtimespec;
- ],
- samba_cv_stat_st_birthtimespec=yes, samba_cv_stat_st_birthtimespec=no)
- ])
-
-if test x"$samba_cv_stat_st_birthtimespec" = x"yes" ; then
- AC_DEFINE(HAVE_STAT_ST_BIRTHTIMESPEC, 1, [whether struct stat contains st_birthtimespec])
-fi
-
-AC_CACHE_CHECK([whether struct stat has st_birthtimensec], samba_cv_stat_st_birthtimensec,
- [
- AC_TRY_COMPILE(
- [
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
-#endif
-#ifdef HAVE_SYS_STAT_H
-#include <sys/stat.h>
-#endif
- ],
- [
- struct timespec t;
- struct stat s = {0};
- t.tv_nsec = s.st_birthtimensec;
- ],
- samba_cv_stat_st_birthtimensec=yes, samba_cv_stat_st_birthtimensec=no)
- ])
+# recent FreeBSD, NetBSD have creation timestamps called birthtime:
+AC_CHECK_MEMBERS([struct stat.st_birthtimespec.tv_nsec])
+AC_CHECK_MEMBERS([struct stat.st_birthtime], AC_CHECK_MEMBERS([struct stat.st_birthtimensec]))
-if test x"$samba_cv_stat_st_birthtimensec" = x"yes" ; then
- AC_DEFINE(HAVE_STAT_ST_BIRTHTIMENSEC, 1, [whether struct stat contains st_birthtimensec])
-fi
-
-AC_CACHE_CHECK([whether struct stat has st_birthtime], samba_cv_stat_st_birthtime,
- [
- AC_TRY_COMPILE(
- [
-#if TIME_WITH_SYS_TIME
-# include <sys/time.h>
-# include <time.h>
-#else
-# if HAVE_SYS_TIME_H
-# include <sys/time.h>
-# else
-# include <time.h>
-# endif
-#endif
-#ifdef HAVE_SYS_STAT_H
-#include <sys/stat.h>
-#endif
- ],
- [
- struct time_t t;
- struct stat s = {0};
- t = s.st_birthtime;
- ],
- samba_cv_stat_st_birthtime=yes, samba_cv_stat_st_birthtime=no)
- ])
-
-if test x"$samba_cv_stat_st_birthtime" = x"yes" ; then
- AC_DEFINE(HAVE_STAT_ST_BIRTHTIME, 1, [whether struct stat contains st_birthtime])
-fi
AC_CACHE_CHECK([whether there is DOS flags support in the stat struct], samba_cv_stat_dos_flags,
[
diff --git a/source3/include/includes.h b/source3/include/includes.h
index 095fcaa3da..fc77534402 100644
--- a/source3/include/includes.h
+++ b/source3/include/includes.h
@@ -241,8 +241,6 @@ typedef int ber_int_t;
#include <aio.h>
#endif
-/* skip valgrind headers on 64bit AMD boxes */
-#ifndef HAVE_64BIT_LINUX
/* Special macros that are no-ops except when run under Valgrind on
* x86. They've moved a little bit from valgrind 1.0.4 to 1.9.4 */
#if HAVE_VALGRIND_MEMCHECK_H
@@ -251,12 +249,11 @@ typedef int ber_int_t;
#elif HAVE_VALGRIND_H
#include <valgrind.h>
#endif
-#endif
/* If we have --enable-developer and the valgrind header is present,
* then we're OK to use it. Set a macro so this logic can be done only
* once. */
-#if defined(DEVELOPER) && !defined(HAVE_64BIT_LINUX)
+#if defined(DEVELOPER)
#if (HAVE_VALGRIND_H || HAVE_VALGRIND_VALGRIND_H)
#define VALGRIND
#endif
diff --git a/source3/include/proto.h b/source3/include/proto.h
index 8f05c9473d..3478ea4f85 100644
--- a/source3/include/proto.h
+++ b/source3/include/proto.h
@@ -1660,6 +1660,8 @@ bool winbind_sid_to_uid(uid_t *puid, const DOM_SID *sid);
bool winbind_uid_to_sid(DOM_SID *sid, uid_t uid);
bool winbind_sid_to_gid(gid_t *pgid, const DOM_SID *sid);
bool winbind_gid_to_sid(DOM_SID *sid, gid_t gid);
+struct passwd * winbind_getpwnam(const char * sname);
+struct passwd * winbind_getpwsid(const DOM_SID *sid);
wbcErr wb_is_trusted_domain(const char *domain);
bool winbind_lookup_rids(TALLOC_CTX *mem_ctx,
const DOM_SID *domain_sid,
@@ -1668,22 +1670,17 @@ bool winbind_lookup_rids(TALLOC_CTX *mem_ctx,
const char ***names, enum lsa_SidType **types);
bool winbind_allocate_uid(uid_t *uid);
bool winbind_allocate_gid(gid_t *gid);
-bool winbind_lookup_name(const char *dom_name, const char *name, DOM_SID *sid,
- enum lsa_SidType *name_type);
-bool winbind_lookup_sid(TALLOC_CTX *mem_ctx, const DOM_SID *sid,
- const char **domain, const char **name,
- enum lsa_SidType *name_type);
-bool winbind_ping(void);
-bool winbind_sid_to_uid(uid_t *puid, const DOM_SID *sid);
-bool winbind_uid_to_sid(DOM_SID *sid, uid_t uid);
-bool winbind_sid_to_gid(gid_t *pgid, const DOM_SID *sid);
-bool winbind_gid_to_sid(DOM_SID *sid, gid_t gid);
-wbcErr wb_is_trusted_domain(const char *domain);
-bool winbind_lookup_rids(TALLOC_CTX *mem_ctx,
- const DOM_SID *domain_sid,
- int num_rids, uint32 *rids,
- const char **domain_name,
- const char ***names, enum lsa_SidType **types);
+bool winbind_get_groups(TALLOC_CTX *mem_ctx,
+ const char *account,
+ uint32_t *num_groups,
+ gid_t ** _groups);
+bool winbind_get_sid_aliases(TALLOC_CTX *mem_ctx,
+ const DOM_SID *dom_sid,
+ const DOM_SID *members,
+ size_t num_members,
+ uint32_t **pp_alias_rids,
+ size_t *p_num_alias_rids);
+
/* The following definitions come from lib/wins_srv.c */
@@ -4423,7 +4420,6 @@ bool sid_check_is_in_our_domain(const DOM_SID *sid);
/* The following definitions come from passdb/passdb.c */
-const char *my_sam_name(void);
struct samu *samu_new( TALLOC_CTX *ctx );
NTSTATUS samu_set_unix(struct samu *user, const struct passwd *pwd);
NTSTATUS samu_alloc_rid_unix(struct samu *user, const struct passwd *pwd);
diff --git a/source3/include/rpc_spoolss.h b/source3/include/rpc_spoolss.h
index ac306e69e3..472ce45758 100644
--- a/source3/include/rpc_spoolss.h
+++ b/source3/include/rpc_spoolss.h
@@ -122,12 +122,6 @@
#define SPL_XCV_MONITOR_TCPMON ",XcvMonitor Standard TCP/IP Port"
-#define PRINTER_CONTROL_UNPAUSE 0x00000000
-#define PRINTER_CONTROL_PAUSE 0x00000001
-#define PRINTER_CONTROL_RESUME 0x00000002
-#define PRINTER_CONTROL_PURGE 0x00000003
-#define PRINTER_CONTROL_SET_STATUS 0x00000004
-
#define PRINTER_STATUS_OK 0x00000000
#define JOB_ACCESS_READ 0x00000020
@@ -217,8 +211,6 @@
#define PRINTER_NOTIFY_OPTIONS_REFRESH 0x01
-#define PRINTER_NOTIFY_INFO_DISCARDED 0x1
-
/*
* Set of macros for flagging what changed in the PRINTER_INFO_2 struct
* when sending messages to other smbd's
@@ -270,13 +262,6 @@ PRINTER_MESSAGE_INFO;
#define DRIVER_ANY_VERSION 0xffffffff
#define DRIVER_MAX_VERSION 4
-/* FLAGS for SPOOLSS_ADDPRINTERDRIVEREX */
-
-#define APD_STRICT_UPGRADE 0x00000001
-#define APD_STRICT_DOWNGRADE 0x00000002
-#define APD_COPY_ALL_FILES 0x00000004
-#define APD_COPY_NEW_FILES 0x00000008
-
/* this struct is undocumented */
/* thanks to the ddk ... */
diff --git a/source3/lib/time.c b/source3/lib/time.c
index e2cfe687b2..865456b23b 100644
--- a/source3/lib/time.c
+++ b/source3/lib/time.c
@@ -360,12 +360,12 @@ struct timespec get_create_timespec(const SMB_STRUCT_STAT *pst,bool fake_dirs)
return ret;
}
-#if defined(HAVE_STAT_ST_BIRTHTIMESPEC)
+#if defined(HAVE_STRUCT_STAT_ST_BIRTHTIMESPEC_TV_NSEC)
ret = pst->st_birthtimespec;
-#elif defined(HAVE_STAT_ST_BIRTHTIMENSEC)
+#elif defined(HAVE_STRUCT_STAT_ST_BIRTHTIMENSEC)
ret.tv_sec = pst->st_birthtime;
ret.tv_nsec = pst->st_birthtimenspec;
-#elif defined(HAVE_STAT_ST_BIRTHTIME)
+#elif defined(HAVE_STRUCT_STAT_ST_BIRTHTIME)
ret.tv_sec = pst->st_birthtime;
ret.tv_nsec = 0;
#else
@@ -397,24 +397,24 @@ struct timespec get_atimespec(const SMB_STRUCT_STAT *pst)
ret.tv_nsec = 0;
return ret;
#else
-#if defined(HAVE_STAT_ST_ATIM)
+#if defined(HAVE_STRUCT_STAT_ST_MTIM_TV_NSEC)
return pst->st_atim;
-#elif defined(HAVE_STAT_ST_ATIMENSEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMENSEC)
struct timespec ret;
ret.tv_sec = pst->st_atime;
ret.tv_nsec = pst->st_atimensec;
return ret;
-#elif defined(HAVE_STAT_ST_ATIME_N)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIME_N)
struct timespec ret;
ret.tv_sec = pst->st_atime;
ret.tv_nsec = pst->st_atime_n;
return ret;
-#elif defined(HAVE_STAT_ST_UATIME)
+#elif defined(HAVE_STRUCT_STAT_ST_UMTIME)
struct timespec ret;
ret.tv_sec = pst->st_atime;
ret.tv_nsec = pst->st_uatime * 1000;
return ret;
-#elif defined(HAVE_STAT_ST_ATIMESPEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMESPEC_TV_NSEC)
return pst->st_atimespec;
#else
#error CONFIGURE_ERROR_IN_DETECTING_TIMESPEC_IN_STAT
@@ -428,18 +428,18 @@ void set_atimespec(SMB_STRUCT_STAT *pst, struct timespec ts)
/* Old system - no ns timestamp. */
pst->st_atime = ts.tv_sec;
#else
-#if defined(HAVE_STAT_ST_ATIM)
+#if defined(HAVE_STRUCT_STAT_ST_MTIM_TV_NSEC)
pst->st_atim = ts;
-#elif defined(HAVE_STAT_ST_ATIMENSEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMENSEC)
pst->st_atime = ts.tv_sec;
pst->st_atimensec = ts.tv_nsec;
-#elif defined(HAVE_STAT_ST_ATIME_N)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIME_N)
pst->st_atime = ts.tv_sec;
pst->st_atime_n = ts.tv_nsec;
-#elif defined(HAVE_STAT_ST_UATIME)
+#elif defined(HAVE_STRUCT_STAT_ST_UMTIME)
pst->st_atime = ts.tv_sec;
pst->st_uatime = ts.tv_nsec / 1000;
-#elif defined(HAVE_STAT_ST_ATIMESPEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMESPEC_TV_NSEC)
pst->st_atimespec = ts;
#else
#error CONFIGURE_ERROR_IN_DETECTING_TIMESPEC_IN_STAT
@@ -457,24 +457,24 @@ struct timespec get_mtimespec(const SMB_STRUCT_STAT *pst)
ret.tv_nsec = 0;
return ret;
#else
-#if defined(HAVE_STAT_ST_MTIM)
+#if defined(HAVE_STRUCT_STAT_ST_MTIM_TV_NSEC)
return pst->st_mtim;
-#elif defined(HAVE_STAT_ST_MTIMENSEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMENSEC)
struct timespec ret;
ret.tv_sec = pst->st_mtime;
ret.tv_nsec = pst->st_mtimensec;
return ret;
-#elif defined(HAVE_STAT_ST_MTIME_N)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIME_N)
struct timespec ret;
ret.tv_sec = pst->st_mtime;
ret.tv_nsec = pst->st_mtime_n;
return ret;
-#elif defined(HAVE_STAT_ST_UMTIME)
+#elif defined(HAVE_STRUCT_STAT_ST_UMTIME)
struct timespec ret;
ret.tv_sec = pst->st_mtime;
ret.tv_nsec = pst->st_umtime * 1000;
return ret;
-#elif defined(HAVE_STAT_ST_MTIMESPEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMESPEC_TV_NSEC)
return pst->st_mtimespec;
#else
#error CONFIGURE_ERROR_IN_DETECTING_TIMESPEC_IN_STAT
@@ -488,18 +488,18 @@ void set_mtimespec(SMB_STRUCT_STAT *pst, struct timespec ts)
/* Old system - no ns timestamp. */
pst->st_mtime = ts.tv_sec;
#else
-#if defined(HAVE_STAT_ST_MTIM)
+#if defined(HAVE_STRUCT_STAT_ST_MTIM_TV_NSEC)
pst->st_mtim = ts;
-#elif defined(HAVE_STAT_ST_MTIMENSEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMENSEC)
pst->st_mtime = ts.tv_sec;
pst->st_mtimensec = ts.tv_nsec;
-#elif defined(HAVE_STAT_ST_MTIME_N)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIME_N)
pst->st_mtime = ts.tv_sec;
pst->st_mtime_n = ts.tv_nsec;
-#elif defined(HAVE_STAT_ST_UMTIME)
+#elif defined(HAVE_STRUCT_STAT_ST_UMTIME)
pst->st_mtime = ts.tv_sec;
pst->st_umtime = ts.tv_nsec / 1000;
-#elif defined(HAVE_STAT_ST_MTIMESPEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMESPEC_TV_NSEC)
pst->st_mtimespec = ts;
#else
#error CONFIGURE_ERROR_IN_DETECTING_TIMESPEC_IN_STAT
@@ -517,24 +517,24 @@ struct timespec get_ctimespec(const SMB_STRUCT_STAT *pst)
ret.tv_nsec = 0;
return ret;
#else
-#if defined(HAVE_STAT_ST_CTIM)
+#if defined(HAVE_STRUCT_STAT_ST_MTIM_TV_NSEC)
return pst->st_ctim;
-#elif defined(HAVE_STAT_ST_CTIMENSEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMENSEC)
struct timespec ret;
ret.tv_sec = pst->st_ctime;
ret.tv_nsec = pst->st_ctimensec;
return ret;
-#elif defined(HAVE_STAT_ST_CTIME_N)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIME_N)
struct timespec ret;
ret.tv_sec = pst->st_ctime;
ret.tv_nsec = pst->st_ctime_n;
return ret;
-#elif defined(HAVE_STAT_ST_UCTIME)
+#elif defined(HAVE_STRUCT_STAT_ST_UMTIME)
struct timespec ret;
ret.tv_sec = pst->st_ctime;
ret.tv_nsec = pst->st_uctime * 1000;
return ret;
-#elif defined(HAVE_STAT_ST_CTIMESPEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMESPEC_TV_NSEC)
return pst->st_ctimespec;
#else
#error CONFIGURE_ERROR_IN_DETECTING_TIMESPEC_IN_STAT
@@ -548,18 +548,18 @@ void set_ctimespec(SMB_STRUCT_STAT *pst, struct timespec ts)
/* Old system - no ns timestamp. */
pst->st_ctime = ts.tv_sec;
#else
-#if defined(HAVE_STAT_ST_CTIM)
+#if defined(HAVE_STRUCT_STAT_ST_MTIM_TV_NSEC)
pst->st_ctim = ts;
-#elif defined(HAVE_STAT_ST_CTIMENSEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMENSEC)
pst->st_ctime = ts.tv_sec;
pst->st_ctimensec = ts.tv_nsec;
-#elif defined(HAVE_STAT_ST_CTIME_N)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIME_N)
pst->st_ctime = ts.tv_sec;
pst->st_ctime_n = ts.tv_nsec;
-#elif defined(HAVE_STAT_ST_UCTIME)
+#elif defined(HAVE_STRUCT_STAT_ST_UMTIME)
pst->st_ctime = ts.tv_sec;
pst->st_uctime = ts.tv_nsec / 1000;
-#elif defined(HAVE_STAT_ST_CTIMESPEC)
+#elif defined(HAVE_STRUCT_STAT_ST_MTIMESPEC_TV_NSEC)
pst->st_ctimespec = ts;
#else
#error CONFIGURE_ERROR_IN_DETECTING_TIMESPEC_IN_STAT
diff --git a/source3/lib/winbind_util.c b/source3/lib/winbind_util.c
index 14356b09cf..f64a4d3b45 100644
--- a/source3/lib/winbind_util.c
+++ b/source3/lib/winbind_util.c
@@ -24,6 +24,43 @@
#include "nsswitch/libwbclient/wbclient.h"
+struct passwd * winbind_getpwnam(const char * name)
+{
+ wbcErr result;
+ struct passwd * tmp_pwd = NULL;
+ struct passwd * pwd = NULL;
+
+ result = wbcGetpwnam(name, &tmp_pwd);
+ if (result != WBC_ERR_SUCCESS)
+ return pwd;
+
+ pwd = tcopy_passwd(talloc_tos(), tmp_pwd);
+
+ wbcFreeMemory(tmp_pwd);
+
+ return pwd;
+}
+
+struct passwd * winbind_getpwsid(const DOM_SID *sid)
+{
+ wbcErr result;
+ struct passwd * tmp_pwd = NULL;
+ struct passwd * pwd = NULL;
+ struct wbcDomainSid dom_sid;
+
+ memcpy(&dom_sid, sid, sizeof(dom_sid));
+
+ result = wbcGetpwsid(&dom_sid, &tmp_pwd);
+ if (result != WBC_ERR_SUCCESS)
+ return pwd;
+
+ pwd = tcopy_passwd(talloc_tos(), tmp_pwd);
+
+ wbcFreeMemory(tmp_pwd);
+
+ return pwd;
+}
+
/* Call winbindd to convert a name to a sid */
bool winbind_lookup_name(const char *dom_name, const char *name, DOM_SID *sid,
@@ -234,8 +271,87 @@ bool winbind_allocate_gid(gid_t *gid)
return (ret == WBC_ERR_SUCCESS);
}
+bool winbind_get_groups(TALLOC_CTX * mem_ctx, const char *account, uint32_t *num_groups, gid_t **_groups)
+{
+ wbcErr ret;
+ uint32_t ngroups;
+ gid_t *group_list = NULL;
+
+ ret = wbcGetGroups(account, &ngroups, &group_list);
+ if (ret != WBC_ERR_SUCCESS)
+ return false;
+
+ *_groups = TALLOC_ARRAY(mem_ctx, gid_t, ngroups);
+ if (*_groups == NULL) {
+ wbcFreeMemory(group_list);
+ return false;
+ }
+
+ memcpy(*_groups, group_list, ngroups* sizeof(gid_t));
+ *num_groups = ngroups;
+
+ wbcFreeMemory(group_list);
+ return true;
+}
+
+bool winbind_get_sid_aliases(TALLOC_CTX *mem_ctx,
+ const DOM_SID *dom_sid,
+ const DOM_SID *members,
+ size_t num_members,
+ uint32_t **pp_alias_rids,
+ size_t *p_num_alias_rids)
+{
+ wbcErr ret;
+ struct wbcDomainSid domain_sid;
+ struct wbcDomainSid *sid_list = NULL;
+ size_t i;
+ uint32_t * rids;
+ size_t num_rids;
+
+ memcpy(&domain_sid, dom_sid, sizeof(*dom_sid));
+
+ sid_list = TALLOC_ARRAY(mem_ctx, struct wbcDomainSid, num_members);
+
+ for (i=0; i < num_members; i++) {
+ memcpy(&sid_list[i], &members[i], sizeof(sid_list[i]));
+ }
+
+ ret = wbcGetSidAliases(&domain_sid,
+ sid_list,
+ num_members,
+ &rids,
+ &num_rids);
+ if (ret != WBC_ERR_SUCCESS) {
+ wbcFreeMemory(rids);
+ return false;
+ }
+
+ *pp_alias_rids = TALLOC_ARRAY(mem_ctx, uint32_t, num_rids);
+ if (*pp_alias_rids == NULL) {
+ wbcFreeMemory(rids);
+ return false;
+ }
+
+ memcpy(*pp_alias_rids, rids, sizeof(uint32_t) * num_rids);
+
+ *p_num_alias_rids = num_rids;
+ wbcFreeMemory(rids);
+
+ return true;
+}
+
#else /* WITH_WINBIND */
+struct passwd * winbind_getpwnam(const char * name)
+{
+ return NULL;
+}
+
+struct passwd * winbind_getpwsid(const DOM_SID *sid)
+{
+ return NULL;
+}
+
bool winbind_lookup_name(const char *dom_name, const char *name, DOM_SID *sid,
enum lsa_SidType *name_type)
{
@@ -318,4 +434,19 @@ bool winbind_allocate_gid(gid_t *gid)
return false;
}
+bool winbind_get_groups(TALLOC_CTX *mem_ctx, const char *account, uint32_t *num_groups, gid_t **_groups)
+{
+ return false;
+}
+
+bool winbind_get_sid_aliases(TALLOC_CTX *mem_ctx,
+ const DOM_SID *dom_sid,
+ const DOM_SID *members,
+ size_t num_members,
+ uint32_t **pp_alias_rids,
+ size_t *p_num_alias_rids)
+{
+ return false;
+}
+
#endif /* WITH_WINBIND */
diff --git a/source3/modules/onefs_acl.c b/source3/modules/onefs_acl.c
index 0ef7e0be51..02394794c2 100644
--- a/source3/modules/onefs_acl.c
+++ b/source3/modules/onefs_acl.c
@@ -619,6 +619,12 @@ onefs_fget_nt_acl(vfs_handle_struct *handle, files_struct *fsp,
DEBUG(5, ("Getting sd for file %s. security_info=%u\n",
fsp->fsp_name, security_info));
+ if (lp_parm_bool(SNUM(fsp->conn), PARM_ONEFS_TYPE,
+ PARM_IGNORE_SACL, PARM_IGNORE_SACL_DEFAULT)) {
+ DEBUG(5, ("Ignoring SACL on %s.\n", fsp->fsp_name));
+ security_info &= ~SACL_SECURITY_INFORMATION;
+ }
+
if (fsp->fh->fd == -1) {
if ((fsp->fh->fd = onefs_sys_create_file(handle->conn,
-1,
diff --git a/source3/modules/onefs_open.c b/source3/modules/onefs_open.c
index b2b11ebaac..e335dc7e28 100644
--- a/source3/modules/onefs_open.c
+++ b/source3/modules/onefs_open.c
@@ -744,6 +744,11 @@ NTSTATUS onefs_open_file_ntcreate(connection_struct *conn,
open_access_mask |= FILE_WRITE_DATA;
}
+ if (lp_parm_bool(SNUM(fsp->conn), PARM_ONEFS_TYPE,
+ PARM_IGNORE_SACL, PARM_IGNORE_SACL_DEFAULT)) {
+ access_mask &= ~SYSTEM_SECURITY_ACCESS;
+ }
+
DEBUG(10, ("onefs_open_file_ntcreate: fname=%s, after mapping "
"open_access_mask=%#x, access_mask=0x%x\n",
fname, open_access_mask, access_mask));
diff --git a/source3/passdb/passdb.c b/source3/passdb/passdb.c
index d26a667f44..c526a175f2 100644
--- a/source3/passdb/passdb.c
+++ b/source3/passdb/passdb.c
@@ -27,25 +27,6 @@
#undef DBGC_CLASS
#define DBGC_CLASS DBGC_PASSDB
-/******************************************************************
- get the default domain/netbios name to be used when
- testing authentication. For example, if you connect
- to a Windows member server using a bogus domain name, the
- Windows box will map the BOGUS\user to DOMAIN\user. A
- standalone box will map to WKS\user.
-******************************************************************/
-
-const char *my_sam_name(void)
-{
- /* standalone servers can only use the local netbios name */
- if ( lp_server_role() == ROLE_STANDALONE )
- return global_myname();
-
- /* Windows domain members default to the DOMAIN
- name when not specified */
- return lp_workgroup();
-}
-
/**********************************************************************
***********************************************************************/
diff --git a/source3/rpc_server/srv_spoolss_nt.c b/source3/rpc_server/srv_spoolss_nt.c
index 36984fc209..5c4ff61b17 100644
--- a/source3/rpc_server/srv_spoolss_nt.c
+++ b/source3/rpc_server/srv_spoolss_nt.c
@@ -5925,18 +5925,18 @@ static WERROR control_printer(POLICY_HND *handle, uint32 command,
return WERR_BADFID;
switch (command) {
- case PRINTER_CONTROL_PAUSE:
+ case SPOOLSS_PRINTER_CONTROL_PAUSE:
if (print_queue_pause(p->server_info, snum, &errcode)) {
errcode = WERR_OK;
}
break;
- case PRINTER_CONTROL_RESUME:
- case PRINTER_CONTROL_UNPAUSE:
+ case SPOOLSS_PRINTER_CONTROL_RESUME:
+ case SPOOLSS_PRINTER_CONTROL_UNPAUSE:
if (print_queue_resume(p->server_info, snum, &errcode)) {
errcode = WERR_OK;
}
break;
- case PRINTER_CONTROL_PURGE:
+ case SPOOLSS_PRINTER_CONTROL_PURGE:
if (print_queue_purge(p->server_info, snum, &errcode)) {
errcode = WERR_OK;
}
@@ -7381,6 +7381,8 @@ WERROR _spoolss_GetForm(pipes_struct *p,
return WERR_BADFID;
}
+ ZERO_STRUCT(form_1);
+
switch (level) {
case 1:
if (foundBuiltin) {
@@ -10473,22 +10475,22 @@ WERROR _spoolss_RemoteFindFirstPrinterChangeNotifyEx(pipes_struct *p,
}
/****************************************************************
- _spoolss_RouterRefreshPrinterChangeNotification
+ _spoolss_RouterReplyPrinterEx
****************************************************************/
-WERROR _spoolss_RouterRefreshPrinterChangeNotification(pipes_struct *p,
- struct spoolss_RouterRefreshPrinterChangeNotification *r)
+WERROR _spoolss_RouterReplyPrinterEx(pipes_struct *p,
+ struct spoolss_RouterReplyPrinterEx *r)
{
p->rng_fault_state = true;
return WERR_NOT_SUPPORTED;
}
/****************************************************************
- _spoolss_RemoteFindNextPrinterChangeNotifyEx
+ _dcesrv_spoolss_RouterRefreshPrinterChangeNotify
****************************************************************/
-WERROR _spoolss_RemoteFindNextPrinterChangeNotifyEx(pipes_struct *p,
- struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r)
+WERROR _spoolss_RouterRefreshPrinterChangeNotify(pipes_struct *p,
+ struct spoolss_RouterRefreshPrinterChangeNotify *r)
{
p->rng_fault_state = true;
return WERR_NOT_SUPPORTED;
diff --git a/source3/winbindd/winbindd.c b/source3/winbindd/winbindd.c
index 5720bfc517..be91611bfb 100644
--- a/source3/winbindd/winbindd.c
+++ b/source3/winbindd/winbindd.c
@@ -420,6 +420,7 @@ static struct winbindd_dispatch_table {
{ WINBINDD_GETPWNAM, winbindd_getpwnam, "GETPWNAM" },
{ WINBINDD_GETPWUID, winbindd_getpwuid, "GETPWUID" },
+ { WINBINDD_GETPWSID, winbindd_getpwsid, "GETPWSID" },
{ WINBINDD_SETPWENT, winbindd_setpwent, "SETPWENT" },
{ WINBINDD_ENDPWENT, winbindd_endpwent, "ENDPWENT" },
@@ -429,6 +430,8 @@ static struct winbindd_dispatch_table {
{ WINBINDD_GETUSERSIDS, winbindd_getusersids, "GETUSERSIDS" },
{ WINBINDD_GETUSERDOMGROUPS, winbindd_getuserdomgroups,
"GETUSERDOMGROUPS" },
+ { WINBINDD_GETSIDALIASES, winbindd_getsidaliases,
+ "LOOKUPUSERALIASES" },
/* Group functions */
diff --git a/source3/winbindd/winbindd_async.c b/source3/winbindd/winbindd_async.c
index 7b93f963b4..0271abbd2b 100644
--- a/source3/winbindd/winbindd_async.c
+++ b/source3/winbindd/winbindd_async.c
@@ -632,8 +632,8 @@ bool print_sidlist(TALLOC_CTX *mem_ctx, const DOM_SID *sids,
return True;
}
-static bool parse_sidlist(TALLOC_CTX *mem_ctx, char *sidstr,
- DOM_SID **sids, size_t *num_sids)
+bool parse_sidlist(TALLOC_CTX *mem_ctx, char *sidstr,
+ DOM_SID **sids, size_t *num_sids)
{
char *p, *q;
@@ -822,92 +822,6 @@ void winbindd_getsidaliases_async(struct winbindd_domain *domain,
(void *)cont, private_data);
}
-enum winbindd_result winbindd_dual_getsidaliases(struct winbindd_domain *domain,
- struct winbindd_cli_state *state)
-{
- DOM_SID *sids = NULL;
- size_t num_sids = 0;
- char *sidstr = NULL;
- ssize_t len;
- size_t i;
- uint32 num_aliases;
- uint32 *alias_rids;
- NTSTATUS result;
-
- DEBUG(3, ("[%5lu]: getsidaliases\n", (unsigned long)state->pid));
-
- sidstr = state->request.extra_data.data;
- if (sidstr == NULL) {
- sidstr = talloc_strdup(state->mem_ctx, "\n"); /* No SID */
- if (!sidstr) {
- DEBUG(0, ("Out of memory\n"));
- return WINBINDD_ERROR;
- }
- }
-
- DEBUG(10, ("Sidlist: %s\n", sidstr));
-
- if (!parse_sidlist(state->mem_ctx, sidstr, &sids, &num_sids)) {
- DEBUG(0, ("Could not parse SID list: %s\n", sidstr));
- return WINBINDD_ERROR;
- }
-
- num_aliases = 0;
- alias_rids = NULL;
-
- result = domain->methods->lookup_useraliases(domain,
- state->mem_ctx,
- num_sids, sids,
- &num_aliases,
- &alias_rids);
-
- if (!NT_STATUS_IS_OK(result)) {
- DEBUG(3, ("Could not lookup_useraliases: %s\n",
- nt_errstr(result)));
- return WINBINDD_ERROR;
- }
-
- num_sids = 0;
- sids = NULL;
- sidstr = NULL;
-
- DEBUG(10, ("Got %d aliases\n", num_aliases));
-
- for (i=0; i<num_aliases; i++) {
- DOM_SID sid;
- DEBUGADD(10, (" rid %d\n", alias_rids[i]));
- sid_copy(&sid, &domain->sid);
- sid_append_rid(&sid, alias_rids[i]);
- result = add_sid_to_array(state->mem_ctx, &sid, &sids,
- &num_sids);
- if (!NT_STATUS_IS_OK(result)) {
- return WINBINDD_ERROR;
- }
- }
-
-
- if (!print_sidlist(state->mem_ctx, sids, num_sids, &sidstr, &len)) {
- DEBUG(0, ("Could not print_sidlist\n"));
- state->response.extra_data.data = NULL;
- return WINBINDD_ERROR;
- }
-
- state->response.extra_data.data = NULL;
-
- if (sidstr) {
- state->response.extra_data.data = SMB_STRDUP(sidstr);
- if (!state->response.extra_data.data) {
- DEBUG(0, ("Out of memory\n"));
- return WINBINDD_ERROR;
- }
- DEBUG(10, ("aliases_list: %s\n",
- (char *)state->response.extra_data.data));
- state->response.length += len+1;
- }
-
- return WINBINDD_OK;
-}
-
struct gettoken_state {
TALLOC_CTX *mem_ctx;
DOM_SID user_sid;
diff --git a/source3/winbindd/winbindd_domain.c b/source3/winbindd/winbindd_domain.c
index 2e8c6175ca..1fc3ce7304 100644
--- a/source3/winbindd/winbindd_domain.c
+++ b/source3/winbindd/winbindd_domain.c
@@ -110,6 +110,10 @@ static const struct winbindd_child_dispatch_table domain_dispatch_table[] = {
.struct_cmd = WINBINDD_DUAL_GETSIDALIASES,
.struct_fn = winbindd_dual_getsidaliases,
},{
+ .name = "GETSIDALIASES",
+ .struct_cmd = WINBINDD_GETSIDALIASES,
+ .struct_fn = winbindd_dual_getsidaliases,
+ },{
.name = "CCACHE_NTLM_AUTH",
.struct_cmd = WINBINDD_CCACHE_NTLMAUTH,
.struct_fn = winbindd_dual_ccache_ntlm_auth,
diff --git a/source3/winbindd/winbindd_group.c b/source3/winbindd/winbindd_group.c
index 9d9b264124..043f26e578 100644
--- a/source3/winbindd/winbindd_group.c
+++ b/source3/winbindd/winbindd_group.c
@@ -1867,3 +1867,118 @@ enum winbindd_result winbindd_dual_getuserdomgroups(struct winbindd_domain *doma
return WINBINDD_OK;
}
+
+void winbindd_getsidaliases(struct winbindd_cli_state *state)
+{
+ DOM_SID domain_sid;
+ struct winbindd_domain *domain;
+
+ /* Ensure null termination */
+ state->request.data.sid[sizeof(state->request.data.sid)-1]='\0';
+
+ if (!string_to_sid(&domain_sid, state->request.data.sid)) {
+ DEBUG(1, ("Could not get convert sid %s from string\n",
+ state->request.data.sid));
+ request_error(state);
+ return;
+ }
+
+ /* Get info for the domain */
+ if ((domain = find_domain_from_sid_noinit(&domain_sid)) == NULL) {
+ DEBUG(0,("could not find domain entry for sid %s\n",
+ sid_string_dbg(&domain_sid)));
+ request_error(state);
+ return;
+ }
+
+ sendto_domain(state, domain);
+}
+
+enum winbindd_result winbindd_dual_getsidaliases(struct winbindd_domain *domain,
+ struct winbindd_cli_state *state)
+{
+ DOM_SID *sids = NULL;
+ size_t num_sids = 0;
+ char *sidstr = NULL;
+ ssize_t len;
+ size_t i;
+ uint32 num_aliases;
+ uint32 *alias_rids;
+ NTSTATUS result;
+
+ DEBUG(3, ("[%5lu]: getsidaliases\n", (unsigned long)state->pid));
+
+ sidstr = state->request.extra_data.data;
+ if (sidstr == NULL) {
+ sidstr = talloc_strdup(state->mem_ctx, "\n"); /* No SID */
+ if (!sidstr) {
+ DEBUG(0, ("Out of memory\n"));
+ return WINBINDD_ERROR;
+ }
+ }
+
+ DEBUG(10, ("Sidlist: %s\n", sidstr));
+
+ if (!parse_sidlist(state->mem_ctx, sidstr, &sids, &num_sids)) {
+ DEBUG(0, ("Could not parse SID list: %s\n", sidstr));
+ return WINBINDD_ERROR;
+ }
+
+ num_aliases = 0;
+ alias_rids = NULL;
+
+ result = domain->methods->lookup_useraliases(domain,
+ state->mem_ctx,
+ num_sids, sids,
+ &num_aliases,
+ &alias_rids);
+
+ if (!NT_STATUS_IS_OK(result)) {
+ DEBUG(3, ("Could not lookup_useraliases: %s\n",
+ nt_errstr(result)));
+ return WINBINDD_ERROR;
+ }
+
+ num_sids = 0;
+ sids = NULL;
+ sidstr = NULL;
+
+ DEBUG(10, ("Got %d aliases\n", num_aliases));
+
+ for (i=0; i<num_aliases; i++) {
+ DOM_SID sid;
+ DEBUGADD(10, (" rid %d\n", alias_rids[i]));
+ sid_copy(&sid, &domain->sid);
+ sid_append_rid(&sid, alias_rids[i]);
+ result = add_sid_to_array(state->mem_ctx, &sid, &sids,
+ &num_sids);
+ if (!NT_STATUS_IS_OK(result)) {
+ return WINBINDD_ERROR;
+ }
+ }
+
+
+ if (!print_sidlist(state->mem_ctx, sids, num_sids, &sidstr, &len)) {
+ DEBUG(0, ("Could not print_sidlist\n"));
+ state->response.extra_data.data = NULL;
+ return WINBINDD_ERROR;
+ }
+
+ state->response.extra_data.data = NULL;
+
+ if (sidstr) {
+ state->response.extra_data.data = SMB_STRDUP(sidstr);
+ if (!state->response.extra_data.data) {
+ DEBUG(0, ("Out of memory\n"));
+ return WINBINDD_ERROR;
+ }
+ DEBUG(10, ("aliases_list: %s\n",
+ (char *)state->response.extra_data.data));
+ state->response.length += len+1;
+ state->response.data.num_entries = num_sids;
+ }
+
+ return WINBINDD_OK;
+}
+
+
diff --git a/source3/winbindd/winbindd_proto.h b/source3/winbindd/winbindd_proto.h
index c302dd1d62..5120402e3d 100644
--- a/source3/winbindd/winbindd_proto.h
+++ b/source3/winbindd/winbindd_proto.h
@@ -112,6 +112,8 @@ enum winbindd_result winbindd_dual_list_groups(struct winbindd_domain *domain,
struct winbindd_cli_state *state);
bool print_sidlist(TALLOC_CTX *mem_ctx, const DOM_SID *sids,
size_t num_sids, char **result, ssize_t *len);
+bool parse_sidlist(TALLOC_CTX *mem_ctx, char *sidstr,
+ DOM_SID **sids, size_t *num_sids);
enum winbindd_result winbindd_dual_lookuprids(struct winbindd_domain *domain,
struct winbindd_cli_state *state);
void winbindd_getsidaliases_async(struct winbindd_domain *domain,
@@ -342,6 +344,7 @@ void winbindd_list_groups(struct winbindd_cli_state *state);
void winbindd_getgroups(struct winbindd_cli_state *state);
void winbindd_getusersids(struct winbindd_cli_state *state);
void winbindd_getuserdomgroups(struct winbindd_cli_state *state);
+void winbindd_getsidaliases(struct winbindd_cli_state *state);
enum winbindd_result winbindd_dual_getuserdomgroups(struct winbindd_domain *domain,
struct winbindd_cli_state *state);
bool get_sam_group_entries(struct getent_state *ent);
@@ -495,6 +498,7 @@ enum winbindd_result winbindd_dual_userinfo(struct winbindd_domain *domain,
struct winbindd_cli_state *state);
void winbindd_getpwnam(struct winbindd_cli_state *state);
void winbindd_getpwuid(struct winbindd_cli_state *state);
+void winbindd_getpwsid(struct winbindd_cli_state *state);
void winbindd_setpwent(struct winbindd_cli_state *state);
void winbindd_endpwent(struct winbindd_cli_state *state);
void winbindd_getpwent(struct winbindd_cli_state *state);
diff --git a/source3/winbindd/winbindd_user.c b/source3/winbindd/winbindd_user.c
index a6740b1fb8..50aea4e0cb 100644
--- a/source3/winbindd/winbindd_user.c
+++ b/source3/winbindd/winbindd_user.c
@@ -217,8 +217,8 @@ static void getpwsid_queryuser_recv(void *private_data, bool success,
static void getpwsid_sid2uid_recv(void *private_data, bool success, uid_t uid);
static void getpwsid_sid2gid_recv(void *private_data, bool success, gid_t gid);
-static void winbindd_getpwsid(struct winbindd_cli_state *state,
- const DOM_SID *sid)
+static void getpwsid_queryuser(struct winbindd_cli_state *state,
+ const DOM_SID *sid)
{
struct getpwsid_state *s;
@@ -509,7 +509,7 @@ static void getpwnam_name2sid_recv(void *private_data, bool success,
check_domain_trusted(domname, sid);
}
- winbindd_getpwsid(state, sid);
+ getpwsid_queryuser(state, sid);
}
static void getpwuid_recv(void *private_data, bool success, const char *sid)
@@ -535,7 +535,7 @@ static void getpwuid_recv(void *private_data, bool success, const char *sid)
return;
}
- winbindd_getpwsid(state, &user_sid);
+ getpwsid_queryuser(state, &user_sid);
}
/* Return a password structure given a uid number */
@@ -553,6 +553,26 @@ void winbindd_getpwuid(struct winbindd_cli_state *state)
winbindd_uid2sid_async(state->mem_ctx, uid, getpwuid_recv, state);
}
+/* Return a password structure given a sid */
+void winbindd_getpwsid(struct winbindd_cli_state *state)
+{
+ DOM_SID sid;
+
+ /* Ensure null termination */
+ state->request.data.sid[sizeof(state->request.data.sid)-1]='\0';
+
+ DEBUG(3, ("[%5lu]: getpwsid %s\n", (unsigned long)state->pid,
+ state->request.data.sid));
+
+ if (!string_to_sid(&sid, state->request.data.sid)) {
+ DEBUG(5, ("%s not a SID\n", state->request.data.sid));
+ request_error(state);
+ return;
+ }
+
+ getpwsid_queryuser(state, &sid);
+}
+
/*
* set/get/endpwent functions
*/
diff --git a/source4/rpc_server/spoolss/dcesrv_spoolss.c b/source4/rpc_server/spoolss/dcesrv_spoolss.c
index d127837382..c0330c0ae8 100644
--- a/source4/rpc_server/spoolss/dcesrv_spoolss.c
+++ b/source4/rpc_server/spoolss/dcesrv_spoolss.c
@@ -1197,20 +1197,20 @@ static WERROR dcesrv_spoolss_RemoteFindFirstPrinterChangeNotifyEx(struct dcesrv_
/*
- spoolss_RouterRefreshPrinterChangeNotification
+ spoolss_RouterReplyPrinterEx
*/
-static WERROR dcesrv_spoolss_RouterRefreshPrinterChangeNotification(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
- struct spoolss_RouterRefreshPrinterChangeNotification *r)
+static WERROR dcesrv_spoolss_RouterReplyPrinterEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
+ struct spoolss_RouterReplyPrinterEx *r)
{
DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
}
/*
- spoolss_RemoteFindNextPrinterChangeNotifyEx
+ spoolss_RouterRefreshPrinterChangeNotify
*/
-static WERROR dcesrv_spoolss_RemoteFindNextPrinterChangeNotifyEx(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
- struct spoolss_RemoteFindNextPrinterChangeNotifyEx *r)
+static WERROR dcesrv_spoolss_RouterRefreshPrinterChangeNotify(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
+ struct spoolss_RouterRefreshPrinterChangeNotify *r)
{
DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
}
diff --git a/source4/torture/basic/locking.c b/source4/torture/basic/locking.c
index fcac52ca6a..06a960bc81 100644
--- a/source4/torture/basic/locking.c
+++ b/source4/torture/basic/locking.c
@@ -610,7 +610,7 @@ ret = NT_STATUS_IS_OK(smbcli_unlock(cli1->tree, fnum1, 0, 4)) &&
NT_STATUS_IS_OK(smbcli_unlock(cli1->tree, fnum1, 0, 4));
EXPECTED(ret, true);
- torture_comment(tctx, "the same process %s unlock the stack of 4 locks\n", ret?"can":"cannot");
+ torture_comment(tctx, "the same process %s unlock the stack of 3 locks\n", ret?"can":"cannot");
/* Ensure the next unlock fails. */
ret = NT_STATUS_IS_OK(smbcli_unlock(cli1->tree, fnum1, 0, 4));
diff --git a/source4/torture/ndr/spoolss.c b/source4/torture/ndr/spoolss.c
index eecd91edba..c1ca0c20c9 100644
--- a/source4/torture/ndr/spoolss.c
+++ b/source4/torture/ndr/spoolss.c
@@ -109,14 +109,14 @@ static const uint8_t RFFPCNEX_out_data[] = {
0x00, 0x00, 0x00, 0x00
};
-static const uint8_t RFNPCNEX_in_data[] = {
+static const uint8_t RRPCN_in_data[] = {
0x00, 0x00, 0x00, 0x00, 0x1e, 0x9b, 0x8b, 0xe5, 0x32, 0x9a, 0xd5, 0x45,
0xa8, 0x0a, 0x10, 0x30, 0x5b, 0x87, 0x6f, 0x69, 0x01, 0x00, 0x00, 0x00,
0x44, 0x0d, 0x0b, 0x00, 0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
};
-static const uint8_t RFNPCNEX_out_data[] = {
+static const uint8_t RRPCN_out_data[] = {
0x00, 0x00, 0x02, 0x00, 0x1a, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
0x00, 0x00, 0x00, 0x00, 0x1a, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0x02, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00,
@@ -459,8 +459,8 @@ struct torture_suite *ndr_spoolss_suite(TALLOC_CTX *ctx)
torture_suite_add_ndr_pull_fn_test(suite, spoolss_RemoteFindFirstPrinterChangeNotifyEx, RFFPCNEX_in_data, NDR_IN, NULL );
torture_suite_add_ndr_pull_fn_test(suite, spoolss_RemoteFindFirstPrinterChangeNotifyEx, RFFPCNEX_out_data, NDR_OUT, NULL );
- torture_suite_add_ndr_pull_fn_test(suite, spoolss_RemoteFindNextPrinterChangeNotifyEx, RFNPCNEX_in_data, NDR_IN, NULL );
- torture_suite_add_ndr_pull_fn_test(suite, spoolss_RemoteFindNextPrinterChangeNotifyEx, RFNPCNEX_out_data, NDR_OUT, NULL );
+ torture_suite_add_ndr_pull_fn_test(suite, spoolss_RouterRefreshPrinterChangeNotify, RRPCN_in_data, NDR_IN, NULL );
+ torture_suite_add_ndr_pull_fn_test(suite, spoolss_RouterRefreshPrinterChangeNotify, RRPCN_out_data, NDR_OUT, NULL );
torture_suite_add_ndr_pull_fn_test(suite, spoolss_EnumForms, enumforms_in_data, NDR_IN, NULL );
torture_suite_add_ndr_pull_fn_test(suite, spoolss_EnumForms, enumforms_out_data, NDR_OUT, NULL );
diff --git a/source4/torture/raw/lock.c b/source4/torture/raw/lock.c
index 2d1eae3a69..72a03e1623 100644
--- a/source4/torture/raw/lock.c
+++ b/source4/torture/raw/lock.c
@@ -38,8 +38,34 @@
goto done; \
}} while (0)
+#define CHECK_STATUS_CONT(status, correct) do { \
+ if (!NT_STATUS_EQUAL(status, correct)) { \
+ printf("(%s) Incorrect status %s - should be %s\n", \
+ __location__, nt_errstr(status), nt_errstr(correct)); \
+ ret = false; \
+ }} while (0)
+
+#define CHECK_STATUS_OR(status, correct1, correct2) do { \
+ if ((!NT_STATUS_EQUAL(status, correct1)) && \
+ (!NT_STATUS_EQUAL(status, correct2))) { \
+ printf("(%s) Incorrect status %s - should be %s or %s\n", \
+ __location__, nt_errstr(status), nt_errstr(correct1), \
+ nt_errstr(correct2)); \
+ ret = false; \
+ goto done; \
+ }} while (0)
+
+#define CHECK_STATUS_OR_CONT(status, correct1, correct2) do { \
+ if ((!NT_STATUS_EQUAL(status, correct1)) && \
+ (!NT_STATUS_EQUAL(status, correct2))) { \
+ printf("(%s) Incorrect status %s - should be %s or %s\n", \
+ __location__, nt_errstr(status), nt_errstr(correct1), \
+ nt_errstr(correct2)); \
+ ret = false; \
+ }} while (0)
#define BASEDIR "\\testlock"
+#define TARGET_IS_WIN7(_tctx) (torture_setting_bool(_tctx, "win7", false))
/*
test SMBlock and SMBunlock ops
@@ -337,15 +363,25 @@ static bool test_lockx(struct torture_context *tctx, struct smbcli_state *cli)
lock[0].pid++;
lock[0].count = 2;
status = smb_raw_lock(cli->tree, &io);
- CHECK_STATUS(status, NT_STATUS_OK);
+ if (TARGET_IS_WIN7(tctx))
+ CHECK_STATUS(status, NT_STATUS_WIN7_INVALID_RANGE);
+ else
+ CHECK_STATUS(status, NT_STATUS_OK);
lock[0].pid--;
io.lockx.in.ulock_cnt = 1;
io.lockx.in.lock_cnt = 0;
lock[0].count = 1;
status = smb_raw_lock(cli->tree, &io);
- CHECK_STATUS(status, NT_STATUS_OK);
- status = smb_raw_lock(cli->tree, &io);
- CHECK_STATUS(status, NT_STATUS_RANGE_NOT_LOCKED);
+
+ /* XXX This is very strange - Win7 gives us an invalid range when we
+ * unlock the range even though the range is locked! Win7 bug? */
+ if (TARGET_IS_WIN7(tctx))
+ CHECK_STATUS(status, NT_STATUS_WIN7_INVALID_RANGE);
+ else {
+ CHECK_STATUS(status, NT_STATUS_OK);
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_RANGE_NOT_LOCKED);
+ }
done:
smbcli_close(cli->tree, fnum);
@@ -354,7 +390,6 @@ done:
return ret;
}
-
/*
test high pid
*/
@@ -410,8 +445,6 @@ static bool test_pidhigh(struct torture_context *tctx,
goto done;
}
- cli->session->pid |= 0x10000;
-
cli->session->pid = 2;
if (smbcli_read(cli->tree, fnum, &c, 0, 1) == 1) {
@@ -1321,6 +1354,525 @@ done:
return ret;
}
+struct double_lock_test {
+ struct smb_lock_entry lock1;
+ struct smb_lock_entry lock2;
+ NTSTATUS exp_status;
+};
+
+/**
+ * Tests zero byte locks.
+ */
+struct double_lock_test zero_byte_tests[] = {
+ /* {pid, offset, count}, {pid, offset, count}, status */
+
+ /** First, takes a zero byte lock at offset 10. Then:
+ * - Taking 0 byte lock at 10 should succeed.
+ * - Taking 1 byte locks at 9,10,11 should succeed.
+ * - Taking 2 byte lock at 9 should fail.
+ * - Taking 2 byte lock at 10 should succeed.
+ * - Taking 3 byte lock at 9 should fail.
+ */
+ {{1000, 10, 0}, {1001, 10, 0}, NT_STATUS_OK},
+ {{1000, 10, 0}, {1001, 9, 1}, NT_STATUS_OK},
+ {{1000, 10, 0}, {1001, 10, 1}, NT_STATUS_OK},
+ {{1000, 10, 0}, {1001, 11, 1}, NT_STATUS_OK},
+ {{1000, 10, 0}, {1001, 9, 2}, NT_STATUS_LOCK_NOT_GRANTED},
+ {{1000, 10, 0}, {1001, 10, 2}, NT_STATUS_OK},
+ {{1000, 10, 0}, {1001, 9, 3}, NT_STATUS_LOCK_NOT_GRANTED},
+
+ /** Same, but opposite order. */
+ {{1001, 10, 0}, {1000, 10, 0}, NT_STATUS_OK},
+ {{1001, 9, 1}, {1000, 10, 0}, NT_STATUS_OK},
+ {{1001, 10, 1}, {1000, 10, 0}, NT_STATUS_OK},
+ {{1001, 11, 1}, {1000, 10, 0}, NT_STATUS_OK},
+ {{1001, 9, 2}, {1000, 10, 0}, NT_STATUS_LOCK_NOT_GRANTED},
+ {{1001, 10, 2}, {1000, 10, 0}, NT_STATUS_OK},
+ {{1001, 9, 3}, {1000, 10, 0}, NT_STATUS_LOCK_NOT_GRANTED},
+
+ /** Zero zero case. */
+ {{1000, 0, 0}, {1001, 0, 0}, NT_STATUS_OK},
+};
+
+static bool test_zerobytelocks(struct torture_context *tctx, struct smbcli_state *cli)
+{
+ union smb_lock io;
+ struct smb_lock_entry zerozero;
+ NTSTATUS status;
+ bool ret = true;
+ int fnum, i;
+ const char *fname = BASEDIR "\\zero.txt";
+
+ printf("Testing zero length byte range locks:\n");
+
+ if (!torture_setup_dir(cli, BASEDIR)) {
+ return false;
+ }
+
+ io.generic.level = RAW_LOCK_LOCKX;
+
+ fnum = smbcli_open(cli->tree, fname, O_RDWR|O_CREAT, DENY_NONE);
+ if (fnum == -1) {
+ printf("Failed to create %s - %s\n", fname, smbcli_errstr(cli->tree));
+ ret = false;
+ goto done;
+ }
+
+ /* Setup initial parameters */
+ io.lockx.level = RAW_LOCK_LOCKX;
+ io.lockx.in.file.fnum = fnum;
+ io.lockx.in.mode = LOCKING_ANDX_LARGE_FILES; /* Exclusive */
+ io.lockx.in.timeout = 0;
+
+ /* Try every combination of locks in zero_byte_tests. The first lock is
+ * assumed to succeed. The second lock may contend, depending on the
+ * expected status. */
+ for (i = 0;
+ i < sizeof(zero_byte_tests) / sizeof(struct double_lock_test);
+ i++) {
+ printf(" ... {%d, %llu, %llu} + {%d, %llu, %llu} = %s\n",
+ zero_byte_tests[i].lock1.pid,
+ zero_byte_tests[i].lock1.offset,
+ zero_byte_tests[i].lock1.count,
+ zero_byte_tests[i].lock2.pid,
+ zero_byte_tests[i].lock2.offset,
+ zero_byte_tests[i].lock2.count,
+ nt_errstr(zero_byte_tests[i].exp_status));
+
+ /* Lock both locks. */
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+
+ io.lockx.in.locks = &zero_byte_tests[i].lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ io.lockx.in.locks = &zero_byte_tests[i].lock2;
+ status = smb_raw_lock(cli->tree, &io);
+
+ if (NT_STATUS_EQUAL(zero_byte_tests[i].exp_status,
+ NT_STATUS_LOCK_NOT_GRANTED)) {
+ /* Allow either of the failure messages and keep going
+ * if we see the wrong status. */
+ CHECK_STATUS_OR_CONT(status,
+ NT_STATUS_LOCK_NOT_GRANTED,
+ NT_STATUS_FILE_LOCK_CONFLICT);
+
+ } else {
+ CHECK_STATUS_CONT(status,
+ zero_byte_tests[i].exp_status);
+ }
+
+ /* Unlock both locks. */
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+
+ if (NT_STATUS_EQUAL(status, NT_STATUS_OK)) {
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+ }
+
+ io.lockx.in.locks = &zero_byte_tests[i].lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+ }
+
+done:
+ smbcli_close(cli->tree, fnum);
+ smb_raw_exit(cli->session);
+ smbcli_deltree(cli->tree, BASEDIR);
+ return ret;
+}
+
+static bool test_unlock(struct torture_context *tctx, struct smbcli_state *cli)
+{
+ union smb_lock io;
+ NTSTATUS status;
+ bool ret = true;
+ int fnum1, fnum2;
+ const char *fname = BASEDIR "\\unlock.txt";
+ struct smb_lock_entry lock1;
+ struct smb_lock_entry lock2;
+
+ printf("Testing LOCKX unlock:\n");
+
+ if (!torture_setup_dir(cli, BASEDIR)) {
+ return false;
+ }
+
+ fnum1 = smbcli_open(cli->tree, fname, O_RDWR|O_CREAT, DENY_NONE);
+ if (fnum1 == -1) {
+ printf("Failed to create %s - %s\n", fname, smbcli_errstr(cli->tree));
+ ret = false;
+ goto done;
+ }
+ fnum2 = smbcli_open(cli->tree, fname, O_RDWR|O_CREAT, DENY_NONE);
+ if (fnum2 == -1) {
+ printf("Failed to create %s - %s\n", fname, smbcli_errstr(cli->tree));
+ ret = false;
+ goto done;
+ }
+
+ /* Setup initial parameters */
+ io.lockx.level = RAW_LOCK_LOCKX;
+ io.lockx.in.timeout = 0;
+
+ lock1.pid = cli->session->pid;
+ lock1.offset = 0;
+ lock1.count = 10;
+ lock2.pid = cli->session->pid - 1;
+ lock2.offset = 0;
+ lock2.count = 10;
+
+ /**
+ * Take exclusive lock, then unlock it with a shared-unlock call.
+ */
+ printf(" taking exclusive lock.\n");
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.mode = 0;
+ io.lockx.in.file.fnum = fnum1;
+ io.lockx.in.locks = &lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ printf(" unlock the exclusive with a shared unlock call.\n");
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ io.lockx.in.mode = LOCKING_ANDX_SHARED_LOCK;
+ io.lockx.in.file.fnum = fnum1;
+ io.lockx.in.locks = &lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ printf(" try shared lock on pid2/fnum2, testing the unlock.\n");
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.mode = LOCKING_ANDX_SHARED_LOCK;
+ io.lockx.in.file.fnum = fnum2;
+ io.lockx.in.locks = &lock2;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /**
+ * Unlock a shared lock with an exclusive-unlock call.
+ */
+ printf(" unlock new shared lock with exclusive unlock call.\n");
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ io.lockx.in.mode = 0;
+ io.lockx.in.file.fnum = fnum2;
+ io.lockx.in.locks = &lock2;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ printf(" try exclusive lock on pid1, testing the unlock.\n");
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.mode = 0;
+ io.lockx.in.file.fnum = fnum1;
+ io.lockx.in.locks = &lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /* cleanup */
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /**
+ * Test unlocking of 0-byte locks.
+ */
+
+ printf(" lock shared and exclusive 0-byte locks, testing that Windows "
+ "always unlocks the exclusive first.\n");
+ lock1.pid = cli->session->pid;
+ lock1.offset = 10;
+ lock1.count = 0;
+ lock2.pid = cli->session->pid;
+ lock2.offset = 5;
+ lock2.count = 10;
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.file.fnum = fnum1;
+ io.lockx.in.locks = &lock1;
+
+ /* lock 0-byte shared
+ * Note: Order of the shared/exclusive locks doesn't matter. */
+ io.lockx.in.mode = LOCKING_ANDX_SHARED_LOCK;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /* lock 0-byte exclusive */
+ io.lockx.in.mode = 0;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /* test contention */
+ io.lockx.in.mode = LOCKING_ANDX_SHARED_LOCK;
+ io.lockx.in.locks = &lock2;
+ io.lockx.in.file.fnum = fnum2;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS_OR(status, NT_STATUS_LOCK_NOT_GRANTED,
+ NT_STATUS_FILE_LOCK_CONFLICT);
+
+ /* unlock */
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ io.lockx.in.file.fnum = fnum1;
+ io.lockx.in.locks = &lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /* test - can we take a shared lock? */
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.mode = LOCKING_ANDX_SHARED_LOCK;
+ io.lockx.in.file.fnum = fnum2;
+ io.lockx.in.locks = &lock2;
+ status = smb_raw_lock(cli->tree, &io);
+
+ /* XXX Samba will fail this test. This is temporary(because this isn't
+ * new to Win7, it succeeds in WinXP too), until I can come to a
+ * resolution as to whether Samba should support this or not. There is
+ * code to preference unlocking exclusive locks before shared locks,
+ * but its wrapped with "#ifdef ZERO_ZERO". -zkirsch */
+ if (TARGET_IS_WIN7(tctx))
+ CHECK_STATUS(status, NT_STATUS_OK);
+ else {
+ CHECK_STATUS_OR(status, NT_STATUS_LOCK_NOT_GRANTED,
+ NT_STATUS_FILE_LOCK_CONFLICT);
+ }
+
+ /* cleanup */
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ status = smb_raw_lock(cli->tree, &io);
+
+ /* XXX Same as above. */
+ if (TARGET_IS_WIN7(tctx))
+ CHECK_STATUS(status, NT_STATUS_OK);
+ else
+ CHECK_STATUS(status, NT_STATUS_RANGE_NOT_LOCKED);
+
+ io.lockx.in.file.fnum = fnum1;
+ io.lockx.in.locks = &lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+done:
+ smbcli_close(cli->tree, fnum1);
+ smbcli_close(cli->tree, fnum2);
+ smb_raw_exit(cli->session);
+ smbcli_deltree(cli->tree, BASEDIR);
+ return ret;
+}
+
+static bool test_multiple_unlock(struct torture_context *tctx, struct smbcli_state *cli)
+{
+ union smb_lock io;
+ NTSTATUS status;
+ bool ret = true;
+ int fnum1;
+ const char *fname = BASEDIR "\\unlock_multiple.txt";
+ struct smb_lock_entry lock1;
+ struct smb_lock_entry lock2;
+ struct smb_lock_entry locks[2];
+
+ printf("Testing LOCKX multiple unlock:\n");
+
+ if (!torture_setup_dir(cli, BASEDIR)) {
+ return false;
+ }
+
+ fnum1 = smbcli_open(cli->tree, fname, O_RDWR|O_CREAT, DENY_NONE);
+ if (fnum1 == -1) {
+ printf("Failed to create %s - %s\n", fname, smbcli_errstr(cli->tree));
+ ret = false;
+ goto done;
+ }
+
+ /* Setup initial parameters */
+ io.lockx.level = RAW_LOCK_LOCKX;
+ io.lockx.in.timeout = 0;
+
+ lock1.pid = cli->session->pid;
+ lock1.offset = 0;
+ lock1.count = 10;
+ lock2.pid = cli->session->pid;
+ lock2.offset = 10;
+ lock2.count = 10;
+
+ locks[0] = lock1;
+ locks[1] = lock2;
+
+ io.lockx.in.file.fnum = fnum1;
+ io.lockx.in.mode = 0; /* exclusive */
+
+ /** Test1: Take second lock, but not first. */
+ printf(" unlock 2 locks, first one not locked. Expect no locks "
+ "unlocked. \n");
+
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.locks = &lock2;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /* Try to unlock both locks. */
+ io.lockx.in.ulock_cnt = 2;
+ io.lockx.in.lock_cnt = 0;
+ io.lockx.in.locks = locks;
+
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_RANGE_NOT_LOCKED);
+
+ /* Second lock should not be unlocked. */
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.locks = &lock2;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_LOCK_NOT_GRANTED);
+
+ /* cleanup */
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ io.lockx.in.locks = &lock2;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /** Test2: Take first lock, but not second. */
+ printf(" unlock 2 locks, second one not locked. Expect first lock "
+ "unlocked.\n");
+
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.locks = &lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /* Try to unlock both locks. */
+ io.lockx.in.ulock_cnt = 2;
+ io.lockx.in.lock_cnt = 0;
+ io.lockx.in.locks = locks;
+
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_RANGE_NOT_LOCKED);
+
+ /* First lock should be unlocked. */
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.locks = &lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /* cleanup */
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ io.lockx.in.locks = &lock1;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+done:
+ smbcli_close(cli->tree, fnum1);
+ smb_raw_exit(cli->session);
+ smbcli_deltree(cli->tree, BASEDIR);
+ return ret;
+}
+
+/**
+ * torture_locktest5 covers stacking pretty well, but its missing two tests:
+ * - stacking an exclusive on top of shared fails
+ * - stacking two exclusives fail
+ */
+static bool test_stacking(struct torture_context *tctx, struct smbcli_state *cli)
+{
+ union smb_lock io;
+ NTSTATUS status;
+ bool ret = true;
+ int fnum1;
+ const char *fname = BASEDIR "\\stacking.txt";
+ struct smb_lock_entry lock1;
+ struct smb_lock_entry lock2;
+
+ printf("Testing stacking:\n");
+
+ if (!torture_setup_dir(cli, BASEDIR)) {
+ return false;
+ }
+
+ io.generic.level = RAW_LOCK_LOCKX;
+
+ fnum1 = smbcli_open(cli->tree, fname, O_RDWR|O_CREAT, DENY_NONE);
+ if (fnum1 == -1) {
+ printf("Failed to create %s - %s\n", fname, smbcli_errstr(cli->tree));
+ ret = false;
+ goto done;
+ }
+
+ /* Setup initial parameters */
+ io.lockx.level = RAW_LOCK_LOCKX;
+ io.lockx.in.timeout = 0;
+
+ lock1.pid = cli->session->pid;
+ lock1.offset = 0;
+ lock1.count = 10;
+ lock2.pid = cli->session->pid - 1;
+ lock2.offset = 0;
+ lock2.count = 10;
+
+ /**
+ * Try to take a shared lock, then stack an exclusive.
+ */
+ printf(" stacking an exclusive on top of a shared lock fails.\n");
+ io.lockx.in.file.fnum = fnum1;
+ io.lockx.in.locks = &lock1;
+
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.mode = LOCKING_ANDX_SHARED_LOCK;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.mode = 0;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS_OR(status, NT_STATUS_LOCK_NOT_GRANTED,
+ NT_STATUS_FILE_LOCK_CONFLICT);
+
+ /* cleanup */
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+ /**
+ * Prove that two exclusive locks do not stack.
+ */
+ printf(" two exclusive locks do not stack.\n");
+ io.lockx.in.ulock_cnt = 0;
+ io.lockx.in.lock_cnt = 1;
+ io.lockx.in.mode = 0;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS_OR(status, NT_STATUS_LOCK_NOT_GRANTED,
+ NT_STATUS_FILE_LOCK_CONFLICT);
+
+ /* cleanup */
+ io.lockx.in.ulock_cnt = 1;
+ io.lockx.in.lock_cnt = 0;
+ status = smb_raw_lock(cli->tree, &io);
+ CHECK_STATUS(status, NT_STATUS_OK);
+
+done:
+ smbcli_close(cli->tree, fnum1);
+ smb_raw_exit(cli->session);
+ smbcli_deltree(cli->tree, BASEDIR);
+ return ret;
+}
/*
basic testing of lock calls
@@ -1336,5 +1888,12 @@ struct torture_suite *torture_raw_lock(TALLOC_CTX *mem_ctx)
torture_suite_add_1smb_test(suite, "errorcode", test_errorcode);
torture_suite_add_1smb_test(suite, "changetype", test_changetype);
+ torture_suite_add_1smb_test(suite, "stacking", test_stacking);
+ torture_suite_add_1smb_test(suite, "unlock", test_unlock);
+ torture_suite_add_1smb_test(suite, "multiple_unlock",
+ test_multiple_unlock);
+ torture_suite_add_1smb_test(suite, "zerobytelocks",
+ test_zerobytelocks);
+
return suite;
}
diff --git a/source4/torture/smbtorture.c b/source4/torture/smbtorture.c
index 635990354c..d01dc9a856 100644
--- a/source4/torture/smbtorture.c
+++ b/source4/torture/smbtorture.c
@@ -559,6 +559,8 @@ int main(int argc,char *argv[])
lp_set_cmdline(cmdline_lp_ctx, "torture:samba3", "true");
} else if (strcmp(target, "samba4") == 0) {
lp_set_cmdline(cmdline_lp_ctx, "torture:samba4", "true");
+ } else if (strcmp(target, "win7") == 0) {
+ lp_set_cmdline(cmdline_lp_ctx, "torture:win7", "true");
}
if (max_runtime) {