2 Unix SMB/CIFS implementation.
4 Copyright (C) Tim Potter 2000-2001,
5 Copyright (C) Andrew Tridgell 1992-1997,2000,
6 Copyright (C) Rafal Szczesniak 2002.
7 Copyright (C) Jeremy Allison 2005.
9 This program is free software; you can redistribute it and/or modify
10 it under the terms of the GNU General Public License as published by
11 the Free Software Foundation; either version 3 of the License, or
12 (at your option) any later version.
14 This program is distributed in the hope that it will be useful,
15 but WITHOUT ANY WARRANTY; without even the implied warranty of
16 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
17 GNU General Public License for more details.
19 You should have received a copy of the GNU General Public License
20 along with this program. If not, see <http://www.gnu.org/licenses/>.
25 /* Connect to SAMR database */
27 NTSTATUS
rpccli_samr_connect(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
28 uint32 access_mask
, POLICY_HND
*connect_pol
)
30 prs_struct qbuf
, rbuf
;
33 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
35 DEBUG(10,("cli_samr_connect to %s\n", cli
->cli
->desthost
));
40 /* Marshall data and send request */
42 init_samr_q_connect(&q
, cli
->cli
->desthost
, access_mask
);
44 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_CONNECT
,
49 NT_STATUS_UNSUCCESSFUL
);
50 /* Return output parameters */
52 if (NT_STATUS_IS_OK(result
= r
.status
)) {
53 *connect_pol
= r
.connect_pol
;
55 connect_pol
->marker
= malloc(1);
62 /* Connect to SAMR database */
64 NTSTATUS
rpccli_samr_connect4(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
65 uint32 access_mask
, POLICY_HND
*connect_pol
)
67 prs_struct qbuf
, rbuf
;
70 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
75 /* Marshall data and send request */
77 init_samr_q_connect4(&q
, cli
->cli
->desthost
, access_mask
);
79 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_CONNECT4
,
84 NT_STATUS_UNSUCCESSFUL
);
86 /* Return output parameters */
88 if (NT_STATUS_IS_OK(result
= r
.status
)) {
89 *connect_pol
= r
.connect_pol
;
91 connect_pol
->marker
= malloc(1);
98 /* Add a domain group member */
100 NTSTATUS
rpccli_samr_add_groupmem(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
101 POLICY_HND
*group_pol
, uint32 rid
)
103 prs_struct qbuf
, rbuf
;
104 SAMR_Q_ADD_GROUPMEM q
;
105 SAMR_R_ADD_GROUPMEM r
;
106 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
108 DEBUG(10,("cli_samr_add_groupmem\n"));
113 /* Marshall data and send request */
115 init_samr_q_add_groupmem(&q
, group_pol
, rid
);
117 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_ADD_GROUPMEM
,
120 samr_io_q_add_groupmem
,
121 samr_io_r_add_groupmem
,
122 NT_STATUS_UNSUCCESSFUL
);
124 /* Return output parameters */
131 /* Delete a domain group member */
133 NTSTATUS
rpccli_samr_del_groupmem(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
134 POLICY_HND
*group_pol
, uint32 rid
)
136 prs_struct qbuf
, rbuf
;
137 SAMR_Q_DEL_GROUPMEM q
;
138 SAMR_R_DEL_GROUPMEM r
;
139 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
141 DEBUG(10,("cli_samr_del_groupmem\n"));
146 /* Marshall data and send request */
148 init_samr_q_del_groupmem(&q
, group_pol
, rid
);
150 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_DEL_GROUPMEM
,
153 samr_io_q_del_groupmem
,
154 samr_io_r_del_groupmem
,
155 NT_STATUS_UNSUCCESSFUL
);
157 /* Return output parameters */
164 /* Query user info */
166 NTSTATUS
rpccli_samr_query_userinfo(struct rpc_pipe_client
*cli
,
168 const POLICY_HND
*user_pol
,
170 SAM_USERINFO_CTR
**ctr
)
172 prs_struct qbuf
, rbuf
;
173 SAMR_Q_QUERY_USERINFO q
;
174 SAMR_R_QUERY_USERINFO r
;
175 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
177 DEBUG(10,("cli_samr_query_userinfo\n"));
182 /* Marshall data and send request */
184 init_samr_q_query_userinfo(&q
, user_pol
, switch_value
);
186 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_USERINFO
,
189 samr_io_q_query_userinfo
,
190 samr_io_r_query_userinfo
,
191 NT_STATUS_UNSUCCESSFUL
);
193 /* Return output parameters */
203 NTSTATUS
rpccli_samr_set_groupinfo(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
204 POLICY_HND
*group_pol
, GROUP_INFO_CTR
*ctr
)
206 prs_struct qbuf
, rbuf
;
207 SAMR_Q_SET_GROUPINFO q
;
208 SAMR_R_SET_GROUPINFO r
;
209 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
211 DEBUG(10,("cli_samr_set_groupinfo\n"));
216 /* Marshall data and send request */
218 init_samr_q_set_groupinfo(&q
, group_pol
, ctr
);
220 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_SET_GROUPINFO
,
223 samr_io_q_set_groupinfo
,
224 samr_io_r_set_groupinfo
,
225 NT_STATUS_UNSUCCESSFUL
);
227 /* Return output parameters */
234 /* Query group info */
236 NTSTATUS
rpccli_samr_query_groupinfo(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
237 POLICY_HND
*group_pol
, uint32 info_level
,
238 GROUP_INFO_CTR
**ctr
)
240 prs_struct qbuf
, rbuf
;
241 SAMR_Q_QUERY_GROUPINFO q
;
242 SAMR_R_QUERY_GROUPINFO r
;
243 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
245 DEBUG(10,("cli_samr_query_groupinfo\n"));
250 /* Marshall data and send request */
252 init_samr_q_query_groupinfo(&q
, group_pol
, info_level
);
254 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_GROUPINFO
,
257 samr_io_q_query_groupinfo
,
258 samr_io_r_query_groupinfo
,
259 NT_STATUS_UNSUCCESSFUL
);
263 /* Return output parameters */
270 /* Query user groups */
272 NTSTATUS
rpccli_samr_query_usergroups(struct rpc_pipe_client
*cli
,
274 POLICY_HND
*user_pol
,
278 prs_struct qbuf
, rbuf
;
279 SAMR_Q_QUERY_USERGROUPS q
;
280 SAMR_R_QUERY_USERGROUPS r
;
281 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
283 DEBUG(10,("cli_samr_query_usergroups\n"));
288 /* Marshall data and send request */
290 init_samr_q_query_usergroups(&q
, user_pol
);
292 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_USERGROUPS
,
295 samr_io_q_query_usergroups
,
296 samr_io_r_query_usergroups
,
297 NT_STATUS_UNSUCCESSFUL
);
299 /* Return output parameters */
301 if (NT_STATUS_IS_OK(result
= r
.status
)) {
302 *num_groups
= r
.num_entries
;
311 NTSTATUS
rpccli_samr_set_aliasinfo(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
312 POLICY_HND
*alias_pol
, ALIAS_INFO_CTR
*ctr
)
314 prs_struct qbuf
, rbuf
;
315 SAMR_Q_SET_ALIASINFO q
;
316 SAMR_R_SET_ALIASINFO r
;
317 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
319 DEBUG(10,("cli_samr_set_aliasinfo\n"));
324 /* Marshall data and send request */
326 init_samr_q_set_aliasinfo(&q
, alias_pol
, ctr
);
328 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_SET_ALIASINFO
,
331 samr_io_q_set_aliasinfo
,
332 samr_io_r_set_aliasinfo
,
333 NT_STATUS_UNSUCCESSFUL
);
335 /* Return output parameters */
342 /* Query user aliases */
344 NTSTATUS
rpccli_samr_query_useraliases(struct rpc_pipe_client
*cli
,
346 POLICY_HND
*dom_pol
, uint32 num_sids
,
348 uint32
*num_aliases
, uint32
**als_rids
)
350 prs_struct qbuf
, rbuf
;
351 SAMR_Q_QUERY_USERALIASES q
;
352 SAMR_R_QUERY_USERALIASES r
;
353 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
357 DEBUG(10,("cli_samr_query_useraliases\n"));
363 sid_ptrs
= TALLOC_ARRAY(mem_ctx
, uint32
, num_sids
);
364 if (sid_ptrs
== NULL
)
365 return NT_STATUS_NO_MEMORY
;
370 for (i
=0; i
<num_sids
; i
++)
373 /* Marshall data and send request */
375 init_samr_q_query_useraliases(&q
, dom_pol
, num_sids
, sid_ptrs
, sid
);
377 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_USERALIASES
,
380 samr_io_q_query_useraliases
,
381 samr_io_r_query_useraliases
,
382 NT_STATUS_UNSUCCESSFUL
);
384 /* Return output parameters */
386 if (NT_STATUS_IS_OK(result
= r
.status
)) {
387 *num_aliases
= r
.num_entries
;
394 /* Query user groups */
396 NTSTATUS
rpccli_samr_query_groupmem(struct rpc_pipe_client
*cli
,
398 POLICY_HND
*group_pol
, uint32
*num_mem
,
399 uint32
**rid
, uint32
**attr
)
401 prs_struct qbuf
, rbuf
;
402 SAMR_Q_QUERY_GROUPMEM q
;
403 SAMR_R_QUERY_GROUPMEM r
;
404 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
406 DEBUG(10,("cli_samr_query_groupmem\n"));
411 /* Marshall data and send request */
413 init_samr_q_query_groupmem(&q
, group_pol
);
415 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_GROUPMEM
,
418 samr_io_q_query_groupmem
,
419 samr_io_r_query_groupmem
,
420 NT_STATUS_UNSUCCESSFUL
);
422 /* Return output parameters */
424 if (NT_STATUS_IS_OK(result
= r
.status
)) {
425 *num_mem
= r
.num_entries
;
434 * Enumerate domain users
436 * @param cli client state structure
437 * @param mem_ctx talloc context
438 * @param pol opened domain policy handle
439 * @param start_idx starting index of enumeration, returns context for
441 * @param acb_mask account control bit mask (to enumerate some particular
443 * @param size max acceptable size of response
444 * @param dom_users returned array of domain user names
445 * @param rids returned array of domain user RIDs
446 * @param num_dom_users numer returned entries
448 * @return NTSTATUS returned in rpc response
451 NTSTATUS
rpccli_samr_enum_dom_users(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
452 POLICY_HND
*pol
, uint32
*start_idx
, uint32 acb_mask
,
453 uint32 size
, char ***dom_users
, uint32
**rids
,
454 uint32
*num_dom_users
)
458 SAMR_Q_ENUM_DOM_USERS q
;
459 SAMR_R_ENUM_DOM_USERS r
;
460 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
463 DEBUG(10,("cli_samr_enum_dom_users starting at index %u\n", (unsigned int)*start_idx
));
468 /* always init this */
471 /* Fill query structure with parameters */
473 init_samr_q_enum_dom_users(&q
, pol
, *start_idx
, acb_mask
, size
);
475 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_ENUM_DOM_USERS
,
478 samr_io_q_enum_dom_users
,
479 samr_io_r_enum_dom_users
,
480 NT_STATUS_UNSUCCESSFUL
);
484 if (!NT_STATUS_IS_OK(result
) &&
485 NT_STATUS_V(result
) != NT_STATUS_V(STATUS_MORE_ENTRIES
))
488 *start_idx
= r
.next_idx
;
489 *num_dom_users
= r
.num_entries2
;
491 if (r
.num_entries2
) {
492 /* allocate memory needed to return received data */
493 *rids
= TALLOC_ARRAY(mem_ctx
, uint32
, r
.num_entries2
);
495 DEBUG(0, ("Error in cli_samr_enum_dom_users(): out of memory\n"));
496 return NT_STATUS_NO_MEMORY
;
499 *dom_users
= TALLOC_ARRAY(mem_ctx
, char*, r
.num_entries2
);
501 DEBUG(0, ("Error in cli_samr_enum_dom_users(): out of memory\n"));
502 return NT_STATUS_NO_MEMORY
;
505 /* fill output buffers with rpc response */
506 for (i
= 0; i
< r
.num_entries2
; i
++) {
509 (*rids
)[i
] = r
.sam
[i
].rid
;
510 unistr2_to_ascii(conv_buf
, &(r
.uni_acct_name
[i
]), sizeof(conv_buf
));
511 (*dom_users
)[i
] = talloc_strdup(mem_ctx
, conv_buf
);
519 /* Enumerate domain groups */
521 NTSTATUS
rpccli_samr_enum_dom_groups(struct rpc_pipe_client
*cli
,
523 POLICY_HND
*pol
, uint32
*start_idx
,
524 uint32 size
, struct acct_info
**dom_groups
,
525 uint32
*num_dom_groups
)
527 prs_struct qbuf
, rbuf
;
528 SAMR_Q_ENUM_DOM_GROUPS q
;
529 SAMR_R_ENUM_DOM_GROUPS r
;
530 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
533 DEBUG(10,("cli_samr_enum_dom_groups starting at index %u\n", (unsigned int)*start_idx
));
538 /* Marshall data and send request */
540 init_samr_q_enum_dom_groups(&q
, pol
, *start_idx
, size
);
542 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_ENUM_DOM_GROUPS
,
545 samr_io_q_enum_dom_groups
,
546 samr_io_r_enum_dom_groups
,
547 NT_STATUS_UNSUCCESSFUL
);
549 /* Return output parameters */
553 if (!NT_STATUS_IS_OK(result
) &&
554 NT_STATUS_V(result
) != NT_STATUS_V(STATUS_MORE_ENTRIES
))
557 *num_dom_groups
= r
.num_entries2
;
559 if (*num_dom_groups
== 0)
562 if (!((*dom_groups
) = TALLOC_ARRAY(mem_ctx
, struct acct_info
, *num_dom_groups
))) {
563 result
= NT_STATUS_NO_MEMORY
;
567 memset(*dom_groups
, 0, sizeof(struct acct_info
) * (*num_dom_groups
));
571 for (i
= 0; i
< *num_dom_groups
; i
++) {
573 (*dom_groups
)[i
].rid
= r
.sam
[i
].rid
;
575 if (r
.sam
[i
].hdr_name
.buffer
) {
576 unistr2_to_ascii((*dom_groups
)[i
].acct_name
,
577 &r
.uni_grp_name
[name_idx
],
578 sizeof((*dom_groups
)[i
].acct_name
));
582 *start_idx
= r
.next_idx
;
589 /* Enumerate domain groups */
591 NTSTATUS
rpccli_samr_enum_als_groups(struct rpc_pipe_client
*cli
,
593 POLICY_HND
*pol
, uint32
*start_idx
,
594 uint32 size
, struct acct_info
**dom_aliases
,
595 uint32
*num_dom_aliases
)
597 prs_struct qbuf
, rbuf
;
598 SAMR_Q_ENUM_DOM_ALIASES q
;
599 SAMR_R_ENUM_DOM_ALIASES r
;
600 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
603 DEBUG(10,("cli_samr_enum_als_groups starting at index %u\n", (unsigned int)*start_idx
));
608 /* Marshall data and send request */
610 init_samr_q_enum_dom_aliases(&q
, pol
, *start_idx
, size
);
612 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_ENUM_DOM_ALIASES
,
615 samr_io_q_enum_dom_aliases
,
616 samr_io_r_enum_dom_aliases
,
617 NT_STATUS_UNSUCCESSFUL
);
619 /* Return output parameters */
623 if (!NT_STATUS_IS_OK(result
) &&
624 NT_STATUS_V(result
) != NT_STATUS_V(STATUS_MORE_ENTRIES
)) {
628 *num_dom_aliases
= r
.num_entries2
;
630 if (*num_dom_aliases
== 0)
633 if (!((*dom_aliases
) = TALLOC_ARRAY(mem_ctx
, struct acct_info
, *num_dom_aliases
))) {
634 result
= NT_STATUS_NO_MEMORY
;
638 memset(*dom_aliases
, 0, sizeof(struct acct_info
) * *num_dom_aliases
);
642 for (i
= 0; i
< *num_dom_aliases
; i
++) {
644 (*dom_aliases
)[i
].rid
= r
.sam
[i
].rid
;
646 if (r
.sam
[i
].hdr_name
.buffer
) {
647 unistr2_to_ascii((*dom_aliases
)[i
].acct_name
,
648 &r
.uni_grp_name
[name_idx
],
649 sizeof((*dom_aliases
)[i
].acct_name
));
653 *start_idx
= r
.next_idx
;
660 /* Query alias members */
662 NTSTATUS
rpccli_samr_query_aliasmem(struct rpc_pipe_client
*cli
,
664 POLICY_HND
*alias_pol
, uint32
*num_mem
,
667 prs_struct qbuf
, rbuf
;
668 SAMR_Q_QUERY_ALIASMEM q
;
669 SAMR_R_QUERY_ALIASMEM r
;
670 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
673 DEBUG(10,("cli_samr_query_aliasmem\n"));
678 /* Marshall data and send request */
680 init_samr_q_query_aliasmem(&q
, alias_pol
);
682 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_ALIASMEM
,
685 samr_io_q_query_aliasmem
,
686 samr_io_r_query_aliasmem
,
687 NT_STATUS_UNSUCCESSFUL
);
689 /* Return output parameters */
691 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
695 *num_mem
= r
.num_sids
;
699 result
= NT_STATUS_OK
;
703 if (!(*sids
= TALLOC_ARRAY(mem_ctx
, DOM_SID
, *num_mem
))) {
704 result
= NT_STATUS_UNSUCCESSFUL
;
708 for (i
= 0; i
< *num_mem
; i
++) {
709 (*sids
)[i
] = r
.sid
[i
].sid
;
716 /* Add an alias member */
718 NTSTATUS
rpccli_samr_add_aliasmem(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
719 POLICY_HND
*alias_pol
, DOM_SID
*member
)
721 prs_struct qbuf
, rbuf
;
722 SAMR_Q_ADD_ALIASMEM q
;
723 SAMR_R_ADD_ALIASMEM r
;
726 DEBUG(10,("cli_samr_add_aliasmem"));
731 /* Marshall data and send request */
733 init_samr_q_add_aliasmem(&q
, alias_pol
, member
);
735 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_ADD_ALIASMEM
,
738 samr_io_q_add_aliasmem
,
739 samr_io_r_add_aliasmem
,
740 NT_STATUS_UNSUCCESSFUL
);
747 /* Delete an alias member */
749 NTSTATUS
rpccli_samr_del_aliasmem(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
750 POLICY_HND
*alias_pol
, DOM_SID
*member
)
752 prs_struct qbuf
, rbuf
;
753 SAMR_Q_DEL_ALIASMEM q
;
754 SAMR_R_DEL_ALIASMEM r
;
757 DEBUG(10,("cli_samr_del_aliasmem"));
762 /* Marshall data and send request */
764 init_samr_q_del_aliasmem(&q
, alias_pol
, member
);
766 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_DEL_ALIASMEM
,
769 samr_io_q_del_aliasmem
,
770 samr_io_r_del_aliasmem
,
771 NT_STATUS_UNSUCCESSFUL
);
778 /* Query alias info */
780 NTSTATUS
rpccli_samr_query_alias_info(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
781 POLICY_HND
*alias_pol
, uint16 switch_value
,
784 prs_struct qbuf
, rbuf
;
785 SAMR_Q_QUERY_ALIASINFO q
;
786 SAMR_R_QUERY_ALIASINFO r
;
787 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
789 DEBUG(10,("cli_samr_query_alias_info\n"));
794 /* Marshall data and send request */
796 init_samr_q_query_aliasinfo(&q
, alias_pol
, switch_value
);
798 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_ALIASINFO
,
801 samr_io_q_query_aliasinfo
,
802 samr_io_r_query_aliasinfo
,
803 NT_STATUS_UNSUCCESSFUL
);
805 /* Return output parameters */
807 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
818 /* Query domain info */
820 NTSTATUS
rpccli_samr_query_dom_info(struct rpc_pipe_client
*cli
,
822 POLICY_HND
*domain_pol
,
826 prs_struct qbuf
, rbuf
;
827 SAMR_Q_QUERY_DOMAIN_INFO q
;
828 SAMR_R_QUERY_DOMAIN_INFO r
;
829 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
831 DEBUG(10,("cli_samr_query_dom_info\n"));
836 /* Marshall data and send request */
838 init_samr_q_query_domain_info(&q
, domain_pol
, switch_value
);
842 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_DOMAIN_INFO
,
845 samr_io_q_query_domain_info
,
846 samr_io_r_query_domain_info
,
847 NT_STATUS_UNSUCCESSFUL
);
849 /* Return output parameters */
851 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
860 /* Query domain info2 */
862 NTSTATUS
rpccli_samr_query_dom_info2(struct rpc_pipe_client
*cli
,
864 POLICY_HND
*domain_pol
,
868 prs_struct qbuf
, rbuf
;
869 SAMR_Q_QUERY_DOMAIN_INFO2 q
;
870 SAMR_R_QUERY_DOMAIN_INFO2 r
;
871 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
873 DEBUG(10,("cli_samr_query_dom_info2\n"));
878 /* Marshall data and send request */
880 init_samr_q_query_domain_info2(&q
, domain_pol
, switch_value
);
884 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_DOMAIN_INFO2
,
887 samr_io_q_query_domain_info2
,
888 samr_io_r_query_domain_info2
,
889 NT_STATUS_UNSUCCESSFUL
);
891 /* Return output parameters */
893 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
902 /* Set domain info */
904 NTSTATUS
rpccli_samr_set_domain_info(struct rpc_pipe_client
*cli
,
906 POLICY_HND
*domain_pol
,
910 prs_struct qbuf
, rbuf
;
911 SAMR_Q_SET_DOMAIN_INFO q
;
912 SAMR_R_SET_DOMAIN_INFO r
;
913 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
915 DEBUG(10,("cli_samr_set_domain_info\n"));
920 /* Marshall data and send request */
922 init_samr_q_set_domain_info(&q
, domain_pol
, switch_value
, ctr
);
924 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_SET_DOMAIN_INFO
,
927 samr_io_q_set_domain_info
,
928 samr_io_r_set_domain_info
,
929 NT_STATUS_UNSUCCESSFUL
);
931 /* Return output parameters */
933 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
942 /* User change password */
944 NTSTATUS
rpccli_samr_chgpasswd_user(struct rpc_pipe_client
*cli
,
946 const char *username
,
947 const char *newpassword
,
948 const char *oldpassword
)
950 prs_struct qbuf
, rbuf
;
951 SAMR_Q_CHGPASSWD_USER q
;
952 SAMR_R_CHGPASSWD_USER r
;
953 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
955 uchar new_nt_password
[516];
956 uchar new_lm_password
[516];
957 uchar old_nt_hash
[16];
958 uchar old_lanman_hash
[16];
959 uchar old_nt_hash_enc
[16];
960 uchar old_lanman_hash_enc
[16];
962 uchar new_nt_hash
[16];
963 uchar new_lanman_hash
[16];
965 char *srv_name_slash
= talloc_asprintf(mem_ctx
, "\\\\%s", cli
->cli
->desthost
);
967 DEBUG(10,("rpccli_samr_chgpasswd_user\n"));
972 /* Calculate the MD4 hash (NT compatible) of the password */
973 E_md4hash(oldpassword
, old_nt_hash
);
974 E_md4hash(newpassword
, new_nt_hash
);
976 if (lp_client_lanman_auth()
977 && E_deshash(newpassword
, new_lanman_hash
)
978 && E_deshash(oldpassword
, old_lanman_hash
)) {
979 /* E_deshash returns false for 'long' passwords (> 14
980 DOS chars). This allows us to match Win2k, which
981 does not store a LM hash for these passwords (which
982 would reduce the effective password length to 14) */
984 encode_pw_buffer(new_lm_password
, newpassword
, STR_UNICODE
);
986 SamOEMhash( new_lm_password
, old_nt_hash
, 516);
987 E_old_pw_hash( new_nt_hash
, old_lanman_hash
, old_lanman_hash_enc
);
989 ZERO_STRUCT(new_lm_password
);
990 ZERO_STRUCT(old_lanman_hash_enc
);
993 encode_pw_buffer(new_nt_password
, newpassword
, STR_UNICODE
);
995 SamOEMhash( new_nt_password
, old_nt_hash
, 516);
996 E_old_pw_hash( new_nt_hash
, old_nt_hash
, old_nt_hash_enc
);
998 /* Marshall data and send request */
1000 init_samr_q_chgpasswd_user(&q
, srv_name_slash
, username
,
1004 old_lanman_hash_enc
);
1006 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_CHGPASSWD_USER
,
1009 samr_io_q_chgpasswd_user
,
1010 samr_io_r_chgpasswd_user
,
1011 NT_STATUS_UNSUCCESSFUL
);
1013 /* Return output parameters */
1015 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
1024 /* User change password given blobs */
1026 NTSTATUS
rpccli_samr_chng_pswd_auth_crap(struct rpc_pipe_client
*cli
,
1027 TALLOC_CTX
*mem_ctx
,
1028 const char *username
,
1029 DATA_BLOB new_nt_password
,
1030 DATA_BLOB old_nt_hash_enc
,
1031 DATA_BLOB new_lm_password
,
1032 DATA_BLOB old_lm_hash_enc
)
1034 prs_struct qbuf
, rbuf
;
1035 SAMR_Q_CHGPASSWD_USER q
;
1036 SAMR_R_CHGPASSWD_USER r
;
1037 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1039 char *srv_name_slash
= talloc_asprintf(mem_ctx
, "\\\\%s", cli
->cli
->desthost
);
1041 DEBUG(10,("rpccli_samr_chng_pswd_auth_crap\n"));
1046 /* Marshall data and send request */
1048 init_samr_q_chgpasswd_user(&q
, srv_name_slash
, username
,
1049 new_nt_password
.data
,
1050 old_nt_hash_enc
.data
,
1051 new_lm_password
.data
,
1052 old_lm_hash_enc
.data
);
1054 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_CHGPASSWD_USER
,
1057 samr_io_q_chgpasswd_user
,
1058 samr_io_r_chgpasswd_user
,
1059 NT_STATUS_UNSUCCESSFUL
);
1061 /* Return output parameters */
1063 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
1073 /* change password 3 */
1075 NTSTATUS
rpccli_samr_chgpasswd3(struct rpc_pipe_client
*cli
,
1076 TALLOC_CTX
*mem_ctx
,
1077 const char *username
,
1078 const char *newpassword
,
1079 const char *oldpassword
,
1080 SAM_UNK_INFO_1
*info
,
1081 SAMR_CHANGE_REJECT
*reject
)
1083 prs_struct qbuf
, rbuf
;
1084 SAMR_Q_CHGPASSWD_USER3 q
;
1085 SAMR_R_CHGPASSWD_USER3 r
;
1087 uchar new_nt_password
[516];
1088 uchar new_lm_password
[516];
1089 uchar old_nt_hash
[16];
1090 uchar old_lanman_hash
[16];
1091 uchar old_nt_hash_enc
[16];
1092 uchar old_lanman_hash_enc
[16];
1094 uchar new_nt_hash
[16];
1095 uchar new_lanman_hash
[16];
1097 char *srv_name_slash
= talloc_asprintf(mem_ctx
, "\\\\%s", cli
->cli
->desthost
);
1099 DEBUG(10,("rpccli_samr_chgpasswd_user3\n"));
1104 /* Calculate the MD4 hash (NT compatible) of the password */
1105 E_md4hash(oldpassword
, old_nt_hash
);
1106 E_md4hash(newpassword
, new_nt_hash
);
1108 if (lp_client_lanman_auth()
1109 && E_deshash(newpassword
, new_lanman_hash
)
1110 && E_deshash(oldpassword
, old_lanman_hash
)) {
1111 /* E_deshash returns false for 'long' passwords (> 14
1112 DOS chars). This allows us to match Win2k, which
1113 does not store a LM hash for these passwords (which
1114 would reduce the effective password length to 14) */
1116 encode_pw_buffer(new_lm_password
, newpassword
, STR_UNICODE
);
1118 SamOEMhash( new_lm_password
, old_nt_hash
, 516);
1119 E_old_pw_hash( new_nt_hash
, old_lanman_hash
, old_lanman_hash_enc
);
1121 ZERO_STRUCT(new_lm_password
);
1122 ZERO_STRUCT(old_lanman_hash_enc
);
1125 encode_pw_buffer(new_nt_password
, newpassword
, STR_UNICODE
);
1127 SamOEMhash( new_nt_password
, old_nt_hash
, 516);
1128 E_old_pw_hash( new_nt_hash
, old_nt_hash
, old_nt_hash_enc
);
1130 /* Marshall data and send request */
1132 init_samr_q_chgpasswd_user3(&q
, srv_name_slash
, username
,
1136 old_lanman_hash_enc
);
1140 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_CHGPASSWD_USER3
,
1143 samr_io_q_chgpasswd_user3
,
1144 samr_io_r_chgpasswd_user3
,
1145 NT_STATUS_UNSUCCESSFUL
);
1147 /* Return output parameters */
1152 /* This function returns the bizzare set of (max_entries, max_size) required
1153 for the QueryDisplayInfo RPC to actually work against a domain controller
1154 with large (10k and higher) numbers of users. These values were
1155 obtained by inspection using ethereal and NT4 running User Manager. */
1157 void get_query_dispinfo_params(int loop_count
, uint32
*max_entries
,
1160 switch(loop_count
) {
1166 *max_entries
= 1024;
1170 *max_entries
= 2048;
1174 *max_entries
= 4096;
1177 default: /* loop_count >= 4 */
1178 *max_entries
= 4096;
1184 /* Query display info */
1186 NTSTATUS
rpccli_samr_query_dispinfo(struct rpc_pipe_client
*cli
,
1187 TALLOC_CTX
*mem_ctx
,
1188 POLICY_HND
*domain_pol
, uint32
*start_idx
,
1189 uint16 switch_value
, uint32
*num_entries
,
1190 uint32 max_entries
, uint32 max_size
,
1191 SAM_DISPINFO_CTR
*ctr
)
1193 prs_struct qbuf
, rbuf
;
1194 SAMR_Q_QUERY_DISPINFO q
;
1195 SAMR_R_QUERY_DISPINFO r
;
1196 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1198 DEBUG(10,("cli_samr_query_dispinfo for start_idx = %u\n", *start_idx
));
1205 /* Marshall data and send request */
1207 init_samr_q_query_dispinfo(&q
, domain_pol
, switch_value
,
1208 *start_idx
, max_entries
, max_size
);
1212 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_DISPINFO
,
1215 samr_io_q_query_dispinfo
,
1216 samr_io_r_query_dispinfo
,
1217 NT_STATUS_UNSUCCESSFUL
);
1219 /* Return output parameters */
1223 if (!NT_STATUS_IS_OK(result
) &&
1224 NT_STATUS_V(result
) != NT_STATUS_V(STATUS_MORE_ENTRIES
)) {
1228 *num_entries
= r
.num_entries
;
1229 *start_idx
+= r
.num_entries
; /* No next_idx in this structure! */
1235 /* Lookup rids. Note that NT4 seems to crash if more than ~1000 rids are
1236 looked up in one packet. */
1238 NTSTATUS
rpccli_samr_lookup_rids(struct rpc_pipe_client
*cli
,
1239 TALLOC_CTX
*mem_ctx
,
1240 POLICY_HND
*domain_pol
,
1241 uint32 num_rids
, uint32
*rids
,
1242 uint32
*num_names
, char ***names
,
1243 uint32
**name_types
)
1245 prs_struct qbuf
, rbuf
;
1246 SAMR_Q_LOOKUP_RIDS q
;
1247 SAMR_R_LOOKUP_RIDS r
;
1248 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1251 DEBUG(10,("cli_samr_lookup_rids\n"));
1253 if (num_rids
> 1000) {
1254 DEBUG(2, ("cli_samr_lookup_rids: warning: NT4 can crash if "
1255 "more than ~1000 rids are looked up at once.\n"));
1261 /* Marshall data and send request */
1263 init_samr_q_lookup_rids(mem_ctx
, &q
, domain_pol
, 1000, num_rids
, rids
);
1265 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_LOOKUP_RIDS
,
1268 samr_io_q_lookup_rids
,
1269 samr_io_r_lookup_rids
,
1270 NT_STATUS_UNSUCCESSFUL
);
1272 /* Return output parameters */
1276 if (!NT_STATUS_IS_OK(result
) &&
1277 !NT_STATUS_EQUAL(result
, STATUS_SOME_UNMAPPED
))
1280 if (r
.num_names1
== 0) {
1286 *num_names
= r
.num_names1
;
1287 *names
= TALLOC_ARRAY(mem_ctx
, char *, r
.num_names1
);
1288 *name_types
= TALLOC_ARRAY(mem_ctx
, uint32
, r
.num_names1
);
1290 if ((*names
== NULL
) || (*name_types
== NULL
)) {
1291 TALLOC_FREE(*names
);
1292 TALLOC_FREE(*name_types
);
1293 return NT_STATUS_NO_MEMORY
;
1296 for (i
= 0; i
< r
.num_names1
; i
++) {
1299 unistr2_to_ascii(tmp
, &r
.uni_name
[i
], sizeof(tmp
));
1300 (*names
)[i
] = talloc_strdup(mem_ctx
, tmp
);
1301 (*name_types
)[i
] = r
.type
[i
];
1311 NTSTATUS
rpccli_samr_lookup_names(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
1312 POLICY_HND
*domain_pol
, uint32 flags
,
1313 uint32 num_names
, const char **names
,
1314 uint32
*num_rids
, uint32
**rids
,
1317 prs_struct qbuf
, rbuf
;
1318 SAMR_Q_LOOKUP_NAMES q
;
1319 SAMR_R_LOOKUP_NAMES r
;
1320 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1323 DEBUG(10,("cli_samr_lookup_names\n"));
1328 /* Marshall data and send request */
1330 init_samr_q_lookup_names(mem_ctx
, &q
, domain_pol
, flags
,
1333 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_LOOKUP_NAMES
,
1336 samr_io_q_lookup_names
,
1337 samr_io_r_lookup_names
,
1338 NT_STATUS_UNSUCCESSFUL
);
1340 /* Return output parameters */
1342 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
1346 if (r
.num_rids1
== 0) {
1351 *num_rids
= r
.num_rids1
;
1352 *rids
= TALLOC_ARRAY(mem_ctx
, uint32
, r
.num_rids1
);
1353 *rid_types
= TALLOC_ARRAY(mem_ctx
, uint32
, r
.num_rids1
);
1355 if ((*rids
== NULL
) || (*rid_types
== NULL
)) {
1357 TALLOC_FREE(*rid_types
);
1358 return NT_STATUS_NO_MEMORY
;
1361 for (i
= 0; i
< r
.num_rids1
; i
++) {
1362 (*rids
)[i
] = r
.rids
[i
];
1363 (*rid_types
)[i
] = r
.types
[i
];
1373 NTSTATUS
rpccli_samr_set_userinfo(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
1374 const POLICY_HND
*user_pol
, uint16 switch_value
,
1375 DATA_BLOB
*sess_key
, SAM_USERINFO_CTR
*ctr
)
1377 prs_struct qbuf
, rbuf
;
1378 SAMR_Q_SET_USERINFO q
;
1379 SAMR_R_SET_USERINFO r
;
1380 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1382 DEBUG(10,("cli_samr_set_userinfo\n"));
1387 if (!sess_key
->length
) {
1388 DEBUG(1, ("No user session key\n"));
1389 return NT_STATUS_NO_USER_SESSION_KEY
;
1392 /* Initialise parse structures */
1394 prs_init(&qbuf
, RPC_MAX_PDU_FRAG_LEN
, mem_ctx
, MARSHALL
);
1395 prs_init(&rbuf
, 0, mem_ctx
, UNMARSHALL
);
1397 /* Marshall data and send request */
1401 init_samr_q_set_userinfo(&q
, user_pol
, sess_key
, switch_value
,
1404 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_SET_USERINFO
,
1407 samr_io_q_set_userinfo
,
1408 samr_io_r_set_userinfo
,
1409 NT_STATUS_UNSUCCESSFUL
);
1411 /* Return output parameters */
1413 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
1424 NTSTATUS
rpccli_samr_set_userinfo2(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
1425 const POLICY_HND
*user_pol
, uint16 switch_value
,
1426 DATA_BLOB
*sess_key
, SAM_USERINFO_CTR
*ctr
)
1428 prs_struct qbuf
, rbuf
;
1429 SAMR_Q_SET_USERINFO2 q
;
1430 SAMR_R_SET_USERINFO2 r
;
1431 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1433 DEBUG(10,("cli_samr_set_userinfo2\n"));
1435 if (!sess_key
->length
) {
1436 DEBUG(1, ("No user session key\n"));
1437 return NT_STATUS_NO_USER_SESSION_KEY
;
1443 /* Marshall data and send request */
1445 init_samr_q_set_userinfo2(&q
, user_pol
, sess_key
, switch_value
, ctr
);
1447 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_SET_USERINFO2
,
1450 samr_io_q_set_userinfo2
,
1451 samr_io_r_set_userinfo2
,
1452 NT_STATUS_UNSUCCESSFUL
);
1454 /* Return output parameters */
1456 if (!NT_STATUS_IS_OK(result
= r
.status
)) {
1465 /* Remove foreign SID */
1467 NTSTATUS
rpccli_samr_remove_sid_foreign_domain(struct rpc_pipe_client
*cli
,
1468 TALLOC_CTX
*mem_ctx
,
1469 POLICY_HND
*user_pol
,
1472 prs_struct qbuf
, rbuf
;
1473 SAMR_Q_REMOVE_SID_FOREIGN_DOMAIN q
;
1474 SAMR_R_REMOVE_SID_FOREIGN_DOMAIN r
;
1475 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1477 DEBUG(10,("cli_samr_remove_sid_foreign_domain\n"));
1482 /* Marshall data and send request */
1484 init_samr_q_remove_sid_foreign_domain(&q
, user_pol
, sid
);
1486 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_REMOVE_SID_FOREIGN_DOMAIN
,
1489 samr_io_q_remove_sid_foreign_domain
,
1490 samr_io_r_remove_sid_foreign_domain
,
1491 NT_STATUS_UNSUCCESSFUL
);
1493 /* Return output parameters */
1500 /* Query user security object */
1502 NTSTATUS
rpccli_samr_query_sec_obj(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
1503 POLICY_HND
*user_pol
, uint32 sec_info
,
1504 TALLOC_CTX
*ctx
, SEC_DESC_BUF
**sec_desc_buf
)
1506 prs_struct qbuf
, rbuf
;
1507 SAMR_Q_QUERY_SEC_OBJ q
;
1508 SAMR_R_QUERY_SEC_OBJ r
;
1509 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1511 DEBUG(10,("cli_samr_query_sec_obj\n"));
1516 /* Marshall data and send request */
1518 init_samr_q_query_sec_obj(&q
, user_pol
, sec_info
);
1520 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_QUERY_SEC_OBJECT
,
1523 samr_io_q_query_sec_obj
,
1524 samr_io_r_query_sec_obj
,
1525 NT_STATUS_UNSUCCESSFUL
);
1527 /* Return output parameters */
1530 *sec_desc_buf
=dup_sec_desc_buf(ctx
, r
.buf
);
1535 /* Set user security object */
1537 NTSTATUS
rpccli_samr_set_sec_obj(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
1538 POLICY_HND
*user_pol
, uint32 sec_info
,
1539 SEC_DESC_BUF
*sec_desc_buf
)
1541 prs_struct qbuf
, rbuf
;
1542 SAMR_Q_SET_SEC_OBJ q
;
1543 SAMR_R_SET_SEC_OBJ r
;
1544 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1546 DEBUG(10,("cli_samr_set_sec_obj\n"));
1551 /* Marshall data and send request */
1553 init_samr_q_set_sec_obj(&q
, user_pol
, sec_info
, sec_desc_buf
);
1555 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_SET_SEC_OBJECT
,
1558 samr_io_q_set_sec_obj
,
1559 samr_io_r_set_sec_obj
,
1560 NT_STATUS_UNSUCCESSFUL
);
1562 /* Return output parameters */
1569 /* Lookup Domain Name */
1571 NTSTATUS
rpccli_samr_lookup_domain(struct rpc_pipe_client
*cli
, TALLOC_CTX
*mem_ctx
,
1572 POLICY_HND
*user_pol
, char *domain_name
,
1575 prs_struct qbuf
, rbuf
;
1576 SAMR_Q_LOOKUP_DOMAIN q
;
1577 SAMR_R_LOOKUP_DOMAIN r
;
1578 NTSTATUS result
= NT_STATUS_UNSUCCESSFUL
;
1580 DEBUG(10,("cli_samr_lookup_domain\n"));
1585 /* Marshall data and send request */
1587 init_samr_q_lookup_domain(&q
, user_pol
, domain_name
);
1589 CLI_DO_RPC(cli
, mem_ctx
, PI_SAMR
, SAMR_LOOKUP_DOMAIN
,
1592 samr_io_q_lookup_domain
,
1593 samr_io_r_lookup_domain
,
1594 NT_STATUS_UNSUCCESSFUL
);
1596 /* Return output parameters */
1600 if (NT_STATUS_IS_OK(result
))
1601 sid_copy(sid
, &r
.dom_sid
.sid
);