2 * Unix SMB/CIFS implementation.
3 * RPC Pipe client / server routines
4 * Copyright (C) Andrew Tridgell 1992-1997,
5 * Copyright (C) Luke Kenneth Casson Leighton 1996-1997,
6 * Copyright (C) Paul Ashton 1997,
7 * Copyright (C) Marc Jacobsen 1999,
8 * Copyright (C) Jeremy Allison 2001-2008,
9 * Copyright (C) Jean François Micouleau 1998-2001,
10 * Copyright (C) Jim McDonough <jmcd@us.ibm.com> 2002,
11 * Copyright (C) Gerald (Jerry) Carter 2003-2004,
12 * Copyright (C) Simo Sorce 2003.
13 * Copyright (C) Volker Lendecke 2005.
14 * Copyright (C) Guenther Deschner 2008.
16 * This program is free software; you can redistribute it and/or modify
17 * it under the terms of the GNU General Public License as published by
18 * the Free Software Foundation; either version 3 of the License, or
19 * (at your option) any later version.
21 * This program is distributed in the hope that it will be useful,
22 * but WITHOUT ANY WARRANTY; without even the implied warranty of
23 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 * GNU General Public License for more details.
26 * You should have received a copy of the GNU General Public License
27 * along with this program; if not, see <http://www.gnu.org/licenses/>.
31 * This is the implementation of the SAMR code.
37 #define DBGC_CLASS DBGC_RPC_SRV
39 #define SAMR_USR_RIGHTS_WRITE_PW \
40 ( READ_CONTROL_ACCESS | \
41 SA_RIGHT_USER_CHANGE_PASSWORD | \
42 SA_RIGHT_USER_SET_LOC_COM )
43 #define SAMR_USR_RIGHTS_CANT_WRITE_PW \
44 ( READ_CONTROL_ACCESS | SA_RIGHT_USER_SET_LOC_COM )
46 #define DISP_INFO_CACHE_TIMEOUT 10
48 typedef struct disp_info
{
49 DOM_SID sid
; /* identify which domain this is. */
50 bool builtin_domain
; /* Quick flag to check if this is the builtin domain. */
51 struct pdb_search
*users
; /* querydispinfo 1 and 4 */
52 struct pdb_search
*machines
; /* querydispinfo 2 */
53 struct pdb_search
*groups
; /* querydispinfo 3 and 5, enumgroups */
54 struct pdb_search
*aliases
; /* enumaliases */
57 struct pdb_search
*enum_users
; /* enumusers with a mask */
59 struct timed_event
*cache_timeout_event
; /* cache idle timeout
63 /* We keep a static list of these by SID as modern clients close down
64 all resources between each request in a complete enumeration. */
67 /* for use by the \PIPE\samr policy */
69 bool builtin_domain
; /* Quick flag to check if this is the builtin domain. */
70 uint32 status
; /* some sort of flag. best to record it. comes from opnum 0x39 */
76 static const struct generic_mapping sam_generic_mapping
= {
77 GENERIC_RIGHTS_SAM_READ
,
78 GENERIC_RIGHTS_SAM_WRITE
,
79 GENERIC_RIGHTS_SAM_EXECUTE
,
80 GENERIC_RIGHTS_SAM_ALL_ACCESS
};
81 static const struct generic_mapping dom_generic_mapping
= {
82 GENERIC_RIGHTS_DOMAIN_READ
,
83 GENERIC_RIGHTS_DOMAIN_WRITE
,
84 GENERIC_RIGHTS_DOMAIN_EXECUTE
,
85 GENERIC_RIGHTS_DOMAIN_ALL_ACCESS
};
86 static const struct generic_mapping usr_generic_mapping
= {
87 GENERIC_RIGHTS_USER_READ
,
88 GENERIC_RIGHTS_USER_WRITE
,
89 GENERIC_RIGHTS_USER_EXECUTE
,
90 GENERIC_RIGHTS_USER_ALL_ACCESS
};
91 static const struct generic_mapping usr_nopwchange_generic_mapping
= {
92 GENERIC_RIGHTS_USER_READ
,
93 GENERIC_RIGHTS_USER_WRITE
,
94 GENERIC_RIGHTS_USER_EXECUTE
& ~SA_RIGHT_USER_CHANGE_PASSWORD
,
95 GENERIC_RIGHTS_USER_ALL_ACCESS
};
96 static const struct generic_mapping grp_generic_mapping
= {
97 GENERIC_RIGHTS_GROUP_READ
,
98 GENERIC_RIGHTS_GROUP_WRITE
,
99 GENERIC_RIGHTS_GROUP_EXECUTE
,
100 GENERIC_RIGHTS_GROUP_ALL_ACCESS
};
101 static const struct generic_mapping ali_generic_mapping
= {
102 GENERIC_RIGHTS_ALIAS_READ
,
103 GENERIC_RIGHTS_ALIAS_WRITE
,
104 GENERIC_RIGHTS_ALIAS_EXECUTE
,
105 GENERIC_RIGHTS_ALIAS_ALL_ACCESS
};
107 /*******************************************************************
108 *******************************************************************/
110 static NTSTATUS
make_samr_object_sd( TALLOC_CTX
*ctx
, SEC_DESC
**psd
, size_t *sd_size
,
111 const struct generic_mapping
*map
,
112 DOM_SID
*sid
, uint32 sid_access
)
114 DOM_SID domadmin_sid
;
115 SEC_ACE ace
[5]; /* at most 5 entries */
121 /* basic access for Everyone */
123 init_sec_access(&mask
, map
->generic_execute
| map
->generic_read
);
124 init_sec_ace(&ace
[i
++], &global_sid_World
, SEC_ACE_TYPE_ACCESS_ALLOWED
, mask
, 0);
126 /* add Full Access 'BUILTIN\Administrators' and 'BUILTIN\Account Operators */
128 init_sec_access(&mask
, map
->generic_all
);
130 init_sec_ace(&ace
[i
++], &global_sid_Builtin_Administrators
, SEC_ACE_TYPE_ACCESS_ALLOWED
, mask
, 0);
131 init_sec_ace(&ace
[i
++], &global_sid_Builtin_Account_Operators
, SEC_ACE_TYPE_ACCESS_ALLOWED
, mask
, 0);
133 /* Add Full Access for Domain Admins if we are a DC */
136 sid_copy( &domadmin_sid
, get_global_sam_sid() );
137 sid_append_rid( &domadmin_sid
, DOMAIN_GROUP_RID_ADMINS
);
138 init_sec_ace(&ace
[i
++], &domadmin_sid
, SEC_ACE_TYPE_ACCESS_ALLOWED
, mask
, 0);
141 /* if we have a sid, give it some special access */
144 init_sec_access( &mask
, sid_access
);
145 init_sec_ace(&ace
[i
++], sid
, SEC_ACE_TYPE_ACCESS_ALLOWED
, mask
, 0);
148 /* create the security descriptor */
150 if ((psa
= make_sec_acl(ctx
, NT4_ACL_REVISION
, i
, ace
)) == NULL
)
151 return NT_STATUS_NO_MEMORY
;
153 if ((*psd
= make_sec_desc(ctx
, SECURITY_DESCRIPTOR_REVISION_1
,
154 SEC_DESC_SELF_RELATIVE
, NULL
, NULL
, NULL
,
155 psa
, sd_size
)) == NULL
)
156 return NT_STATUS_NO_MEMORY
;
161 /*******************************************************************
162 Checks if access to an object should be granted, and returns that
163 level of access for further checks.
164 ********************************************************************/
166 static NTSTATUS
access_check_samr_object( SEC_DESC
*psd
, NT_USER_TOKEN
*token
,
167 SE_PRIV
*rights
, uint32 rights_mask
,
168 uint32 des_access
, uint32
*acc_granted
,
171 NTSTATUS status
= NT_STATUS_ACCESS_DENIED
;
172 uint32 saved_mask
= 0;
174 /* check privileges; certain SAM access bits should be overridden
175 by privileges (mostly having to do with creating/modifying/deleting
178 if ( rights
&& user_has_any_privilege( token
, rights
) ) {
180 saved_mask
= (des_access
& rights_mask
);
181 des_access
&= ~saved_mask
;
183 DEBUG(4,("access_check_samr_object: user rights access mask [0x%x]\n",
188 /* check the security descriptor first */
190 if ( se_access_check(psd
, token
, des_access
, acc_granted
, &status
) )
193 /* give root a free pass */
195 if ( geteuid() == sec_initial_uid() ) {
197 DEBUG(4,("%s: ACCESS should be DENIED (requested: %#010x)\n", debug
, des_access
));
198 DEBUGADD(4,("but overritten by euid == sec_initial_uid()\n"));
200 *acc_granted
= des_access
;
202 status
= NT_STATUS_OK
;
208 /* add in any bits saved during the privilege check (only
209 matters is status is ok) */
211 *acc_granted
|= rights_mask
;
213 DEBUG(4,("%s: access %s (requested: 0x%08x, granted: 0x%08x)\n",
214 debug
, NT_STATUS_IS_OK(status
) ? "GRANTED" : "DENIED",
215 des_access
, *acc_granted
));
220 /*******************************************************************
221 Checks if access to a function can be granted
222 ********************************************************************/
224 static NTSTATUS
access_check_samr_function(uint32 acc_granted
, uint32 acc_required
, const char *debug
)
226 DEBUG(5,("%s: access check ((granted: %#010x; required: %#010x)\n",
227 debug
, acc_granted
, acc_required
));
229 /* check the security descriptor first */
231 if ( (acc_granted
&acc_required
) == acc_required
)
234 /* give root a free pass */
236 if (geteuid() == sec_initial_uid()) {
238 DEBUG(4,("%s: ACCESS should be DENIED (granted: %#010x; required: %#010x)\n",
239 debug
, acc_granted
, acc_required
));
240 DEBUGADD(4,("but overwritten by euid == 0\n"));
245 DEBUG(2,("%s: ACCESS DENIED (granted: %#010x; required: %#010x)\n",
246 debug
, acc_granted
, acc_required
));
248 return NT_STATUS_ACCESS_DENIED
;
251 /*******************************************************************
252 Map any MAXIMUM_ALLOWED_ACCESS request to a valid access set.
253 ********************************************************************/
255 static void map_max_allowed_access(const NT_USER_TOKEN
*token
,
256 uint32_t *pacc_requested
)
258 if (!((*pacc_requested
) & MAXIMUM_ALLOWED_ACCESS
)) {
261 *pacc_requested
&= ~MAXIMUM_ALLOWED_ACCESS
;
263 /* At least try for generic read. */
264 *pacc_requested
= GENERIC_READ_ACCESS
;
266 /* root gets anything. */
267 if (geteuid() == sec_initial_uid()) {
268 *pacc_requested
|= GENERIC_ALL_ACCESS
;
272 /* Full Access for 'BUILTIN\Administrators' and 'BUILTIN\Account Operators */
274 if (is_sid_in_token(token
, &global_sid_Builtin_Administrators
) ||
275 is_sid_in_token(token
, &global_sid_Builtin_Account_Operators
)) {
276 *pacc_requested
|= GENERIC_ALL_ACCESS
;
280 /* Full access for DOMAIN\Domain Admins. */
282 DOM_SID domadmin_sid
;
283 sid_copy( &domadmin_sid
, get_global_sam_sid() );
284 sid_append_rid( &domadmin_sid
, DOMAIN_GROUP_RID_ADMINS
);
285 if (is_sid_in_token(token
, &domadmin_sid
)) {
286 *pacc_requested
|= GENERIC_ALL_ACCESS
;
290 /* TODO ! Check privileges. */
293 /*******************************************************************
294 Fetch or create a dispinfo struct.
295 ********************************************************************/
297 static DISP_INFO
*get_samr_dispinfo_by_sid(DOM_SID
*psid
)
300 * We do a static cache for DISP_INFO's here. Explanation can be found
301 * in Jeremy's checkin message to r11793:
303 * Fix the SAMR cache so it works across completely insane
304 * client behaviour (ie.:
305 * open pipe/open SAMR handle/enumerate 0 - 1024
306 * close SAMR handle, close pipe.
307 * open pipe/open SAMR handle/enumerate 1024 - 2048...
308 * close SAMR handle, close pipe.
309 * And on ad-nausium. Amazing.... probably object-oriented
310 * client side programming in action yet again.
311 * This change should *massively* improve performance when
312 * enumerating users from an LDAP database.
315 * "Our" and the builtin domain are the only ones where we ever
316 * enumerate stuff, so just cache 2 entries.
319 static struct disp_info builtin_dispinfo
;
320 static struct disp_info domain_dispinfo
;
322 /* There are two cases to consider here:
323 1) The SID is a domain SID and we look for an equality match, or
324 2) This is an account SID and so we return the DISP_INFO* for our
331 if (sid_check_is_builtin(psid
) || sid_check_is_in_builtin(psid
)) {
333 * Necessary only once, but it does not really hurt.
335 sid_copy(&builtin_dispinfo
.sid
, &global_sid_Builtin
);
337 return &builtin_dispinfo
;
340 if (sid_check_is_domain(psid
) || sid_check_is_in_our_domain(psid
)) {
342 * Necessary only once, but it does not really hurt.
344 sid_copy(&domain_dispinfo
.sid
, get_global_sam_sid());
346 return &domain_dispinfo
;
352 /*******************************************************************
353 Create a samr_info struct.
354 ********************************************************************/
356 static struct samr_info
*get_samr_info_by_sid(DOM_SID
*psid
)
358 struct samr_info
*info
;
363 sid_to_fstring(sid_str
, psid
);
365 fstrcpy(sid_str
,"(NULL)");
368 mem_ctx
= talloc_init("samr_info for domain sid %s", sid_str
);
370 if ((info
= TALLOC_ZERO_P(mem_ctx
, struct samr_info
)) == NULL
)
373 DEBUG(10,("get_samr_info_by_sid: created new info for sid %s\n", sid_str
));
375 sid_copy( &info
->sid
, psid
);
376 info
->builtin_domain
= sid_check_is_builtin(psid
);
378 DEBUG(10,("get_samr_info_by_sid: created new info for NULL sid.\n"));
379 info
->builtin_domain
= False
;
381 info
->mem_ctx
= mem_ctx
;
383 info
->disp_info
= get_samr_dispinfo_by_sid(psid
);
388 /*******************************************************************
389 Function to free the per SID data.
390 ********************************************************************/
392 static void free_samr_cache(DISP_INFO
*disp_info
)
394 DEBUG(10, ("free_samr_cache: deleting cache for SID %s\n",
395 sid_string_dbg(&disp_info
->sid
)));
397 /* We need to become root here because the paged search might have to
398 * tell the LDAP server we're not interested in the rest anymore. */
402 if (disp_info
->users
) {
403 DEBUG(10,("free_samr_cache: deleting users cache\n"));
404 pdb_search_destroy(disp_info
->users
);
405 disp_info
->users
= NULL
;
407 if (disp_info
->machines
) {
408 DEBUG(10,("free_samr_cache: deleting machines cache\n"));
409 pdb_search_destroy(disp_info
->machines
);
410 disp_info
->machines
= NULL
;
412 if (disp_info
->groups
) {
413 DEBUG(10,("free_samr_cache: deleting groups cache\n"));
414 pdb_search_destroy(disp_info
->groups
);
415 disp_info
->groups
= NULL
;
417 if (disp_info
->aliases
) {
418 DEBUG(10,("free_samr_cache: deleting aliases cache\n"));
419 pdb_search_destroy(disp_info
->aliases
);
420 disp_info
->aliases
= NULL
;
422 if (disp_info
->enum_users
) {
423 DEBUG(10,("free_samr_cache: deleting enum_users cache\n"));
424 pdb_search_destroy(disp_info
->enum_users
);
425 disp_info
->enum_users
= NULL
;
427 disp_info
->enum_acb_mask
= 0;
432 /*******************************************************************
433 Function to free the per handle data.
434 ********************************************************************/
436 static void free_samr_info(void *ptr
)
438 struct samr_info
*info
=(struct samr_info
*) ptr
;
440 /* Only free the dispinfo cache if no one bothered to set up
443 if (info
->disp_info
&& info
->disp_info
->cache_timeout_event
== NULL
) {
444 free_samr_cache(info
->disp_info
);
447 talloc_destroy(info
->mem_ctx
);
450 /*******************************************************************
451 Idle event handler. Throw away the disp info cache.
452 ********************************************************************/
454 static void disp_info_cache_idle_timeout_handler(struct event_context
*ev_ctx
,
455 struct timed_event
*te
,
456 const struct timeval
*now
,
459 DISP_INFO
*disp_info
= (DISP_INFO
*)private_data
;
461 TALLOC_FREE(disp_info
->cache_timeout_event
);
463 DEBUG(10, ("disp_info_cache_idle_timeout_handler: caching timed "
465 free_samr_cache(disp_info
);
468 /*******************************************************************
469 Setup cache removal idle event handler.
470 ********************************************************************/
472 static void set_disp_info_cache_timeout(DISP_INFO
*disp_info
, time_t secs_fromnow
)
474 /* Remove any pending timeout and update. */
476 TALLOC_FREE(disp_info
->cache_timeout_event
);
478 DEBUG(10,("set_disp_info_cache_timeout: caching enumeration for "
479 "SID %s for %u seconds\n", sid_string_dbg(&disp_info
->sid
),
480 (unsigned int)secs_fromnow
));
482 disp_info
->cache_timeout_event
= event_add_timed(
483 smbd_event_context(), NULL
,
484 timeval_current_ofs(secs_fromnow
, 0),
485 "disp_info_cache_idle_timeout_handler",
486 disp_info_cache_idle_timeout_handler
, (void *)disp_info
);
489 /*******************************************************************
490 Force flush any cache. We do this on any samr_set_xxx call.
491 We must also remove the timeout handler.
492 ********************************************************************/
494 static void force_flush_samr_cache(DISP_INFO
*disp_info
)
496 if ((disp_info
== NULL
) || (disp_info
->cache_timeout_event
== NULL
)) {
500 DEBUG(10,("force_flush_samr_cache: clearing idle event\n"));
501 TALLOC_FREE(disp_info
->cache_timeout_event
);
502 free_samr_cache(disp_info
);
505 /*******************************************************************
506 Ensure password info is never given out. Paranioa... JRA.
507 ********************************************************************/
509 static void samr_clear_sam_passwd(struct samu
*sam_pass
)
515 /* These now zero out the old password */
517 pdb_set_lanman_passwd(sam_pass
, NULL
, PDB_DEFAULT
);
518 pdb_set_nt_passwd(sam_pass
, NULL
, PDB_DEFAULT
);
521 static uint32
count_sam_users(struct disp_info
*info
, uint32 acct_flags
)
523 struct samr_displayentry
*entry
;
525 if (info
->builtin_domain
) {
526 /* No users in builtin. */
530 if (info
->users
== NULL
) {
531 info
->users
= pdb_search_users(acct_flags
);
532 if (info
->users
== NULL
) {
536 /* Fetch the last possible entry, thus trigger an enumeration */
537 pdb_search_entries(info
->users
, 0xffffffff, 1, &entry
);
539 /* Ensure we cache this enumeration. */
540 set_disp_info_cache_timeout(info
, DISP_INFO_CACHE_TIMEOUT
);
542 return info
->users
->num_entries
;
545 static uint32
count_sam_groups(struct disp_info
*info
)
547 struct samr_displayentry
*entry
;
549 if (info
->builtin_domain
) {
550 /* No groups in builtin. */
554 if (info
->groups
== NULL
) {
555 info
->groups
= pdb_search_groups();
556 if (info
->groups
== NULL
) {
560 /* Fetch the last possible entry, thus trigger an enumeration */
561 pdb_search_entries(info
->groups
, 0xffffffff, 1, &entry
);
563 /* Ensure we cache this enumeration. */
564 set_disp_info_cache_timeout(info
, DISP_INFO_CACHE_TIMEOUT
);
566 return info
->groups
->num_entries
;
569 static uint32
count_sam_aliases(struct disp_info
*info
)
571 struct samr_displayentry
*entry
;
573 if (info
->aliases
== NULL
) {
574 info
->aliases
= pdb_search_aliases(&info
->sid
);
575 if (info
->aliases
== NULL
) {
579 /* Fetch the last possible entry, thus trigger an enumeration */
580 pdb_search_entries(info
->aliases
, 0xffffffff, 1, &entry
);
582 /* Ensure we cache this enumeration. */
583 set_disp_info_cache_timeout(info
, DISP_INFO_CACHE_TIMEOUT
);
585 return info
->aliases
->num_entries
;
588 /*******************************************************************
590 ********************************************************************/
592 NTSTATUS
_samr_Close(pipes_struct
*p
, struct samr_Close
*r
)
594 if (!close_policy_hnd(p
, r
->in
.handle
)) {
595 return NT_STATUS_INVALID_HANDLE
;
598 ZERO_STRUCTP(r
->out
.handle
);
603 /*******************************************************************
605 ********************************************************************/
607 NTSTATUS
_samr_OpenDomain(pipes_struct
*p
,
608 struct samr_OpenDomain
*r
)
610 struct samr_info
*info
;
611 SEC_DESC
*psd
= NULL
;
613 uint32 des_access
= r
->in
.access_mask
;
618 /* find the connection policy handle. */
620 if ( !find_policy_by_hnd(p
, r
->in
.connect_handle
, (void**)(void *)&info
) )
621 return NT_STATUS_INVALID_HANDLE
;
623 status
= access_check_samr_function(info
->acc_granted
,
624 SA_RIGHT_SAM_OPEN_DOMAIN
,
625 "_samr_OpenDomain" );
627 if ( !NT_STATUS_IS_OK(status
) )
630 /*check if access can be granted as requested by client. */
631 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
633 make_samr_object_sd( p
->mem_ctx
, &psd
, &sd_size
, &dom_generic_mapping
, NULL
, 0 );
634 se_map_generic( &des_access
, &dom_generic_mapping
);
636 se_priv_copy( &se_rights
, &se_machine_account
);
637 se_priv_add( &se_rights
, &se_add_users
);
639 status
= access_check_samr_object( psd
, p
->pipe_user
.nt_user_token
,
640 &se_rights
, GENERIC_RIGHTS_DOMAIN_WRITE
, des_access
,
641 &acc_granted
, "_samr_OpenDomain" );
643 if ( !NT_STATUS_IS_OK(status
) )
646 if (!sid_check_is_domain(r
->in
.sid
) &&
647 !sid_check_is_builtin(r
->in
.sid
)) {
648 return NT_STATUS_NO_SUCH_DOMAIN
;
651 /* associate the domain SID with the (unique) handle. */
652 if ((info
= get_samr_info_by_sid(r
->in
.sid
))==NULL
)
653 return NT_STATUS_NO_MEMORY
;
654 info
->acc_granted
= acc_granted
;
656 /* get a (unique) handle. open a policy on it. */
657 if (!create_policy_hnd(p
, r
->out
.domain_handle
, free_samr_info
, (void *)info
))
658 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
660 DEBUG(5,("_samr_OpenDomain: %d\n", __LINE__
));
665 /*******************************************************************
667 ********************************************************************/
669 NTSTATUS
_samr_GetUserPwInfo(pipes_struct
*p
,
670 struct samr_GetUserPwInfo
*r
)
672 struct samr_info
*info
= NULL
;
673 enum lsa_SidType sid_type
;
674 uint32_t min_password_length
= 0;
675 uint32_t password_properties
= 0;
679 DEBUG(5,("_samr_GetUserPwInfo: %d\n", __LINE__
));
681 /* find the policy handle. open a policy on it. */
682 if (!find_policy_by_hnd(p
, r
->in
.user_handle
, (void **)(void *)&info
)) {
683 return NT_STATUS_INVALID_HANDLE
;
686 status
= access_check_samr_function(info
->acc_granted
,
687 SAMR_USER_ACCESS_GET_ATTRIBUTES
,
688 "_samr_GetUserPwInfo" );
689 if (!NT_STATUS_IS_OK(status
)) {
693 if (!sid_check_is_in_our_domain(&info
->sid
)) {
694 return NT_STATUS_OBJECT_TYPE_MISMATCH
;
698 ret
= lookup_sid(p
->mem_ctx
, &info
->sid
, NULL
, NULL
, &sid_type
);
701 return NT_STATUS_NO_SUCH_USER
;
707 pdb_get_account_policy(AP_MIN_PASSWORD_LEN
,
708 &min_password_length
);
709 pdb_get_account_policy(AP_USER_MUST_LOGON_TO_CHG_PASS
,
710 &password_properties
);
713 if (lp_check_password_script() && *lp_check_password_script()) {
714 password_properties
|= DOMAIN_PASSWORD_COMPLEX
;
722 r
->out
.info
->min_password_length
= min_password_length
;
723 r
->out
.info
->password_properties
= password_properties
;
725 DEBUG(5,("_samr_GetUserPwInfo: %d\n", __LINE__
));
730 /*******************************************************************
731 ********************************************************************/
733 static bool get_lsa_policy_samr_sid( pipes_struct
*p
, POLICY_HND
*pol
,
734 DOM_SID
*sid
, uint32
*acc_granted
,
735 DISP_INFO
**ppdisp_info
)
737 struct samr_info
*info
= NULL
;
739 /* find the policy handle. open a policy on it. */
740 if (!find_policy_by_hnd(p
, pol
, (void **)(void *)&info
))
747 *acc_granted
= info
->acc_granted
;
749 *ppdisp_info
= info
->disp_info
;
755 /*******************************************************************
757 ********************************************************************/
759 NTSTATUS
_samr_SetSecurity(pipes_struct
*p
,
760 struct samr_SetSecurity
*r
)
763 uint32 acc_granted
, i
;
766 struct samu
*sampass
=NULL
;
769 if (!get_lsa_policy_samr_sid(p
, r
->in
.handle
, &pol_sid
, &acc_granted
, NULL
))
770 return NT_STATUS_INVALID_HANDLE
;
772 if (!(sampass
= samu_new( p
->mem_ctx
))) {
773 DEBUG(0,("No memory!\n"));
774 return NT_STATUS_NO_MEMORY
;
777 /* get the user record */
779 ret
= pdb_getsampwsid(sampass
, &pol_sid
);
783 DEBUG(4, ("User %s not found\n", sid_string_dbg(&pol_sid
)));
784 TALLOC_FREE(sampass
);
785 return NT_STATUS_INVALID_HANDLE
;
788 dacl
= r
->in
.sdbuf
->sd
->dacl
;
789 for (i
=0; i
< dacl
->num_aces
; i
++) {
790 if (sid_equal(&pol_sid
, &dacl
->aces
[i
].trustee
)) {
791 ret
= pdb_set_pass_can_change(sampass
,
792 (dacl
->aces
[i
].access_mask
&
793 SA_RIGHT_USER_CHANGE_PASSWORD
) ?
800 TALLOC_FREE(sampass
);
801 return NT_STATUS_ACCESS_DENIED
;
804 status
= access_check_samr_function(acc_granted
,
805 SA_RIGHT_USER_SET_ATTRIBUTES
,
806 "_samr_SetSecurity");
807 if (NT_STATUS_IS_OK(status
)) {
809 status
= pdb_update_sam_account(sampass
);
813 TALLOC_FREE(sampass
);
818 /*******************************************************************
819 build correct perms based on policies and password times for _samr_query_sec_obj
820 *******************************************************************/
821 static bool check_change_pw_access(TALLOC_CTX
*mem_ctx
, DOM_SID
*user_sid
)
823 struct samu
*sampass
=NULL
;
826 if ( !(sampass
= samu_new( mem_ctx
)) ) {
827 DEBUG(0,("No memory!\n"));
832 ret
= pdb_getsampwsid(sampass
, user_sid
);
836 DEBUG(4,("User %s not found\n", sid_string_dbg(user_sid
)));
837 TALLOC_FREE(sampass
);
841 DEBUG(3,("User:[%s]\n", pdb_get_username(sampass
) ));
843 if (pdb_get_pass_can_change(sampass
)) {
844 TALLOC_FREE(sampass
);
847 TALLOC_FREE(sampass
);
852 /*******************************************************************
854 ********************************************************************/
856 NTSTATUS
_samr_QuerySecurity(pipes_struct
*p
,
857 struct samr_QuerySecurity
*r
)
861 SEC_DESC
* psd
= NULL
;
866 if (!get_lsa_policy_samr_sid(p
, r
->in
.handle
, &pol_sid
, &acc_granted
, NULL
))
867 return NT_STATUS_INVALID_HANDLE
;
869 DEBUG(10,("_samr_QuerySecurity: querying security on SID: %s\n",
870 sid_string_dbg(&pol_sid
)));
872 status
= access_check_samr_function(acc_granted
,
873 STD_RIGHT_READ_CONTROL_ACCESS
,
874 "_samr_QuerySecurity");
875 if (!NT_STATUS_IS_OK(status
)) {
879 /* Check what typ of SID is beeing queried (e.g Domain SID, User SID, Group SID) */
881 /* To query the security of the SAM it self an invalid SID with S-0-0 is passed to this function */
882 if (pol_sid
.sid_rev_num
== 0) {
883 DEBUG(5,("_samr_QuerySecurity: querying security on SAM\n"));
884 status
= make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &sam_generic_mapping
, NULL
, 0);
885 } else if (sid_equal(&pol_sid
,get_global_sam_sid())) {
886 /* check if it is our domain SID */
887 DEBUG(5,("_samr_QuerySecurity: querying security on Domain "
888 "with SID: %s\n", sid_string_dbg(&pol_sid
)));
889 status
= make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &dom_generic_mapping
, NULL
, 0);
890 } else if (sid_equal(&pol_sid
,&global_sid_Builtin
)) {
891 /* check if it is the Builtin Domain */
892 /* TODO: Builtin probably needs a different SD with restricted write access*/
893 DEBUG(5,("_samr_QuerySecurity: querying security on Builtin "
894 "Domain with SID: %s\n", sid_string_dbg(&pol_sid
)));
895 status
= make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &dom_generic_mapping
, NULL
, 0);
896 } else if (sid_check_is_in_our_domain(&pol_sid
) ||
897 sid_check_is_in_builtin(&pol_sid
)) {
898 /* TODO: different SDs have to be generated for aliases groups and users.
899 Currently all three get a default user SD */
900 DEBUG(10,("_samr_QuerySecurity: querying security on Object "
901 "with SID: %s\n", sid_string_dbg(&pol_sid
)));
902 if (check_change_pw_access(p
->mem_ctx
, &pol_sid
)) {
903 status
= make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &usr_generic_mapping
,
904 &pol_sid
, SAMR_USR_RIGHTS_WRITE_PW
);
906 status
= make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &usr_nopwchange_generic_mapping
,
907 &pol_sid
, SAMR_USR_RIGHTS_CANT_WRITE_PW
);
910 return NT_STATUS_OBJECT_TYPE_MISMATCH
;
913 if ((*r
->out
.sdbuf
= make_sec_desc_buf(p
->mem_ctx
, sd_size
, psd
)) == NULL
)
914 return NT_STATUS_NO_MEMORY
;
919 /*******************************************************************
920 makes a SAM_ENTRY / UNISTR2* structure from a user list.
921 ********************************************************************/
923 static NTSTATUS
make_user_sam_entry_list(TALLOC_CTX
*ctx
,
924 struct samr_SamEntry
**sam_pp
,
925 uint32_t num_entries
,
927 struct samr_displayentry
*entries
)
930 struct samr_SamEntry
*sam
;
934 if (num_entries
== 0) {
938 sam
= TALLOC_ZERO_ARRAY(ctx
, struct samr_SamEntry
, num_entries
);
940 DEBUG(0, ("make_user_sam_entry_list: TALLOC_ZERO failed!\n"));
941 return NT_STATUS_NO_MEMORY
;
944 for (i
= 0; i
< num_entries
; i
++) {
947 * usrmgr expects a non-NULL terminated string with
948 * trust relationships
950 if (entries
[i
].acct_flags
& ACB_DOMTRUST
) {
951 init_unistr2(&uni_temp_name
, entries
[i
].account_name
,
954 init_unistr2(&uni_temp_name
, entries
[i
].account_name
,
958 init_lsa_String(&sam
[i
].name
, entries
[i
].account_name
);
959 sam
[i
].idx
= entries
[i
].rid
;
967 #define MAX_SAM_ENTRIES MAX_SAM_ENTRIES_W2K
969 /*******************************************************************
970 _samr_EnumDomainUsers
971 ********************************************************************/
973 NTSTATUS
_samr_EnumDomainUsers(pipes_struct
*p
,
974 struct samr_EnumDomainUsers
*r
)
977 struct samr_info
*info
= NULL
;
979 uint32 enum_context
= *r
->in
.resume_handle
;
980 enum remote_arch_types ra_type
= get_remote_arch();
981 int max_sam_entries
= (ra_type
== RA_WIN95
) ? MAX_SAM_ENTRIES_W95
: MAX_SAM_ENTRIES_W2K
;
982 uint32 max_entries
= max_sam_entries
;
983 struct samr_displayentry
*entries
= NULL
;
984 struct samr_SamArray
*samr_array
= NULL
;
985 struct samr_SamEntry
*samr_entries
= NULL
;
987 /* find the policy handle. open a policy on it. */
988 if (!find_policy_by_hnd(p
, r
->in
.domain_handle
, (void **)(void *)&info
))
989 return NT_STATUS_INVALID_HANDLE
;
991 status
= access_check_samr_function(info
->acc_granted
,
992 SA_RIGHT_DOMAIN_ENUM_ACCOUNTS
,
993 "_samr_EnumDomainUsers");
994 if (!NT_STATUS_IS_OK(status
)) {
998 DEBUG(5,("_samr_EnumDomainUsers: %d\n", __LINE__
));
1000 if (info
->builtin_domain
) {
1001 /* No users in builtin. */
1002 *r
->out
.resume_handle
= *r
->in
.resume_handle
;
1003 DEBUG(5,("_samr_EnumDomainUsers: No users in BUILTIN\n"));
1007 samr_array
= TALLOC_ZERO_P(p
->mem_ctx
, struct samr_SamArray
);
1009 return NT_STATUS_NO_MEMORY
;
1016 if ((info
->disp_info
->enum_users
!= NULL
) &&
1017 (info
->disp_info
->enum_acb_mask
!= r
->in
.acct_flags
)) {
1018 pdb_search_destroy(info
->disp_info
->enum_users
);
1019 info
->disp_info
->enum_users
= NULL
;
1022 if (info
->disp_info
->enum_users
== NULL
) {
1023 info
->disp_info
->enum_users
= pdb_search_users(r
->in
.acct_flags
);
1024 info
->disp_info
->enum_acb_mask
= r
->in
.acct_flags
;
1027 if (info
->disp_info
->enum_users
== NULL
) {
1028 /* END AS ROOT !!!! */
1030 return NT_STATUS_ACCESS_DENIED
;
1033 num_account
= pdb_search_entries(info
->disp_info
->enum_users
,
1034 enum_context
, max_entries
,
1037 /* END AS ROOT !!!! */
1041 if (num_account
== 0) {
1042 DEBUG(5, ("_samr_EnumDomainUsers: enumeration handle over "
1043 "total entries\n"));
1044 *r
->out
.resume_handle
= *r
->in
.resume_handle
;
1045 return NT_STATUS_OK
;
1048 status
= make_user_sam_entry_list(p
->mem_ctx
, &samr_entries
,
1049 num_account
, enum_context
,
1051 if (!NT_STATUS_IS_OK(status
)) {
1055 if (max_entries
<= num_account
) {
1056 status
= STATUS_MORE_ENTRIES
;
1058 status
= NT_STATUS_OK
;
1061 /* Ensure we cache this enumeration. */
1062 set_disp_info_cache_timeout(info
->disp_info
, DISP_INFO_CACHE_TIMEOUT
);
1064 DEBUG(5, ("_samr_EnumDomainUsers: %d\n", __LINE__
));
1066 samr_array
->count
= num_account
;
1067 samr_array
->entries
= samr_entries
;
1069 *r
->out
.resume_handle
= *r
->in
.resume_handle
+ num_account
;
1070 *r
->out
.sam
= samr_array
;
1071 *r
->out
.num_entries
= num_account
;
1073 DEBUG(5,("_samr_EnumDomainUsers: %d\n", __LINE__
));
1078 /*******************************************************************
1079 makes a SAM_ENTRY / UNISTR2* structure from a group list.
1080 ********************************************************************/
1082 static void make_group_sam_entry_list(TALLOC_CTX
*ctx
,
1083 struct samr_SamEntry
**sam_pp
,
1084 uint32_t num_sam_entries
,
1085 struct samr_displayentry
*entries
)
1087 struct samr_SamEntry
*sam
;
1092 if (num_sam_entries
== 0) {
1096 sam
= TALLOC_ZERO_ARRAY(ctx
, struct samr_SamEntry
, num_sam_entries
);
1101 for (i
= 0; i
< num_sam_entries
; i
++) {
1103 * JRA. I think this should include the null. TNG does not.
1105 init_lsa_String(&sam
[i
].name
, entries
[i
].account_name
);
1106 sam
[i
].idx
= entries
[i
].rid
;
1112 /*******************************************************************
1113 _samr_EnumDomainGroups
1114 ********************************************************************/
1116 NTSTATUS
_samr_EnumDomainGroups(pipes_struct
*p
,
1117 struct samr_EnumDomainGroups
*r
)
1120 struct samr_info
*info
= NULL
;
1121 struct samr_displayentry
*groups
;
1123 struct samr_SamArray
*samr_array
= NULL
;
1124 struct samr_SamEntry
*samr_entries
= NULL
;
1126 /* find the policy handle. open a policy on it. */
1127 if (!find_policy_by_hnd(p
, r
->in
.domain_handle
, (void **)(void *)&info
))
1128 return NT_STATUS_INVALID_HANDLE
;
1130 status
= access_check_samr_function(info
->acc_granted
,
1131 SA_RIGHT_DOMAIN_ENUM_ACCOUNTS
,
1132 "_samr_EnumDomainGroups");
1133 if (!NT_STATUS_IS_OK(status
)) {
1137 DEBUG(5,("_samr_EnumDomainGroups: %d\n", __LINE__
));
1139 if (info
->builtin_domain
) {
1140 /* No groups in builtin. */
1141 *r
->out
.resume_handle
= *r
->in
.resume_handle
;
1142 DEBUG(5,("_samr_EnumDomainGroups: No groups in BUILTIN\n"));
1146 samr_array
= TALLOC_ZERO_P(p
->mem_ctx
, struct samr_SamArray
);
1148 return NT_STATUS_NO_MEMORY
;
1151 /* the domain group array is being allocated in the function below */
1155 if (info
->disp_info
->groups
== NULL
) {
1156 info
->disp_info
->groups
= pdb_search_groups();
1158 if (info
->disp_info
->groups
== NULL
) {
1160 return NT_STATUS_ACCESS_DENIED
;
1164 num_groups
= pdb_search_entries(info
->disp_info
->groups
,
1165 *r
->in
.resume_handle
,
1166 MAX_SAM_ENTRIES
, &groups
);
1169 /* Ensure we cache this enumeration. */
1170 set_disp_info_cache_timeout(info
->disp_info
, DISP_INFO_CACHE_TIMEOUT
);
1172 make_group_sam_entry_list(p
->mem_ctx
, &samr_entries
,
1173 num_groups
, groups
);
1175 samr_array
->count
= num_groups
;
1176 samr_array
->entries
= samr_entries
;
1178 *r
->out
.sam
= samr_array
;
1179 *r
->out
.num_entries
= num_groups
;
1180 /* this was missing, IMHO:
1181 *r->out.resume_handle = num_groups + *r->in.resume_handle;
1184 DEBUG(5,("_samr_EnumDomainGroups: %d\n", __LINE__
));
1189 /*******************************************************************
1190 _samr_EnumDomainAliases
1191 ********************************************************************/
1193 NTSTATUS
_samr_EnumDomainAliases(pipes_struct
*p
,
1194 struct samr_EnumDomainAliases
*r
)
1197 struct samr_info
*info
;
1198 struct samr_displayentry
*aliases
;
1199 uint32 num_aliases
= 0;
1200 struct samr_SamArray
*samr_array
= NULL
;
1201 struct samr_SamEntry
*samr_entries
= NULL
;
1203 /* find the policy handle. open a policy on it. */
1204 if (!find_policy_by_hnd(p
, r
->in
.domain_handle
, (void **)(void *)&info
))
1205 return NT_STATUS_INVALID_HANDLE
;
1207 DEBUG(5,("_samr_EnumDomainAliases: sid %s\n",
1208 sid_string_dbg(&info
->sid
)));
1210 status
= access_check_samr_function(info
->acc_granted
,
1211 SA_RIGHT_DOMAIN_ENUM_ACCOUNTS
,
1212 "_samr_EnumDomainAliases");
1213 if (!NT_STATUS_IS_OK(status
)) {
1217 samr_array
= TALLOC_ZERO_P(p
->mem_ctx
, struct samr_SamArray
);
1219 return NT_STATUS_NO_MEMORY
;
1224 if (info
->disp_info
->aliases
== NULL
) {
1225 info
->disp_info
->aliases
= pdb_search_aliases(&info
->sid
);
1226 if (info
->disp_info
->aliases
== NULL
) {
1228 return NT_STATUS_ACCESS_DENIED
;
1232 num_aliases
= pdb_search_entries(info
->disp_info
->aliases
,
1233 *r
->in
.resume_handle
,
1234 MAX_SAM_ENTRIES
, &aliases
);
1237 /* Ensure we cache this enumeration. */
1238 set_disp_info_cache_timeout(info
->disp_info
, DISP_INFO_CACHE_TIMEOUT
);
1240 make_group_sam_entry_list(p
->mem_ctx
, &samr_entries
,
1241 num_aliases
, aliases
);
1243 DEBUG(5,("_samr_EnumDomainAliases: %d\n", __LINE__
));
1245 samr_array
->count
= num_aliases
;
1246 samr_array
->entries
= samr_entries
;
1248 *r
->out
.sam
= samr_array
;
1249 *r
->out
.num_entries
= num_aliases
;
1250 *r
->out
.resume_handle
= num_aliases
+ *r
->in
.resume_handle
;
1255 /*******************************************************************
1256 inits a samr_DispInfoGeneral structure.
1257 ********************************************************************/
1259 static NTSTATUS
init_samr_dispinfo_1(TALLOC_CTX
*ctx
,
1260 struct samr_DispInfoGeneral
*r
,
1261 uint32_t num_entries
,
1263 struct samr_displayentry
*entries
)
1267 DEBUG(10, ("init_samr_dispinfo_1: num_entries: %d\n", num_entries
));
1269 if (num_entries
== 0) {
1270 return NT_STATUS_OK
;
1273 r
->count
= num_entries
;
1275 r
->entries
= TALLOC_ZERO_ARRAY(ctx
, struct samr_DispEntryGeneral
, num_entries
);
1277 return NT_STATUS_NO_MEMORY
;
1280 for (i
= 0; i
< num_entries
; i
++) {
1282 init_lsa_String(&r
->entries
[i
].account_name
,
1283 entries
[i
].account_name
);
1285 init_lsa_String(&r
->entries
[i
].description
,
1286 entries
[i
].description
);
1288 init_lsa_String(&r
->entries
[i
].full_name
,
1289 entries
[i
].fullname
);
1291 r
->entries
[i
].rid
= entries
[i
].rid
;
1292 r
->entries
[i
].acct_flags
= entries
[i
].acct_flags
;
1293 r
->entries
[i
].idx
= start_idx
+i
+1;
1296 return NT_STATUS_OK
;
1299 /*******************************************************************
1300 inits a samr_DispInfoFull structure.
1301 ********************************************************************/
1303 static NTSTATUS
init_samr_dispinfo_2(TALLOC_CTX
*ctx
,
1304 struct samr_DispInfoFull
*r
,
1305 uint32_t num_entries
,
1307 struct samr_displayentry
*entries
)
1311 DEBUG(10, ("init_samr_dispinfo_2: num_entries: %d\n", num_entries
));
1313 if (num_entries
== 0) {
1314 return NT_STATUS_OK
;
1317 r
->count
= num_entries
;
1319 r
->entries
= TALLOC_ZERO_ARRAY(ctx
, struct samr_DispEntryFull
, num_entries
);
1321 return NT_STATUS_NO_MEMORY
;
1324 for (i
= 0; i
< num_entries
; i
++) {
1326 init_lsa_String(&r
->entries
[i
].account_name
,
1327 entries
[i
].account_name
);
1329 init_lsa_String(&r
->entries
[i
].description
,
1330 entries
[i
].description
);
1332 r
->entries
[i
].rid
= entries
[i
].rid
;
1333 r
->entries
[i
].acct_flags
= entries
[i
].acct_flags
;
1334 r
->entries
[i
].idx
= start_idx
+i
+1;
1337 return NT_STATUS_OK
;
1340 /*******************************************************************
1341 inits a samr_DispInfoFullGroups structure.
1342 ********************************************************************/
1344 static NTSTATUS
init_samr_dispinfo_3(TALLOC_CTX
*ctx
,
1345 struct samr_DispInfoFullGroups
*r
,
1346 uint32_t num_entries
,
1348 struct samr_displayentry
*entries
)
1352 DEBUG(5, ("init_samr_dispinfo_3: num_entries: %d\n", num_entries
));
1354 if (num_entries
== 0) {
1355 return NT_STATUS_OK
;
1358 r
->count
= num_entries
;
1360 r
->entries
= TALLOC_ZERO_ARRAY(ctx
, struct samr_DispEntryFullGroup
, num_entries
);
1362 return NT_STATUS_NO_MEMORY
;
1365 for (i
= 0; i
< num_entries
; i
++) {
1367 init_lsa_String(&r
->entries
[i
].account_name
,
1368 entries
[i
].account_name
);
1370 init_lsa_String(&r
->entries
[i
].description
,
1371 entries
[i
].description
);
1373 r
->entries
[i
].rid
= entries
[i
].rid
;
1374 r
->entries
[i
].acct_flags
= entries
[i
].acct_flags
;
1375 r
->entries
[i
].idx
= start_idx
+i
+1;
1378 return NT_STATUS_OK
;
1381 /*******************************************************************
1382 inits a samr_DispInfoAscii structure.
1383 ********************************************************************/
1385 static NTSTATUS
init_samr_dispinfo_4(TALLOC_CTX
*ctx
,
1386 struct samr_DispInfoAscii
*r
,
1387 uint32_t num_entries
,
1389 struct samr_displayentry
*entries
)
1393 DEBUG(5, ("init_samr_dispinfo_4: num_entries: %d\n", num_entries
));
1395 if (num_entries
== 0) {
1396 return NT_STATUS_OK
;
1399 r
->count
= num_entries
;
1401 r
->entries
= TALLOC_ZERO_ARRAY(ctx
, struct samr_DispEntryAscii
, num_entries
);
1403 return NT_STATUS_NO_MEMORY
;
1406 for (i
= 0; i
< num_entries
; i
++) {
1408 init_lsa_AsciiStringLarge(&r
->entries
[i
].account_name
,
1409 entries
[i
].account_name
);
1411 r
->entries
[i
].idx
= start_idx
+i
+1;
1414 return NT_STATUS_OK
;
1417 /*******************************************************************
1418 inits a samr_DispInfoAscii structure.
1419 ********************************************************************/
1421 static NTSTATUS
init_samr_dispinfo_5(TALLOC_CTX
*ctx
,
1422 struct samr_DispInfoAscii
*r
,
1423 uint32_t num_entries
,
1425 struct samr_displayentry
*entries
)
1429 DEBUG(5, ("init_samr_dispinfo_5: num_entries: %d\n", num_entries
));
1431 if (num_entries
== 0) {
1432 return NT_STATUS_OK
;
1435 r
->count
= num_entries
;
1437 r
->entries
= TALLOC_ZERO_ARRAY(ctx
, struct samr_DispEntryAscii
, num_entries
);
1439 return NT_STATUS_NO_MEMORY
;
1442 for (i
= 0; i
< num_entries
; i
++) {
1444 init_lsa_AsciiStringLarge(&r
->entries
[i
].account_name
,
1445 entries
[i
].account_name
);
1447 r
->entries
[i
].idx
= start_idx
+i
+1;
1450 return NT_STATUS_OK
;
1453 /*******************************************************************
1454 _samr_QueryDisplayInfo
1455 ********************************************************************/
1457 NTSTATUS
_samr_QueryDisplayInfo(pipes_struct
*p
,
1458 struct samr_QueryDisplayInfo
*r
)
1461 struct samr_info
*info
= NULL
;
1462 uint32 struct_size
=0x20; /* W2K always reply that, client doesn't care */
1464 uint32 max_entries
= r
->in
.max_entries
;
1465 uint32 enum_context
= r
->in
.start_idx
;
1466 uint32 max_size
= r
->in
.buf_size
;
1468 union samr_DispInfo
*disp_info
= r
->out
.info
;
1470 uint32 temp_size
=0, total_data_size
=0;
1471 NTSTATUS disp_ret
= NT_STATUS_UNSUCCESSFUL
;
1472 uint32 num_account
= 0;
1473 enum remote_arch_types ra_type
= get_remote_arch();
1474 int max_sam_entries
= (ra_type
== RA_WIN95
) ? MAX_SAM_ENTRIES_W95
: MAX_SAM_ENTRIES_W2K
;
1475 struct samr_displayentry
*entries
= NULL
;
1477 DEBUG(5,("_samr_QueryDisplayInfo: %d\n", __LINE__
));
1479 /* find the policy handle. open a policy on it. */
1480 if (!find_policy_by_hnd(p
, r
->in
.domain_handle
, (void **)(void *)&info
))
1481 return NT_STATUS_INVALID_HANDLE
;
1483 status
= access_check_samr_function(info
->acc_granted
,
1484 SA_RIGHT_DOMAIN_ENUM_ACCOUNTS
,
1485 "_samr_QueryDisplayInfo");
1486 if (!NT_STATUS_IS_OK(status
)) {
1491 * calculate how many entries we will return.
1493 * - the number of entries the client asked
1494 * - our limit on that
1495 * - the starting point (enumeration context)
1496 * - the buffer size the client will accept
1500 * We are a lot more like W2K. Instead of reading the SAM
1501 * each time to find the records we need to send back,
1502 * we read it once and link that copy to the sam handle.
1503 * For large user list (over the MAX_SAM_ENTRIES)
1504 * it's a definitive win.
1505 * second point to notice: between enumerations
1506 * our sam is now the same as it's a snapshoot.
1507 * third point: got rid of the static SAM_USER_21 struct
1508 * no more intermediate.
1509 * con: it uses much more memory, as a full copy is stored
1512 * If you want to change it, think twice and think
1513 * of the second point , that's really important.
1518 if ((r
->in
.level
< 1) || (r
->in
.level
> 5)) {
1519 DEBUG(0,("_samr_QueryDisplayInfo: Unknown info level (%u)\n",
1520 (unsigned int)r
->in
.level
));
1521 return NT_STATUS_INVALID_INFO_CLASS
;
1524 /* first limit the number of entries we will return */
1525 if(max_entries
> max_sam_entries
) {
1526 DEBUG(5, ("_samr_QueryDisplayInfo: client requested %d "
1527 "entries, limiting to %d\n", max_entries
,
1529 max_entries
= max_sam_entries
;
1532 /* calculate the size and limit on the number of entries we will
1535 temp_size
=max_entries
*struct_size
;
1537 if (temp_size
>max_size
) {
1538 max_entries
=MIN((max_size
/struct_size
),max_entries
);;
1539 DEBUG(5, ("_samr_QueryDisplayInfo: buffer size limits to "
1540 "only %d entries\n", max_entries
));
1545 /* THe following done as ROOT. Don't return without unbecome_root(). */
1547 switch (r
->in
.level
) {
1550 if (info
->disp_info
->users
== NULL
) {
1551 info
->disp_info
->users
= pdb_search_users(ACB_NORMAL
);
1552 if (info
->disp_info
->users
== NULL
) {
1554 return NT_STATUS_ACCESS_DENIED
;
1556 DEBUG(10,("_samr_QueryDisplayInfo: starting user enumeration at index %u\n",
1557 (unsigned int)enum_context
));
1559 DEBUG(10,("_samr_QueryDisplayInfo: using cached user enumeration at index %u\n",
1560 (unsigned int)enum_context
));
1563 num_account
= pdb_search_entries(info
->disp_info
->users
,
1564 enum_context
, max_entries
,
1568 if (info
->disp_info
->machines
== NULL
) {
1569 info
->disp_info
->machines
=
1570 pdb_search_users(ACB_WSTRUST
|ACB_SVRTRUST
);
1571 if (info
->disp_info
->machines
== NULL
) {
1573 return NT_STATUS_ACCESS_DENIED
;
1575 DEBUG(10,("_samr_QueryDisplayInfo: starting machine enumeration at index %u\n",
1576 (unsigned int)enum_context
));
1578 DEBUG(10,("_samr_QueryDisplayInfo: using cached machine enumeration at index %u\n",
1579 (unsigned int)enum_context
));
1582 num_account
= pdb_search_entries(info
->disp_info
->machines
,
1583 enum_context
, max_entries
,
1588 if (info
->disp_info
->groups
== NULL
) {
1589 info
->disp_info
->groups
= pdb_search_groups();
1590 if (info
->disp_info
->groups
== NULL
) {
1592 return NT_STATUS_ACCESS_DENIED
;
1594 DEBUG(10,("_samr_QueryDisplayInfo: starting group enumeration at index %u\n",
1595 (unsigned int)enum_context
));
1597 DEBUG(10,("_samr_QueryDisplayInfo: using cached group enumeration at index %u\n",
1598 (unsigned int)enum_context
));
1601 num_account
= pdb_search_entries(info
->disp_info
->groups
,
1602 enum_context
, max_entries
,
1607 smb_panic("info class changed");
1613 /* Now create reply structure */
1614 switch (r
->in
.level
) {
1616 disp_ret
= init_samr_dispinfo_1(p
->mem_ctx
, &disp_info
->info1
,
1617 num_account
, enum_context
,
1621 disp_ret
= init_samr_dispinfo_2(p
->mem_ctx
, &disp_info
->info2
,
1622 num_account
, enum_context
,
1626 disp_ret
= init_samr_dispinfo_3(p
->mem_ctx
, &disp_info
->info3
,
1627 num_account
, enum_context
,
1631 disp_ret
= init_samr_dispinfo_4(p
->mem_ctx
, &disp_info
->info4
,
1632 num_account
, enum_context
,
1636 disp_ret
= init_samr_dispinfo_5(p
->mem_ctx
, &disp_info
->info5
,
1637 num_account
, enum_context
,
1641 smb_panic("info class changed");
1645 if (!NT_STATUS_IS_OK(disp_ret
))
1648 /* calculate the total size */
1649 total_data_size
=num_account
*struct_size
;
1651 if (max_entries
<= num_account
) {
1652 status
= STATUS_MORE_ENTRIES
;
1654 status
= NT_STATUS_OK
;
1657 /* Ensure we cache this enumeration. */
1658 set_disp_info_cache_timeout(info
->disp_info
, DISP_INFO_CACHE_TIMEOUT
);
1660 DEBUG(5, ("_samr_QueryDisplayInfo: %d\n", __LINE__
));
1662 *r
->out
.total_size
= total_data_size
;
1663 *r
->out
.returned_size
= temp_size
;
1668 /****************************************************************
1669 _samr_QueryDisplayInfo2
1670 ****************************************************************/
1672 NTSTATUS
_samr_QueryDisplayInfo2(pipes_struct
*p
,
1673 struct samr_QueryDisplayInfo2
*r
)
1675 struct samr_QueryDisplayInfo q
;
1677 q
.in
.domain_handle
= r
->in
.domain_handle
;
1678 q
.in
.level
= r
->in
.level
;
1679 q
.in
.start_idx
= r
->in
.start_idx
;
1680 q
.in
.max_entries
= r
->in
.max_entries
;
1681 q
.in
.buf_size
= r
->in
.buf_size
;
1683 q
.out
.total_size
= r
->out
.total_size
;
1684 q
.out
.returned_size
= r
->out
.returned_size
;
1685 q
.out
.info
= r
->out
.info
;
1687 return _samr_QueryDisplayInfo(p
, &q
);
1690 /****************************************************************
1691 _samr_QueryDisplayInfo3
1692 ****************************************************************/
1694 NTSTATUS
_samr_QueryDisplayInfo3(pipes_struct
*p
,
1695 struct samr_QueryDisplayInfo3
*r
)
1697 struct samr_QueryDisplayInfo q
;
1699 q
.in
.domain_handle
= r
->in
.domain_handle
;
1700 q
.in
.level
= r
->in
.level
;
1701 q
.in
.start_idx
= r
->in
.start_idx
;
1702 q
.in
.max_entries
= r
->in
.max_entries
;
1703 q
.in
.buf_size
= r
->in
.buf_size
;
1705 q
.out
.total_size
= r
->out
.total_size
;
1706 q
.out
.returned_size
= r
->out
.returned_size
;
1707 q
.out
.info
= r
->out
.info
;
1709 return _samr_QueryDisplayInfo(p
, &q
);
1712 /*******************************************************************
1713 _samr_QueryAliasInfo
1714 ********************************************************************/
1716 NTSTATUS
_samr_QueryAliasInfo(pipes_struct
*p
,
1717 struct samr_QueryAliasInfo
*r
)
1720 struct acct_info info
;
1723 union samr_AliasInfo
*alias_info
= NULL
;
1724 const char *alias_name
= NULL
;
1725 const char *alias_description
= NULL
;
1727 DEBUG(5,("_samr_QueryAliasInfo: %d\n", __LINE__
));
1729 alias_info
= TALLOC_ZERO_P(p
->mem_ctx
, union samr_AliasInfo
);
1731 return NT_STATUS_NO_MEMORY
;
1734 /* find the policy handle. open a policy on it. */
1735 if (!get_lsa_policy_samr_sid(p
, r
->in
.alias_handle
, &sid
, &acc_granted
, NULL
))
1736 return NT_STATUS_INVALID_HANDLE
;
1738 status
= access_check_samr_function(acc_granted
,
1739 SA_RIGHT_ALIAS_LOOKUP_INFO
,
1740 "_samr_QueryAliasInfo");
1741 if (!NT_STATUS_IS_OK(status
)) {
1746 status
= pdb_get_aliasinfo(&sid
, &info
);
1749 if ( !NT_STATUS_IS_OK(status
))
1752 /* FIXME: info contains fstrings */
1753 alias_name
= talloc_strdup(r
, info
.acct_name
);
1754 alias_description
= talloc_strdup(r
, info
.acct_desc
);
1756 switch (r
->in
.level
) {
1758 init_samr_alias_info1(&alias_info
->all
,
1763 case ALIASINFODESCRIPTION
:
1764 init_samr_alias_info3(&alias_info
->description
,
1768 return NT_STATUS_INVALID_INFO_CLASS
;
1771 *r
->out
.info
= alias_info
;
1773 DEBUG(5,("_samr_QueryAliasInfo: %d\n", __LINE__
));
1775 return NT_STATUS_OK
;
1779 /*******************************************************************
1780 samr_reply_lookup_ids
1781 ********************************************************************/
1783 uint32
_samr_lookup_ids(pipes_struct
*p
, SAMR_Q_LOOKUP_IDS
*q_u
, SAMR_R_LOOKUP_IDS
*r_u
)
1785 uint32 rid
[MAX_SAM_ENTRIES
];
1786 int num_rids
= q_u
->num_sids1
;
1788 r_u
->status
= NT_STATUS_OK
;
1790 DEBUG(5,("_samr_lookup_ids: %d\n", __LINE__
));
1792 if (num_rids
> MAX_SAM_ENTRIES
) {
1793 num_rids
= MAX_SAM_ENTRIES
;
1794 DEBUG(5,("_samr_lookup_ids: truncating entries to %d\n", num_rids
));
1799 SMB_ASSERT_ARRAY(q_u
->uni_user_name
, num_rids
);
1801 for (i
= 0; i
< num_rids
&& status
== 0; i
++)
1803 struct sam_passwd
*sam_pass
;
1807 fstrcpy(user_name
, unistrn2(q_u
->uni_user_name
[i
].buffer
,
1808 q_u
->uni_user_name
[i
].uni_str_len
));
1810 /* find the user account */
1812 sam_pass
= get_smb21pwd_entry(user_name
, 0);
1815 if (sam_pass
== NULL
)
1817 status
= 0xC0000000 | NT_STATUS_NO_SUCH_USER
;
1822 rid
[i
] = sam_pass
->user_rid
;
1828 rid
[0] = BUILTIN_ALIAS_RID_USERS
;
1830 init_samr_r_lookup_ids(&r_u
, num_rids
, rid
, NT_STATUS_OK
);
1832 DEBUG(5,("_samr_lookup_ids: %d\n", __LINE__
));
1838 /*******************************************************************
1840 ********************************************************************/
1842 NTSTATUS
_samr_LookupNames(pipes_struct
*p
,
1843 struct samr_LookupNames
*r
)
1847 enum lsa_SidType
*type
;
1849 int num_rids
= r
->in
.num_names
;
1852 struct samr_Ids rids
, types
;
1854 DEBUG(5,("_samr_LookupNames: %d\n", __LINE__
));
1856 if (!get_lsa_policy_samr_sid(p
, r
->in
.domain_handle
, &pol_sid
, &acc_granted
, NULL
)) {
1857 return NT_STATUS_OBJECT_TYPE_MISMATCH
;
1860 status
= access_check_samr_function(acc_granted
,
1861 0, /* Don't know the acc_bits yet */
1862 "_samr_LookupNames");
1863 if (!NT_STATUS_IS_OK(status
)) {
1867 if (num_rids
> MAX_SAM_ENTRIES
) {
1868 num_rids
= MAX_SAM_ENTRIES
;
1869 DEBUG(5,("_samr_LookupNames: truncating entries to %d\n", num_rids
));
1872 rid
= talloc_array(p
->mem_ctx
, uint32
, num_rids
);
1873 NT_STATUS_HAVE_NO_MEMORY(rid
);
1875 type
= talloc_array(p
->mem_ctx
, enum lsa_SidType
, num_rids
);
1876 NT_STATUS_HAVE_NO_MEMORY(type
);
1878 DEBUG(5,("_samr_LookupNames: looking name on SID %s\n",
1879 sid_string_dbg(&pol_sid
)));
1881 for (i
= 0; i
< num_rids
; i
++) {
1883 status
= NT_STATUS_NONE_MAPPED
;
1884 type
[i
] = SID_NAME_UNKNOWN
;
1886 rid
[i
] = 0xffffffff;
1888 if (sid_check_is_builtin(&pol_sid
)) {
1889 if (lookup_builtin_name(r
->in
.names
[i
].string
,
1892 type
[i
] = SID_NAME_ALIAS
;
1895 lookup_global_sam_name(r
->in
.names
[i
].string
, 0,
1899 if (type
[i
] != SID_NAME_UNKNOWN
) {
1900 status
= NT_STATUS_OK
;
1904 rids
.count
= num_rids
;
1907 types
.count
= num_rids
;
1910 *r
->out
.rids
= rids
;
1911 *r
->out
.types
= types
;
1913 DEBUG(5,("_samr_LookupNames: %d\n", __LINE__
));
1918 /*******************************************************************
1919 _samr_ChangePasswordUser2
1920 ********************************************************************/
1922 NTSTATUS
_samr_ChangePasswordUser2(pipes_struct
*p
,
1923 struct samr_ChangePasswordUser2
*r
)
1929 DEBUG(5,("_samr_ChangePasswordUser2: %d\n", __LINE__
));
1931 fstrcpy(user_name
, r
->in
.account
->string
);
1932 fstrcpy(wks
, r
->in
.server
->string
);
1934 DEBUG(5,("_samr_ChangePasswordUser2: user: %s wks: %s\n", user_name
, wks
));
1937 * Pass the user through the NT -> unix user mapping
1941 (void)map_username(user_name
);
1944 * UNIX username case mangling not required, pass_oem_change
1945 * is case insensitive.
1948 status
= pass_oem_change(user_name
,
1949 r
->in
.lm_password
->data
,
1950 r
->in
.lm_verifier
->hash
,
1951 r
->in
.nt_password
->data
,
1952 r
->in
.nt_verifier
->hash
,
1955 DEBUG(5,("_samr_ChangePasswordUser2: %d\n", __LINE__
));
1960 /*******************************************************************
1961 _samr_ChangePasswordUser3
1962 ********************************************************************/
1964 NTSTATUS
_samr_ChangePasswordUser3(pipes_struct
*p
,
1965 struct samr_ChangePasswordUser3
*r
)
1969 const char *wks
= NULL
;
1970 uint32 reject_reason
;
1971 struct samr_DomInfo1
*dominfo
= NULL
;
1972 struct samr_ChangeReject
*reject
= NULL
;
1974 DEBUG(5,("_samr_ChangePasswordUser3: %d\n", __LINE__
));
1976 fstrcpy(user_name
, r
->in
.account
->string
);
1977 if (r
->in
.server
&& r
->in
.server
->string
) {
1978 wks
= r
->in
.server
->string
;
1981 DEBUG(5,("_samr_ChangePasswordUser3: user: %s wks: %s\n", user_name
, wks
));
1984 * Pass the user through the NT -> unix user mapping
1988 (void)map_username(user_name
);
1991 * UNIX username case mangling not required, pass_oem_change
1992 * is case insensitive.
1995 status
= pass_oem_change(user_name
,
1996 r
->in
.lm_password
->data
,
1997 r
->in
.lm_verifier
->hash
,
1998 r
->in
.nt_password
->data
,
1999 r
->in
.nt_verifier
->hash
,
2002 if (NT_STATUS_EQUAL(status
, NT_STATUS_PASSWORD_RESTRICTION
) ||
2003 NT_STATUS_EQUAL(status
, NT_STATUS_ACCOUNT_RESTRICTION
)) {
2005 uint32 min_pass_len
,pass_hist
,password_properties
;
2006 time_t u_expire
, u_min_age
;
2007 NTTIME nt_expire
, nt_min_age
;
2008 uint32 account_policy_temp
;
2010 dominfo
= TALLOC_ZERO_P(p
->mem_ctx
, struct samr_DomInfo1
);
2012 return NT_STATUS_NO_MEMORY
;
2015 reject
= TALLOC_ZERO_P(p
->mem_ctx
, struct samr_ChangeReject
);
2017 return NT_STATUS_NO_MEMORY
;
2024 pdb_get_account_policy(AP_MIN_PASSWORD_LEN
, &account_policy_temp
);
2025 min_pass_len
= account_policy_temp
;
2027 pdb_get_account_policy(AP_PASSWORD_HISTORY
, &account_policy_temp
);
2028 pass_hist
= account_policy_temp
;
2030 pdb_get_account_policy(AP_USER_MUST_LOGON_TO_CHG_PASS
, &account_policy_temp
);
2031 password_properties
= account_policy_temp
;
2033 pdb_get_account_policy(AP_MAX_PASSWORD_AGE
, &account_policy_temp
);
2034 u_expire
= account_policy_temp
;
2036 pdb_get_account_policy(AP_MIN_PASSWORD_AGE
, &account_policy_temp
);
2037 u_min_age
= account_policy_temp
;
2043 unix_to_nt_time_abs(&nt_expire
, u_expire
);
2044 unix_to_nt_time_abs(&nt_min_age
, u_min_age
);
2046 if (lp_check_password_script() && *lp_check_password_script()) {
2047 password_properties
|= DOMAIN_PASSWORD_COMPLEX
;
2050 init_samr_DomInfo1(dominfo
,
2053 password_properties
,
2057 reject
->reason
= reject_reason
;
2059 *r
->out
.dominfo
= dominfo
;
2060 *r
->out
.reject
= reject
;
2063 DEBUG(5,("_samr_ChangePasswordUser3: %d\n", __LINE__
));
2068 /*******************************************************************
2069 makes a SAMR_R_LOOKUP_RIDS structure.
2070 ********************************************************************/
2072 static bool make_samr_lookup_rids(TALLOC_CTX
*ctx
, uint32 num_names
,
2074 struct lsa_String
**lsa_name_array_p
)
2076 struct lsa_String
*lsa_name_array
= NULL
;
2079 *lsa_name_array_p
= NULL
;
2081 if (num_names
!= 0) {
2082 lsa_name_array
= TALLOC_ZERO_ARRAY(ctx
, struct lsa_String
, num_names
);
2083 if (!lsa_name_array
) {
2088 for (i
= 0; i
< num_names
; i
++) {
2089 DEBUG(10, ("names[%d]:%s\n", i
, names
[i
] && *names
[i
] ? names
[i
] : ""));
2090 init_lsa_String(&lsa_name_array
[i
], names
[i
]);
2093 *lsa_name_array_p
= lsa_name_array
;
2098 /*******************************************************************
2100 ********************************************************************/
2102 NTSTATUS
_samr_LookupRids(pipes_struct
*p
,
2103 struct samr_LookupRids
*r
)
2107 enum lsa_SidType
*attrs
= NULL
;
2108 uint32
*wire_attrs
= NULL
;
2110 int num_rids
= (int)r
->in
.num_rids
;
2113 struct lsa_Strings names_array
;
2114 struct samr_Ids types_array
;
2115 struct lsa_String
*lsa_names
= NULL
;
2117 DEBUG(5,("_samr_LookupRids: %d\n", __LINE__
));
2119 /* find the policy handle. open a policy on it. */
2120 if (!get_lsa_policy_samr_sid(p
, r
->in
.domain_handle
, &pol_sid
, &acc_granted
, NULL
))
2121 return NT_STATUS_INVALID_HANDLE
;
2123 status
= access_check_samr_function(acc_granted
,
2124 SA_RIGHT_DOMAIN_ENUM_ACCOUNTS
,
2125 "_samr__LookupRids");
2126 if (!NT_STATUS_IS_OK(status
)) {
2130 if (num_rids
> 1000) {
2131 DEBUG(0, ("Got asked for %d rids (more than 1000) -- according "
2132 "to samba4 idl this is not possible\n", num_rids
));
2133 return NT_STATUS_UNSUCCESSFUL
;
2137 names
= TALLOC_ZERO_ARRAY(p
->mem_ctx
, const char *, num_rids
);
2138 attrs
= TALLOC_ZERO_ARRAY(p
->mem_ctx
, enum lsa_SidType
, num_rids
);
2139 wire_attrs
= TALLOC_ZERO_ARRAY(p
->mem_ctx
, uint32
, num_rids
);
2141 if ((names
== NULL
) || (attrs
== NULL
) || (wire_attrs
==NULL
))
2142 return NT_STATUS_NO_MEMORY
;
2149 become_root(); /* lookup_sid can require root privs */
2150 status
= pdb_lookup_rids(&pol_sid
, num_rids
, r
->in
.rids
,
2154 if (NT_STATUS_EQUAL(status
, NT_STATUS_NONE_MAPPED
) && (num_rids
== 0)) {
2155 status
= NT_STATUS_OK
;
2158 if (!make_samr_lookup_rids(p
->mem_ctx
, num_rids
, names
,
2160 return NT_STATUS_NO_MEMORY
;
2163 /* Convert from enum lsa_SidType to uint32 for wire format. */
2164 for (i
= 0; i
< num_rids
; i
++) {
2165 wire_attrs
[i
] = (uint32
)attrs
[i
];
2168 names_array
.count
= num_rids
;
2169 names_array
.names
= lsa_names
;
2171 types_array
.count
= num_rids
;
2172 types_array
.ids
= wire_attrs
;
2174 *r
->out
.names
= names_array
;
2175 *r
->out
.types
= types_array
;
2177 DEBUG(5,("_samr_LookupRids: %d\n", __LINE__
));
2182 /*******************************************************************
2184 ********************************************************************/
2186 NTSTATUS
_samr_OpenUser(pipes_struct
*p
,
2187 struct samr_OpenUser
*r
)
2189 struct samu
*sampass
=NULL
;
2191 POLICY_HND domain_pol
= *r
->in
.domain_handle
;
2192 POLICY_HND
*user_pol
= r
->out
.user_handle
;
2193 struct samr_info
*info
= NULL
;
2194 SEC_DESC
*psd
= NULL
;
2196 uint32 des_access
= r
->in
.access_mask
;
2202 /* find the domain policy handle and get domain SID / access bits in the domain policy. */
2204 if ( !get_lsa_policy_samr_sid(p
, &domain_pol
, &sid
, &acc_granted
, NULL
) )
2205 return NT_STATUS_INVALID_HANDLE
;
2207 nt_status
= access_check_samr_function(acc_granted
,
2208 SA_RIGHT_DOMAIN_OPEN_ACCOUNT
,
2211 if ( !NT_STATUS_IS_OK(nt_status
) )
2214 if ( !(sampass
= samu_new( p
->mem_ctx
)) ) {
2215 return NT_STATUS_NO_MEMORY
;
2218 /* append the user's RID to it */
2220 if (!sid_append_rid(&sid
, r
->in
.rid
))
2221 return NT_STATUS_NO_SUCH_USER
;
2223 /* check if access can be granted as requested by client. */
2225 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
2227 make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &usr_generic_mapping
, &sid
, SAMR_USR_RIGHTS_WRITE_PW
);
2228 se_map_generic(&des_access
, &usr_generic_mapping
);
2230 se_priv_copy( &se_rights
, &se_machine_account
);
2231 se_priv_add( &se_rights
, &se_add_users
);
2233 nt_status
= access_check_samr_object(psd
, p
->pipe_user
.nt_user_token
,
2234 &se_rights
, GENERIC_RIGHTS_USER_WRITE
, des_access
,
2235 &acc_granted
, "_samr_OpenUser");
2237 if ( !NT_STATUS_IS_OK(nt_status
) )
2241 ret
=pdb_getsampwsid(sampass
, &sid
);
2244 /* check that the SID exists in our domain. */
2246 return NT_STATUS_NO_SUCH_USER
;
2249 TALLOC_FREE(sampass
);
2251 /* associate the user's SID and access bits with the new handle. */
2252 if ((info
= get_samr_info_by_sid(&sid
)) == NULL
)
2253 return NT_STATUS_NO_MEMORY
;
2254 info
->acc_granted
= acc_granted
;
2256 /* get a (unique) handle. open a policy on it. */
2257 if (!create_policy_hnd(p
, user_pol
, free_samr_info
, (void *)info
))
2258 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
2260 return NT_STATUS_OK
;
2263 /*************************************************************************
2264 *************************************************************************/
2266 static NTSTATUS
init_samr_parameters_string(TALLOC_CTX
*mem_ctx
,
2268 struct lsa_BinaryString
**_r
)
2270 struct lsa_BinaryString
*r
;
2273 return NT_STATUS_INVALID_PARAMETER
;
2276 r
= TALLOC_ZERO_P(mem_ctx
, struct lsa_BinaryString
);
2278 return NT_STATUS_NO_MEMORY
;
2281 r
->array
= TALLOC_ZERO_ARRAY(mem_ctx
, uint16_t, blob
->length
/2);
2283 return NT_STATUS_NO_MEMORY
;
2285 memcpy(r
->array
, blob
->data
, blob
->length
);
2286 r
->size
= blob
->length
;
2287 r
->length
= blob
->length
;
2290 return NT_STATUS_NO_MEMORY
;
2295 return NT_STATUS_OK
;
2298 /*************************************************************************
2299 get_user_info_7. Safe. Only gives out account_name.
2300 *************************************************************************/
2302 static NTSTATUS
get_user_info_7(TALLOC_CTX
*mem_ctx
,
2303 struct samr_UserInfo7
*r
,
2306 struct samu
*smbpass
=NULL
;
2308 const char *account_name
= NULL
;
2312 if ( !(smbpass
= samu_new( mem_ctx
)) ) {
2313 return NT_STATUS_NO_MEMORY
;
2317 ret
= pdb_getsampwsid(smbpass
, user_sid
);
2321 DEBUG(4,("User %s not found\n", sid_string_dbg(user_sid
)));
2322 return NT_STATUS_NO_SUCH_USER
;
2325 account_name
= talloc_strdup(mem_ctx
, pdb_get_username(smbpass
));
2326 if (!account_name
) {
2327 TALLOC_FREE(smbpass
);
2328 return NT_STATUS_NO_MEMORY
;
2330 TALLOC_FREE(smbpass
);
2332 DEBUG(3,("User:[%s]\n", account_name
));
2334 init_samr_user_info7(r
, account_name
);
2336 return NT_STATUS_OK
;
2339 /*************************************************************************
2340 get_user_info_9. Only gives out primary group SID.
2341 *************************************************************************/
2343 static NTSTATUS
get_user_info_9(TALLOC_CTX
*mem_ctx
,
2344 struct samr_UserInfo9
*r
,
2347 struct samu
*smbpass
=NULL
;
2352 if ( !(smbpass
= samu_new( mem_ctx
)) ) {
2353 return NT_STATUS_NO_MEMORY
;
2357 ret
= pdb_getsampwsid(smbpass
, user_sid
);
2361 DEBUG(4,("User %s not found\n", sid_string_dbg(user_sid
)));
2362 TALLOC_FREE(smbpass
);
2363 return NT_STATUS_NO_SUCH_USER
;
2366 DEBUG(3,("User:[%s]\n", pdb_get_username(smbpass
) ));
2368 init_samr_user_info9(r
, pdb_get_group_rid(smbpass
));
2370 TALLOC_FREE(smbpass
);
2372 return NT_STATUS_OK
;
2375 /*************************************************************************
2376 get_user_info_16. Safe. Only gives out acb bits.
2377 *************************************************************************/
2379 static NTSTATUS
get_user_info_16(TALLOC_CTX
*mem_ctx
,
2380 struct samr_UserInfo16
*r
,
2383 struct samu
*smbpass
=NULL
;
2388 if ( !(smbpass
= samu_new( mem_ctx
)) ) {
2389 return NT_STATUS_NO_MEMORY
;
2393 ret
= pdb_getsampwsid(smbpass
, user_sid
);
2397 DEBUG(4,("User %s not found\n", sid_string_dbg(user_sid
)));
2398 TALLOC_FREE(smbpass
);
2399 return NT_STATUS_NO_SUCH_USER
;
2402 DEBUG(3,("User:[%s]\n", pdb_get_username(smbpass
) ));
2404 init_samr_user_info16(r
, pdb_get_acct_ctrl(smbpass
));
2406 TALLOC_FREE(smbpass
);
2408 return NT_STATUS_OK
;
2411 /*************************************************************************
2412 get_user_info_18. OK - this is the killer as it gives out password info.
2413 Ensure that this is only allowed on an encrypted connection with a root
2415 *************************************************************************/
2417 static NTSTATUS
get_user_info_18(pipes_struct
*p
,
2418 TALLOC_CTX
*mem_ctx
,
2419 struct samr_UserInfo18
*r
,
2422 struct samu
*smbpass
=NULL
;
2427 if (p
->auth
.auth_type
!= PIPE_AUTH_TYPE_NTLMSSP
|| p
->auth
.auth_type
!= PIPE_AUTH_TYPE_SPNEGO_NTLMSSP
) {
2428 return NT_STATUS_ACCESS_DENIED
;
2431 if (p
->auth
.auth_level
!= PIPE_AUTH_LEVEL_PRIVACY
) {
2432 return NT_STATUS_ACCESS_DENIED
;
2436 * Do *NOT* do become_root()/unbecome_root() here ! JRA.
2439 if ( !(smbpass
= samu_new( mem_ctx
)) ) {
2440 return NT_STATUS_NO_MEMORY
;
2443 ret
= pdb_getsampwsid(smbpass
, user_sid
);
2446 DEBUG(4, ("User %s not found\n", sid_string_dbg(user_sid
)));
2447 TALLOC_FREE(smbpass
);
2448 return (geteuid() == (uid_t
)0) ? NT_STATUS_NO_SUCH_USER
: NT_STATUS_ACCESS_DENIED
;
2451 DEBUG(3,("User:[%s] 0x%x\n", pdb_get_username(smbpass
), pdb_get_acct_ctrl(smbpass
) ));
2453 if ( pdb_get_acct_ctrl(smbpass
) & ACB_DISABLED
) {
2454 TALLOC_FREE(smbpass
);
2455 return NT_STATUS_ACCOUNT_DISABLED
;
2458 init_samr_user_info18(r
, pdb_get_lanman_passwd(smbpass
),
2459 pdb_get_nt_passwd(smbpass
));
2461 TALLOC_FREE(smbpass
);
2463 return NT_STATUS_OK
;
2466 /*************************************************************************
2468 *************************************************************************/
2470 static NTSTATUS
get_user_info_20(TALLOC_CTX
*mem_ctx
,
2471 struct samr_UserInfo20
*r
,
2474 struct samu
*sampass
=NULL
;
2476 const char *munged_dial
= NULL
;
2479 struct lsa_BinaryString
*parameters
= NULL
;
2483 if ( !(sampass
= samu_new( mem_ctx
)) ) {
2484 return NT_STATUS_NO_MEMORY
;
2488 ret
= pdb_getsampwsid(sampass
, user_sid
);
2492 DEBUG(4,("User %s not found\n", sid_string_dbg(user_sid
)));
2493 TALLOC_FREE(sampass
);
2494 return NT_STATUS_NO_SUCH_USER
;
2497 munged_dial
= pdb_get_munged_dial(sampass
);
2499 samr_clear_sam_passwd(sampass
);
2501 DEBUG(3,("User:[%s] has [%s] (length: %d)\n", pdb_get_username(sampass
),
2502 munged_dial
, (int)strlen(munged_dial
)));
2505 blob
= base64_decode_data_blob(munged_dial
);
2507 blob
= data_blob_string_const("");
2510 status
= init_samr_parameters_string(mem_ctx
, &blob
, ¶meters
);
2511 data_blob_free(&blob
);
2512 TALLOC_FREE(sampass
);
2513 if (!NT_STATUS_IS_OK(status
)) {
2517 init_samr_user_info20(r
, parameters
);
2519 return NT_STATUS_OK
;
2523 /*************************************************************************
2525 *************************************************************************/
2527 static NTSTATUS
get_user_info_21(TALLOC_CTX
*mem_ctx
,
2528 struct samr_UserInfo21
*r
,
2530 DOM_SID
*domain_sid
)
2533 struct samu
*pw
= NULL
;
2535 const DOM_SID
*sid_user
, *sid_group
;
2536 uint32_t rid
, primary_gid
;
2537 NTTIME last_logon
, last_logoff
, last_password_change
,
2538 acct_expiry
, allow_password_change
, force_password_change
;
2539 time_t must_change_time
;
2540 uint8_t password_expired
;
2541 const char *account_name
, *full_name
, *home_directory
, *home_drive
,
2542 *logon_script
, *profile_path
, *description
,
2543 *workstations
, *comment
;
2544 struct samr_LogonHours logon_hours
;
2545 struct lsa_BinaryString
*parameters
= NULL
;
2546 const char *munged_dial
= NULL
;
2551 if (!(pw
= samu_new(mem_ctx
))) {
2552 return NT_STATUS_NO_MEMORY
;
2556 ret
= pdb_getsampwsid(pw
, user_sid
);
2560 DEBUG(4,("User %s not found\n", sid_string_dbg(user_sid
)));
2562 return NT_STATUS_NO_SUCH_USER
;
2565 samr_clear_sam_passwd(pw
);
2567 DEBUG(3,("User:[%s]\n", pdb_get_username(pw
)));
2569 sid_user
= pdb_get_user_sid(pw
);
2571 if (!sid_peek_check_rid(domain_sid
, sid_user
, &rid
)) {
2572 DEBUG(0, ("get_user_info_21: User %s has SID %s, \nwhich conflicts with "
2573 "the domain sid %s. Failing operation.\n",
2574 pdb_get_username(pw
), sid_string_dbg(sid_user
),
2575 sid_string_dbg(domain_sid
)));
2577 return NT_STATUS_UNSUCCESSFUL
;
2581 sid_group
= pdb_get_group_sid(pw
);
2584 if (!sid_peek_check_rid(domain_sid
, sid_group
, &primary_gid
)) {
2585 DEBUG(0, ("get_user_info_21: User %s has Primary Group SID %s, \n"
2586 "which conflicts with the domain sid %s. Failing operation.\n",
2587 pdb_get_username(pw
), sid_string_dbg(sid_group
),
2588 sid_string_dbg(domain_sid
)));
2590 return NT_STATUS_UNSUCCESSFUL
;
2593 unix_to_nt_time(&last_logon
, pdb_get_logon_time(pw
));
2594 unix_to_nt_time(&last_logoff
, pdb_get_logoff_time(pw
));
2595 unix_to_nt_time(&acct_expiry
, pdb_get_kickoff_time(pw
));
2596 unix_to_nt_time(&last_password_change
, pdb_get_pass_last_set_time(pw
));
2597 unix_to_nt_time(&allow_password_change
, pdb_get_pass_can_change_time(pw
));
2599 must_change_time
= pdb_get_pass_must_change_time(pw
);
2600 if (must_change_time
== get_time_t_max()) {
2601 unix_to_nt_time_abs(&force_password_change
, must_change_time
);
2603 unix_to_nt_time(&force_password_change
, must_change_time
);
2606 if (pdb_get_pass_must_change_time(pw
) == 0) {
2607 password_expired
= PASS_MUST_CHANGE_AT_NEXT_LOGON
;
2609 password_expired
= 0;
2612 munged_dial
= pdb_get_munged_dial(pw
);
2614 blob
= base64_decode_data_blob(munged_dial
);
2616 blob
= data_blob_string_const("");
2619 status
= init_samr_parameters_string(mem_ctx
, &blob
, ¶meters
);
2620 data_blob_free(&blob
);
2621 if (!NT_STATUS_IS_OK(status
)) {
2626 account_name
= talloc_strdup(mem_ctx
, pdb_get_username(pw
));
2627 full_name
= talloc_strdup(mem_ctx
, pdb_get_fullname(pw
));
2628 home_directory
= talloc_strdup(mem_ctx
, pdb_get_homedir(pw
));
2629 home_drive
= talloc_strdup(mem_ctx
, pdb_get_dir_drive(pw
));
2630 logon_script
= talloc_strdup(mem_ctx
, pdb_get_logon_script(pw
));
2631 profile_path
= talloc_strdup(mem_ctx
, pdb_get_profile_path(pw
));
2632 description
= talloc_strdup(mem_ctx
, pdb_get_acct_desc(pw
));
2633 workstations
= talloc_strdup(mem_ctx
, pdb_get_workstations(pw
));
2634 comment
= talloc_strdup(mem_ctx
, pdb_get_comment(pw
));
2636 logon_hours
= get_logon_hours_from_pdb(mem_ctx
, pw
);
2640 Look at a user on a real NT4 PDC with usrmgr, press
2641 'ok'. Then you will see that fields_present is set to
2642 0x08f827fa. Look at the user immediately after that again,
2643 and you will see that 0x00fffff is returned. This solves
2644 the problem that you get access denied after having looked
2651 init_samr_user_info21(r
,
2654 last_password_change
,
2656 allow_password_change
,
2657 force_password_change
,
2670 pdb_get_acct_ctrl(pw
),
2671 pdb_build_fields_present(pw
),
2673 pdb_get_bad_password_count(pw
),
2674 pdb_get_logon_count(pw
),
2675 0, /* country_code */
2677 0, /* nt_password_set */
2678 0, /* lm_password_set */
2682 return NT_STATUS_OK
;
2685 /*******************************************************************
2687 ********************************************************************/
2689 NTSTATUS
_samr_QueryUserInfo(pipes_struct
*p
,
2690 struct samr_QueryUserInfo
*r
)
2693 union samr_UserInfo
*user_info
= NULL
;
2694 struct samr_info
*info
= NULL
;
2698 /* search for the handle */
2699 if (!find_policy_by_hnd(p
, r
->in
.user_handle
, (void **)(void *)&info
))
2700 return NT_STATUS_INVALID_HANDLE
;
2702 status
= access_check_samr_function(info
->acc_granted
,
2703 SA_RIGHT_DOMAIN_OPEN_ACCOUNT
,
2704 "_samr_QueryUserInfo");
2705 if (!NT_STATUS_IS_OK(status
)) {
2709 domain_sid
= info
->sid
;
2711 sid_split_rid(&domain_sid
, &rid
);
2713 if (!sid_check_is_in_our_domain(&info
->sid
))
2714 return NT_STATUS_OBJECT_TYPE_MISMATCH
;
2716 DEBUG(5,("_samr_QueryUserInfo: sid:%s\n",
2717 sid_string_dbg(&info
->sid
)));
2719 user_info
= TALLOC_ZERO_P(p
->mem_ctx
, union samr_UserInfo
);
2721 return NT_STATUS_NO_MEMORY
;
2724 DEBUG(5,("_samr_QueryUserInfo: user info level: %d\n", r
->in
.level
));
2726 switch (r
->in
.level
) {
2728 status
= get_user_info_7(p
->mem_ctx
, &user_info
->info7
, &info
->sid
);
2729 if (!NT_STATUS_IS_OK(status
)) {
2734 status
= get_user_info_9(p
->mem_ctx
, &user_info
->info9
, &info
->sid
);
2735 if (!NT_STATUS_IS_OK(status
)) {
2740 status
= get_user_info_16(p
->mem_ctx
, &user_info
->info16
, &info
->sid
);
2741 if (!NT_STATUS_IS_OK(status
)) {
2747 status
= get_user_info_18(p
, p
->mem_ctx
, &user_info
->info18
, &info
->sid
);
2748 if (!NT_STATUS_IS_OK(status
)) {
2754 status
= get_user_info_20(p
->mem_ctx
, &user_info
->info20
, &info
->sid
);
2755 if (!NT_STATUS_IS_OK(status
)) {
2761 status
= get_user_info_21(p
->mem_ctx
, &user_info
->info21
,
2762 &info
->sid
, &domain_sid
);
2763 if (!NT_STATUS_IS_OK(status
)) {
2769 return NT_STATUS_INVALID_INFO_CLASS
;
2772 *r
->out
.info
= user_info
;
2774 DEBUG(5,("_samr_QueryUserInfo: %d\n", __LINE__
));
2779 /*******************************************************************
2780 _samr_GetGroupsForUser
2781 ********************************************************************/
2783 NTSTATUS
_samr_GetGroupsForUser(pipes_struct
*p
,
2784 struct samr_GetGroupsForUser
*r
)
2786 struct samu
*sam_pass
=NULL
;
2789 struct samr_RidWithAttribute dom_gid
;
2790 struct samr_RidWithAttribute
*gids
= NULL
;
2791 uint32 primary_group_rid
;
2792 size_t num_groups
= 0;
2798 bool success
= False
;
2800 struct samr_RidWithAttributeArray
*rids
= NULL
;
2803 * from the SID in the request:
2804 * we should send back the list of DOMAIN GROUPS
2805 * the user is a member of
2807 * and only the DOMAIN GROUPS
2808 * no ALIASES !!! neither aliases of the domain
2809 * nor aliases of the builtin SID
2814 DEBUG(5,("_samr_GetGroupsForUser: %d\n", __LINE__
));
2816 rids
= TALLOC_ZERO_P(p
->mem_ctx
, struct samr_RidWithAttributeArray
);
2818 return NT_STATUS_NO_MEMORY
;
2821 /* find the policy handle. open a policy on it. */
2822 if (!get_lsa_policy_samr_sid(p
, r
->in
.user_handle
, &sid
, &acc_granted
, NULL
))
2823 return NT_STATUS_INVALID_HANDLE
;
2825 result
= access_check_samr_function(acc_granted
,
2826 SA_RIGHT_USER_GET_GROUPS
,
2827 "_samr_GetGroupsForUser");
2828 if (!NT_STATUS_IS_OK(result
)) {
2832 if (!sid_check_is_in_our_domain(&sid
))
2833 return NT_STATUS_OBJECT_TYPE_MISMATCH
;
2835 if ( !(sam_pass
= samu_new( p
->mem_ctx
)) ) {
2836 return NT_STATUS_NO_MEMORY
;
2840 ret
= pdb_getsampwsid(sam_pass
, &sid
);
2844 DEBUG(10, ("pdb_getsampwsid failed for %s\n",
2845 sid_string_dbg(&sid
)));
2846 return NT_STATUS_NO_SUCH_USER
;
2851 /* make both calls inside the root block */
2853 result
= pdb_enum_group_memberships(p
->mem_ctx
, sam_pass
,
2854 &sids
, &unix_gids
, &num_groups
);
2855 if ( NT_STATUS_IS_OK(result
) ) {
2856 success
= sid_peek_check_rid(get_global_sam_sid(),
2857 pdb_get_group_sid(sam_pass
),
2858 &primary_group_rid
);
2862 if (!NT_STATUS_IS_OK(result
)) {
2863 DEBUG(10, ("pdb_enum_group_memberships failed for %s\n",
2864 sid_string_dbg(&sid
)));
2869 DEBUG(5, ("Group sid %s for user %s not in our domain\n",
2870 sid_string_dbg(pdb_get_group_sid(sam_pass
)),
2871 pdb_get_username(sam_pass
)));
2872 TALLOC_FREE(sam_pass
);
2873 return NT_STATUS_INTERNAL_DB_CORRUPTION
;
2879 dom_gid
.attributes
= (SE_GROUP_MANDATORY
|SE_GROUP_ENABLED_BY_DEFAULT
|
2881 dom_gid
.rid
= primary_group_rid
;
2882 ADD_TO_ARRAY(p
->mem_ctx
, struct samr_RidWithAttribute
, dom_gid
, &gids
, &num_gids
);
2884 for (i
=0; i
<num_groups
; i
++) {
2886 if (!sid_peek_check_rid(get_global_sam_sid(),
2887 &(sids
[i
]), &dom_gid
.rid
)) {
2888 DEBUG(10, ("Found sid %s not in our domain\n",
2889 sid_string_dbg(&sids
[i
])));
2893 if (dom_gid
.rid
== primary_group_rid
) {
2894 /* We added the primary group directly from the
2895 * sam_account. The other SIDs are unique from
2896 * enum_group_memberships */
2900 ADD_TO_ARRAY(p
->mem_ctx
, struct samr_RidWithAttribute
, dom_gid
, &gids
, &num_gids
);
2903 rids
->count
= num_gids
;
2906 *r
->out
.rids
= rids
;
2908 DEBUG(5,("_samr_GetGroupsForUser: %d\n", __LINE__
));
2913 /*******************************************************************
2914 _samr_QueryDomainInfo
2915 ********************************************************************/
2917 NTSTATUS
_samr_QueryDomainInfo(pipes_struct
*p
,
2918 struct samr_QueryDomainInfo
*r
)
2920 NTSTATUS status
= NT_STATUS_OK
;
2921 struct samr_info
*info
= NULL
;
2922 union samr_DomainInfo
*dom_info
;
2923 uint32 min_pass_len
,pass_hist
,password_properties
;
2924 time_t u_expire
, u_min_age
;
2925 NTTIME nt_expire
, nt_min_age
;
2927 time_t u_lock_duration
, u_reset_time
;
2928 NTTIME nt_lock_duration
, nt_reset_time
;
2933 uint32 account_policy_temp
;
2938 uint32 num_users
=0, num_groups
=0, num_aliases
=0;
2940 DEBUG(5,("_samr_QueryDomainInfo: %d\n", __LINE__
));
2942 dom_info
= TALLOC_ZERO_P(p
->mem_ctx
, union samr_DomainInfo
);
2944 return NT_STATUS_NO_MEMORY
;
2947 /* find the policy handle. open a policy on it. */
2948 if (!find_policy_by_hnd(p
, r
->in
.domain_handle
, (void **)(void *)&info
)) {
2949 return NT_STATUS_INVALID_HANDLE
;
2952 status
= access_check_samr_function(info
->acc_granted
,
2953 SA_RIGHT_SAM_OPEN_DOMAIN
,
2954 "_samr_QueryDomainInfo" );
2956 if ( !NT_STATUS_IS_OK(status
) )
2959 switch (r
->in
.level
) {
2966 pdb_get_account_policy(AP_MIN_PASSWORD_LEN
, &account_policy_temp
);
2967 min_pass_len
= account_policy_temp
;
2969 pdb_get_account_policy(AP_PASSWORD_HISTORY
, &account_policy_temp
);
2970 pass_hist
= account_policy_temp
;
2972 pdb_get_account_policy(AP_USER_MUST_LOGON_TO_CHG_PASS
, &account_policy_temp
);
2973 password_properties
= account_policy_temp
;
2975 pdb_get_account_policy(AP_MAX_PASSWORD_AGE
, &account_policy_temp
);
2976 u_expire
= account_policy_temp
;
2978 pdb_get_account_policy(AP_MIN_PASSWORD_AGE
, &account_policy_temp
);
2979 u_min_age
= account_policy_temp
;
2985 unix_to_nt_time_abs(&nt_expire
, u_expire
);
2986 unix_to_nt_time_abs(&nt_min_age
, u_min_age
);
2988 if (lp_check_password_script() && *lp_check_password_script()) {
2989 password_properties
|= DOMAIN_PASSWORD_COMPLEX
;
2992 init_samr_DomInfo1(&dom_info
->info1
,
2993 (uint16
)min_pass_len
,
2995 password_properties
,
3005 num_users
= count_sam_users(info
->disp_info
, ACB_NORMAL
);
3006 num_groups
= count_sam_groups(info
->disp_info
);
3007 num_aliases
= count_sam_aliases(info
->disp_info
);
3009 pdb_get_account_policy(AP_TIME_TO_LOGOUT
, &account_policy_temp
);
3010 u_logout
= account_policy_temp
;
3012 unix_to_nt_time_abs(&nt_logout
, u_logout
);
3014 if (!pdb_get_seq_num(&seq_num
))
3015 seq_num
= time(NULL
);
3021 server_role
= ROLE_DOMAIN_PDC
;
3022 if (lp_server_role() == ROLE_DOMAIN_BDC
)
3023 server_role
= ROLE_DOMAIN_BDC
;
3025 init_samr_DomInfo2(&dom_info
->info2
,
3046 pdb_get_account_policy(AP_TIME_TO_LOGOUT
, &ul
);
3047 u_logout
= (time_t)ul
;
3054 unix_to_nt_time_abs(&nt_logout
, u_logout
);
3056 init_samr_DomInfo3(&dom_info
->info3
,
3061 init_samr_DomInfo4(&dom_info
->info4
,
3065 init_samr_DomInfo5(&dom_info
->info5
,
3066 get_global_sam_name());
3069 /* NT returns its own name when a PDC. win2k and later
3070 * only the name of the PDC if itself is a BDC (samba4
3072 init_samr_DomInfo6(&dom_info
->info6
,
3076 server_role
= ROLE_DOMAIN_PDC
;
3077 if (lp_server_role() == ROLE_DOMAIN_BDC
)
3078 server_role
= ROLE_DOMAIN_BDC
;
3080 init_samr_DomInfo7(&dom_info
->info7
,
3089 if (!pdb_get_seq_num(&seq_num
)) {
3090 seq_num
= time(NULL
);
3097 init_samr_DomInfo8(&dom_info
->info8
,
3107 pdb_get_account_policy(AP_LOCK_ACCOUNT_DURATION
, &account_policy_temp
);
3108 u_lock_duration
= account_policy_temp
;
3109 if (u_lock_duration
!= -1) {
3110 u_lock_duration
*= 60;
3113 pdb_get_account_policy(AP_RESET_COUNT_TIME
, &account_policy_temp
);
3114 u_reset_time
= account_policy_temp
* 60;
3116 pdb_get_account_policy(AP_BAD_ATTEMPT_LOCKOUT
, &account_policy_temp
);
3117 lockout
= account_policy_temp
;
3123 unix_to_nt_time_abs(&nt_lock_duration
, u_lock_duration
);
3124 unix_to_nt_time_abs(&nt_reset_time
, u_reset_time
);
3126 init_samr_DomInfo12(&dom_info
->info12
,
3132 return NT_STATUS_INVALID_INFO_CLASS
;
3135 *r
->out
.info
= dom_info
;
3137 DEBUG(5,("_samr_QueryDomainInfo: %d\n", __LINE__
));
3142 /* W2k3 seems to use the same check for all 3 objects that can be created via
3143 * SAMR, if you try to create for example "Dialup" as an alias it says
3144 * "NT_STATUS_USER_EXISTS". This is racy, but we can't really lock the user
3147 static NTSTATUS
can_create(TALLOC_CTX
*mem_ctx
, const char *new_name
)
3149 enum lsa_SidType type
;
3152 DEBUG(10, ("Checking whether [%s] can be created\n", new_name
));
3155 /* Lookup in our local databases (LOOKUP_NAME_REMOTE not set)
3156 * whether the name already exists */
3157 result
= lookup_name(mem_ctx
, new_name
, LOOKUP_NAME_LOCAL
,
3158 NULL
, NULL
, NULL
, &type
);
3162 DEBUG(10, ("%s does not exist, can create it\n", new_name
));
3163 return NT_STATUS_OK
;
3166 DEBUG(5, ("trying to create %s, exists as %s\n",
3167 new_name
, sid_type_lookup(type
)));
3169 if (type
== SID_NAME_DOM_GRP
) {
3170 return NT_STATUS_GROUP_EXISTS
;
3172 if (type
== SID_NAME_ALIAS
) {
3173 return NT_STATUS_ALIAS_EXISTS
;
3176 /* Yes, the default is NT_STATUS_USER_EXISTS */
3177 return NT_STATUS_USER_EXISTS
;
3180 /*******************************************************************
3182 ********************************************************************/
3184 NTSTATUS
_samr_CreateUser2(pipes_struct
*p
,
3185 struct samr_CreateUser2
*r
)
3187 const char *account
= NULL
;
3189 POLICY_HND dom_pol
= *r
->in
.domain_handle
;
3190 uint32_t acb_info
= r
->in
.acct_flags
;
3191 POLICY_HND
*user_pol
= r
->out
.user_handle
;
3192 struct samr_info
*info
= NULL
;
3197 /* check this, when giving away 'add computer to domain' privs */
3198 uint32 des_access
= GENERIC_RIGHTS_USER_ALL_ACCESS
;
3199 bool can_add_account
= False
;
3201 DISP_INFO
*disp_info
= NULL
;
3203 /* Get the domain SID stored in the domain policy */
3204 if (!get_lsa_policy_samr_sid(p
, &dom_pol
, &sid
, &acc_granted
,
3206 return NT_STATUS_INVALID_HANDLE
;
3208 nt_status
= access_check_samr_function(acc_granted
,
3209 SA_RIGHT_DOMAIN_CREATE_USER
,
3210 "_samr_CreateUser2");
3211 if (!NT_STATUS_IS_OK(nt_status
)) {
3215 if (!(acb_info
== ACB_NORMAL
|| acb_info
== ACB_DOMTRUST
||
3216 acb_info
== ACB_WSTRUST
|| acb_info
== ACB_SVRTRUST
)) {
3217 /* Match Win2k, and return NT_STATUS_INVALID_PARAMETER if
3218 this parameter is not an account type */
3219 return NT_STATUS_INVALID_PARAMETER
;
3222 account
= r
->in
.account_name
->string
;
3223 if (account
== NULL
) {
3224 return NT_STATUS_NO_MEMORY
;
3227 nt_status
= can_create(p
->mem_ctx
, account
);
3228 if (!NT_STATUS_IS_OK(nt_status
)) {
3232 /* determine which user right we need to check based on the acb_info */
3234 if ( acb_info
& ACB_WSTRUST
)
3236 se_priv_copy( &se_rights
, &se_machine_account
);
3237 can_add_account
= user_has_privileges(
3238 p
->pipe_user
.nt_user_token
, &se_rights
);
3240 /* usrmgr.exe (and net rpc trustdom grant) creates a normal user
3241 account for domain trusts and changes the ACB flags later */
3242 else if ( acb_info
& ACB_NORMAL
&&
3243 (account
[strlen(account
)-1] != '$') )
3245 se_priv_copy( &se_rights
, &se_add_users
);
3246 can_add_account
= user_has_privileges(
3247 p
->pipe_user
.nt_user_token
, &se_rights
);
3249 else /* implicit assumption of a BDC or domain trust account here
3250 * (we already check the flags earlier) */
3252 if ( lp_enable_privileges() ) {
3253 /* only Domain Admins can add a BDC or domain trust */
3254 se_priv_copy( &se_rights
, &se_priv_none
);
3255 can_add_account
= nt_token_check_domain_rid(
3256 p
->pipe_user
.nt_user_token
,
3257 DOMAIN_GROUP_RID_ADMINS
);
3261 DEBUG(5, ("_samr_CreateUser2: %s can add this account : %s\n",
3262 uidtoname(p
->pipe_user
.ut
.uid
),
3263 can_add_account
? "True":"False" ));
3265 /********** BEGIN Admin BLOCK **********/
3267 if ( can_add_account
)
3270 nt_status
= pdb_create_user(p
->mem_ctx
, account
, acb_info
,
3273 if ( can_add_account
)
3276 /********** END Admin BLOCK **********/
3278 /* now check for failure */
3280 if ( !NT_STATUS_IS_OK(nt_status
) )
3283 /* Get the user's SID */
3285 sid_compose(&sid
, get_global_sam_sid(), *r
->out
.rid
);
3287 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
3289 make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &usr_generic_mapping
,
3290 &sid
, SAMR_USR_RIGHTS_WRITE_PW
);
3291 se_map_generic(&des_access
, &usr_generic_mapping
);
3293 nt_status
= access_check_samr_object(psd
, p
->pipe_user
.nt_user_token
,
3294 &se_rights
, GENERIC_RIGHTS_USER_WRITE
, des_access
,
3295 &acc_granted
, "_samr_CreateUser2");
3297 if ( !NT_STATUS_IS_OK(nt_status
) ) {
3301 /* associate the user's SID with the new handle. */
3302 if ((info
= get_samr_info_by_sid(&sid
)) == NULL
) {
3303 return NT_STATUS_NO_MEMORY
;
3308 info
->acc_granted
= acc_granted
;
3310 /* get a (unique) handle. open a policy on it. */
3311 if (!create_policy_hnd(p
, user_pol
, free_samr_info
, (void *)info
)) {
3312 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
3315 /* After a "set" ensure we have no cached display info. */
3316 force_flush_samr_cache(info
->disp_info
);
3318 *r
->out
.access_granted
= acc_granted
;
3320 return NT_STATUS_OK
;
3323 /*******************************************************************
3325 ********************************************************************/
3327 NTSTATUS
_samr_Connect(pipes_struct
*p
,
3328 struct samr_Connect
*r
)
3330 struct samr_info
*info
= NULL
;
3331 uint32 des_access
= r
->in
.access_mask
;
3335 if (!pipe_access_check(p
)) {
3336 DEBUG(3, ("access denied to _samr_Connect\n"));
3337 return NT_STATUS_ACCESS_DENIED
;
3340 /* set up the SAMR connect_anon response */
3342 /* associate the user's SID with the new handle. */
3343 if ((info
= get_samr_info_by_sid(NULL
)) == NULL
)
3344 return NT_STATUS_NO_MEMORY
;
3346 /* don't give away the farm but this is probably ok. The SA_RIGHT_SAM_ENUM_DOMAINS
3347 was observed from a win98 client trying to enumerate users (when configured
3348 user level access control on shares) --jerry */
3350 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
3352 se_map_generic( &des_access
, &sam_generic_mapping
);
3353 info
->acc_granted
= des_access
& (SA_RIGHT_SAM_ENUM_DOMAINS
|SA_RIGHT_SAM_OPEN_DOMAIN
);
3355 /* get a (unique) handle. open a policy on it. */
3356 if (!create_policy_hnd(p
, r
->out
.connect_handle
, free_samr_info
, (void *)info
))
3357 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
3359 return NT_STATUS_OK
;
3362 /*******************************************************************
3364 ********************************************************************/
3366 NTSTATUS
_samr_Connect2(pipes_struct
*p
,
3367 struct samr_Connect2
*r
)
3369 struct samr_info
*info
= NULL
;
3370 SEC_DESC
*psd
= NULL
;
3372 uint32 des_access
= r
->in
.access_mask
;
3377 DEBUG(5,("_samr_Connect2: %d\n", __LINE__
));
3381 if (!pipe_access_check(p
)) {
3382 DEBUG(3, ("access denied to _samr_Connect2\n"));
3383 return NT_STATUS_ACCESS_DENIED
;
3386 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
3388 make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &sam_generic_mapping
, NULL
, 0);
3389 se_map_generic(&des_access
, &sam_generic_mapping
);
3391 nt_status
= access_check_samr_object(psd
, p
->pipe_user
.nt_user_token
,
3392 NULL
, 0, des_access
, &acc_granted
, "_samr_Connect2");
3394 if ( !NT_STATUS_IS_OK(nt_status
) )
3397 /* associate the user's SID and access granted with the new handle. */
3398 if ((info
= get_samr_info_by_sid(NULL
)) == NULL
)
3399 return NT_STATUS_NO_MEMORY
;
3401 info
->acc_granted
= acc_granted
;
3402 info
->status
= r
->in
.access_mask
; /* this looks so wrong... - gd */
3404 /* get a (unique) handle. open a policy on it. */
3405 if (!create_policy_hnd(p
, r
->out
.connect_handle
, free_samr_info
, (void *)info
))
3406 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
3408 DEBUG(5,("_samr_Connect2: %d\n", __LINE__
));
3413 /*******************************************************************
3415 ********************************************************************/
3417 NTSTATUS
_samr_Connect4(pipes_struct
*p
,
3418 struct samr_Connect4
*r
)
3420 struct samr_info
*info
= NULL
;
3421 SEC_DESC
*psd
= NULL
;
3423 uint32 des_access
= r
->in
.access_mask
;
3428 DEBUG(5,("_samr_Connect4: %d\n", __LINE__
));
3432 if (!pipe_access_check(p
)) {
3433 DEBUG(3, ("access denied to samr_Connect4\n"));
3434 return NT_STATUS_ACCESS_DENIED
;
3437 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
3439 make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &sam_generic_mapping
, NULL
, 0);
3440 se_map_generic(&des_access
, &sam_generic_mapping
);
3442 nt_status
= access_check_samr_object(psd
, p
->pipe_user
.nt_user_token
,
3443 NULL
, 0, des_access
, &acc_granted
, "_samr_Connect4");
3445 if ( !NT_STATUS_IS_OK(nt_status
) )
3448 /* associate the user's SID and access granted with the new handle. */
3449 if ((info
= get_samr_info_by_sid(NULL
)) == NULL
)
3450 return NT_STATUS_NO_MEMORY
;
3452 info
->acc_granted
= acc_granted
;
3453 info
->status
= r
->in
.access_mask
; /* ??? */
3455 /* get a (unique) handle. open a policy on it. */
3456 if (!create_policy_hnd(p
, r
->out
.connect_handle
, free_samr_info
, (void *)info
))
3457 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
3459 DEBUG(5,("_samr_Connect4: %d\n", __LINE__
));
3461 return NT_STATUS_OK
;
3464 /*******************************************************************
3466 ********************************************************************/
3468 NTSTATUS
_samr_Connect5(pipes_struct
*p
,
3469 struct samr_Connect5
*r
)
3471 struct samr_info
*info
= NULL
;
3472 SEC_DESC
*psd
= NULL
;
3474 uint32 des_access
= r
->in
.access_mask
;
3477 struct samr_ConnectInfo1 info1
;
3479 DEBUG(5,("_samr_Connect5: %d\n", __LINE__
));
3483 if (!pipe_access_check(p
)) {
3484 DEBUG(3, ("access denied to samr_Connect5\n"));
3485 return NT_STATUS_ACCESS_DENIED
;
3488 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
3490 make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &sam_generic_mapping
, NULL
, 0);
3491 se_map_generic(&des_access
, &sam_generic_mapping
);
3493 nt_status
= access_check_samr_object(psd
, p
->pipe_user
.nt_user_token
,
3494 NULL
, 0, des_access
, &acc_granted
, "_samr_Connect5");
3496 if ( !NT_STATUS_IS_OK(nt_status
) )
3499 /* associate the user's SID and access granted with the new handle. */
3500 if ((info
= get_samr_info_by_sid(NULL
)) == NULL
)
3501 return NT_STATUS_NO_MEMORY
;
3503 info
->acc_granted
= acc_granted
;
3504 info
->status
= r
->in
.access_mask
; /* ??? */
3506 /* get a (unique) handle. open a policy on it. */
3507 if (!create_policy_hnd(p
, r
->out
.connect_handle
, free_samr_info
, (void *)info
))
3508 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
3510 DEBUG(5,("_samr_Connect5: %d\n", __LINE__
));
3512 info1
.client_version
= SAMR_CONNECT_AFTER_W2K
;
3515 *r
->out
.level_out
= 1;
3516 r
->out
.info_out
->info1
= info1
;
3518 return NT_STATUS_OK
;
3521 /**********************************************************************
3523 **********************************************************************/
3525 NTSTATUS
_samr_LookupDomain(pipes_struct
*p
,
3526 struct samr_LookupDomain
*r
)
3528 NTSTATUS status
= NT_STATUS_OK
;
3529 struct samr_info
*info
;
3530 const char *domain_name
;
3531 DOM_SID
*sid
= NULL
;
3533 if (!find_policy_by_hnd(p
, r
->in
.connect_handle
, (void**)(void *)&info
))
3534 return NT_STATUS_INVALID_HANDLE
;
3536 /* win9x user manager likes to use SA_RIGHT_SAM_ENUM_DOMAINS here.
3537 Reverted that change so we will work with RAS servers again */
3539 status
= access_check_samr_function(info
->acc_granted
,
3540 SA_RIGHT_SAM_OPEN_DOMAIN
,
3541 "_samr_LookupDomain");
3542 if (!NT_STATUS_IS_OK(status
)) {
3546 domain_name
= r
->in
.domain_name
->string
;
3548 sid
= TALLOC_ZERO_P(p
->mem_ctx
, struct dom_sid2
);
3550 return NT_STATUS_NO_MEMORY
;
3553 if (strequal(domain_name
, builtin_domain_name())) {
3554 sid_copy(sid
, &global_sid_Builtin
);
3556 if (!secrets_fetch_domain_sid(domain_name
, sid
)) {
3557 status
= NT_STATUS_NO_SUCH_DOMAIN
;
3561 DEBUG(2,("Returning domain sid for domain %s -> %s\n", domain_name
,
3562 sid_string_dbg(sid
)));
3569 /**********************************************************************
3571 **********************************************************************/
3573 NTSTATUS
_samr_EnumDomains(pipes_struct
*p
,
3574 struct samr_EnumDomains
*r
)
3577 struct samr_info
*info
;
3578 uint32_t num_entries
= 2;
3579 struct samr_SamEntry
*entry_array
= NULL
;
3580 struct samr_SamArray
*sam
;
3582 if (!find_policy_by_hnd(p
, r
->in
.connect_handle
, (void**)(void *)&info
))
3583 return NT_STATUS_INVALID_HANDLE
;
3585 status
= access_check_samr_function(info
->acc_granted
,
3586 SA_RIGHT_SAM_ENUM_DOMAINS
,
3587 "_samr_EnumDomains");
3588 if (!NT_STATUS_IS_OK(status
)) {
3592 sam
= TALLOC_ZERO_P(p
->mem_ctx
, struct samr_SamArray
);
3594 return NT_STATUS_NO_MEMORY
;
3597 entry_array
= TALLOC_ZERO_ARRAY(p
->mem_ctx
,
3598 struct samr_SamEntry
,
3601 return NT_STATUS_NO_MEMORY
;
3604 entry_array
[0].idx
= 0;
3605 init_lsa_String(&entry_array
[0].name
, get_global_sam_name());
3607 entry_array
[1].idx
= 1;
3608 init_lsa_String(&entry_array
[1].name
, "Builtin");
3610 sam
->count
= num_entries
;
3611 sam
->entries
= entry_array
;
3614 *r
->out
.num_entries
= num_entries
;
3619 /*******************************************************************
3621 ********************************************************************/
3623 NTSTATUS
_samr_OpenAlias(pipes_struct
*p
,
3624 struct samr_OpenAlias
*r
)
3627 POLICY_HND domain_pol
= *r
->in
.domain_handle
;
3628 uint32 alias_rid
= r
->in
.rid
;
3629 POLICY_HND
*alias_pol
= r
->out
.alias_handle
;
3630 struct samr_info
*info
= NULL
;
3631 SEC_DESC
*psd
= NULL
;
3633 uint32 des_access
= r
->in
.access_mask
;
3638 /* find the domain policy and get the SID / access bits stored in the domain policy */
3640 if ( !get_lsa_policy_samr_sid(p
, &domain_pol
, &sid
, &acc_granted
, NULL
) )
3641 return NT_STATUS_INVALID_HANDLE
;
3643 status
= access_check_samr_function(acc_granted
,
3644 SA_RIGHT_DOMAIN_OPEN_ACCOUNT
,
3647 if ( !NT_STATUS_IS_OK(status
) )
3650 /* append the alias' RID to it */
3652 if (!sid_append_rid(&sid
, alias_rid
))
3653 return NT_STATUS_NO_SUCH_ALIAS
;
3655 /*check if access can be granted as requested by client. */
3657 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
3659 make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &ali_generic_mapping
, NULL
, 0);
3660 se_map_generic(&des_access
,&ali_generic_mapping
);
3662 se_priv_copy( &se_rights
, &se_add_users
);
3665 status
= access_check_samr_object(psd
, p
->pipe_user
.nt_user_token
,
3666 &se_rights
, GENERIC_RIGHTS_ALIAS_WRITE
, des_access
,
3667 &acc_granted
, "_samr_OpenAlias");
3669 if ( !NT_STATUS_IS_OK(status
) )
3673 /* Check we actually have the requested alias */
3674 enum lsa_SidType type
;
3679 result
= lookup_sid(NULL
, &sid
, NULL
, NULL
, &type
);
3682 if (!result
|| (type
!= SID_NAME_ALIAS
)) {
3683 return NT_STATUS_NO_SUCH_ALIAS
;
3686 /* make sure there is a mapping */
3688 if ( !sid_to_gid( &sid
, &gid
) ) {
3689 return NT_STATUS_NO_SUCH_ALIAS
;
3694 /* associate the alias SID with the new handle. */
3695 if ((info
= get_samr_info_by_sid(&sid
)) == NULL
)
3696 return NT_STATUS_NO_MEMORY
;
3698 info
->acc_granted
= acc_granted
;
3700 /* get a (unique) handle. open a policy on it. */
3701 if (!create_policy_hnd(p
, alias_pol
, free_samr_info
, (void *)info
))
3702 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
3704 return NT_STATUS_OK
;
3707 /*******************************************************************
3709 ********************************************************************/
3711 static NTSTATUS
set_user_info_7(TALLOC_CTX
*mem_ctx
,
3712 struct samr_UserInfo7
*id7
,
3718 DEBUG(5, ("set_user_info_7: NULL id7\n"));
3720 return NT_STATUS_ACCESS_DENIED
;
3723 if (!id7
->account_name
.string
) {
3724 DEBUG(5, ("set_user_info_7: failed to get new username\n"));
3726 return NT_STATUS_ACCESS_DENIED
;
3729 /* check to see if the new username already exists. Note: we can't
3730 reliably lock all backends, so there is potentially the
3731 possibility that a user can be created in between this check and
3732 the rename. The rename should fail, but may not get the
3733 exact same failure status code. I think this is small enough
3734 of a window for this type of operation and the results are
3735 simply that the rename fails with a slightly different status
3736 code (like UNSUCCESSFUL instead of ALREADY_EXISTS). */
3738 rc
= can_create(mem_ctx
, id7
->account_name
.string
);
3739 if (!NT_STATUS_IS_OK(rc
)) {
3743 rc
= pdb_rename_sam_account(pwd
, id7
->account_name
.string
);
3749 /*******************************************************************
3751 ********************************************************************/
3753 static bool set_user_info_16(struct samr_UserInfo16
*id16
,
3757 DEBUG(5, ("set_user_info_16: NULL id16\n"));
3762 /* FIX ME: check if the value is really changed --metze */
3763 if (!pdb_set_acct_ctrl(pwd
, id16
->acct_flags
, PDB_CHANGED
)) {
3768 if(!NT_STATUS_IS_OK(pdb_update_sam_account(pwd
))) {
3778 /*******************************************************************
3780 ********************************************************************/
3782 static bool set_user_info_18(struct samr_UserInfo18
*id18
,
3786 DEBUG(2, ("set_user_info_18: id18 is NULL\n"));
3791 if (!pdb_set_lanman_passwd (pwd
, id18
->lm_pwd
.hash
, PDB_CHANGED
)) {
3795 if (!pdb_set_nt_passwd (pwd
, id18
->nt_pwd
.hash
, PDB_CHANGED
)) {
3799 if (!pdb_set_pass_last_set_time (pwd
, time(NULL
), PDB_CHANGED
)) {
3804 if(!NT_STATUS_IS_OK(pdb_update_sam_account(pwd
))) {
3813 /*******************************************************************
3815 ********************************************************************/
3817 static bool set_user_info_20(struct samr_UserInfo20
*id20
,
3821 DEBUG(5, ("set_user_info_20: NULL id20\n"));
3825 copy_id20_to_sam_passwd(pwd
, id20
);
3827 /* write the change out */
3828 if(!NT_STATUS_IS_OK(pdb_update_sam_account(pwd
))) {
3838 /*******************************************************************
3840 ********************************************************************/
3842 static NTSTATUS
set_user_info_21(TALLOC_CTX
*mem_ctx
,
3843 struct samr_UserInfo21
*id21
,
3849 DEBUG(5, ("set_user_info_21: NULL id21\n"));
3850 return NT_STATUS_INVALID_PARAMETER
;
3853 /* we need to separately check for an account rename first */
3855 if (id21
->account_name
.string
&&
3856 (!strequal(id21
->account_name
.string
, pdb_get_username(pwd
))))
3859 /* check to see if the new username already exists. Note: we can't
3860 reliably lock all backends, so there is potentially the
3861 possibility that a user can be created in between this check and
3862 the rename. The rename should fail, but may not get the
3863 exact same failure status code. I think this is small enough
3864 of a window for this type of operation and the results are
3865 simply that the rename fails with a slightly different status
3866 code (like UNSUCCESSFUL instead of ALREADY_EXISTS). */
3868 status
= can_create(mem_ctx
, id21
->account_name
.string
);
3869 if (!NT_STATUS_IS_OK(status
)) {
3873 status
= pdb_rename_sam_account(pwd
, id21
->account_name
.string
);
3875 if (!NT_STATUS_IS_OK(status
)) {
3876 DEBUG(0,("set_user_info_21: failed to rename account: %s\n",
3877 nt_errstr(status
)));
3882 /* set the new username so that later
3883 functions can work on the new account */
3884 pdb_set_username(pwd
, id21
->account_name
.string
, PDB_SET
);
3887 copy_id21_to_sam_passwd("INFO_21", pwd
, id21
);
3890 * The funny part about the previous two calls is
3891 * that pwd still has the password hashes from the
3892 * passdb entry. These have not been updated from
3893 * id21. I don't know if they need to be set. --jerry
3896 if ( IS_SAM_CHANGED(pwd
, PDB_GROUPSID
) ) {
3897 status
= pdb_set_unix_primary_group(mem_ctx
, pwd
);
3898 if ( !NT_STATUS_IS_OK(status
) ) {
3903 /* Don't worry about writing out the user account since the
3904 primary group SID is generated solely from the user's Unix
3907 /* write the change out */
3908 if(!NT_STATUS_IS_OK(status
= pdb_update_sam_account(pwd
))) {
3915 return NT_STATUS_OK
;
3918 /*******************************************************************
3920 ********************************************************************/
3922 static NTSTATUS
set_user_info_23(TALLOC_CTX
*mem_ctx
,
3923 struct samr_UserInfo23
*id23
,
3926 char *plaintext_buf
= NULL
;
3932 DEBUG(5, ("set_user_info_23: NULL id23\n"));
3933 return NT_STATUS_INVALID_PARAMETER
;
3936 DEBUG(5, ("Attempting administrator password change (level 23) for user %s\n",
3937 pdb_get_username(pwd
)));
3939 acct_ctrl
= pdb_get_acct_ctrl(pwd
);
3941 if (!decode_pw_buffer(mem_ctx
,
3942 id23
->password
.data
,
3947 return NT_STATUS_INVALID_PARAMETER
;
3950 if (!pdb_set_plaintext_passwd (pwd
, plaintext_buf
)) {
3952 return NT_STATUS_ACCESS_DENIED
;
3955 copy_id23_to_sam_passwd(pwd
, id23
);
3957 /* if it's a trust account, don't update /etc/passwd */
3958 if ( ( (acct_ctrl
& ACB_DOMTRUST
) == ACB_DOMTRUST
) ||
3959 ( (acct_ctrl
& ACB_WSTRUST
) == ACB_WSTRUST
) ||
3960 ( (acct_ctrl
& ACB_SVRTRUST
) == ACB_SVRTRUST
) ) {
3961 DEBUG(5, ("Changing trust account. Not updating /etc/passwd\n"));
3963 /* update the UNIX password */
3964 if (lp_unix_password_sync() ) {
3965 struct passwd
*passwd
;
3966 if (pdb_get_username(pwd
) == NULL
) {
3967 DEBUG(1, ("chgpasswd: User without name???\n"));
3969 return NT_STATUS_ACCESS_DENIED
;
3972 passwd
= Get_Pwnam_alloc(pwd
, pdb_get_username(pwd
));
3973 if (passwd
== NULL
) {
3974 DEBUG(1, ("chgpasswd: Username does not exist in system !?!\n"));
3977 if(!chgpasswd(pdb_get_username(pwd
), passwd
, "", plaintext_buf
, True
)) {
3979 return NT_STATUS_ACCESS_DENIED
;
3981 TALLOC_FREE(passwd
);
3985 memset(plaintext_buf
, '\0', strlen(plaintext_buf
));
3987 if (IS_SAM_CHANGED(pwd
, PDB_GROUPSID
) &&
3988 (!NT_STATUS_IS_OK(status
= pdb_set_unix_primary_group(mem_ctx
,
3994 if(!NT_STATUS_IS_OK(status
= pdb_update_sam_account(pwd
))) {
4001 return NT_STATUS_OK
;
4004 /*******************************************************************
4006 ********************************************************************/
4008 static bool set_user_info_pw(uint8
*pass
, struct samu
*pwd
,
4012 char *plaintext_buf
= NULL
;
4014 time_t last_set_time
;
4015 enum pdb_value_state last_set_state
;
4017 DEBUG(5, ("Attempting administrator password change for user %s\n",
4018 pdb_get_username(pwd
)));
4020 acct_ctrl
= pdb_get_acct_ctrl(pwd
);
4021 /* we need to know if it's expired, because this is an admin change, not a
4022 user change, so it's still expired when we're done */
4023 last_set_state
= pdb_get_init_flags(pwd
, PDB_PASSLASTSET
);
4024 last_set_time
= pdb_get_pass_last_set_time(pwd
);
4026 if (!decode_pw_buffer(talloc_tos(),
4035 if (!pdb_set_plaintext_passwd (pwd
, plaintext_buf
)) {
4040 /* if it's a trust account, don't update /etc/passwd */
4041 if ( ( (acct_ctrl
& ACB_DOMTRUST
) == ACB_DOMTRUST
) ||
4042 ( (acct_ctrl
& ACB_WSTRUST
) == ACB_WSTRUST
) ||
4043 ( (acct_ctrl
& ACB_SVRTRUST
) == ACB_SVRTRUST
) ) {
4044 DEBUG(5, ("Changing trust account or non-unix-user password, not updating /etc/passwd\n"));
4046 /* update the UNIX password */
4047 if (lp_unix_password_sync()) {
4048 struct passwd
*passwd
;
4050 if (pdb_get_username(pwd
) == NULL
) {
4051 DEBUG(1, ("chgpasswd: User without name???\n"));
4056 passwd
= Get_Pwnam_alloc(pwd
, pdb_get_username(pwd
));
4057 if (passwd
== NULL
) {
4058 DEBUG(1, ("chgpasswd: Username does not exist in system !?!\n"));
4061 if(!chgpasswd(pdb_get_username(pwd
), passwd
, "", plaintext_buf
, True
)) {
4065 TALLOC_FREE(passwd
);
4069 memset(plaintext_buf
, '\0', strlen(plaintext_buf
));
4072 * A level 25 change does reset the pwdlastset field, a level 24
4073 * change does not. I know this is probably not the full story, but
4074 * it is needed to make XP join LDAP correctly, without it the later
4075 * auth2 check can fail with PWD_MUST_CHANGE.
4079 * restore last set time as this is an admin change, not a
4082 pdb_set_pass_last_set_time (pwd
, last_set_time
,
4086 DEBUG(5,("set_user_info_pw: pdb_update_pwd()\n"));
4088 /* update the SAMBA password */
4089 if(!NT_STATUS_IS_OK(pdb_update_sam_account(pwd
))) {
4099 /*******************************************************************
4101 ********************************************************************/
4103 static NTSTATUS
set_user_info_25(TALLOC_CTX
*mem_ctx
,
4104 struct samr_UserInfo25
*id25
,
4110 DEBUG(5, ("set_user_info_25: NULL id25\n"));
4111 return NT_STATUS_INVALID_PARAMETER
;
4114 copy_id25_to_sam_passwd(pwd
, id25
);
4116 /* write the change out */
4117 if(!NT_STATUS_IS_OK(status
= pdb_update_sam_account(pwd
))) {
4123 * We need to "pdb_update_sam_account" before the unix primary group
4124 * is set, because the idealx scripts would also change the
4125 * sambaPrimaryGroupSid using the ldap replace method. pdb_ldap uses
4126 * the delete explicit / add explicit, which would then fail to find
4127 * the previous primaryGroupSid value.
4130 if ( IS_SAM_CHANGED(pwd
, PDB_GROUPSID
) ) {
4131 status
= pdb_set_unix_primary_group(mem_ctx
, pwd
);
4132 if ( !NT_STATUS_IS_OK(status
) ) {
4137 /* WARNING: No TALLOC_FREE(pwd), we are about to set the password
4140 return NT_STATUS_OK
;
4143 /*******************************************************************
4145 ********************************************************************/
4147 NTSTATUS
_samr_SetUserInfo(pipes_struct
*p
,
4148 struct samr_SetUserInfo
*r
)
4151 struct samu
*pwd
= NULL
;
4153 POLICY_HND
*pol
= r
->in
.user_handle
;
4154 union samr_UserInfo
*info
= r
->in
.info
;
4155 uint16_t switch_value
= r
->in
.level
;
4156 uint32_t acc_granted
;
4157 uint32_t acc_required
;
4159 bool has_enough_rights
= False
;
4161 DISP_INFO
*disp_info
= NULL
;
4163 DEBUG(5,("_samr_SetUserInfo: %d\n", __LINE__
));
4165 /* find the policy handle. open a policy on it. */
4166 if (!get_lsa_policy_samr_sid(p
, pol
, &sid
, &acc_granted
, &disp_info
)) {
4167 return NT_STATUS_INVALID_HANDLE
;
4170 /* This is tricky. A WinXP domain join sets
4171 (SA_RIGHT_USER_SET_PASSWORD|SA_RIGHT_USER_SET_ATTRIBUTES|SA_RIGHT_USER_ACCT_FLAGS_EXPIRY)
4172 The MMC lusrmgr plugin includes these perms and more in the SamrOpenUser(). But the
4173 standard Win32 API calls just ask for SA_RIGHT_USER_SET_PASSWORD in the SamrOpenUser().
4174 This should be enough for levels 18, 24, 25,& 26. Info level 23 can set more so
4175 we'll use the set from the WinXP join as the basis. */
4177 switch (switch_value
) {
4182 acc_required
= SA_RIGHT_USER_SET_PASSWORD
;
4185 acc_required
= SA_RIGHT_USER_SET_PASSWORD
|
4186 SA_RIGHT_USER_SET_ATTRIBUTES
|
4187 SA_RIGHT_USER_ACCT_FLAGS_EXPIRY
;
4191 status
= access_check_samr_function(acc_granted
,
4193 "_samr_SetUserInfo");
4194 if (!NT_STATUS_IS_OK(status
)) {
4198 DEBUG(5, ("_samr_SetUserInfo: sid:%s, level:%d\n",
4199 sid_string_dbg(&sid
), switch_value
));
4202 DEBUG(5, ("_samr_SetUserInfo: NULL info level\n"));
4203 return NT_STATUS_INVALID_INFO_CLASS
;
4206 if (!(pwd
= samu_new(NULL
))) {
4207 return NT_STATUS_NO_MEMORY
;
4211 ret
= pdb_getsampwsid(pwd
, &sid
);
4216 return NT_STATUS_NO_SUCH_USER
;
4219 /* deal with machine password changes differently from userinfo changes */
4220 /* check to see if we have the sufficient rights */
4222 acb_info
= pdb_get_acct_ctrl(pwd
);
4223 if (acb_info
& ACB_WSTRUST
)
4224 has_enough_rights
= user_has_privileges(p
->pipe_user
.nt_user_token
,
4225 &se_machine_account
);
4226 else if (acb_info
& ACB_NORMAL
)
4227 has_enough_rights
= user_has_privileges(p
->pipe_user
.nt_user_token
,
4229 else if (acb_info
& (ACB_SVRTRUST
|ACB_DOMTRUST
)) {
4230 if (lp_enable_privileges()) {
4231 has_enough_rights
= nt_token_check_domain_rid(p
->pipe_user
.nt_user_token
,
4232 DOMAIN_GROUP_RID_ADMINS
);
4236 DEBUG(5, ("_samr_SetUserInfo: %s does%s possess sufficient rights\n",
4237 uidtoname(p
->pipe_user
.ut
.uid
),
4238 has_enough_rights
? "" : " not"));
4240 /* ================ BEGIN SeMachineAccountPrivilege BLOCK ================ */
4242 if (has_enough_rights
) {
4246 /* ok! user info levels (lots: see MSDEV help), off we go... */
4248 switch (switch_value
) {
4251 status
= set_user_info_7(p
->mem_ctx
,
4256 if (!set_user_info_16(&info
->info16
, pwd
)) {
4257 status
= NT_STATUS_ACCESS_DENIED
;
4262 /* Used by AS/U JRA. */
4263 if (!set_user_info_18(&info
->info18
, pwd
)) {
4264 status
= NT_STATUS_ACCESS_DENIED
;
4269 if (!set_user_info_20(&info
->info20
, pwd
)) {
4270 status
= NT_STATUS_ACCESS_DENIED
;
4275 status
= set_user_info_21(p
->mem_ctx
,
4276 &info
->info21
, pwd
);
4280 if (!p
->session_key
.length
) {
4281 status
= NT_STATUS_NO_USER_SESSION_KEY
;
4283 SamOEMhashBlob(info
->info23
.password
.data
, 516,
4286 dump_data(100, info
->info23
.password
.data
, 516);
4288 status
= set_user_info_23(p
->mem_ctx
,
4289 &info
->info23
, pwd
);
4293 if (!p
->session_key
.length
) {
4294 status
= NT_STATUS_NO_USER_SESSION_KEY
;
4296 SamOEMhashBlob(info
->info24
.password
.data
,
4300 dump_data(100, info
->info24
.password
.data
, 516);
4302 if (!set_user_info_pw(info
->info24
.password
.data
, pwd
,
4304 status
= NT_STATUS_ACCESS_DENIED
;
4309 if (!p
->session_key
.length
) {
4310 status
= NT_STATUS_NO_USER_SESSION_KEY
;
4312 encode_or_decode_arc4_passwd_buffer(info
->info25
.password
.data
,
4315 dump_data(100, info
->info25
.password
.data
, 532);
4317 status
= set_user_info_25(p
->mem_ctx
,
4318 &info
->info25
, pwd
);
4319 if (!NT_STATUS_IS_OK(status
)) {
4322 if (!set_user_info_pw(info
->info25
.password
.data
, pwd
,
4324 status
= NT_STATUS_ACCESS_DENIED
;
4329 if (!p
->session_key
.length
) {
4330 status
= NT_STATUS_NO_USER_SESSION_KEY
;
4332 encode_or_decode_arc4_passwd_buffer(info
->info26
.password
.data
,
4335 dump_data(100, info
->info26
.password
.data
, 516);
4337 if (!set_user_info_pw(info
->info26
.password
.data
, pwd
,
4339 status
= NT_STATUS_ACCESS_DENIED
;
4344 status
= NT_STATUS_INVALID_INFO_CLASS
;
4349 if (has_enough_rights
) {
4353 /* ================ END SeMachineAccountPrivilege BLOCK ================ */
4355 if (NT_STATUS_IS_OK(status
)) {
4356 force_flush_samr_cache(disp_info
);
4362 /*******************************************************************
4364 ********************************************************************/
4366 NTSTATUS
_samr_SetUserInfo2(pipes_struct
*p
,
4367 struct samr_SetUserInfo2
*r
)
4369 struct samr_SetUserInfo q
;
4371 q
.in
.user_handle
= r
->in
.user_handle
;
4372 q
.in
.level
= r
->in
.level
;
4373 q
.in
.info
= r
->in
.info
;
4375 return _samr_SetUserInfo(p
, &q
);
4378 /*********************************************************************
4379 _samr_GetAliasMembership
4380 *********************************************************************/
4382 NTSTATUS
_samr_GetAliasMembership(pipes_struct
*p
,
4383 struct samr_GetAliasMembership
*r
)
4385 size_t num_alias_rids
;
4387 struct samr_info
*info
= NULL
;
4395 DEBUG(5,("_samr_GetAliasMembership: %d\n", __LINE__
));
4397 /* find the policy handle. open a policy on it. */
4398 if (!find_policy_by_hnd(p
, r
->in
.domain_handle
, (void **)(void *)&info
))
4399 return NT_STATUS_INVALID_HANDLE
;
4401 ntstatus1
= access_check_samr_function(info
->acc_granted
,
4402 SA_RIGHT_DOMAIN_LOOKUP_ALIAS_BY_MEM
,
4403 "_samr_GetAliasMembership");
4404 ntstatus2
= access_check_samr_function(info
->acc_granted
,
4405 SA_RIGHT_DOMAIN_OPEN_ACCOUNT
,
4406 "_samr_GetAliasMembership");
4408 if (!NT_STATUS_IS_OK(ntstatus1
) || !NT_STATUS_IS_OK(ntstatus2
)) {
4409 if (!(NT_STATUS_EQUAL(ntstatus1
,NT_STATUS_ACCESS_DENIED
) && NT_STATUS_IS_OK(ntstatus2
)) &&
4410 !(NT_STATUS_EQUAL(ntstatus1
,NT_STATUS_ACCESS_DENIED
) && NT_STATUS_IS_OK(ntstatus1
))) {
4411 return (NT_STATUS_IS_OK(ntstatus1
)) ? ntstatus2
: ntstatus1
;
4415 if (!sid_check_is_domain(&info
->sid
) &&
4416 !sid_check_is_builtin(&info
->sid
))
4417 return NT_STATUS_OBJECT_TYPE_MISMATCH
;
4419 if (r
->in
.sids
->num_sids
) {
4420 members
= TALLOC_ARRAY(p
->mem_ctx
, DOM_SID
, r
->in
.sids
->num_sids
);
4422 if (members
== NULL
)
4423 return NT_STATUS_NO_MEMORY
;
4428 for (i
=0; i
<r
->in
.sids
->num_sids
; i
++)
4429 sid_copy(&members
[i
], r
->in
.sids
->sids
[i
].sid
);
4435 ntstatus1
= pdb_enum_alias_memberships(p
->mem_ctx
, &info
->sid
, members
,
4436 r
->in
.sids
->num_sids
,
4437 &alias_rids
, &num_alias_rids
);
4440 if (!NT_STATUS_IS_OK(ntstatus1
)) {
4444 r
->out
.rids
->count
= num_alias_rids
;
4445 r
->out
.rids
->ids
= alias_rids
;
4447 return NT_STATUS_OK
;
4450 /*********************************************************************
4451 _samr_GetMembersInAlias
4452 *********************************************************************/
4454 NTSTATUS
_samr_GetMembersInAlias(pipes_struct
*p
,
4455 struct samr_GetMembersInAlias
*r
)
4459 size_t num_sids
= 0;
4460 struct lsa_SidPtr
*sids
= NULL
;
4461 DOM_SID
*pdb_sids
= NULL
;
4467 /* find the policy handle. open a policy on it. */
4468 if (!get_lsa_policy_samr_sid(p
, r
->in
.alias_handle
, &alias_sid
, &acc_granted
, NULL
))
4469 return NT_STATUS_INVALID_HANDLE
;
4471 status
= access_check_samr_function(acc_granted
,
4472 SA_RIGHT_ALIAS_GET_MEMBERS
,
4473 "_samr_GetMembersInAlias");
4474 if (!NT_STATUS_IS_OK(status
)) {
4478 DEBUG(10, ("sid is %s\n", sid_string_dbg(&alias_sid
)));
4481 status
= pdb_enum_aliasmem(&alias_sid
, &pdb_sids
, &num_sids
);
4484 if (!NT_STATUS_IS_OK(status
)) {
4489 sids
= TALLOC_ZERO_ARRAY(p
->mem_ctx
, struct lsa_SidPtr
, num_sids
);
4491 TALLOC_FREE(pdb_sids
);
4492 return NT_STATUS_NO_MEMORY
;
4496 for (i
= 0; i
< num_sids
; i
++) {
4497 sids
[i
].sid
= sid_dup_talloc(p
->mem_ctx
, &pdb_sids
[i
]);
4499 TALLOC_FREE(pdb_sids
);
4500 return NT_STATUS_NO_MEMORY
;
4504 r
->out
.sids
->num_sids
= num_sids
;
4505 r
->out
.sids
->sids
= sids
;
4507 TALLOC_FREE(pdb_sids
);
4509 return NT_STATUS_OK
;
4512 /*********************************************************************
4513 _samr_QueryGroupMember
4514 *********************************************************************/
4516 NTSTATUS
_samr_QueryGroupMember(pipes_struct
*p
,
4517 struct samr_QueryGroupMember
*r
)
4520 size_t i
, num_members
;
4528 struct samr_RidTypeArray
*rids
= NULL
;
4530 rids
= TALLOC_ZERO_P(p
->mem_ctx
, struct samr_RidTypeArray
);
4532 return NT_STATUS_NO_MEMORY
;
4535 /* find the policy handle. open a policy on it. */
4536 if (!get_lsa_policy_samr_sid(p
, r
->in
.group_handle
, &group_sid
, &acc_granted
, NULL
))
4537 return NT_STATUS_INVALID_HANDLE
;
4539 status
= access_check_samr_function(acc_granted
,
4540 SA_RIGHT_GROUP_GET_MEMBERS
,
4541 "_samr_QueryGroupMember");
4542 if (!NT_STATUS_IS_OK(status
)) {
4546 DEBUG(10, ("sid is %s\n", sid_string_dbg(&group_sid
)));
4548 if (!sid_check_is_in_our_domain(&group_sid
)) {
4549 DEBUG(3, ("sid %s is not in our domain\n",
4550 sid_string_dbg(&group_sid
)));
4551 return NT_STATUS_NO_SUCH_GROUP
;
4554 DEBUG(10, ("lookup on Domain SID\n"));
4557 status
= pdb_enum_group_members(p
->mem_ctx
, &group_sid
,
4558 &rid
, &num_members
);
4561 if (!NT_STATUS_IS_OK(status
))
4565 attr
=TALLOC_ZERO_ARRAY(p
->mem_ctx
, uint32
, num_members
);
4567 return NT_STATUS_NO_MEMORY
;
4573 for (i
=0; i
<num_members
; i
++)
4574 attr
[i
] = SID_NAME_USER
;
4576 rids
->count
= num_members
;
4580 *r
->out
.rids
= rids
;
4582 return NT_STATUS_OK
;
4585 /*********************************************************************
4586 _samr_AddAliasMember
4587 *********************************************************************/
4589 NTSTATUS
_samr_AddAliasMember(pipes_struct
*p
,
4590 struct samr_AddAliasMember
*r
)
4595 bool can_add_accounts
;
4597 DISP_INFO
*disp_info
= NULL
;
4599 /* Find the policy handle. Open a policy on it. */
4600 if (!get_lsa_policy_samr_sid(p
, r
->in
.alias_handle
, &alias_sid
, &acc_granted
, &disp_info
))
4601 return NT_STATUS_INVALID_HANDLE
;
4603 status
= access_check_samr_function(acc_granted
,
4604 SA_RIGHT_ALIAS_ADD_MEMBER
,
4605 "_samr_AddAliasMember");
4606 if (!NT_STATUS_IS_OK(status
)) {
4610 DEBUG(10, ("sid is %s\n", sid_string_dbg(&alias_sid
)));
4612 se_priv_copy( &se_rights
, &se_add_users
);
4613 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_rights
);
4615 /******** BEGIN SeAddUsers BLOCK *********/
4617 if ( can_add_accounts
)
4620 status
= pdb_add_aliasmem(&alias_sid
, r
->in
.sid
);
4622 if ( can_add_accounts
)
4625 /******** END SeAddUsers BLOCK *********/
4627 if (NT_STATUS_IS_OK(status
)) {
4628 force_flush_samr_cache(disp_info
);
4634 /*********************************************************************
4635 _samr_DeleteAliasMember
4636 *********************************************************************/
4638 NTSTATUS
_samr_DeleteAliasMember(pipes_struct
*p
,
4639 struct samr_DeleteAliasMember
*r
)
4644 bool can_add_accounts
;
4646 DISP_INFO
*disp_info
= NULL
;
4648 /* Find the policy handle. Open a policy on it. */
4649 if (!get_lsa_policy_samr_sid(p
, r
->in
.alias_handle
, &alias_sid
, &acc_granted
, &disp_info
))
4650 return NT_STATUS_INVALID_HANDLE
;
4652 status
= access_check_samr_function(acc_granted
,
4653 SA_RIGHT_ALIAS_REMOVE_MEMBER
,
4654 "_samr_DeleteAliasMember");
4655 if (!NT_STATUS_IS_OK(status
)) {
4659 DEBUG(10, ("_samr_del_aliasmem:sid is %s\n",
4660 sid_string_dbg(&alias_sid
)));
4662 se_priv_copy( &se_rights
, &se_add_users
);
4663 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_rights
);
4665 /******** BEGIN SeAddUsers BLOCK *********/
4667 if ( can_add_accounts
)
4670 status
= pdb_del_aliasmem(&alias_sid
, r
->in
.sid
);
4672 if ( can_add_accounts
)
4675 /******** END SeAddUsers BLOCK *********/
4677 if (NT_STATUS_IS_OK(status
)) {
4678 force_flush_samr_cache(disp_info
);
4684 /*********************************************************************
4685 _samr_AddGroupMember
4686 *********************************************************************/
4688 NTSTATUS
_samr_AddGroupMember(pipes_struct
*p
,
4689 struct samr_AddGroupMember
*r
)
4696 bool can_add_accounts
;
4697 DISP_INFO
*disp_info
= NULL
;
4699 /* Find the policy handle. Open a policy on it. */
4700 if (!get_lsa_policy_samr_sid(p
, r
->in
.group_handle
, &group_sid
, &acc_granted
, &disp_info
))
4701 return NT_STATUS_INVALID_HANDLE
;
4703 status
= access_check_samr_function(acc_granted
,
4704 SA_RIGHT_GROUP_ADD_MEMBER
,
4705 "_samr_AddGroupMember");
4706 if (!NT_STATUS_IS_OK(status
)) {
4710 DEBUG(10, ("sid is %s\n", sid_string_dbg(&group_sid
)));
4712 if (!sid_peek_check_rid(get_global_sam_sid(), &group_sid
,
4714 return NT_STATUS_INVALID_HANDLE
;
4717 se_priv_copy( &se_rights
, &se_add_users
);
4718 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_rights
);
4720 /******** BEGIN SeAddUsers BLOCK *********/
4722 if ( can_add_accounts
)
4725 status
= pdb_add_groupmem(p
->mem_ctx
, group_rid
, r
->in
.rid
);
4727 if ( can_add_accounts
)
4730 /******** END SeAddUsers BLOCK *********/
4732 force_flush_samr_cache(disp_info
);
4737 /*********************************************************************
4738 _samr_DeleteGroupMember
4739 *********************************************************************/
4741 NTSTATUS
_samr_DeleteGroupMember(pipes_struct
*p
,
4742 struct samr_DeleteGroupMember
*r
)
4750 bool can_add_accounts
;
4751 DISP_INFO
*disp_info
= NULL
;
4754 * delete the group member named r->in.rid
4755 * who is a member of the sid associated with the handle
4756 * the rid is a user's rid as the group is a domain group.
4759 /* Find the policy handle. Open a policy on it. */
4760 if (!get_lsa_policy_samr_sid(p
, r
->in
.group_handle
, &group_sid
, &acc_granted
, &disp_info
))
4761 return NT_STATUS_INVALID_HANDLE
;
4763 status
= access_check_samr_function(acc_granted
,
4764 SA_RIGHT_GROUP_REMOVE_MEMBER
,
4765 "_samr_DeleteGroupMember");
4766 if (!NT_STATUS_IS_OK(status
)) {
4770 if (!sid_peek_check_rid(get_global_sam_sid(), &group_sid
,
4772 return NT_STATUS_INVALID_HANDLE
;
4775 se_priv_copy( &se_rights
, &se_add_users
);
4776 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_rights
);
4778 /******** BEGIN SeAddUsers BLOCK *********/
4780 if ( can_add_accounts
)
4783 status
= pdb_del_groupmem(p
->mem_ctx
, group_rid
, r
->in
.rid
);
4785 if ( can_add_accounts
)
4788 /******** END SeAddUsers BLOCK *********/
4790 force_flush_samr_cache(disp_info
);
4795 /*********************************************************************
4797 *********************************************************************/
4799 NTSTATUS
_samr_DeleteUser(pipes_struct
*p
,
4800 struct samr_DeleteUser
*r
)
4804 struct samu
*sam_pass
=NULL
;
4806 bool can_add_accounts
;
4808 DISP_INFO
*disp_info
= NULL
;
4811 DEBUG(5, ("_samr_DeleteUser: %d\n", __LINE__
));
4813 /* Find the policy handle. Open a policy on it. */
4814 if (!get_lsa_policy_samr_sid(p
, r
->in
.user_handle
, &user_sid
, &acc_granted
, &disp_info
))
4815 return NT_STATUS_INVALID_HANDLE
;
4817 status
= access_check_samr_function(acc_granted
,
4818 STD_RIGHT_DELETE_ACCESS
,
4819 "_samr_DeleteUser");
4820 if (!NT_STATUS_IS_OK(status
)) {
4824 if (!sid_check_is_in_our_domain(&user_sid
))
4825 return NT_STATUS_CANNOT_DELETE
;
4827 /* check if the user exists before trying to delete */
4828 if ( !(sam_pass
= samu_new( NULL
)) ) {
4829 return NT_STATUS_NO_MEMORY
;
4833 ret
= pdb_getsampwsid(sam_pass
, &user_sid
);
4837 DEBUG(5,("_samr_DeleteUser: User %s doesn't exist.\n",
4838 sid_string_dbg(&user_sid
)));
4839 TALLOC_FREE(sam_pass
);
4840 return NT_STATUS_NO_SUCH_USER
;
4843 acb_info
= pdb_get_acct_ctrl(sam_pass
);
4845 /* For machine accounts it's the SeMachineAccountPrivilege that counts. */
4846 if ( acb_info
& ACB_WSTRUST
) {
4847 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_machine_account
);
4849 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_add_users
);
4852 /******** BEGIN SeAddUsers BLOCK *********/
4854 if ( can_add_accounts
)
4857 status
= pdb_delete_user(p
->mem_ctx
, sam_pass
);
4859 if ( can_add_accounts
)
4862 /******** END SeAddUsers BLOCK *********/
4864 if ( !NT_STATUS_IS_OK(status
) ) {
4865 DEBUG(5,("_samr_DeleteUser: Failed to delete entry for "
4866 "user %s: %s.\n", pdb_get_username(sam_pass
),
4867 nt_errstr(status
)));
4868 TALLOC_FREE(sam_pass
);
4873 TALLOC_FREE(sam_pass
);
4875 if (!close_policy_hnd(p
, r
->in
.user_handle
))
4876 return NT_STATUS_OBJECT_NAME_INVALID
;
4878 ZERO_STRUCTP(r
->out
.user_handle
);
4880 force_flush_samr_cache(disp_info
);
4882 return NT_STATUS_OK
;
4885 /*********************************************************************
4886 _samr_DeleteDomainGroup
4887 *********************************************************************/
4889 NTSTATUS
_samr_DeleteDomainGroup(pipes_struct
*p
,
4890 struct samr_DeleteDomainGroup
*r
)
4897 bool can_add_accounts
;
4898 DISP_INFO
*disp_info
= NULL
;
4900 DEBUG(5, ("samr_DeleteDomainGroup: %d\n", __LINE__
));
4902 /* Find the policy handle. Open a policy on it. */
4903 if (!get_lsa_policy_samr_sid(p
, r
->in
.group_handle
, &group_sid
, &acc_granted
, &disp_info
))
4904 return NT_STATUS_INVALID_HANDLE
;
4906 status
= access_check_samr_function(acc_granted
,
4907 STD_RIGHT_DELETE_ACCESS
,
4908 "_samr_DeleteDomainGroup");
4909 if (!NT_STATUS_IS_OK(status
)) {
4913 DEBUG(10, ("sid is %s\n", sid_string_dbg(&group_sid
)));
4915 if (!sid_peek_check_rid(get_global_sam_sid(), &group_sid
,
4917 return NT_STATUS_NO_SUCH_GROUP
;
4920 se_priv_copy( &se_rights
, &se_add_users
);
4921 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_rights
);
4923 /******** BEGIN SeAddUsers BLOCK *********/
4925 if ( can_add_accounts
)
4928 status
= pdb_delete_dom_group(p
->mem_ctx
, group_rid
);
4930 if ( can_add_accounts
)
4933 /******** END SeAddUsers BLOCK *********/
4935 if ( !NT_STATUS_IS_OK(status
) ) {
4936 DEBUG(5,("_samr_DeleteDomainGroup: Failed to delete mapping "
4937 "entry for group %s: %s\n",
4938 sid_string_dbg(&group_sid
),
4939 nt_errstr(status
)));
4943 if (!close_policy_hnd(p
, r
->in
.group_handle
))
4944 return NT_STATUS_OBJECT_NAME_INVALID
;
4946 force_flush_samr_cache(disp_info
);
4948 return NT_STATUS_OK
;
4951 /*********************************************************************
4952 _samr_DeleteDomAlias
4953 *********************************************************************/
4955 NTSTATUS
_samr_DeleteDomAlias(pipes_struct
*p
,
4956 struct samr_DeleteDomAlias
*r
)
4961 bool can_add_accounts
;
4963 DISP_INFO
*disp_info
= NULL
;
4965 DEBUG(5, ("_samr_DeleteDomAlias: %d\n", __LINE__
));
4967 /* Find the policy handle. Open a policy on it. */
4968 if (!get_lsa_policy_samr_sid(p
, r
->in
.alias_handle
, &alias_sid
, &acc_granted
, &disp_info
))
4969 return NT_STATUS_INVALID_HANDLE
;
4971 /* copy the handle to the outgoing reply */
4973 memcpy(r
->out
.alias_handle
, r
->in
.alias_handle
, sizeof(r
->out
.alias_handle
));
4975 status
= access_check_samr_function(acc_granted
,
4976 STD_RIGHT_DELETE_ACCESS
,
4977 "_samr_DeleteDomAlias");
4978 if (!NT_STATUS_IS_OK(status
)) {
4982 DEBUG(10, ("sid is %s\n", sid_string_dbg(&alias_sid
)));
4984 /* Don't let Windows delete builtin groups */
4986 if ( sid_check_is_in_builtin( &alias_sid
) ) {
4987 return NT_STATUS_SPECIAL_ACCOUNT
;
4990 if (!sid_check_is_in_our_domain(&alias_sid
))
4991 return NT_STATUS_NO_SUCH_ALIAS
;
4993 DEBUG(10, ("lookup on Local SID\n"));
4995 se_priv_copy( &se_rights
, &se_add_users
);
4996 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_rights
);
4998 /******** BEGIN SeAddUsers BLOCK *********/
5000 if ( can_add_accounts
)
5003 /* Have passdb delete the alias */
5004 status
= pdb_delete_alias(&alias_sid
);
5006 if ( can_add_accounts
)
5009 /******** END SeAddUsers BLOCK *********/
5011 if ( !NT_STATUS_IS_OK(status
))
5014 if (!close_policy_hnd(p
, r
->in
.alias_handle
))
5015 return NT_STATUS_OBJECT_NAME_INVALID
;
5017 force_flush_samr_cache(disp_info
);
5019 return NT_STATUS_OK
;
5022 /*********************************************************************
5023 _samr_CreateDomainGroup
5024 *********************************************************************/
5026 NTSTATUS
_samr_CreateDomainGroup(pipes_struct
*p
,
5027 struct samr_CreateDomainGroup
*r
)
5034 struct samr_info
*info
;
5037 bool can_add_accounts
;
5038 DISP_INFO
*disp_info
= NULL
;
5040 /* Find the policy handle. Open a policy on it. */
5041 if (!get_lsa_policy_samr_sid(p
, r
->in
.domain_handle
, &dom_sid
, &acc_granted
, &disp_info
))
5042 return NT_STATUS_INVALID_HANDLE
;
5044 status
= access_check_samr_function(acc_granted
,
5045 SA_RIGHT_DOMAIN_CREATE_GROUP
,
5046 "_samr_CreateDomainGroup");
5047 if (!NT_STATUS_IS_OK(status
)) {
5051 if (!sid_equal(&dom_sid
, get_global_sam_sid()))
5052 return NT_STATUS_ACCESS_DENIED
;
5054 name
= r
->in
.name
->string
;
5056 return NT_STATUS_NO_MEMORY
;
5059 status
= can_create(p
->mem_ctx
, name
);
5060 if (!NT_STATUS_IS_OK(status
)) {
5064 se_priv_copy( &se_rights
, &se_add_users
);
5065 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_rights
);
5067 /******** BEGIN SeAddUsers BLOCK *********/
5069 if ( can_add_accounts
)
5072 /* check that we successfully create the UNIX group */
5074 status
= pdb_create_dom_group(p
->mem_ctx
, name
, r
->out
.rid
);
5076 if ( can_add_accounts
)
5079 /******** END SeAddUsers BLOCK *********/
5081 /* check if we should bail out here */
5083 if ( !NT_STATUS_IS_OK(status
) )
5086 sid_compose(&info_sid
, get_global_sam_sid(), *r
->out
.rid
);
5088 if ((info
= get_samr_info_by_sid(&info_sid
)) == NULL
)
5089 return NT_STATUS_NO_MEMORY
;
5091 /* they created it; let the user do what he wants with it */
5093 info
->acc_granted
= GENERIC_RIGHTS_GROUP_ALL_ACCESS
;
5095 /* get a (unique) handle. open a policy on it. */
5096 if (!create_policy_hnd(p
, r
->out
.group_handle
, free_samr_info
, (void *)info
))
5097 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
5099 force_flush_samr_cache(disp_info
);
5101 return NT_STATUS_OK
;
5104 /*********************************************************************
5105 _samr_CreateDomAlias
5106 *********************************************************************/
5108 NTSTATUS
_samr_CreateDomAlias(pipes_struct
*p
,
5109 struct samr_CreateDomAlias
*r
)
5113 const char *name
= NULL
;
5114 struct samr_info
*info
;
5119 bool can_add_accounts
;
5120 DISP_INFO
*disp_info
= NULL
;
5122 /* Find the policy handle. Open a policy on it. */
5123 if (!get_lsa_policy_samr_sid(p
, r
->in
.domain_handle
, &dom_sid
, &acc_granted
, &disp_info
))
5124 return NT_STATUS_INVALID_HANDLE
;
5126 result
= access_check_samr_function(acc_granted
,
5127 SA_RIGHT_DOMAIN_CREATE_ALIAS
,
5128 "_samr_CreateDomAlias");
5129 if (!NT_STATUS_IS_OK(result
)) {
5133 if (!sid_equal(&dom_sid
, get_global_sam_sid()))
5134 return NT_STATUS_ACCESS_DENIED
;
5136 name
= r
->in
.alias_name
->string
;
5138 se_priv_copy( &se_rights
, &se_add_users
);
5139 can_add_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_rights
);
5141 result
= can_create(p
->mem_ctx
, name
);
5142 if (!NT_STATUS_IS_OK(result
)) {
5146 /******** BEGIN SeAddUsers BLOCK *********/
5148 if ( can_add_accounts
)
5151 /* Have passdb create the alias */
5152 result
= pdb_create_alias(name
, r
->out
.rid
);
5154 if ( can_add_accounts
)
5157 /******** END SeAddUsers BLOCK *********/
5159 if (!NT_STATUS_IS_OK(result
)) {
5160 DEBUG(10, ("pdb_create_alias failed: %s\n",
5161 nt_errstr(result
)));
5165 sid_copy(&info_sid
, get_global_sam_sid());
5166 sid_append_rid(&info_sid
, *r
->out
.rid
);
5168 if (!sid_to_gid(&info_sid
, &gid
)) {
5169 DEBUG(10, ("Could not find alias just created\n"));
5170 return NT_STATUS_ACCESS_DENIED
;
5173 /* check if the group has been successfully created */
5174 if ( getgrgid(gid
) == NULL
) {
5175 DEBUG(10, ("getgrgid(%d) of just created alias failed\n",
5177 return NT_STATUS_ACCESS_DENIED
;
5180 if ((info
= get_samr_info_by_sid(&info_sid
)) == NULL
)
5181 return NT_STATUS_NO_MEMORY
;
5183 /* they created it; let the user do what he wants with it */
5185 info
->acc_granted
= GENERIC_RIGHTS_ALIAS_ALL_ACCESS
;
5187 /* get a (unique) handle. open a policy on it. */
5188 if (!create_policy_hnd(p
, r
->out
.alias_handle
, free_samr_info
, (void *)info
))
5189 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
5191 force_flush_samr_cache(disp_info
);
5193 return NT_STATUS_OK
;
5196 /*********************************************************************
5197 _samr_QueryGroupInfo
5198 *********************************************************************/
5200 NTSTATUS
_samr_QueryGroupInfo(pipes_struct
*p
,
5201 struct samr_QueryGroupInfo
*r
)
5206 union samr_GroupInfo
*info
= NULL
;
5209 uint32_t attributes
= SE_GROUP_MANDATORY
|
5210 SE_GROUP_ENABLED_BY_DEFAULT
|
5212 const char *group_name
= NULL
;
5213 const char *group_description
= NULL
;
5215 if (!get_lsa_policy_samr_sid(p
, r
->in
.group_handle
, &group_sid
, &acc_granted
, NULL
))
5216 return NT_STATUS_INVALID_HANDLE
;
5218 status
= access_check_samr_function(acc_granted
,
5219 SA_RIGHT_GROUP_LOOKUP_INFO
,
5220 "_samr_QueryGroupInfo");
5221 if (!NT_STATUS_IS_OK(status
)) {
5226 ret
= get_domain_group_from_sid(group_sid
, &map
);
5229 return NT_STATUS_INVALID_HANDLE
;
5231 /* FIXME: map contains fstrings */
5232 group_name
= talloc_strdup(r
, map
.nt_name
);
5233 group_description
= talloc_strdup(r
, map
.comment
);
5235 info
= TALLOC_ZERO_P(p
->mem_ctx
, union samr_GroupInfo
);
5237 return NT_STATUS_NO_MEMORY
;
5240 switch (r
->in
.level
) {
5246 status
= pdb_enum_group_members(
5247 p
->mem_ctx
, &group_sid
, &members
, &num_members
);
5250 if (!NT_STATUS_IS_OK(status
)) {
5254 init_samr_group_info1(&info
->all
,
5262 init_samr_group_info2(&info
->name
,
5266 init_samr_group_info3(&info
->attributes
,
5270 init_samr_group_info4(&info
->description
,
5281 status = pdb_enum_group_members(
5282 p->mem_ctx, &group_sid, &members, &num_members);
5285 if (!NT_STATUS_IS_OK(status)) {
5289 init_samr_group_info5(&info
->all2
,
5292 0, /* num_members - in w2k3 this is always 0 */
5298 return NT_STATUS_INVALID_INFO_CLASS
;
5301 *r
->out
.info
= info
;
5303 return NT_STATUS_OK
;
5306 /*********************************************************************
5308 *********************************************************************/
5310 NTSTATUS
_samr_SetGroupInfo(pipes_struct
*p
,
5311 struct samr_SetGroupInfo
*r
)
5318 bool can_mod_accounts
;
5319 DISP_INFO
*disp_info
= NULL
;
5321 if (!get_lsa_policy_samr_sid(p
, r
->in
.group_handle
, &group_sid
, &acc_granted
, &disp_info
))
5322 return NT_STATUS_INVALID_HANDLE
;
5324 status
= access_check_samr_function(acc_granted
,
5325 SA_RIGHT_GROUP_SET_INFO
,
5326 "_samr_SetGroupInfo");
5327 if (!NT_STATUS_IS_OK(status
)) {
5332 ret
= get_domain_group_from_sid(group_sid
, &map
);
5335 return NT_STATUS_NO_SUCH_GROUP
;
5337 switch (r
->in
.level
) {
5339 fstrcpy(map
.comment
, r
->in
.info
->all
.description
.string
);
5342 fstrcpy(map
.comment
, r
->in
.info
->description
.string
);
5345 return NT_STATUS_INVALID_INFO_CLASS
;
5348 can_mod_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_add_users
);
5350 /******** BEGIN SeAddUsers BLOCK *********/
5352 if ( can_mod_accounts
)
5355 status
= pdb_update_group_mapping_entry(&map
);
5357 if ( can_mod_accounts
)
5360 /******** End SeAddUsers BLOCK *********/
5362 if (NT_STATUS_IS_OK(status
)) {
5363 force_flush_samr_cache(disp_info
);
5369 /*********************************************************************
5371 *********************************************************************/
5373 NTSTATUS
_samr_SetAliasInfo(pipes_struct
*p
,
5374 struct samr_SetAliasInfo
*r
)
5377 struct acct_info info
;
5379 bool can_mod_accounts
;
5381 DISP_INFO
*disp_info
= NULL
;
5383 if (!get_lsa_policy_samr_sid(p
, r
->in
.alias_handle
, &group_sid
, &acc_granted
, &disp_info
))
5384 return NT_STATUS_INVALID_HANDLE
;
5386 status
= access_check_samr_function(acc_granted
,
5387 SA_RIGHT_ALIAS_SET_INFO
,
5388 "_samr_SetAliasInfo");
5389 if (!NT_STATUS_IS_OK(status
)) {
5393 /* get the current group information */
5396 status
= pdb_get_aliasinfo( &group_sid
, &info
);
5399 if ( !NT_STATUS_IS_OK(status
))
5402 switch (r
->in
.level
) {
5407 /* We currently do not support renaming groups in the
5408 the BUILTIN domain. Refer to util_builtin.c to understand
5409 why. The eventually needs to be fixed to be like Windows
5410 where you can rename builtin groups, just not delete them */
5412 if ( sid_check_is_in_builtin( &group_sid
) ) {
5413 return NT_STATUS_SPECIAL_ACCOUNT
;
5416 /* There has to be a valid name (and it has to be different) */
5418 if ( !r
->in
.info
->name
.string
)
5419 return NT_STATUS_INVALID_PARAMETER
;
5421 /* If the name is the same just reply "ok". Yes this
5422 doesn't allow you to change the case of a group name. */
5424 if ( strequal( r
->in
.info
->name
.string
, info
.acct_name
) )
5425 return NT_STATUS_OK
;
5427 fstrcpy( info
.acct_name
, r
->in
.info
->name
.string
);
5429 /* make sure the name doesn't already exist as a user
5432 fstr_sprintf( group_name
, "%s\\%s", global_myname(), info
.acct_name
);
5433 status
= can_create( p
->mem_ctx
, group_name
);
5434 if ( !NT_STATUS_IS_OK( status
) )
5438 case ALIASINFODESCRIPTION
:
5439 if (r
->in
.info
->description
.string
) {
5440 fstrcpy(info
.acct_desc
,
5441 r
->in
.info
->description
.string
);
5443 fstrcpy( info
.acct_desc
, "" );
5447 return NT_STATUS_INVALID_INFO_CLASS
;
5450 can_mod_accounts
= user_has_privileges( p
->pipe_user
.nt_user_token
, &se_add_users
);
5452 /******** BEGIN SeAddUsers BLOCK *********/
5454 if ( can_mod_accounts
)
5457 status
= pdb_set_aliasinfo( &group_sid
, &info
);
5459 if ( can_mod_accounts
)
5462 /******** End SeAddUsers BLOCK *********/
5464 if (NT_STATUS_IS_OK(status
))
5465 force_flush_samr_cache(disp_info
);
5470 /****************************************************************
5472 ****************************************************************/
5474 NTSTATUS
_samr_GetDomPwInfo(pipes_struct
*p
,
5475 struct samr_GetDomPwInfo
*r
)
5477 uint32_t min_password_length
= 0;
5478 uint32_t password_properties
= 0;
5480 /* Perform access check. Since this rpc does not require a
5481 policy handle it will not be caught by the access checks on
5482 SAMR_CONNECT or SAMR_CONNECT_ANON. */
5484 if (!pipe_access_check(p
)) {
5485 DEBUG(3, ("access denied to _samr_GetDomPwInfo\n"));
5486 return NT_STATUS_ACCESS_DENIED
;
5490 pdb_get_account_policy(AP_MIN_PASSWORD_LEN
,
5491 &min_password_length
);
5492 pdb_get_account_policy(AP_USER_MUST_LOGON_TO_CHG_PASS
,
5493 &password_properties
);
5496 if (lp_check_password_script() && *lp_check_password_script()) {
5497 password_properties
|= DOMAIN_PASSWORD_COMPLEX
;
5500 r
->out
.info
->min_password_length
= min_password_length
;
5501 r
->out
.info
->password_properties
= password_properties
;
5503 return NT_STATUS_OK
;
5506 /*********************************************************************
5508 *********************************************************************/
5510 NTSTATUS
_samr_OpenGroup(pipes_struct
*p
,
5511 struct samr_OpenGroup
*r
)
5517 struct samr_info
*info
;
5518 SEC_DESC
*psd
= NULL
;
5520 uint32 des_access
= r
->in
.access_mask
;
5527 if (!get_lsa_policy_samr_sid(p
, r
->in
.domain_handle
, &sid
, &acc_granted
, NULL
))
5528 return NT_STATUS_INVALID_HANDLE
;
5530 status
= access_check_samr_function(acc_granted
,
5531 SA_RIGHT_DOMAIN_OPEN_ACCOUNT
,
5534 if ( !NT_STATUS_IS_OK(status
) )
5537 /*check if access can be granted as requested by client. */
5538 map_max_allowed_access(p
->pipe_user
.nt_user_token
, &des_access
);
5540 make_samr_object_sd(p
->mem_ctx
, &psd
, &sd_size
, &grp_generic_mapping
, NULL
, 0);
5541 se_map_generic(&des_access
,&grp_generic_mapping
);
5543 se_priv_copy( &se_rights
, &se_add_users
);
5545 status
= access_check_samr_object(psd
, p
->pipe_user
.nt_user_token
,
5546 &se_rights
, GENERIC_RIGHTS_GROUP_WRITE
, des_access
,
5547 &acc_granted
, "_samr_OpenGroup");
5549 if ( !NT_STATUS_IS_OK(status
) )
5552 /* this should not be hard-coded like this */
5554 if (!sid_equal(&sid
, get_global_sam_sid()))
5555 return NT_STATUS_ACCESS_DENIED
;
5557 sid_copy(&info_sid
, get_global_sam_sid());
5558 sid_append_rid(&info_sid
, r
->in
.rid
);
5559 sid_to_fstring(sid_string
, &info_sid
);
5561 if ((info
= get_samr_info_by_sid(&info_sid
)) == NULL
)
5562 return NT_STATUS_NO_MEMORY
;
5564 info
->acc_granted
= acc_granted
;
5566 DEBUG(10, ("_samr_OpenGroup:Opening SID: %s\n", sid_string
));
5568 /* check if that group really exists */
5570 ret
= get_domain_group_from_sid(info
->sid
, &map
);
5573 return NT_STATUS_NO_SUCH_GROUP
;
5575 /* get a (unique) handle. open a policy on it. */
5576 if (!create_policy_hnd(p
, r
->out
.group_handle
, free_samr_info
, (void *)info
))
5577 return NT_STATUS_OBJECT_NAME_NOT_FOUND
;
5579 return NT_STATUS_OK
;
5582 /*********************************************************************
5583 _samr_RemoveMemberFromForeignDomain
5584 *********************************************************************/
5586 NTSTATUS
_samr_RemoveMemberFromForeignDomain(pipes_struct
*p
,
5587 struct samr_RemoveMemberFromForeignDomain
*r
)
5589 DOM_SID delete_sid
, domain_sid
;
5592 DISP_INFO
*disp_info
= NULL
;
5594 sid_copy( &delete_sid
, r
->in
.sid
);
5596 DEBUG(5,("_samr_RemoveMemberFromForeignDomain: removing SID [%s]\n",
5597 sid_string_dbg(&delete_sid
)));
5599 /* Find the policy handle. Open a policy on it. */
5601 if (!get_lsa_policy_samr_sid(p
, r
->in
.domain_handle
, &domain_sid
,
5602 &acc_granted
, &disp_info
))
5603 return NT_STATUS_INVALID_HANDLE
;
5605 result
= access_check_samr_function(acc_granted
,
5606 STD_RIGHT_DELETE_ACCESS
,
5607 "_samr_RemoveMemberFromForeignDomain");
5609 if (!NT_STATUS_IS_OK(result
))
5612 DEBUG(8, ("_samr_RemoveMemberFromForeignDomain: sid is %s\n",
5613 sid_string_dbg(&domain_sid
)));
5615 /* we can only delete a user from a group since we don't have
5616 nested groups anyways. So in the latter case, just say OK */
5618 /* TODO: The above comment nowadays is bogus. Since we have nested
5619 * groups now, and aliases members are never reported out of the unix
5620 * group membership, the "just say OK" makes this call a no-op. For
5621 * us. This needs fixing however. */
5623 /* I've only ever seen this in the wild when deleting a user from
5624 * usrmgr.exe. domain_sid is the builtin domain, and the sid to delete
5625 * is the user about to be deleted. I very much suspect this is the
5626 * only application of this call. To verify this, let people report
5629 if (!sid_check_is_builtin(&domain_sid
)) {
5630 DEBUG(1,("_samr_RemoveMemberFromForeignDomain: domain_sid = %s, "
5631 "global_sam_sid() = %s\n",
5632 sid_string_dbg(&domain_sid
),
5633 sid_string_dbg(get_global_sam_sid())));
5634 DEBUGADD(1,("please report to samba-technical@samba.org!\n"));
5635 return NT_STATUS_OK
;
5638 force_flush_samr_cache(disp_info
);
5640 result
= NT_STATUS_OK
;
5645 /*******************************************************************
5646 _samr_QueryDomainInfo2
5647 ********************************************************************/
5649 NTSTATUS
_samr_QueryDomainInfo2(pipes_struct
*p
,
5650 struct samr_QueryDomainInfo2
*r
)
5652 struct samr_QueryDomainInfo q
;
5654 q
.in
.domain_handle
= r
->in
.domain_handle
;
5655 q
.in
.level
= r
->in
.level
;
5657 q
.out
.info
= r
->out
.info
;
5659 return _samr_QueryDomainInfo(p
, &q
);
5662 /*******************************************************************
5664 ********************************************************************/
5666 NTSTATUS
_samr_SetDomainInfo(pipes_struct
*p
,
5667 struct samr_SetDomainInfo
*r
)
5669 struct samr_info
*info
= NULL
;
5670 time_t u_expire
, u_min_age
;
5672 time_t u_lock_duration
, u_reset_time
;
5675 DEBUG(5,("_samr_SetDomainInfo: %d\n", __LINE__
));
5677 /* find the policy handle. open a policy on it. */
5678 if (!find_policy_by_hnd(p
, r
->in
.domain_handle
, (void **)(void *)&info
))
5679 return NT_STATUS_INVALID_HANDLE
;
5681 /* We do have different access bits for info
5682 * levels here, but we're really just looking for
5683 * GENERIC_RIGHTS_DOMAIN_WRITE access. Unfortunately
5684 * this maps to different specific bits. So
5685 * assume if we have SA_RIGHT_DOMAIN_SET_INFO_1
5688 result
= access_check_samr_function(info
->acc_granted
,
5689 SA_RIGHT_DOMAIN_SET_INFO_1
,
5690 "_samr_SetDomainInfo");
5692 if (!NT_STATUS_IS_OK(result
))
5695 DEBUG(5,("_samr_SetDomainInfo: level: %d\n", r
->in
.level
));
5697 switch (r
->in
.level
) {
5699 u_expire
=nt_time_to_unix_abs((NTTIME
*)&r
->in
.info
->info1
.max_password_age
);
5700 u_min_age
=nt_time_to_unix_abs((NTTIME
*)&r
->in
.info
->info1
.min_password_age
);
5701 pdb_set_account_policy(AP_MIN_PASSWORD_LEN
, (uint32
)r
->in
.info
->info1
.min_password_length
);
5702 pdb_set_account_policy(AP_PASSWORD_HISTORY
, (uint32
)r
->in
.info
->info1
.password_history_length
);
5703 pdb_set_account_policy(AP_USER_MUST_LOGON_TO_CHG_PASS
, (uint32
)r
->in
.info
->info1
.password_properties
);
5704 pdb_set_account_policy(AP_MAX_PASSWORD_AGE
, (int)u_expire
);
5705 pdb_set_account_policy(AP_MIN_PASSWORD_AGE
, (int)u_min_age
);
5710 u_logout
=nt_time_to_unix_abs((NTTIME
*)&r
->in
.info
->info3
.force_logoff_time
);
5711 pdb_set_account_policy(AP_TIME_TO_LOGOUT
, (int)u_logout
);
5720 u_lock_duration
=nt_time_to_unix_abs((NTTIME
*)&r
->in
.info
->info12
.lockout_duration
);
5721 if (u_lock_duration
!= -1)
5722 u_lock_duration
/= 60;
5724 u_reset_time
=nt_time_to_unix_abs((NTTIME
*)&r
->in
.info
->info12
.lockout_window
)/60;
5726 pdb_set_account_policy(AP_LOCK_ACCOUNT_DURATION
, (int)u_lock_duration
);
5727 pdb_set_account_policy(AP_RESET_COUNT_TIME
, (int)u_reset_time
);
5728 pdb_set_account_policy(AP_BAD_ATTEMPT_LOCKOUT
, (uint32
)r
->in
.info
->info12
.lockout_threshold
);
5731 return NT_STATUS_INVALID_INFO_CLASS
;
5734 DEBUG(5,("_samr_SetDomainInfo: %d\n", __LINE__
));
5736 return NT_STATUS_OK
;
5739 /****************************************************************
5740 _samr_GetDisplayEnumerationIndex
5741 ****************************************************************/
5743 NTSTATUS
_samr_GetDisplayEnumerationIndex(pipes_struct
*p
,
5744 struct samr_GetDisplayEnumerationIndex
*r
)
5746 struct samr_info
*info
= NULL
;
5747 uint32_t max_entries
= (uint32_t) -1;
5748 uint32_t enum_context
= 0;
5750 uint32_t num_account
= 0;
5751 struct samr_displayentry
*entries
= NULL
;
5754 DEBUG(5,("_samr_GetDisplayEnumerationIndex: %d\n", __LINE__
));
5756 /* find the policy handle. open a policy on it. */
5757 if (!find_policy_by_hnd(p
, r
->in
.domain_handle
, (void **)(void *)&info
)) {
5758 return NT_STATUS_INVALID_HANDLE
;
5761 status
= access_check_samr_function(info
->acc_granted
,
5762 SA_RIGHT_DOMAIN_ENUM_ACCOUNTS
,
5763 "_samr_GetDisplayEnumerationIndex");
5764 if (!NT_STATUS_IS_OK(status
)) {
5768 if ((r
->in
.level
< 1) || (r
->in
.level
> 3)) {
5769 DEBUG(0,("_samr_GetDisplayEnumerationIndex: "
5770 "Unknown info level (%u)\n",
5772 return NT_STATUS_INVALID_INFO_CLASS
;
5777 /* The following done as ROOT. Don't return without unbecome_root(). */
5779 switch (r
->in
.level
) {
5781 if (info
->disp_info
->users
== NULL
) {
5782 info
->disp_info
->users
= pdb_search_users(ACB_NORMAL
);
5783 if (info
->disp_info
->users
== NULL
) {
5785 return NT_STATUS_ACCESS_DENIED
;
5787 DEBUG(10,("_samr_GetDisplayEnumerationIndex: "
5788 "starting user enumeration at index %u\n",
5789 (unsigned int)enum_context
));
5791 DEBUG(10,("_samr_GetDisplayEnumerationIndex: "
5792 "using cached user enumeration at index %u\n",
5793 (unsigned int)enum_context
));
5795 num_account
= pdb_search_entries(info
->disp_info
->users
,
5796 enum_context
, max_entries
,
5800 if (info
->disp_info
->machines
== NULL
) {
5801 info
->disp_info
->machines
=
5802 pdb_search_users(ACB_WSTRUST
|ACB_SVRTRUST
);
5803 if (info
->disp_info
->machines
== NULL
) {
5805 return NT_STATUS_ACCESS_DENIED
;
5807 DEBUG(10,("_samr_GetDisplayEnumerationIndex: "
5808 "starting machine enumeration at index %u\n",
5809 (unsigned int)enum_context
));
5811 DEBUG(10,("_samr_GetDisplayEnumerationIndex: "
5812 "using cached machine enumeration at index %u\n",
5813 (unsigned int)enum_context
));
5815 num_account
= pdb_search_entries(info
->disp_info
->machines
,
5816 enum_context
, max_entries
,
5820 if (info
->disp_info
->groups
== NULL
) {
5821 info
->disp_info
->groups
= pdb_search_groups();
5822 if (info
->disp_info
->groups
== NULL
) {
5824 return NT_STATUS_ACCESS_DENIED
;
5826 DEBUG(10,("_samr_GetDisplayEnumerationIndex: "
5827 "starting group enumeration at index %u\n",
5828 (unsigned int)enum_context
));
5830 DEBUG(10,("_samr_GetDisplayEnumerationIndex: "
5831 "using cached group enumeration at index %u\n",
5832 (unsigned int)enum_context
));
5834 num_account
= pdb_search_entries(info
->disp_info
->groups
,
5835 enum_context
, max_entries
,
5840 smb_panic("info class changed");
5846 /* Ensure we cache this enumeration. */
5847 set_disp_info_cache_timeout(info
->disp_info
, DISP_INFO_CACHE_TIMEOUT
);
5849 DEBUG(10,("_samr_GetDisplayEnumerationIndex: looking for :%s\n",
5850 r
->in
.name
->string
));
5852 for (i
=0; i
<num_account
; i
++) {
5853 if (strequal(entries
[i
].account_name
, r
->in
.name
->string
)) {
5854 DEBUG(10,("_samr_GetDisplayEnumerationIndex: "
5855 "found %s at idx %d\n",
5856 r
->in
.name
->string
, i
));
5858 return NT_STATUS_OK
;
5862 /* assuming account_name lives at the very end */
5863 *r
->out
.idx
= num_account
;
5865 return NT_STATUS_NO_MORE_ENTRIES
;
5868 /****************************************************************
5869 _samr_GetDisplayEnumerationIndex2
5870 ****************************************************************/
5872 NTSTATUS
_samr_GetDisplayEnumerationIndex2(pipes_struct
*p
,
5873 struct samr_GetDisplayEnumerationIndex2
*r
)
5875 struct samr_GetDisplayEnumerationIndex q
;
5877 q
.in
.domain_handle
= r
->in
.domain_handle
;
5878 q
.in
.level
= r
->in
.level
;
5879 q
.in
.name
= r
->in
.name
;
5881 q
.out
.idx
= r
->out
.idx
;
5883 return _samr_GetDisplayEnumerationIndex(p
, &q
);
5886 /****************************************************************
5887 ****************************************************************/
5889 NTSTATUS
_samr_Shutdown(pipes_struct
*p
,
5890 struct samr_Shutdown
*r
)
5892 p
->rng_fault_state
= true;
5893 return NT_STATUS_NOT_IMPLEMENTED
;
5896 /****************************************************************
5897 ****************************************************************/
5899 NTSTATUS
_samr_CreateUser(pipes_struct
*p
,
5900 struct samr_CreateUser
*r
)
5902 p
->rng_fault_state
= true;
5903 return NT_STATUS_NOT_IMPLEMENTED
;
5906 /****************************************************************
5907 ****************************************************************/
5909 NTSTATUS
_samr_SetMemberAttributesOfGroup(pipes_struct
*p
,
5910 struct samr_SetMemberAttributesOfGroup
*r
)
5912 p
->rng_fault_state
= true;
5913 return NT_STATUS_NOT_IMPLEMENTED
;
5916 /****************************************************************
5917 ****************************************************************/
5919 NTSTATUS
_samr_ChangePasswordUser(pipes_struct
*p
,
5920 struct samr_ChangePasswordUser
*r
)
5922 p
->rng_fault_state
= true;
5923 return NT_STATUS_NOT_IMPLEMENTED
;
5926 /****************************************************************
5927 ****************************************************************/
5929 NTSTATUS
_samr_TestPrivateFunctionsDomain(pipes_struct
*p
,
5930 struct samr_TestPrivateFunctionsDomain
*r
)
5932 p
->rng_fault_state
= true;
5933 return NT_STATUS_NOT_IMPLEMENTED
;
5936 /****************************************************************
5937 ****************************************************************/
5939 NTSTATUS
_samr_TestPrivateFunctionsUser(pipes_struct
*p
,
5940 struct samr_TestPrivateFunctionsUser
*r
)
5942 p
->rng_fault_state
= true;
5943 return NT_STATUS_NOT_IMPLEMENTED
;
5946 /****************************************************************
5947 ****************************************************************/
5949 NTSTATUS
_samr_QueryUserInfo2(pipes_struct
*p
,
5950 struct samr_QueryUserInfo2
*r
)
5952 p
->rng_fault_state
= true;
5953 return NT_STATUS_NOT_IMPLEMENTED
;
5956 /****************************************************************
5957 ****************************************************************/
5959 NTSTATUS
_samr_AddMultipleMembersToAlias(pipes_struct
*p
,
5960 struct samr_AddMultipleMembersToAlias
*r
)
5962 p
->rng_fault_state
= true;
5963 return NT_STATUS_NOT_IMPLEMENTED
;
5966 /****************************************************************
5967 ****************************************************************/
5969 NTSTATUS
_samr_RemoveMultipleMembersFromAlias(pipes_struct
*p
,
5970 struct samr_RemoveMultipleMembersFromAlias
*r
)
5972 p
->rng_fault_state
= true;
5973 return NT_STATUS_NOT_IMPLEMENTED
;
5976 /****************************************************************
5977 ****************************************************************/
5979 NTSTATUS
_samr_OemChangePasswordUser2(pipes_struct
*p
,
5980 struct samr_OemChangePasswordUser2
*r
)
5982 p
->rng_fault_state
= true;
5983 return NT_STATUS_NOT_IMPLEMENTED
;
5986 /****************************************************************
5987 ****************************************************************/
5989 NTSTATUS
_samr_SetBootKeyInformation(pipes_struct
*p
,
5990 struct samr_SetBootKeyInformation
*r
)
5992 p
->rng_fault_state
= true;
5993 return NT_STATUS_NOT_IMPLEMENTED
;
5996 /****************************************************************
5997 ****************************************************************/
5999 NTSTATUS
_samr_GetBootKeyInformation(pipes_struct
*p
,
6000 struct samr_GetBootKeyInformation
*r
)
6002 p
->rng_fault_state
= true;
6003 return NT_STATUS_NOT_IMPLEMENTED
;
6006 /****************************************************************
6007 ****************************************************************/
6009 NTSTATUS
_samr_Connect3(pipes_struct
*p
,
6010 struct samr_Connect3
*r
)
6012 p
->rng_fault_state
= true;
6013 return NT_STATUS_NOT_IMPLEMENTED
;
6016 /****************************************************************
6017 ****************************************************************/
6019 NTSTATUS
_samr_RidToSid(pipes_struct
*p
,
6020 struct samr_RidToSid
*r
)
6022 p
->rng_fault_state
= true;
6023 return NT_STATUS_NOT_IMPLEMENTED
;
6026 /****************************************************************
6027 ****************************************************************/
6029 NTSTATUS
_samr_SetDsrmPassword(pipes_struct
*p
,
6030 struct samr_SetDsrmPassword
*r
)
6032 p
->rng_fault_state
= true;
6033 return NT_STATUS_NOT_IMPLEMENTED
;
6036 /****************************************************************
6037 ****************************************************************/
6039 NTSTATUS
_samr_ValidatePassword(pipes_struct
*p
,
6040 struct samr_ValidatePassword
*r
)
6042 p
->rng_fault_state
= true;
6043 return NT_STATUS_NOT_IMPLEMENTED
;