2 * Copyright 2002 Andriy Palamarchuk
4 * netapi32 user functions
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
23 * Implement NetUserGetGroups (WIP)
24 * Implement NetUserSetGroups
25 * NetUserGetLocalGroups does not support LG_INCLUDE_INDIRECT yet.
26 * Add missing information levels.
32 #include <ndk/kefuncs.h>
33 #include <ndk/obfuncs.h>
35 WINE_DEFAULT_DEBUG_CHANNEL(netapi32
);
37 typedef struct _ENUM_CONTEXT
39 SAM_HANDLE ServerHandle
;
40 SAM_HANDLE BuiltinDomainHandle
;
41 SAM_HANDLE AccountDomainHandle
;
43 SAM_ENUMERATE_HANDLE EnumerationContext
;
44 PSAM_RID_ENUMERATION Buffer
;
49 } ENUM_CONTEXT
, *PENUM_CONTEXT
;
54 DeltaTimeToSeconds(LARGE_INTEGER DeltaTime
)
56 LARGE_INTEGER Seconds
;
58 if (DeltaTime
.QuadPart
== 0)
61 Seconds
.QuadPart
= -DeltaTime
.QuadPart
/ 10000000;
63 if (Seconds
.HighPart
!= 0)
66 return Seconds
.LowPart
;
72 GetAllowedWorldAce(IN PACL Acl
,
73 OUT PACCESS_ALLOWED_ACE
*Ace
)
75 SID_IDENTIFIER_AUTHORITY WorldAuthority
= {SECURITY_WORLD_SID_AUTHORITY
};
76 ULONG WorldSid
[sizeof(SID
) / sizeof(ULONG
) + SID_MAX_SUB_AUTHORITIES
];
77 ACL_SIZE_INFORMATION AclSize
;
78 PVOID LocalAce
= NULL
;
84 RtlInitializeSid((PSID
)WorldSid
,
87 *(RtlSubAuthoritySid((PSID
)WorldSid
, 0)) = SECURITY_WORLD_RID
;
89 Status
= RtlQueryInformationAcl(Acl
,
93 if (!NT_SUCCESS(Status
))
96 for (i
= 0; i
< AclSize
.AceCount
; i
++)
98 Status
= RtlGetAce(Acl
, i
, &LocalAce
);
99 if (!NT_SUCCESS(Status
))
102 if (((PACE_HEADER
)LocalAce
)->AceType
!= ACCESS_ALLOWED_ACE_TYPE
)
105 if (RtlEqualSid((PSID
)WorldSid
,
106 (PSID
)&((PACCESS_ALLOWED_ACE
)LocalAce
)->SidStart
))
108 *Ace
= (PACCESS_ALLOWED_ACE
)LocalAce
;
109 return STATUS_SUCCESS
;
113 return STATUS_SUCCESS
;
119 GetAccountFlags(ULONG AccountControl
,
122 PACCESS_ALLOWED_ACE Ace
= NULL
;
123 ULONG Flags
= UF_SCRIPT
;
128 Status
= GetAllowedWorldAce(Dacl
, &Ace
);
129 if (NT_SUCCESS(Status
))
133 Flags
|= UF_PASSWD_CANT_CHANGE
;
135 else if ((Ace
->Mask
& USER_CHANGE_PASSWORD
) == 0)
137 Flags
|= UF_PASSWD_CANT_CHANGE
;
142 if (AccountControl
& USER_ACCOUNT_DISABLED
)
143 Flags
|= UF_ACCOUNTDISABLE
;
145 if (AccountControl
& USER_HOME_DIRECTORY_REQUIRED
)
146 Flags
|= UF_HOMEDIR_REQUIRED
;
148 if (AccountControl
& USER_PASSWORD_NOT_REQUIRED
)
149 Flags
|= UF_PASSWD_NOTREQD
;
151 if (AccountControl
& USER_ACCOUNT_AUTO_LOCKED
)
154 if (AccountControl
& USER_DONT_EXPIRE_PASSWORD
)
155 Flags
|= UF_DONT_EXPIRE_PASSWD
;
158 if (AccountControl & USER_ENCRYPTED_TEXT_PASSWORD_ALLOWED)
159 Flags |= UF_ENCRYPTED_TEXT_PASSWORD_ALLOWED;
161 if (AccountControl & USER_SMARTCARD_REQUIRED)
162 Flags |= UF_SMARTCARD_REQUIRED;
164 if (AccountControl & USER_TRUSTED_FOR_DELEGATION)
165 Flags |= UF_TRUSTED_FOR_DELEGATION;
167 if (AccountControl & USER_NOT_DELEGATED)
168 Flags |= UF_NOT_DELEGATED;
170 if (AccountControl & USER_USE_DES_KEY_ONLY)
171 Flags |= UF_USE_DES_KEY_ONLY;
173 if (AccountControl & USER_DONT_REQUIRE_PREAUTH)
174 Flags |= UF_DONT_REQUIRE_PREAUTH;
176 if (AccountControl & USER_PASSWORD_EXPIRED)
177 Flags |= UF_PASSWORD_EXPIRED;
180 /* Set account type flags */
181 if (AccountControl
& USER_TEMP_DUPLICATE_ACCOUNT
)
182 Flags
|= UF_TEMP_DUPLICATE_ACCOUNT
;
183 else if (AccountControl
& USER_NORMAL_ACCOUNT
)
184 Flags
|= UF_NORMAL_ACCOUNT
;
185 else if (AccountControl
& USER_INTERDOMAIN_TRUST_ACCOUNT
)
186 Flags
|= UF_INTERDOMAIN_TRUST_ACCOUNT
;
187 else if (AccountControl
& USER_WORKSTATION_TRUST_ACCOUNT
)
188 Flags
|= UF_WORKSTATION_TRUST_ACCOUNT
;
189 else if (AccountControl
& USER_SERVER_TRUST_ACCOUNT
)
190 Flags
|= UF_SERVER_TRUST_ACCOUNT
;
198 GetAccountControl(ULONG Flags
)
200 ULONG AccountControl
= 0;
202 if (Flags
& UF_ACCOUNTDISABLE
)
203 AccountControl
|= USER_ACCOUNT_DISABLED
;
205 if (Flags
& UF_HOMEDIR_REQUIRED
)
206 AccountControl
|= USER_HOME_DIRECTORY_REQUIRED
;
208 if (Flags
& UF_PASSWD_NOTREQD
)
209 AccountControl
|= USER_PASSWORD_NOT_REQUIRED
;
211 if (Flags
& UF_LOCKOUT
)
212 AccountControl
|= USER_ACCOUNT_AUTO_LOCKED
;
214 if (Flags
& UF_DONT_EXPIRE_PASSWD
)
215 AccountControl
|= USER_DONT_EXPIRE_PASSWORD
;
217 /* Set account type flags */
218 if (Flags
& UF_TEMP_DUPLICATE_ACCOUNT
)
219 AccountControl
|= USER_TEMP_DUPLICATE_ACCOUNT
;
220 else if (Flags
& UF_NORMAL_ACCOUNT
)
221 AccountControl
|= USER_NORMAL_ACCOUNT
;
222 else if (Flags
& UF_INTERDOMAIN_TRUST_ACCOUNT
)
223 AccountControl
|= USER_INTERDOMAIN_TRUST_ACCOUNT
;
224 else if (Flags
& UF_WORKSTATION_TRUST_ACCOUNT
)
225 AccountControl
|= USER_WORKSTATION_TRUST_ACCOUNT
;
226 else if (Flags
& UF_SERVER_TRUST_ACCOUNT
)
227 AccountControl
|= USER_SERVER_TRUST_ACCOUNT
;
229 return AccountControl
;
235 GetPasswordAge(IN PLARGE_INTEGER PasswordLastSet
)
237 LARGE_INTEGER SystemTime
;
238 ULONG SystemSecondsSince1970
;
239 ULONG PasswordSecondsSince1970
;
242 Status
= NtQuerySystemTime(&SystemTime
);
243 if (!NT_SUCCESS(Status
))
246 RtlTimeToSecondsSince1970(&SystemTime
, &SystemSecondsSince1970
);
247 RtlTimeToSecondsSince1970(PasswordLastSet
, &PasswordSecondsSince1970
);
249 return SystemSecondsSince1970
- PasswordSecondsSince1970
;
255 ChangeUserDacl(IN PACL Dacl
,
258 PACCESS_ALLOWED_ACE Ace
= NULL
;
264 Status
= GetAllowedWorldAce(Dacl
, &Ace
);
265 if (!NT_SUCCESS(Status
))
268 if (Flags
& UF_PASSWD_CANT_CHANGE
)
269 Ace
->Mask
&= ~USER_CHANGE_PASSWORD
;
271 Ace
->Mask
|= USER_CHANGE_PASSWORD
;
277 GetUserDacl(IN SAM_HANDLE UserHandle
,
280 PSECURITY_DESCRIPTOR SecurityDescriptor
= NULL
;
285 ACL_SIZE_INFORMATION AclSize
;
286 NET_API_STATUS ApiStatus
;
289 TRACE("(%p %p)\n", UserHandle
, Dacl
);
293 Status
= SamQuerySecurityObject(UserHandle
,
294 DACL_SECURITY_INFORMATION
,
295 &SecurityDescriptor
);
296 if (!NT_SUCCESS(Status
))
298 TRACE("SamQuerySecurityObject() failed (Status 0x%08lx)\n", Status
);
299 ApiStatus
= NetpNtStatusToApiStatus(Status
);
303 Status
= RtlGetDaclSecurityDescriptor(SecurityDescriptor
,
307 if (!NT_SUCCESS(Status
))
309 TRACE("RtlGetDaclSecurityDescriptor() failed (Status 0x%08lx)\n", Status
);
310 ApiStatus
= NERR_InternalError
;
314 if (Present
== FALSE
)
316 TRACE("No DACL present\n");
317 ApiStatus
= NERR_Success
;
321 Status
= RtlQueryInformationAcl(SamDacl
,
325 if (!NT_SUCCESS(Status
))
327 TRACE("RtlQueryInformationAcl() failed (Status 0x%08lx)\n", Status
);
328 ApiStatus
= NERR_InternalError
;
332 LocalDacl
= HeapAlloc(GetProcessHeap(), 0, AclSize
.AclBytesInUse
);
333 if (LocalDacl
== NULL
)
335 TRACE("Memory allocation failed\n");
336 ApiStatus
= ERROR_NOT_ENOUGH_MEMORY
;
340 RtlCopyMemory(LocalDacl
, SamDacl
, AclSize
.AclBytesInUse
);
344 ApiStatus
= NERR_Success
;
347 if (SecurityDescriptor
!= NULL
)
348 SamFreeMemory(SecurityDescriptor
);
350 TRACE("done (ApiStatus: 0x%08lx)\n", ApiStatus
);
358 FreeUserInfo(PUSER_ALL_INFORMATION UserInfo
)
360 if (UserInfo
->UserName
.Buffer
!= NULL
)
361 SamFreeMemory(UserInfo
->UserName
.Buffer
);
363 if (UserInfo
->FullName
.Buffer
!= NULL
)
364 SamFreeMemory(UserInfo
->FullName
.Buffer
);
366 if (UserInfo
->HomeDirectory
.Buffer
!= NULL
)
367 SamFreeMemory(UserInfo
->HomeDirectory
.Buffer
);
369 if (UserInfo
->HomeDirectoryDrive
.Buffer
!= NULL
)
370 SamFreeMemory(UserInfo
->HomeDirectoryDrive
.Buffer
);
372 if (UserInfo
->ScriptPath
.Buffer
!= NULL
)
373 SamFreeMemory(UserInfo
->ScriptPath
.Buffer
);
375 if (UserInfo
->ProfilePath
.Buffer
!= NULL
)
376 SamFreeMemory(UserInfo
->ProfilePath
.Buffer
);
378 if (UserInfo
->AdminComment
.Buffer
!= NULL
)
379 SamFreeMemory(UserInfo
->AdminComment
.Buffer
);
381 if (UserInfo
->WorkStations
.Buffer
!= NULL
)
382 SamFreeMemory(UserInfo
->WorkStations
.Buffer
);
384 if (UserInfo
->UserComment
.Buffer
!= NULL
)
385 SamFreeMemory(UserInfo
->UserComment
.Buffer
);
387 if (UserInfo
->Parameters
.Buffer
!= NULL
)
388 SamFreeMemory(UserInfo
->Parameters
.Buffer
);
390 if (UserInfo
->PrivateData
.Buffer
!= NULL
)
391 SamFreeMemory(UserInfo
->PrivateData
.Buffer
);
393 if (UserInfo
->LogonHours
.LogonHours
!= NULL
)
394 SamFreeMemory(UserInfo
->LogonHours
.LogonHours
);
396 SamFreeMemory(UserInfo
);
402 BuildUserInfoBuffer(SAM_HANDLE UserHandle
,
407 UNICODE_STRING LogonServer
= RTL_CONSTANT_STRING(L
"\\\\*");
408 PUSER_ALL_INFORMATION UserInfo
= NULL
;
409 LPVOID LocalBuffer
= NULL
;
411 PUSER_INFO_0 UserInfo0
;
412 PUSER_INFO_1 UserInfo1
;
413 PUSER_INFO_2 UserInfo2
;
414 PUSER_INFO_3 UserInfo3
;
415 PUSER_INFO_4 UserInfo4
;
416 PUSER_INFO_10 UserInfo10
;
417 PUSER_INFO_11 UserInfo11
;
418 PUSER_INFO_20 UserInfo20
;
419 PUSER_INFO_23 UserInfo23
;
423 NET_API_STATUS ApiStatus
= NERR_Success
;
427 Status
= SamQueryInformationUser(UserHandle
,
430 if (!NT_SUCCESS(Status
))
432 ERR("SamQueryInformationUser failed (Status %08lx)\n", Status
);
433 ApiStatus
= NetpNtStatusToApiStatus(Status
);
437 if ((level
== 1) || (level
== 2) || (level
== 3) ||
438 (level
== 4) || (level
== 20) || (level
== 23))
440 ApiStatus
= GetUserDacl(UserHandle
, &Dacl
);
441 if (ApiStatus
!= NERR_Success
)
448 Size
= sizeof(USER_INFO_0
) +
449 UserInfo
->UserName
.Length
+ sizeof(WCHAR
);
453 Size
= sizeof(USER_INFO_1
) +
454 UserInfo
->UserName
.Length
+ sizeof(WCHAR
) +
455 UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
) +
456 UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
) +
457 UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
);
461 Size
= sizeof(USER_INFO_2
) +
462 UserInfo
->UserName
.Length
+ sizeof(WCHAR
) +
463 UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
) +
464 UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
) +
465 UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
) +
466 UserInfo
->FullName
.Length
+ sizeof(WCHAR
) +
467 UserInfo
->UserComment
.Length
+ sizeof(WCHAR
) +
468 UserInfo
->Parameters
.Length
+ sizeof(WCHAR
) +
469 UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
) +
470 LogonServer
.Length
+ sizeof(WCHAR
);
472 if (UserInfo
->LogonHours
.UnitsPerWeek
> 0)
473 Size
+= (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8;
477 Size
= sizeof(USER_INFO_3
) +
478 UserInfo
->UserName
.Length
+ sizeof(WCHAR
) +
479 UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
) +
480 UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
) +
481 UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
) +
482 UserInfo
->FullName
.Length
+ sizeof(WCHAR
) +
483 UserInfo
->UserComment
.Length
+ sizeof(WCHAR
) +
484 UserInfo
->Parameters
.Length
+ sizeof(WCHAR
) +
485 UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
) +
486 LogonServer
.Length
+ sizeof(WCHAR
) +
487 UserInfo
->ProfilePath
.Length
+ sizeof(WCHAR
) +
488 UserInfo
->HomeDirectoryDrive
.Length
+ sizeof(WCHAR
);
490 if (UserInfo
->LogonHours
.UnitsPerWeek
> 0)
491 Size
+= (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8;
495 Size
= sizeof(USER_INFO_4
) +
496 UserInfo
->UserName
.Length
+ sizeof(WCHAR
) +
497 UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
) +
498 UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
) +
499 UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
) +
500 UserInfo
->FullName
.Length
+ sizeof(WCHAR
) +
501 UserInfo
->UserComment
.Length
+ sizeof(WCHAR
) +
502 UserInfo
->Parameters
.Length
+ sizeof(WCHAR
) +
503 UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
) +
504 LogonServer
.Length
+ sizeof(WCHAR
) +
505 UserInfo
->ProfilePath
.Length
+ sizeof(WCHAR
) +
506 UserInfo
->HomeDirectoryDrive
.Length
+ sizeof(WCHAR
);
508 if (UserInfo
->LogonHours
.UnitsPerWeek
> 0)
509 Size
+= (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8;
511 /* FIXME: usri4_user_sid */
515 Size
= sizeof(USER_INFO_10
) +
516 UserInfo
->UserName
.Length
+ sizeof(WCHAR
) +
517 UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
) +
518 UserInfo
->UserComment
.Length
+ sizeof(WCHAR
) +
519 UserInfo
->FullName
.Length
+ sizeof(WCHAR
);
523 Size
= sizeof(USER_INFO_11
) +
524 UserInfo
->UserName
.Length
+ sizeof(WCHAR
) +
525 UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
) +
526 UserInfo
->UserComment
.Length
+ sizeof(WCHAR
) +
527 UserInfo
->FullName
.Length
+ sizeof(WCHAR
) +
528 UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
) +
529 UserInfo
->Parameters
.Length
+ sizeof(WCHAR
) +
530 LogonServer
.Length
+ sizeof(WCHAR
) +
531 UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
);
533 if (UserInfo
->LogonHours
.UnitsPerWeek
> 0)
534 Size
+= (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8;
538 Size
= sizeof(USER_INFO_20
) +
539 UserInfo
->UserName
.Length
+ sizeof(WCHAR
) +
540 UserInfo
->FullName
.Length
+ sizeof(WCHAR
) +
541 UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
545 Size
= sizeof(USER_INFO_23
) +
546 UserInfo
->UserName
.Length
+ sizeof(WCHAR
) +
547 UserInfo
->FullName
.Length
+ sizeof(WCHAR
) +
548 UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
550 /* FIXME: usri23_user_sid */
554 ApiStatus
= ERROR_INVALID_LEVEL
;
558 ApiStatus
= NetApiBufferAllocate(Size
, &LocalBuffer
);
559 if (ApiStatus
!= NERR_Success
)
562 ZeroMemory(LocalBuffer
, Size
);
567 UserInfo0
= (PUSER_INFO_0
)LocalBuffer
;
569 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo0
+ sizeof(USER_INFO_0
));
571 UserInfo0
->usri0_name
= Ptr
;
573 memcpy(UserInfo0
->usri0_name
,
574 UserInfo
->UserName
.Buffer
,
575 UserInfo
->UserName
.Length
);
576 UserInfo0
->usri0_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
580 UserInfo1
= (PUSER_INFO_1
)LocalBuffer
;
582 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo1
+ sizeof(USER_INFO_1
));
584 UserInfo1
->usri1_name
= Ptr
;
586 memcpy(UserInfo1
->usri1_name
,
587 UserInfo
->UserName
.Buffer
,
588 UserInfo
->UserName
.Length
);
589 UserInfo1
->usri1_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
591 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
593 UserInfo1
->usri1_password
= NULL
;
594 UserInfo1
->usri1_password_age
= GetPasswordAge(&UserInfo
->PasswordLastSet
);
596 /* FIXME: usri1_priv */
598 UserInfo1
->usri1_home_dir
= Ptr
;
599 memcpy(UserInfo1
->usri1_home_dir
,
600 UserInfo
->HomeDirectory
.Buffer
,
601 UserInfo
->HomeDirectory
.Length
);
602 UserInfo1
->usri1_home_dir
[UserInfo
->HomeDirectory
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
603 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
));
605 UserInfo1
->usri1_comment
= Ptr
;
606 memcpy(UserInfo1
->usri1_comment
,
607 UserInfo
->AdminComment
.Buffer
,
608 UserInfo
->AdminComment
.Length
);
609 UserInfo1
->usri1_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
610 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
612 UserInfo1
->usri1_flags
= GetAccountFlags(UserInfo
->UserAccountControl
,
615 UserInfo1
->usri1_script_path
= Ptr
;
616 memcpy(UserInfo1
->usri1_script_path
,
617 UserInfo
->ScriptPath
.Buffer
,
618 UserInfo
->ScriptPath
.Length
);
619 UserInfo1
->usri1_script_path
[UserInfo
->ScriptPath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
623 UserInfo2
= (PUSER_INFO_2
)LocalBuffer
;
625 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo2
+ sizeof(USER_INFO_2
));
627 UserInfo2
->usri2_name
= Ptr
;
629 memcpy(UserInfo2
->usri2_name
,
630 UserInfo
->UserName
.Buffer
,
631 UserInfo
->UserName
.Length
);
632 UserInfo2
->usri2_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
634 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
636 UserInfo2
->usri2_password
= NULL
;
637 UserInfo2
->usri2_password_age
= GetPasswordAge(&UserInfo
->PasswordLastSet
);
639 /* FIXME: usri2_priv */
641 UserInfo2
->usri2_home_dir
= Ptr
;
642 memcpy(UserInfo2
->usri2_home_dir
,
643 UserInfo
->HomeDirectory
.Buffer
,
644 UserInfo
->HomeDirectory
.Length
);
645 UserInfo2
->usri2_home_dir
[UserInfo
->HomeDirectory
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
646 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
));
648 UserInfo2
->usri2_comment
= Ptr
;
649 memcpy(UserInfo2
->usri2_comment
,
650 UserInfo
->AdminComment
.Buffer
,
651 UserInfo
->AdminComment
.Length
);
652 UserInfo2
->usri2_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
653 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
655 UserInfo2
->usri2_flags
= GetAccountFlags(UserInfo
->UserAccountControl
,
658 UserInfo2
->usri2_script_path
= Ptr
;
659 memcpy(UserInfo2
->usri2_script_path
,
660 UserInfo
->ScriptPath
.Buffer
,
661 UserInfo
->ScriptPath
.Length
);
662 UserInfo2
->usri2_script_path
[UserInfo
->ScriptPath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
663 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
));
665 /* FIXME: usri2_auth_flags */
667 UserInfo2
->usri2_full_name
= Ptr
;
668 memcpy(UserInfo2
->usri2_full_name
,
669 UserInfo
->FullName
.Buffer
,
670 UserInfo
->FullName
.Length
);
671 UserInfo2
->usri2_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
672 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
674 UserInfo2
->usri2_usr_comment
= Ptr
;
675 memcpy(UserInfo2
->usri2_usr_comment
,
676 UserInfo
->UserComment
.Buffer
,
677 UserInfo
->UserComment
.Length
);
678 UserInfo2
->usri2_usr_comment
[UserInfo
->UserComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
679 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserComment
.Length
+ sizeof(WCHAR
));
681 UserInfo2
->usri2_parms
= Ptr
;
682 memcpy(UserInfo2
->usri2_parms
,
683 UserInfo
->Parameters
.Buffer
,
684 UserInfo
->Parameters
.Length
);
685 UserInfo2
->usri2_parms
[UserInfo
->Parameters
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
686 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->Parameters
.Length
+ sizeof(WCHAR
));
688 UserInfo2
->usri2_workstations
= Ptr
;
689 memcpy(UserInfo2
->usri2_workstations
,
690 UserInfo
->WorkStations
.Buffer
,
691 UserInfo
->WorkStations
.Length
);
692 UserInfo2
->usri2_workstations
[UserInfo
->WorkStations
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
693 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
));
695 RtlTimeToSecondsSince1970(&UserInfo
->LastLogon
,
696 &UserInfo2
->usri2_last_logon
);
698 RtlTimeToSecondsSince1970(&UserInfo
->LastLogoff
,
699 &UserInfo2
->usri2_last_logoff
);
701 RtlTimeToSecondsSince1970(&UserInfo
->AccountExpires
,
702 &UserInfo2
->usri2_acct_expires
);
704 UserInfo2
->usri2_max_storage
= USER_MAXSTORAGE_UNLIMITED
;
705 UserInfo2
->usri2_units_per_week
= UserInfo
->LogonHours
.UnitsPerWeek
;
707 if (UserInfo
->LogonHours
.UnitsPerWeek
> 0)
709 UserInfo2
->usri2_logon_hours
= (PVOID
)Ptr
;
711 memcpy(UserInfo2
->usri2_logon_hours
,
712 UserInfo
->LogonHours
.LogonHours
,
713 (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8);
715 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8);
718 UserInfo2
->usri2_bad_pw_count
= UserInfo
->BadPasswordCount
;
719 UserInfo2
->usri2_num_logons
= UserInfo
->LogonCount
;
721 UserInfo2
->usri2_logon_server
= Ptr
;
722 memcpy(UserInfo2
->usri2_logon_server
,
725 UserInfo2
->usri2_logon_server
[LogonServer
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
726 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ LogonServer
.Length
+ sizeof(WCHAR
));
728 UserInfo2
->usri2_country_code
= UserInfo
->CountryCode
;
729 UserInfo2
->usri2_code_page
= UserInfo
->CodePage
;
733 UserInfo3
= (PUSER_INFO_3
)LocalBuffer
;
735 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo3
+ sizeof(USER_INFO_3
));
737 UserInfo3
->usri3_name
= Ptr
;
739 memcpy(UserInfo3
->usri3_name
,
740 UserInfo
->UserName
.Buffer
,
741 UserInfo
->UserName
.Length
);
742 UserInfo3
->usri3_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
744 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
746 UserInfo3
->usri3_password
= NULL
;
747 UserInfo3
->usri3_password_age
= GetPasswordAge(&UserInfo
->PasswordLastSet
);
749 /* FIXME: usri3_priv */
751 UserInfo3
->usri3_home_dir
= Ptr
;
752 memcpy(UserInfo3
->usri3_home_dir
,
753 UserInfo
->HomeDirectory
.Buffer
,
754 UserInfo
->HomeDirectory
.Length
);
755 UserInfo3
->usri3_home_dir
[UserInfo
->HomeDirectory
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
756 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
));
758 UserInfo3
->usri3_comment
= Ptr
;
759 memcpy(UserInfo3
->usri3_comment
,
760 UserInfo
->AdminComment
.Buffer
,
761 UserInfo
->AdminComment
.Length
);
762 UserInfo3
->usri3_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
763 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
765 UserInfo3
->usri3_flags
= GetAccountFlags(UserInfo
->UserAccountControl
,
768 UserInfo3
->usri3_script_path
= Ptr
;
769 memcpy(UserInfo3
->usri3_script_path
,
770 UserInfo
->ScriptPath
.Buffer
,
771 UserInfo
->ScriptPath
.Length
);
772 UserInfo3
->usri3_script_path
[UserInfo
->ScriptPath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
773 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
));
775 /* FIXME: usri3_auth_flags */
777 UserInfo3
->usri3_full_name
= Ptr
;
778 memcpy(UserInfo3
->usri3_full_name
,
779 UserInfo
->FullName
.Buffer
,
780 UserInfo
->FullName
.Length
);
781 UserInfo3
->usri3_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
782 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
784 UserInfo3
->usri3_usr_comment
= Ptr
;
785 memcpy(UserInfo3
->usri3_usr_comment
,
786 UserInfo
->UserComment
.Buffer
,
787 UserInfo
->UserComment
.Length
);
788 UserInfo3
->usri3_usr_comment
[UserInfo
->UserComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
789 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserComment
.Length
+ sizeof(WCHAR
));
791 UserInfo3
->usri3_parms
= Ptr
;
792 memcpy(UserInfo3
->usri3_parms
,
793 UserInfo
->Parameters
.Buffer
,
794 UserInfo
->Parameters
.Length
);
795 UserInfo3
->usri3_parms
[UserInfo
->Parameters
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
796 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->Parameters
.Length
+ sizeof(WCHAR
));
798 UserInfo3
->usri3_workstations
= Ptr
;
799 memcpy(UserInfo3
->usri3_workstations
,
800 UserInfo
->WorkStations
.Buffer
,
801 UserInfo
->WorkStations
.Length
);
802 UserInfo3
->usri3_workstations
[UserInfo
->WorkStations
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
803 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
));
805 RtlTimeToSecondsSince1970(&UserInfo
->LastLogon
,
806 &UserInfo3
->usri3_last_logon
);
808 RtlTimeToSecondsSince1970(&UserInfo
->LastLogoff
,
809 &UserInfo3
->usri3_last_logoff
);
811 RtlTimeToSecondsSince1970(&UserInfo
->AccountExpires
,
812 &UserInfo3
->usri3_acct_expires
);
814 UserInfo3
->usri3_max_storage
= USER_MAXSTORAGE_UNLIMITED
;
815 UserInfo3
->usri3_units_per_week
= UserInfo
->LogonHours
.UnitsPerWeek
;
817 if (UserInfo
->LogonHours
.UnitsPerWeek
> 0)
819 UserInfo3
->usri3_logon_hours
= (PVOID
)Ptr
;
821 memcpy(UserInfo3
->usri3_logon_hours
,
822 UserInfo
->LogonHours
.LogonHours
,
823 (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8);
825 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8);
828 UserInfo3
->usri3_bad_pw_count
= UserInfo
->BadPasswordCount
;
829 UserInfo3
->usri3_num_logons
= UserInfo
->LogonCount
;
831 UserInfo3
->usri3_logon_server
= Ptr
;
832 memcpy(UserInfo3
->usri3_logon_server
,
835 UserInfo3
->usri3_logon_server
[LogonServer
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
836 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ LogonServer
.Length
+ sizeof(WCHAR
));
838 UserInfo3
->usri3_country_code
= UserInfo
->CountryCode
;
839 UserInfo3
->usri3_code_page
= UserInfo
->CodePage
;
840 UserInfo3
->usri3_user_id
= RelativeId
;
841 UserInfo3
->usri3_primary_group_id
= UserInfo
->PrimaryGroupId
;
843 UserInfo3
->usri3_profile
= Ptr
;
844 memcpy(UserInfo3
->usri3_profile
,
845 UserInfo
->ProfilePath
.Buffer
,
846 UserInfo
->ProfilePath
.Length
);
847 UserInfo3
->usri3_profile
[UserInfo
->ProfilePath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
848 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->ProfilePath
.Length
+ sizeof(WCHAR
));
850 UserInfo3
->usri3_home_dir_drive
= Ptr
;
851 memcpy(UserInfo3
->usri3_home_dir_drive
,
852 UserInfo
->HomeDirectoryDrive
.Buffer
,
853 UserInfo
->HomeDirectoryDrive
.Length
);
854 UserInfo3
->usri3_home_dir_drive
[UserInfo
->HomeDirectoryDrive
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
855 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectoryDrive
.Length
+ sizeof(WCHAR
));
857 UserInfo3
->usri3_password_expired
= (UserInfo
->UserAccountControl
& USER_PASSWORD_EXPIRED
);
861 UserInfo4
= (PUSER_INFO_4
)LocalBuffer
;
863 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo4
+ sizeof(USER_INFO_4
));
865 UserInfo4
->usri4_name
= Ptr
;
867 memcpy(UserInfo4
->usri4_name
,
868 UserInfo
->UserName
.Buffer
,
869 UserInfo
->UserName
.Length
);
870 UserInfo4
->usri4_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
872 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
874 UserInfo4
->usri4_password
= NULL
;
875 UserInfo4
->usri4_password_age
= GetPasswordAge(&UserInfo
->PasswordLastSet
);
877 /* FIXME: usri4_priv */
879 UserInfo4
->usri4_home_dir
= Ptr
;
880 memcpy(UserInfo4
->usri4_home_dir
,
881 UserInfo
->HomeDirectory
.Buffer
,
882 UserInfo
->HomeDirectory
.Length
);
883 UserInfo4
->usri4_home_dir
[UserInfo
->HomeDirectory
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
884 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
));
886 UserInfo4
->usri4_comment
= Ptr
;
887 memcpy(UserInfo4
->usri4_comment
,
888 UserInfo
->AdminComment
.Buffer
,
889 UserInfo
->AdminComment
.Length
);
890 UserInfo4
->usri4_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
891 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
893 UserInfo4
->usri4_flags
= GetAccountFlags(UserInfo
->UserAccountControl
,
896 UserInfo4
->usri4_script_path
= Ptr
;
897 memcpy(UserInfo4
->usri4_script_path
,
898 UserInfo
->ScriptPath
.Buffer
,
899 UserInfo
->ScriptPath
.Length
);
900 UserInfo4
->usri4_script_path
[UserInfo
->ScriptPath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
901 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
));
903 /* FIXME: usri4_auth_flags */
905 UserInfo4
->usri4_full_name
= Ptr
;
906 memcpy(UserInfo4
->usri4_full_name
,
907 UserInfo
->FullName
.Buffer
,
908 UserInfo
->FullName
.Length
);
909 UserInfo4
->usri4_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
910 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
912 UserInfo4
->usri4_usr_comment
= Ptr
;
913 memcpy(UserInfo4
->usri4_usr_comment
,
914 UserInfo
->UserComment
.Buffer
,
915 UserInfo
->UserComment
.Length
);
916 UserInfo4
->usri4_usr_comment
[UserInfo
->UserComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
917 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserComment
.Length
+ sizeof(WCHAR
));
919 UserInfo4
->usri4_parms
= Ptr
;
920 memcpy(UserInfo4
->usri4_parms
,
921 UserInfo
->Parameters
.Buffer
,
922 UserInfo
->Parameters
.Length
);
923 UserInfo4
->usri4_parms
[UserInfo
->Parameters
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
924 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->Parameters
.Length
+ sizeof(WCHAR
));
926 UserInfo4
->usri4_workstations
= Ptr
;
927 memcpy(UserInfo4
->usri4_workstations
,
928 UserInfo
->WorkStations
.Buffer
,
929 UserInfo
->WorkStations
.Length
);
930 UserInfo4
->usri4_workstations
[UserInfo
->WorkStations
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
931 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
));
933 RtlTimeToSecondsSince1970(&UserInfo
->LastLogon
,
934 &UserInfo4
->usri4_last_logon
);
936 RtlTimeToSecondsSince1970(&UserInfo
->LastLogoff
,
937 &UserInfo4
->usri4_last_logoff
);
939 RtlTimeToSecondsSince1970(&UserInfo
->AccountExpires
,
940 &UserInfo4
->usri4_acct_expires
);
942 UserInfo4
->usri4_max_storage
= USER_MAXSTORAGE_UNLIMITED
;
943 UserInfo4
->usri4_units_per_week
= UserInfo
->LogonHours
.UnitsPerWeek
;
945 if (UserInfo
->LogonHours
.UnitsPerWeek
> 0)
947 UserInfo4
->usri4_logon_hours
= (PVOID
)Ptr
;
949 memcpy(UserInfo4
->usri4_logon_hours
,
950 UserInfo
->LogonHours
.LogonHours
,
951 (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8);
953 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8);
956 UserInfo4
->usri4_bad_pw_count
= UserInfo
->BadPasswordCount
;
957 UserInfo4
->usri4_num_logons
= UserInfo
->LogonCount
;
959 UserInfo4
->usri4_logon_server
= Ptr
;
960 memcpy(UserInfo4
->usri4_logon_server
,
963 UserInfo4
->usri4_logon_server
[LogonServer
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
964 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ LogonServer
.Length
+ sizeof(WCHAR
));
966 UserInfo4
->usri4_country_code
= UserInfo
->CountryCode
;
967 UserInfo4
->usri4_code_page
= UserInfo
->CodePage
;
969 /* FIXME: usri4_user_sid */
971 UserInfo4
->usri4_primary_group_id
= UserInfo
->PrimaryGroupId
;
973 UserInfo4
->usri4_profile
= Ptr
;
974 memcpy(UserInfo4
->usri4_profile
,
975 UserInfo
->ProfilePath
.Buffer
,
976 UserInfo
->ProfilePath
.Length
);
977 UserInfo4
->usri4_profile
[UserInfo
->ProfilePath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
978 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->ProfilePath
.Length
+ sizeof(WCHAR
));
980 UserInfo4
->usri4_home_dir_drive
= Ptr
;
981 memcpy(UserInfo4
->usri4_home_dir_drive
,
982 UserInfo
->HomeDirectoryDrive
.Buffer
,
983 UserInfo
->HomeDirectoryDrive
.Length
);
984 UserInfo4
->usri4_home_dir_drive
[UserInfo
->HomeDirectoryDrive
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
985 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectoryDrive
.Length
+ sizeof(WCHAR
));
987 UserInfo4
->usri4_password_expired
= (UserInfo
->UserAccountControl
& USER_PASSWORD_EXPIRED
);
991 UserInfo10
= (PUSER_INFO_10
)LocalBuffer
;
993 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo10
+ sizeof(USER_INFO_10
));
995 UserInfo10
->usri10_name
= Ptr
;
997 memcpy(UserInfo10
->usri10_name
,
998 UserInfo
->UserName
.Buffer
,
999 UserInfo
->UserName
.Length
);
1000 UserInfo10
->usri10_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1002 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
1004 UserInfo10
->usri10_comment
= Ptr
;
1005 memcpy(UserInfo10
->usri10_comment
,
1006 UserInfo
->AdminComment
.Buffer
,
1007 UserInfo
->AdminComment
.Length
);
1008 UserInfo10
->usri10_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1009 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
1011 UserInfo10
->usri10_usr_comment
= Ptr
;
1012 memcpy(UserInfo10
->usri10_usr_comment
,
1013 UserInfo
->UserComment
.Buffer
,
1014 UserInfo
->UserComment
.Length
);
1015 UserInfo10
->usri10_usr_comment
[UserInfo
->UserComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1016 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserComment
.Length
+ sizeof(WCHAR
));
1018 UserInfo10
->usri10_full_name
= Ptr
;
1019 memcpy(UserInfo10
->usri10_full_name
,
1020 UserInfo
->FullName
.Buffer
,
1021 UserInfo
->FullName
.Length
);
1022 UserInfo10
->usri10_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1026 UserInfo11
= (PUSER_INFO_11
)LocalBuffer
;
1028 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo11
+ sizeof(USER_INFO_11
));
1030 UserInfo11
->usri11_name
= Ptr
;
1032 memcpy(UserInfo11
->usri11_name
,
1033 UserInfo
->UserName
.Buffer
,
1034 UserInfo
->UserName
.Length
);
1035 UserInfo11
->usri11_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1037 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
1039 UserInfo11
->usri11_comment
= Ptr
;
1040 memcpy(UserInfo11
->usri11_comment
,
1041 UserInfo
->AdminComment
.Buffer
,
1042 UserInfo
->AdminComment
.Length
);
1043 UserInfo11
->usri11_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1044 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
1046 UserInfo11
->usri11_usr_comment
= Ptr
;
1047 memcpy(UserInfo11
->usri11_usr_comment
,
1048 UserInfo
->UserComment
.Buffer
,
1049 UserInfo
->UserComment
.Length
);
1050 UserInfo11
->usri11_usr_comment
[UserInfo
->UserComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1051 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserComment
.Length
+ sizeof(WCHAR
));
1053 UserInfo11
->usri11_full_name
= Ptr
;
1054 memcpy(UserInfo11
->usri11_full_name
,
1055 UserInfo
->FullName
.Buffer
,
1056 UserInfo
->FullName
.Length
);
1057 UserInfo11
->usri11_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1058 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
1060 /* FIXME: usri11_priv */
1061 /* FIXME: usri11_auth_flags */
1063 UserInfo11
->usri11_password_age
= GetPasswordAge(&UserInfo
->PasswordLastSet
);
1065 UserInfo11
->usri11_home_dir
= Ptr
;
1066 memcpy(UserInfo11
->usri11_home_dir
,
1067 UserInfo
->HomeDirectory
.Buffer
,
1068 UserInfo
->HomeDirectory
.Length
);
1069 UserInfo11
->usri11_home_dir
[UserInfo
->HomeDirectory
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1070 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
));
1072 UserInfo11
->usri11_parms
= Ptr
;
1073 memcpy(UserInfo11
->usri11_parms
,
1074 UserInfo
->Parameters
.Buffer
,
1075 UserInfo
->Parameters
.Length
);
1076 UserInfo11
->usri11_parms
[UserInfo
->Parameters
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1077 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->Parameters
.Length
+ sizeof(WCHAR
));
1079 RtlTimeToSecondsSince1970(&UserInfo
->LastLogon
,
1080 &UserInfo11
->usri11_last_logon
);
1082 RtlTimeToSecondsSince1970(&UserInfo
->LastLogoff
,
1083 &UserInfo11
->usri11_last_logoff
);
1085 UserInfo11
->usri11_bad_pw_count
= UserInfo
->BadPasswordCount
;
1086 UserInfo11
->usri11_num_logons
= UserInfo
->LogonCount
;
1088 UserInfo11
->usri11_logon_server
= Ptr
;
1089 memcpy(UserInfo11
->usri11_logon_server
,
1091 LogonServer
.Length
);
1092 UserInfo11
->usri11_logon_server
[LogonServer
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1093 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ LogonServer
.Length
+ sizeof(WCHAR
));
1095 UserInfo11
->usri11_country_code
= UserInfo
->CountryCode
;
1097 UserInfo11
->usri11_workstations
= Ptr
;
1098 memcpy(UserInfo11
->usri11_workstations
,
1099 UserInfo
->WorkStations
.Buffer
,
1100 UserInfo
->WorkStations
.Length
);
1101 UserInfo11
->usri11_workstations
[UserInfo
->WorkStations
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1102 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
));
1104 UserInfo11
->usri11_max_storage
= USER_MAXSTORAGE_UNLIMITED
;
1105 UserInfo11
->usri11_units_per_week
= UserInfo
->LogonHours
.UnitsPerWeek
;
1107 if (UserInfo
->LogonHours
.UnitsPerWeek
> 0)
1109 UserInfo11
->usri11_logon_hours
= (PVOID
)Ptr
;
1111 memcpy(UserInfo11
->usri11_logon_hours
,
1112 UserInfo
->LogonHours
.LogonHours
,
1113 (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8);
1115 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ (((ULONG
)UserInfo
->LogonHours
.UnitsPerWeek
) + 7) / 8);
1118 UserInfo11
->usri11_code_page
= UserInfo
->CodePage
;
1122 UserInfo20
= (PUSER_INFO_20
)LocalBuffer
;
1124 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo20
+ sizeof(USER_INFO_20
));
1126 UserInfo20
->usri20_name
= Ptr
;
1128 memcpy(UserInfo20
->usri20_name
,
1129 UserInfo
->UserName
.Buffer
,
1130 UserInfo
->UserName
.Length
);
1131 UserInfo20
->usri20_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1133 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
1135 UserInfo20
->usri20_full_name
= Ptr
;
1136 memcpy(UserInfo20
->usri20_full_name
,
1137 UserInfo
->FullName
.Buffer
,
1138 UserInfo
->FullName
.Length
);
1139 UserInfo20
->usri20_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1140 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
1142 UserInfo20
->usri20_comment
= Ptr
;
1143 memcpy(UserInfo20
->usri20_comment
,
1144 UserInfo
->AdminComment
.Buffer
,
1145 UserInfo
->AdminComment
.Length
);
1146 UserInfo20
->usri20_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1147 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
1149 UserInfo20
->usri20_flags
= GetAccountFlags(UserInfo
->UserAccountControl
,
1152 UserInfo20
->usri20_user_id
= RelativeId
;
1156 UserInfo23
= (PUSER_INFO_23
)LocalBuffer
;
1158 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo23
+ sizeof(USER_INFO_23
));
1160 UserInfo23
->usri23_name
= Ptr
;
1162 memcpy(UserInfo23
->usri23_name
,
1163 UserInfo
->UserName
.Buffer
,
1164 UserInfo
->UserName
.Length
);
1165 UserInfo23
->usri23_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1167 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
1169 UserInfo23
->usri23_full_name
= Ptr
;
1170 memcpy(UserInfo23
->usri23_full_name
,
1171 UserInfo
->FullName
.Buffer
,
1172 UserInfo
->FullName
.Length
);
1173 UserInfo23
->usri23_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1174 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
1176 UserInfo23
->usri23_comment
= Ptr
;
1177 memcpy(UserInfo23
->usri23_comment
,
1178 UserInfo
->AdminComment
.Buffer
,
1179 UserInfo
->AdminComment
.Length
);
1180 UserInfo23
->usri23_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
1181 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
1183 UserInfo23
->usri23_flags
= GetAccountFlags(UserInfo
->UserAccountControl
,
1186 /* FIXME: usri23_user_sid */
1191 if (UserInfo
!= NULL
)
1192 FreeUserInfo(UserInfo
);
1195 HeapFree(GetProcessHeap(), 0, Dacl
);
1197 if (ApiStatus
== NERR_Success
)
1199 *Buffer
= LocalBuffer
;
1203 if (LocalBuffer
!= NULL
)
1204 NetApiBufferFree(LocalBuffer
);
1213 SetUserInfo(SAM_HANDLE UserHandle
,
1217 USER_ALL_INFORMATION UserAllInfo
;
1218 PUSER_INFO_0 UserInfo0
;
1219 PUSER_INFO_1 UserInfo1
;
1220 PUSER_INFO_2 UserInfo2
;
1221 PUSER_INFO_3 UserInfo3
;
1222 PUSER_INFO_4 UserInfo4
;
1223 PUSER_INFO_22 UserInfo22
;
1224 PUSER_INFO_1003 UserInfo1003
;
1225 PUSER_INFO_1006 UserInfo1006
;
1226 PUSER_INFO_1007 UserInfo1007
;
1227 PUSER_INFO_1008 UserInfo1008
;
1228 PUSER_INFO_1009 UserInfo1009
;
1229 PUSER_INFO_1011 UserInfo1011
;
1230 PUSER_INFO_1012 UserInfo1012
;
1231 PUSER_INFO_1013 UserInfo1013
;
1232 PUSER_INFO_1014 UserInfo1014
;
1233 PUSER_INFO_1017 UserInfo1017
;
1234 PUSER_INFO_1018 UserInfo1018
;
1235 PUSER_INFO_1024 UserInfo1024
;
1236 PUSER_INFO_1025 UserInfo1025
;
1237 PUSER_INFO_1051 UserInfo1051
;
1238 PUSER_INFO_1052 UserInfo1052
;
1239 PUSER_INFO_1053 UserInfo1053
;
1241 NET_API_STATUS ApiStatus
= NERR_Success
;
1242 NTSTATUS Status
= STATUS_SUCCESS
;
1244 ZeroMemory(&UserAllInfo
, sizeof(USER_ALL_INFORMATION
));
1246 if ((Level
== 1) || (Level
== 2) || (Level
== 3) ||
1247 (Level
== 4) || (Level
== 22) || (Level
== 1008))
1249 ApiStatus
= GetUserDacl(UserHandle
, &Dacl
);
1250 if (ApiStatus
!= NERR_Success
)
1257 UserInfo0
= (PUSER_INFO_0
)UserInfo
;
1259 RtlInitUnicodeString(&UserAllInfo
.UserName
,
1260 UserInfo0
->usri0_name
);
1262 UserAllInfo
.WhichFields
|= USER_ALL_USERNAME
;
1266 UserInfo1
= (PUSER_INFO_1
)UserInfo
;
1268 // usri1_name ignored
1270 if (UserInfo1
->usri1_password
!= NULL
)
1272 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
1273 UserInfo1
->usri1_password
);
1274 UserAllInfo
.NtPasswordPresent
= TRUE
;
1275 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
1278 // usri1_password_age ignored
1280 // UserInfo1->usri1_priv
1282 if (UserInfo1
->usri1_home_dir
!= NULL
)
1284 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
1285 UserInfo1
->usri1_home_dir
);
1286 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
1289 if (UserInfo1
->usri1_comment
!= NULL
)
1291 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
1292 UserInfo1
->usri1_comment
);
1293 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
1296 ChangeUserDacl(Dacl
, UserInfo1
->usri1_flags
);
1297 UserAllInfo
.UserAccountControl
= GetAccountControl(UserInfo1
->usri1_flags
);
1298 UserAllInfo
.WhichFields
|= USER_ALL_USERACCOUNTCONTROL
;
1300 if (UserInfo1
->usri1_script_path
!= NULL
)
1302 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
1303 UserInfo1
->usri1_script_path
);
1304 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
1309 UserInfo2
= (PUSER_INFO_2
)UserInfo
;
1311 // usri2_name ignored
1313 if (UserInfo2
->usri2_password
!= NULL
)
1315 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
1316 UserInfo2
->usri2_password
);
1317 UserAllInfo
.NtPasswordPresent
= TRUE
;
1318 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
1321 // usri2_password_age ignored
1323 // UserInfo2->usri2_priv;
1325 if (UserInfo2
->usri2_home_dir
!= NULL
)
1327 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
1328 UserInfo2
->usri2_home_dir
);
1329 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
1332 if (UserInfo2
->usri2_comment
!= NULL
)
1334 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
1335 UserInfo2
->usri2_comment
);
1336 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
1339 ChangeUserDacl(Dacl
, UserInfo2
->usri2_flags
);
1340 UserAllInfo
.UserAccountControl
= GetAccountControl(UserInfo2
->usri2_flags
);
1341 UserAllInfo
.WhichFields
|= USER_ALL_USERACCOUNTCONTROL
;
1343 if (UserInfo2
->usri2_script_path
!= NULL
)
1345 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
1346 UserInfo2
->usri2_script_path
);
1347 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
1350 // UserInfo2->usri2_auth_flags;
1352 if (UserInfo2
->usri2_full_name
!= NULL
)
1354 RtlInitUnicodeString(&UserAllInfo
.FullName
,
1355 UserInfo2
->usri2_full_name
);
1356 UserAllInfo
.WhichFields
|= USER_ALL_FULLNAME
;
1359 if (UserInfo2
->usri2_usr_comment
!= NULL
)
1361 RtlInitUnicodeString(&UserAllInfo
.UserComment
,
1362 UserInfo2
->usri2_usr_comment
);
1363 UserAllInfo
.WhichFields
|= USER_ALL_USERCOMMENT
;
1366 if (UserInfo2
->usri2_parms
!= NULL
)
1368 RtlInitUnicodeString(&UserAllInfo
.Parameters
,
1369 UserInfo2
->usri2_parms
);
1370 UserAllInfo
.WhichFields
|= USER_ALL_PARAMETERS
;
1373 if (UserInfo2
->usri2_workstations
!= NULL
)
1375 RtlInitUnicodeString(&UserAllInfo
.WorkStations
,
1376 UserInfo2
->usri2_workstations
);
1377 UserAllInfo
.WhichFields
|= USER_ALL_WORKSTATIONS
;
1380 // usri2_last_logon ignored
1381 // usri2_last_logoff ignored
1383 if (UserInfo2
->usri2_acct_expires
== TIMEQ_FOREVER
)
1385 UserAllInfo
.AccountExpires
.LowPart
= 0;
1386 UserAllInfo
.AccountExpires
.HighPart
= 0;
1390 RtlSecondsSince1970ToTime(UserInfo2
->usri2_acct_expires
,
1391 &UserAllInfo
.AccountExpires
);
1393 UserAllInfo
.WhichFields
|= USER_ALL_ACCOUNTEXPIRES
;
1395 // usri2_max_storage ignored
1397 // UserInfo2->usri2_units_per_week;
1398 // UserInfo2->usri2_logon_hours;
1400 // usri2_bad_pw_count ignored
1401 // usri2_num_logons ignored
1402 // usri2_logon_server ignored
1404 UserAllInfo
.CountryCode
= UserInfo2
->usri2_country_code
;
1405 UserAllInfo
.WhichFields
|= USER_ALL_COUNTRYCODE
;
1407 UserAllInfo
.CodePage
= UserInfo2
->usri2_code_page
;
1408 UserAllInfo
.WhichFields
|= USER_ALL_CODEPAGE
;
1412 UserInfo3
= (PUSER_INFO_3
)UserInfo
;
1414 // usri3_name ignored
1416 if (UserInfo3
->usri3_password
!= NULL
)
1418 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
1419 UserInfo3
->usri3_password
);
1420 UserAllInfo
.NtPasswordPresent
= TRUE
;
1421 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
1424 // usri3_password_age ignored
1426 // UserInfo3->usri3_priv;
1428 if (UserInfo3
->usri3_home_dir
!= NULL
)
1430 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
1431 UserInfo3
->usri3_home_dir
);
1432 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
1435 if (UserInfo3
->usri3_comment
!= NULL
)
1437 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
1438 UserInfo3
->usri3_comment
);
1439 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
1442 ChangeUserDacl(Dacl
, UserInfo3
->usri3_flags
);
1443 UserAllInfo
.UserAccountControl
= GetAccountControl(UserInfo3
->usri3_flags
);
1444 UserAllInfo
.WhichFields
|= USER_ALL_USERACCOUNTCONTROL
;
1446 if (UserInfo3
->usri3_script_path
!= NULL
)
1448 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
1449 UserInfo3
->usri3_script_path
);
1450 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
1453 // UserInfo3->usri3_auth_flags;
1455 if (UserInfo3
->usri3_full_name
!= NULL
)
1457 RtlInitUnicodeString(&UserAllInfo
.FullName
,
1458 UserInfo3
->usri3_full_name
);
1459 UserAllInfo
.WhichFields
|= USER_ALL_FULLNAME
;
1462 if (UserInfo3
->usri3_usr_comment
!= NULL
)
1464 RtlInitUnicodeString(&UserAllInfo
.UserComment
,
1465 UserInfo3
->usri3_usr_comment
);
1466 UserAllInfo
.WhichFields
|= USER_ALL_USERCOMMENT
;
1469 if (UserInfo3
->usri3_parms
!= NULL
)
1471 RtlInitUnicodeString(&UserAllInfo
.Parameters
,
1472 UserInfo3
->usri3_parms
);
1473 UserAllInfo
.WhichFields
|= USER_ALL_PARAMETERS
;
1476 if (UserInfo3
->usri3_workstations
!= NULL
)
1478 RtlInitUnicodeString(&UserAllInfo
.WorkStations
,
1479 UserInfo3
->usri3_workstations
);
1480 UserAllInfo
.WhichFields
|= USER_ALL_WORKSTATIONS
;
1483 // usri3_last_logon ignored
1484 // usri3_last_logoff ignored
1486 if (UserInfo3
->usri3_acct_expires
== TIMEQ_FOREVER
)
1488 UserAllInfo
.AccountExpires
.LowPart
= 0;
1489 UserAllInfo
.AccountExpires
.HighPart
= 0;
1493 RtlSecondsSince1970ToTime(UserInfo3
->usri3_acct_expires
,
1494 &UserAllInfo
.AccountExpires
);
1496 UserAllInfo
.WhichFields
|= USER_ALL_ACCOUNTEXPIRES
;
1498 // usri3_max_storage ignored
1500 // UserInfo3->usri3_units_per_week;
1501 // UserInfo3->usri3_logon_hours;
1503 // usri3_bad_pw_count ignored
1504 // usri3_num_logons ignored
1505 // usri3_logon_server ignored
1507 UserAllInfo
.CountryCode
= UserInfo3
->usri3_country_code
;
1508 UserAllInfo
.WhichFields
|= USER_ALL_COUNTRYCODE
;
1510 UserAllInfo
.CodePage
= UserInfo3
->usri3_code_page
;
1511 UserAllInfo
.WhichFields
|= USER_ALL_CODEPAGE
;
1513 // usri3_user_id ignored
1515 UserAllInfo
.PrimaryGroupId
= UserInfo3
->usri3_primary_group_id
;
1516 UserAllInfo
.WhichFields
|= USER_ALL_PRIMARYGROUPID
;
1518 if (UserInfo3
->usri3_profile
!= NULL
)
1520 RtlInitUnicodeString(&UserAllInfo
.ProfilePath
,
1521 UserInfo3
->usri3_profile
);
1522 UserAllInfo
.WhichFields
|= USER_ALL_PROFILEPATH
;
1525 if (UserInfo3
->usri3_home_dir_drive
!= NULL
)
1527 RtlInitUnicodeString(&UserAllInfo
.HomeDirectoryDrive
,
1528 UserInfo3
->usri3_home_dir_drive
);
1529 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORYDRIVE
;
1532 UserAllInfo
.PasswordExpired
= (UserInfo3
->usri3_password_expired
!= 0);
1533 UserAllInfo
.WhichFields
|= USER_ALL_PASSWORDEXPIRED
;
1537 UserInfo4
= (PUSER_INFO_4
)UserInfo
;
1539 // usri4_name ignored
1541 if (UserInfo4
->usri4_password
!= NULL
)
1543 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
1544 UserInfo4
->usri4_password
);
1545 UserAllInfo
.NtPasswordPresent
= TRUE
;
1546 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
1549 // usri4_password_age ignored
1551 // UserInfo3->usri4_priv;
1553 if (UserInfo4
->usri4_home_dir
!= NULL
)
1555 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
1556 UserInfo4
->usri4_home_dir
);
1557 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
1560 if (UserInfo4
->usri4_comment
!= NULL
)
1562 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
1563 UserInfo4
->usri4_comment
);
1564 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
1567 ChangeUserDacl(Dacl
, UserInfo4
->usri4_flags
);
1568 UserAllInfo
.UserAccountControl
= GetAccountControl(UserInfo4
->usri4_flags
);
1569 UserAllInfo
.WhichFields
|= USER_ALL_USERACCOUNTCONTROL
;
1571 if (UserInfo4
->usri4_script_path
!= NULL
)
1573 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
1574 UserInfo4
->usri4_script_path
);
1575 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
1578 // UserInfo4->usri4_auth_flags;
1580 if (UserInfo4
->usri4_full_name
!= NULL
)
1582 RtlInitUnicodeString(&UserAllInfo
.FullName
,
1583 UserInfo4
->usri4_full_name
);
1584 UserAllInfo
.WhichFields
|= USER_ALL_FULLNAME
;
1587 if (UserInfo4
->usri4_usr_comment
!= NULL
)
1589 RtlInitUnicodeString(&UserAllInfo
.UserComment
,
1590 UserInfo4
->usri4_usr_comment
);
1591 UserAllInfo
.WhichFields
|= USER_ALL_USERCOMMENT
;
1594 if (UserInfo4
->usri4_parms
!= NULL
)
1596 RtlInitUnicodeString(&UserAllInfo
.Parameters
,
1597 UserInfo4
->usri4_parms
);
1598 UserAllInfo
.WhichFields
|= USER_ALL_PARAMETERS
;
1601 if (UserInfo4
->usri4_workstations
!= NULL
)
1603 RtlInitUnicodeString(&UserAllInfo
.WorkStations
,
1604 UserInfo4
->usri4_workstations
);
1605 UserAllInfo
.WhichFields
|= USER_ALL_WORKSTATIONS
;
1608 // usri4_last_logon ignored
1609 // usri4_last_logoff ignored
1611 if (UserInfo4
->usri4_acct_expires
== TIMEQ_FOREVER
)
1613 UserAllInfo
.AccountExpires
.LowPart
= 0;
1614 UserAllInfo
.AccountExpires
.HighPart
= 0;
1618 RtlSecondsSince1970ToTime(UserInfo4
->usri4_acct_expires
,
1619 &UserAllInfo
.AccountExpires
);
1621 UserAllInfo
.WhichFields
|= USER_ALL_ACCOUNTEXPIRES
;
1623 // usri4_max_storage ignored
1625 // UserInfo4->usri4_units_per_week;
1626 // UserInfo4->usri4_logon_hours;
1628 // usri4_bad_pw_count ignored
1629 // usri4_num_logons ignored
1630 // usri4_logon_server ignored
1632 UserAllInfo
.CountryCode
= UserInfo4
->usri4_country_code
;
1633 UserAllInfo
.WhichFields
|= USER_ALL_COUNTRYCODE
;
1635 UserAllInfo
.CodePage
= UserInfo4
->usri4_code_page
;
1636 UserAllInfo
.WhichFields
|= USER_ALL_CODEPAGE
;
1638 // usri4_user_sid ignored
1640 UserAllInfo
.PrimaryGroupId
= UserInfo4
->usri4_primary_group_id
;
1641 UserAllInfo
.WhichFields
|= USER_ALL_PRIMARYGROUPID
;
1643 if (UserInfo4
->usri4_profile
!= NULL
)
1645 RtlInitUnicodeString(&UserAllInfo
.ProfilePath
,
1646 UserInfo4
->usri4_profile
);
1647 UserAllInfo
.WhichFields
|= USER_ALL_PROFILEPATH
;
1650 if (UserInfo4
->usri4_home_dir_drive
!= NULL
)
1652 RtlInitUnicodeString(&UserAllInfo
.HomeDirectoryDrive
,
1653 UserInfo4
->usri4_home_dir_drive
);
1654 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORYDRIVE
;
1657 UserAllInfo
.PasswordExpired
= (UserInfo4
->usri4_password_expired
!= 0);
1658 UserAllInfo
.WhichFields
|= USER_ALL_PASSWORDEXPIRED
;
1665 UserInfo22
= (PUSER_INFO_22
)UserInfo
;
1667 // usri22_name ignored
1669 // UserInfo22->usri22_password[ENCRYPTED_PWLEN];
1671 // usri22_password_age ignored
1673 // UserInfo3->usri3_priv;
1675 if (UserInfo22
->usri22_home_dir
!= NULL
)
1677 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
1678 UserInfo22
->usri22_home_dir
);
1679 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
1682 if (UserInfo22
->usri22_comment
!= NULL
)
1684 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
1685 UserInfo22
->usri22_comment
);
1686 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
1689 ChangeUserDacl(Dacl
, UserInfo22
->usri22_flags
);
1690 UserAllInfo
.UserAccountControl
= GetAccountControl(UserInfo22
->usri22_flags
);
1691 UserAllInfo
.WhichFields
|= USER_ALL_USERACCOUNTCONTROL
;
1693 if (UserInfo22
->usri22_script_path
!= NULL
)
1695 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
1696 UserInfo22
->usri22_script_path
);
1697 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
1700 // UserInfo22->usri22_auth_flags;
1702 if (UserInfo22
->usri22_full_name
!= NULL
)
1704 RtlInitUnicodeString(&UserAllInfo
.FullName
,
1705 UserInfo22
->usri22_full_name
);
1706 UserAllInfo
.WhichFields
|= USER_ALL_FULLNAME
;
1709 if (UserInfo22
->usri22_usr_comment
!= NULL
)
1711 RtlInitUnicodeString(&UserAllInfo
.UserComment
,
1712 UserInfo22
->usri22_usr_comment
);
1713 UserAllInfo
.WhichFields
|= USER_ALL_USERCOMMENT
;
1716 if (UserInfo22
->usri22_parms
!= NULL
)
1718 RtlInitUnicodeString(&UserAllInfo
.Parameters
,
1719 UserInfo22
->usri22_parms
);
1720 UserAllInfo
.WhichFields
|= USER_ALL_PARAMETERS
;
1723 if (UserInfo22
->usri22_workstations
!= NULL
)
1725 RtlInitUnicodeString(&UserAllInfo
.WorkStations
,
1726 UserInfo22
->usri22_workstations
);
1727 UserAllInfo
.WhichFields
|= USER_ALL_WORKSTATIONS
;
1730 // usri22_last_logon ignored
1731 // usri22_last_logoff ignored
1733 if (UserInfo22
->usri22_acct_expires
== TIMEQ_FOREVER
)
1735 UserAllInfo
.AccountExpires
.LowPart
= 0;
1736 UserAllInfo
.AccountExpires
.HighPart
= 0;
1740 RtlSecondsSince1970ToTime(UserInfo22
->usri22_acct_expires
,
1741 &UserAllInfo
.AccountExpires
);
1743 UserAllInfo
.WhichFields
|= USER_ALL_ACCOUNTEXPIRES
;
1745 // usri22_max_storage ignored
1747 // UserInfo22->usri22_units_per_week;
1748 // UserInfo22->usri22_logon_hours;
1750 // usri22_bad_pw_count ignored
1751 // usri22_num_logons ignored
1752 // usri22_logon_server ignored
1754 UserAllInfo
.CountryCode
= UserInfo22
->usri22_country_code
;
1755 UserAllInfo
.WhichFields
|= USER_ALL_COUNTRYCODE
;
1757 UserAllInfo
.CodePage
= UserInfo22
->usri22_code_page
;
1758 UserAllInfo
.WhichFields
|= USER_ALL_CODEPAGE
;
1762 UserInfo1003
= (PUSER_INFO_1003
)UserInfo
;
1764 if (UserInfo1003
->usri1003_password
!= NULL
)
1766 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
1767 UserInfo1003
->usri1003_password
);
1768 UserAllInfo
.NtPasswordPresent
= TRUE
;
1769 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
1777 UserInfo1006
= (PUSER_INFO_1006
)UserInfo
;
1779 if (UserInfo1006
->usri1006_home_dir
!= NULL
)
1781 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
1782 UserInfo1006
->usri1006_home_dir
);
1783 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
1788 UserInfo1007
= (PUSER_INFO_1007
)UserInfo
;
1790 if (UserInfo1007
->usri1007_comment
!= NULL
)
1792 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
1793 UserInfo1007
->usri1007_comment
);
1794 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
1799 UserInfo1008
= (PUSER_INFO_1008
)UserInfo
;
1800 ChangeUserDacl(Dacl
, UserInfo1008
->usri1008_flags
);
1801 UserAllInfo
.UserAccountControl
= GetAccountControl(UserInfo1008
->usri1008_flags
);
1802 UserAllInfo
.WhichFields
|= USER_ALL_USERACCOUNTCONTROL
;
1806 UserInfo1009
= (PUSER_INFO_1009
)UserInfo
;
1808 if (UserInfo1009
->usri1009_script_path
!= NULL
)
1810 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
1811 UserInfo1009
->usri1009_script_path
);
1812 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
1820 UserInfo1011
= (PUSER_INFO_1011
)UserInfo
;
1822 if (UserInfo1011
->usri1011_full_name
!= NULL
)
1824 RtlInitUnicodeString(&UserAllInfo
.FullName
,
1825 UserInfo1011
->usri1011_full_name
);
1826 UserAllInfo
.WhichFields
|= USER_ALL_FULLNAME
;
1831 UserInfo1012
= (PUSER_INFO_1012
)UserInfo
;
1833 if (UserInfo1012
->usri1012_usr_comment
!= NULL
)
1835 RtlInitUnicodeString(&UserAllInfo
.UserComment
,
1836 UserInfo1012
->usri1012_usr_comment
);
1837 UserAllInfo
.WhichFields
|= USER_ALL_USERCOMMENT
;
1842 UserInfo1013
= (PUSER_INFO_1013
)UserInfo
;
1844 if (UserInfo1013
->usri1013_parms
!= NULL
)
1846 RtlInitUnicodeString(&UserAllInfo
.Parameters
,
1847 UserInfo1013
->usri1013_parms
);
1848 UserAllInfo
.WhichFields
|= USER_ALL_PARAMETERS
;
1853 UserInfo1014
= (PUSER_INFO_1014
)UserInfo
;
1855 if (UserInfo1014
->usri1014_workstations
!= NULL
)
1857 RtlInitUnicodeString(&UserAllInfo
.WorkStations
,
1858 UserInfo1014
->usri1014_workstations
);
1859 UserAllInfo
.WhichFields
|= USER_ALL_WORKSTATIONS
;
1864 UserInfo1017
= (PUSER_INFO_1017
)UserInfo
;
1866 if (UserInfo1017
->usri1017_acct_expires
== TIMEQ_FOREVER
)
1868 UserAllInfo
.AccountExpires
.LowPart
= 0;
1869 UserAllInfo
.AccountExpires
.HighPart
= 0;
1873 RtlSecondsSince1970ToTime(UserInfo1017
->usri1017_acct_expires
,
1874 &UserAllInfo
.AccountExpires
);
1876 UserAllInfo
.WhichFields
|= USER_ALL_ACCOUNTEXPIRES
;
1880 UserInfo1018
= (PUSER_INFO_1018
)UserInfo
;
1882 if (UserInfo1018
->usri1018_max_storage
!= USER_MAXSTORAGE_UNLIMITED
)
1884 // FIXME: Report error
1885 return ERROR_INVALID_PARAMETER
;
1893 UserInfo1024
= (PUSER_INFO_1024
)UserInfo
;
1895 UserAllInfo
.CountryCode
= UserInfo1024
->usri1024_country_code
;
1896 UserAllInfo
.WhichFields
|= USER_ALL_COUNTRYCODE
;
1900 UserInfo1025
= (PUSER_INFO_1025
)UserInfo
;
1902 UserAllInfo
.CodePage
= UserInfo1025
->usri1025_code_page
;
1903 UserAllInfo
.WhichFields
|= USER_ALL_CODEPAGE
;
1907 UserInfo1051
= (PUSER_INFO_1051
)UserInfo
;
1909 UserAllInfo
.PrimaryGroupId
= UserInfo1051
->usri1051_primary_group_id
;
1910 UserAllInfo
.WhichFields
|= USER_ALL_PRIMARYGROUPID
;
1914 UserInfo1052
= (PUSER_INFO_1052
)UserInfo
;
1916 if (UserInfo1052
->usri1052_profile
!= NULL
)
1918 RtlInitUnicodeString(&UserAllInfo
.ProfilePath
,
1919 UserInfo1052
->usri1052_profile
);
1920 UserAllInfo
.WhichFields
|= USER_ALL_PROFILEPATH
;
1925 UserInfo1053
= (PUSER_INFO_1053
)UserInfo
;
1927 if (UserInfo1053
->usri1053_home_dir_drive
!= NULL
)
1929 RtlInitUnicodeString(&UserAllInfo
.HomeDirectoryDrive
,
1930 UserInfo1053
->usri1053_home_dir_drive
);
1931 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORYDRIVE
;
1936 ERR("Unsupported level %lu!\n", Level
);
1937 return ERROR_INVALID_PARAMETER
;
1940 Status
= SamSetInformationUser(UserHandle
,
1943 if (!NT_SUCCESS(Status
))
1945 ERR("SamSetInformationUser failed (Status %08lx)\n", Status
);
1946 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1952 HeapFree(GetProcessHeap(), 0, Dacl
);
1960 OpenUserByName(SAM_HANDLE DomainHandle
,
1961 PUNICODE_STRING UserName
,
1962 ULONG DesiredAccess
,
1963 PSAM_HANDLE UserHandle
)
1965 PULONG RelativeIds
= NULL
;
1966 PSID_NAME_USE Use
= NULL
;
1967 NET_API_STATUS ApiStatus
= NERR_Success
;
1968 NTSTATUS Status
= STATUS_SUCCESS
;
1970 /* Get the RID for the given user name */
1971 Status
= SamLookupNamesInDomain(DomainHandle
,
1976 if (!NT_SUCCESS(Status
))
1978 ERR("SamLookupNamesInDomain failed (Status %08lx)\n", Status
);
1979 return NetpNtStatusToApiStatus(Status
);
1982 /* Fail, if it is not an alias account */
1983 if (Use
[0] != SidTypeUser
)
1985 ERR("Object is not a user!\n");
1986 ApiStatus
= NERR_GroupNotFound
;
1990 /* Open the alias account */
1991 Status
= SamOpenUser(DomainHandle
,
1995 if (!NT_SUCCESS(Status
))
1997 ERR("SamOpenUser failed (Status %08lx)\n", Status
);
1998 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2003 if (RelativeIds
!= NULL
)
2004 SamFreeMemory(RelativeIds
);
2013 /************************************************************
2014 * NetUserAdd (NETAPI32.@)
2018 NetUserAdd(LPCWSTR servername
,
2023 UNICODE_STRING ServerName
;
2024 UNICODE_STRING UserName
;
2025 SAM_HANDLE ServerHandle
= NULL
;
2026 SAM_HANDLE DomainHandle
= NULL
;
2027 SAM_HANDLE UserHandle
= NULL
;
2028 ULONG GrantedAccess
;
2030 NET_API_STATUS ApiStatus
= NERR_Success
;
2031 NTSTATUS Status
= STATUS_SUCCESS
;
2033 TRACE("(%s, %d, %p, %p)\n", debugstr_w(servername
), level
, bufptr
, parm_err
);
2035 /* Check the info level */
2045 return ERROR_INVALID_LEVEL
;
2048 if (servername
!= NULL
)
2049 RtlInitUnicodeString(&ServerName
, servername
);
2051 /* Connect to the SAM Server */
2052 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
2054 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
2056 if (!NT_SUCCESS(Status
))
2058 ERR("SamConnect failed (Status %08lx)\n", Status
);
2059 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2063 /* Open the Account Domain */
2064 Status
= OpenAccountDomain(ServerHandle
,
2065 (servername
!= NULL
) ? &ServerName
: NULL
,
2066 DOMAIN_CREATE_USER
| DOMAIN_LOOKUP
| DOMAIN_READ_PASSWORD_PARAMETERS
,
2068 if (!NT_SUCCESS(Status
))
2070 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
2071 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2075 /* Initialize the user name string */
2076 RtlInitUnicodeString(&UserName
,
2077 ((PUSER_INFO_1
)bufptr
)->usri1_name
);
2079 /* Create the user account */
2080 Status
= SamCreateUser2InDomain(DomainHandle
,
2082 USER_NORMAL_ACCOUNT
,
2083 USER_ALL_ACCESS
| DELETE
| WRITE_DAC
,
2087 if (!NT_SUCCESS(Status
))
2089 ERR("SamCreateUser2InDomain failed (Status %08lx)\n", Status
);
2090 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2094 /* Set user information */
2095 ApiStatus
= SetUserInfo(UserHandle
,
2098 if (ApiStatus
!= NERR_Success
)
2100 ERR("SetUserInfo failed (Status %lu)\n", ApiStatus
);
2105 if (UserHandle
!= NULL
)
2107 if (ApiStatus
!= NERR_Success
)
2108 SamDeleteUser(UserHandle
);
2110 SamCloseHandle(UserHandle
);
2113 if (DomainHandle
!= NULL
)
2114 SamCloseHandle(DomainHandle
);
2116 if (ServerHandle
!= NULL
)
2117 SamCloseHandle(ServerHandle
);
2123 /******************************************************************************
2124 * NetUserChangePassword (NETAPI32.@)
2126 * domainname [I] Optional. Domain on which the user resides or the logon
2127 * domain of the current user if NULL.
2128 * username [I] Optional. Username to change the password for or the name
2129 * of the current user if NULL.
2130 * oldpassword [I] The user's current password.
2131 * newpassword [I] The password that the user will be changed to using.
2134 * Success: NERR_Success.
2135 * Failure: NERR_* failure code or win error code.
2140 NetUserChangePassword(LPCWSTR domainname
,
2142 LPCWSTR oldpassword
,
2143 LPCWSTR newpassword
)
2145 PMSV1_0_CHANGEPASSWORD_REQUEST RequestBuffer
= NULL
;
2146 PMSV1_0_CHANGEPASSWORD_RESPONSE ResponseBuffer
= NULL
;
2147 ULONG RequestBufferSize
;
2148 ULONG ResponseBufferSize
= 0;
2150 ANSI_STRING PackageName
;
2151 ULONG AuthenticationPackage
= 0;
2152 HANDLE LsaHandle
= NULL
;
2153 NET_API_STATUS ApiStatus
= NERR_Success
;
2154 NTSTATUS Status
= STATUS_SUCCESS
;
2155 NTSTATUS ProtocolStatus
;
2157 TRACE("(%s, %s, ..., ...)\n", debugstr_w(domainname
), debugstr_w(username
));
2159 /* FIXME: handle null domain or user name */
2161 /* Check the parameters */
2162 if ((oldpassword
== NULL
) ||
2163 (newpassword
== NULL
))
2164 return ERROR_INVALID_PARAMETER
;
2166 /* Connect to the LSA server */
2167 Status
= LsaConnectUntrusted(&LsaHandle
);
2168 if (!NT_SUCCESS(Status
))
2169 return NetpNtStatusToApiStatus(Status
);
2171 /* Get the authentication package ID */
2172 RtlInitAnsiString(&PackageName
,
2173 MSV1_0_PACKAGE_NAME
);
2175 Status
= LsaLookupAuthenticationPackage(LsaHandle
,
2177 &AuthenticationPackage
);
2178 if (!NT_SUCCESS(Status
))
2180 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2184 /* Calculate the request buffer size */
2185 RequestBufferSize
= sizeof(MSV1_0_CHANGEPASSWORD_REQUEST
) +
2186 ((wcslen(domainname
) + 1) * sizeof(WCHAR
)) +
2187 ((wcslen(username
) + 1) * sizeof(WCHAR
)) +
2188 ((wcslen(oldpassword
) + 1) * sizeof(WCHAR
)) +
2189 ((wcslen(newpassword
) + 1) * sizeof(WCHAR
));
2191 /* Allocate the request buffer */
2192 ApiStatus
= NetApiBufferAllocate(RequestBufferSize
,
2193 (PVOID
*)&RequestBuffer
);
2194 if (ApiStatus
!= NERR_Success
)
2197 /* Initialize the request buffer */
2198 RequestBuffer
->MessageType
= MsV1_0ChangePassword
;
2199 RequestBuffer
->Impersonating
= TRUE
;
2201 Ptr
= (LPWSTR
)((ULONG_PTR
)RequestBuffer
+ sizeof(MSV1_0_CHANGEPASSWORD_REQUEST
));
2203 /* Pack the domain name */
2204 RequestBuffer
->DomainName
.Length
= wcslen(domainname
) * sizeof(WCHAR
);
2205 RequestBuffer
->DomainName
.MaximumLength
= RequestBuffer
->DomainName
.Length
+ sizeof(WCHAR
);
2206 RequestBuffer
->DomainName
.Buffer
= Ptr
;
2208 RtlCopyMemory(RequestBuffer
->DomainName
.Buffer
,
2210 RequestBuffer
->DomainName
.MaximumLength
);
2212 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ RequestBuffer
->DomainName
.MaximumLength
);
2214 /* Pack the user name */
2215 RequestBuffer
->AccountName
.Length
= wcslen(username
) * sizeof(WCHAR
);
2216 RequestBuffer
->AccountName
.MaximumLength
= RequestBuffer
->AccountName
.Length
+ sizeof(WCHAR
);
2217 RequestBuffer
->AccountName
.Buffer
= Ptr
;
2219 RtlCopyMemory(RequestBuffer
->AccountName
.Buffer
,
2221 RequestBuffer
->AccountName
.MaximumLength
);
2223 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ RequestBuffer
->AccountName
.MaximumLength
);
2225 /* Pack the old password */
2226 RequestBuffer
->OldPassword
.Length
= wcslen(oldpassword
) * sizeof(WCHAR
);
2227 RequestBuffer
->OldPassword
.MaximumLength
= RequestBuffer
->OldPassword
.Length
+ sizeof(WCHAR
);
2228 RequestBuffer
->OldPassword
.Buffer
= Ptr
;
2230 RtlCopyMemory(RequestBuffer
->OldPassword
.Buffer
,
2232 RequestBuffer
->OldPassword
.MaximumLength
);
2234 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ RequestBuffer
->OldPassword
.MaximumLength
);
2236 /* Pack the new password */
2237 RequestBuffer
->NewPassword
.Length
= wcslen(newpassword
) * sizeof(WCHAR
);
2238 RequestBuffer
->NewPassword
.MaximumLength
= RequestBuffer
->NewPassword
.Length
+ sizeof(WCHAR
);
2239 RequestBuffer
->NewPassword
.Buffer
= Ptr
;
2241 RtlCopyMemory(RequestBuffer
->NewPassword
.Buffer
,
2243 RequestBuffer
->NewPassword
.MaximumLength
);
2245 /* Call the authentication package */
2246 Status
= LsaCallAuthenticationPackage(LsaHandle
,
2247 AuthenticationPackage
,
2250 (PVOID
*)&ResponseBuffer
,
2251 &ResponseBufferSize
,
2253 if (!NT_SUCCESS(Status
))
2255 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2259 if (!NT_SUCCESS(ProtocolStatus
))
2261 ApiStatus
= NetpNtStatusToApiStatus(ProtocolStatus
);
2266 if (RequestBuffer
!= NULL
)
2267 NetApiBufferFree(RequestBuffer
);
2269 if (ResponseBuffer
!= NULL
)
2270 LsaFreeReturnBuffer(ResponseBuffer
);
2272 if (LsaHandle
!= NULL
)
2279 /************************************************************
2280 * NetUserDel (NETAPI32.@)
2284 NetUserDel(LPCWSTR servername
,
2287 UNICODE_STRING ServerName
;
2288 UNICODE_STRING UserName
;
2289 SAM_HANDLE ServerHandle
= NULL
;
2290 SAM_HANDLE DomainHandle
= NULL
;
2291 SAM_HANDLE UserHandle
= NULL
;
2292 NET_API_STATUS ApiStatus
= NERR_Success
;
2293 NTSTATUS Status
= STATUS_SUCCESS
;
2295 TRACE("(%s, %s)\n", debugstr_w(servername
), debugstr_w(username
));
2297 if (servername
!= NULL
)
2298 RtlInitUnicodeString(&ServerName
, servername
);
2300 RtlInitUnicodeString(&UserName
, username
);
2302 /* Connect to the SAM Server */
2303 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
2305 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
2307 if (!NT_SUCCESS(Status
))
2309 ERR("SamConnect failed (Status %08lx)\n", Status
);
2310 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2314 /* Open the Builtin Domain */
2315 Status
= OpenBuiltinDomain(ServerHandle
,
2318 if (!NT_SUCCESS(Status
))
2320 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
2321 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2325 /* Open the user account in the builtin domain */
2326 ApiStatus
= OpenUserByName(DomainHandle
,
2330 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_NONE_MAPPED
)
2332 TRACE("OpenUserByName failed (ApiStatus %lu)\n", ApiStatus
);
2336 if (UserHandle
== NULL
)
2338 if (DomainHandle
!= NULL
)
2340 SamCloseHandle(DomainHandle
);
2341 DomainHandle
= NULL
;
2344 /* Open the Acount Domain */
2345 Status
= OpenAccountDomain(ServerHandle
,
2346 (servername
!= NULL
) ? &ServerName
: NULL
,
2349 if (!NT_SUCCESS(Status
))
2351 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
2352 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2356 /* Open the user account in the account domain */
2357 ApiStatus
= OpenUserByName(DomainHandle
,
2361 if (ApiStatus
!= NERR_Success
)
2363 ERR("OpenUserByName failed (ApiStatus %lu)\n", ApiStatus
);
2364 if (ApiStatus
== ERROR_NONE_MAPPED
)
2365 ApiStatus
= NERR_UserNotFound
;
2370 /* Delete the user */
2371 Status
= SamDeleteUser(UserHandle
);
2372 if (!NT_SUCCESS(Status
))
2374 ERR("SamDeleteUser failed (Status %08lx)\n", Status
);
2375 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2379 /* A successful delete invalidates the handle */
2383 if (UserHandle
!= NULL
)
2384 SamCloseHandle(UserHandle
);
2386 if (DomainHandle
!= NULL
)
2387 SamCloseHandle(DomainHandle
);
2389 if (ServerHandle
!= NULL
)
2390 SamCloseHandle(ServerHandle
);
2396 /************************************************************
2397 * NetUserEnum (NETAPI32.@)
2401 NetUserEnum(LPCWSTR servername
,
2406 LPDWORD entriesread
,
2407 LPDWORD totalentries
,
2408 LPDWORD resume_handle
)
2410 UNICODE_STRING ServerName
;
2411 PSAM_RID_ENUMERATION CurrentUser
;
2412 PENUM_CONTEXT EnumContext
= NULL
;
2413 LPVOID Buffer
= NULL
;
2415 SAM_HANDLE UserHandle
= NULL
;
2416 NET_API_STATUS ApiStatus
= NERR_Success
;
2417 NTSTATUS Status
= STATUS_SUCCESS
;
2419 TRACE("(%s %d 0x%d %p %d %p %p %p)\n", debugstr_w(servername
), level
,
2420 filter
, bufptr
, prefmaxlen
, entriesread
, totalentries
, resume_handle
);
2426 if (servername
!= NULL
)
2427 RtlInitUnicodeString(&ServerName
, servername
);
2429 if (resume_handle
!= NULL
&& *resume_handle
!= 0)
2431 EnumContext
= (PENUM_CONTEXT
)*resume_handle
;
2435 ApiStatus
= NetApiBufferAllocate(sizeof(ENUM_CONTEXT
), (PVOID
*)&EnumContext
);
2436 if (ApiStatus
!= NERR_Success
)
2439 EnumContext
->EnumerationContext
= 0;
2440 EnumContext
->Buffer
= NULL
;
2441 EnumContext
->Count
= 0;
2442 EnumContext
->Index
= 0;
2443 EnumContext
->BuiltinDone
= FALSE
;
2445 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
2446 &EnumContext
->ServerHandle
,
2447 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
2449 if (!NT_SUCCESS(Status
))
2451 ERR("SamConnect failed (Status %08lx)\n", Status
);
2452 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2456 Status
= OpenAccountDomain(EnumContext
->ServerHandle
,
2457 (servername
!= NULL
) ? &ServerName
: NULL
,
2458 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
2459 &EnumContext
->AccountDomainHandle
);
2460 if (!NT_SUCCESS(Status
))
2462 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
2463 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2467 Status
= OpenBuiltinDomain(EnumContext
->ServerHandle
,
2468 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
2469 &EnumContext
->BuiltinDomainHandle
);
2470 if (!NT_SUCCESS(Status
))
2472 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
2473 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2480 TRACE("EnumContext->Index: %lu\n", EnumContext
->Index
);
2481 TRACE("EnumContext->Count: %lu\n", EnumContext
->Count
);
2483 if (EnumContext
->Index
>= EnumContext
->Count
)
2485 // if (EnumContext->BuiltinDone == TRUE)
2487 // ApiStatus = NERR_Success;
2491 TRACE("Calling SamEnumerateUsersInDomain\n");
2492 Status
= SamEnumerateUsersInDomain(EnumContext
->AccountDomainHandle
, //BuiltinDomainHandle,
2493 &EnumContext
->EnumerationContext
,
2495 (PVOID
*)&EnumContext
->Buffer
,
2497 &EnumContext
->Count
);
2499 TRACE("SamEnumerateUsersInDomain returned (Status %08lx)\n", Status
);
2500 if (!NT_SUCCESS(Status
))
2502 ERR("SamEnumerateUsersInDomain failed (Status %08lx)\n", Status
);
2503 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2507 if (Status
== STATUS_MORE_ENTRIES
)
2509 ApiStatus
= NERR_BufTooSmall
;
2514 EnumContext
->BuiltinDone
= TRUE
;
2518 TRACE("EnumContext: %lu\n", EnumContext
);
2519 TRACE("EnumContext->Count: %lu\n", EnumContext
->Count
);
2520 TRACE("EnumContext->Buffer: %p\n", EnumContext
->Buffer
);
2522 /* Get a pointer to the current user */
2523 CurrentUser
= &EnumContext
->Buffer
[EnumContext
->Index
];
2525 TRACE("RID: %lu\n", CurrentUser
->RelativeId
);
2527 Status
= SamOpenUser(EnumContext
->AccountDomainHandle
, //BuiltinDomainHandle,
2528 READ_CONTROL
| USER_READ_GENERAL
| USER_READ_PREFERENCES
| USER_READ_LOGON
| USER_READ_ACCOUNT
,
2529 CurrentUser
->RelativeId
,
2531 if (!NT_SUCCESS(Status
))
2533 ERR("SamOpenUser failed (Status %08lx)\n", Status
);
2534 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2538 ApiStatus
= BuildUserInfoBuffer(UserHandle
,
2540 CurrentUser
->RelativeId
,
2542 if (ApiStatus
!= NERR_Success
)
2544 ERR("BuildUserInfoBuffer failed (ApiStatus %lu)\n", ApiStatus
);
2548 SamCloseHandle(UserHandle
);
2551 EnumContext
->Index
++;
2557 if (ApiStatus
== NERR_Success
&& EnumContext
->Index
< EnumContext
->Count
)
2558 ApiStatus
= ERROR_MORE_DATA
;
2560 if (EnumContext
!= NULL
)
2561 *totalentries
= EnumContext
->Count
;
2563 if (resume_handle
== NULL
|| ApiStatus
!= ERROR_MORE_DATA
)
2565 if (EnumContext
!= NULL
)
2567 if (EnumContext
->BuiltinDomainHandle
!= NULL
)
2568 SamCloseHandle(EnumContext
->BuiltinDomainHandle
);
2570 if (EnumContext
->AccountDomainHandle
!= NULL
)
2571 SamCloseHandle(EnumContext
->AccountDomainHandle
);
2573 if (EnumContext
->ServerHandle
!= NULL
)
2574 SamCloseHandle(EnumContext
->ServerHandle
);
2576 if (EnumContext
->Buffer
!= NULL
)
2578 for (i
= 0; i
< EnumContext
->Count
; i
++)
2580 SamFreeMemory(EnumContext
->Buffer
[i
].Name
.Buffer
);
2583 SamFreeMemory(EnumContext
->Buffer
);
2586 NetApiBufferFree(EnumContext
);
2591 if (UserHandle
!= NULL
)
2592 SamCloseHandle(UserHandle
);
2594 if (resume_handle
!= NULL
)
2595 *resume_handle
= (DWORD_PTR
)EnumContext
;
2597 *bufptr
= (LPBYTE
)Buffer
;
2599 TRACE("return %lu\n", ApiStatus
);
2605 /************************************************************
2606 * NetUserGetGroups (NETAPI32.@)
2610 NetUserGetGroups(LPCWSTR servername
,
2615 LPDWORD entriesread
,
2616 LPDWORD totalentries
)
2618 UNICODE_STRING ServerName
;
2619 UNICODE_STRING UserName
;
2620 SAM_HANDLE ServerHandle
= NULL
;
2621 SAM_HANDLE AccountDomainHandle
= NULL
;
2622 SAM_HANDLE UserHandle
= NULL
;
2623 PSID AccountDomainSid
= NULL
;
2624 PULONG RelativeIds
= NULL
;
2625 PSID_NAME_USE Use
= NULL
;
2626 PGROUP_MEMBERSHIP GroupMembership
= NULL
;
2629 NET_API_STATUS ApiStatus
= NERR_Success
;
2630 NTSTATUS Status
= STATUS_SUCCESS
;
2632 TRACE("%s %s %d %p %d %p %p stub\n", debugstr_w(servername
),
2633 debugstr_w(username
), level
, bufptr
, prefixmaxlen
, entriesread
,
2636 if (servername
!= NULL
)
2637 RtlInitUnicodeString(&ServerName
, servername
);
2639 RtlInitUnicodeString(&UserName
, username
);
2641 /* Connect to the SAM Server */
2642 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
2644 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
2646 if (!NT_SUCCESS(Status
))
2648 ERR("SamConnect failed (Status %08lx)\n", Status
);
2649 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2653 /* Get the Account Domain SID */
2654 Status
= GetAccountDomainSid((servername
!= NULL
) ? &ServerName
: NULL
,
2656 if (!NT_SUCCESS(Status
))
2658 ERR("GetAccountDomainSid failed (Status %08lx)\n", Status
);
2659 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2663 /* Open the Account Domain */
2664 Status
= SamOpenDomain(ServerHandle
,
2665 DOMAIN_LOOKUP
| DOMAIN_GET_ALIAS_MEMBERSHIP
,
2667 &AccountDomainHandle
);
2668 if (!NT_SUCCESS(Status
))
2670 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
2671 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2675 /* Get the RID for the given user name */
2676 Status
= SamLookupNamesInDomain(AccountDomainHandle
,
2681 if (!NT_SUCCESS(Status
))
2683 ERR("SamLookupNamesInDomain failed (Status %08lx)\n", Status
);
2684 if (Status
== STATUS_NONE_MAPPED
)
2685 ApiStatus
= NERR_UserNotFound
;
2687 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2691 /* Fail, if it is not a user account */
2692 if (Use
[0] != SidTypeUser
)
2694 ERR("Account is not a User!\n");
2695 ApiStatus
= NERR_UserNotFound
;
2699 /* Open the user object */
2700 Status
= SamOpenUser(AccountDomainHandle
,
2704 if (!NT_SUCCESS(Status
))
2706 ERR("SamOpenUser failed (Status %08lx)\n", Status
);
2707 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2711 /* Get the group memberships of this user */
2712 Status
= SamGetGroupsForUser(UserHandle
,
2715 if (!NT_SUCCESS(Status
))
2717 ERR("SamGetGroupsForUser failed (Status %08lx)\n", Status
);
2718 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2722 /* If there is no group membership, we're done */
2723 if (GroupCount
== 0)
2725 ApiStatus
= NERR_Success
;
2732 if (GroupMembership
!= NULL
)
2733 SamFreeMemory(GroupMembership
);
2735 if (UserHandle
!= NULL
)
2736 SamCloseHandle(UserHandle
);
2738 if (RelativeIds
!= NULL
)
2739 SamFreeMemory(RelativeIds
);
2744 if (AccountDomainSid
!= NULL
)
2745 RtlFreeHeap(RtlGetProcessHeap(), 0, AccountDomainSid
);
2747 if (AccountDomainHandle
!= NULL
)
2748 SamCloseHandle(AccountDomainHandle
);
2750 if (ServerHandle
!= NULL
)
2751 SamCloseHandle(ServerHandle
);
2753 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_MORE_DATA
)
2760 // *entriesread = Count;
2761 // *totalentries = Count;
2764 // *bufptr = (LPBYTE)Buffer;
2770 /************************************************************
2771 * NetUserGetInfo (NETAPI32.@)
2775 NetUserGetInfo(LPCWSTR servername
,
2780 UNICODE_STRING ServerName
;
2781 UNICODE_STRING UserName
;
2782 SAM_HANDLE ServerHandle
= NULL
;
2783 SAM_HANDLE AccountDomainHandle
= NULL
;
2784 SAM_HANDLE UserHandle
= NULL
;
2785 PULONG RelativeIds
= NULL
;
2786 PSID_NAME_USE Use
= NULL
;
2787 LPVOID Buffer
= NULL
;
2788 NET_API_STATUS ApiStatus
= NERR_Success
;
2789 NTSTATUS Status
= STATUS_SUCCESS
;
2791 TRACE("(%s, %s, %d, %p)\n", debugstr_w(servername
),
2792 debugstr_w(username
), level
, bufptr
);
2794 if (servername
!= NULL
)
2795 RtlInitUnicodeString(&ServerName
, servername
);
2797 RtlInitUnicodeString(&UserName
, username
);
2799 /* Connect to the SAM Server */
2800 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
2802 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
2804 if (!NT_SUCCESS(Status
))
2806 ERR("SamConnect failed (Status %08lx)\n", Status
);
2807 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2811 /* Open the Account Domain */
2812 Status
= OpenAccountDomain(ServerHandle
,
2813 (servername
!= NULL
) ? &ServerName
: NULL
,
2814 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
2815 &AccountDomainHandle
);
2816 if (!NT_SUCCESS(Status
))
2818 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
2819 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2823 /* Get the RID for the given user name */
2824 Status
= SamLookupNamesInDomain(AccountDomainHandle
,
2829 if (!NT_SUCCESS(Status
))
2831 ERR("SamOpenDomain failed (Status %08lx)\n", Status
);
2832 if (Status
== STATUS_NONE_MAPPED
)
2833 ApiStatus
= NERR_UserNotFound
;
2835 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2839 /* Check if the account is a user account */
2840 if (Use
[0] != SidTypeUser
)
2842 ERR("No user found!\n");
2843 ApiStatus
= NERR_UserNotFound
;
2847 TRACE("RID: %lu\n", RelativeIds
[0]);
2849 /* Open the user object */
2850 Status
= SamOpenUser(AccountDomainHandle
,
2851 READ_CONTROL
| USER_READ_GENERAL
| USER_READ_PREFERENCES
| USER_READ_LOGON
| USER_READ_ACCOUNT
,
2854 if (!NT_SUCCESS(Status
))
2856 ERR("SamOpenUser failed (Status %08lx)\n", Status
);
2857 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2861 ApiStatus
= BuildUserInfoBuffer(UserHandle
,
2865 if (ApiStatus
!= NERR_Success
)
2867 ERR("BuildUserInfoBuffer failed (ApiStatus %08lu)\n", ApiStatus
);
2872 if (UserHandle
!= NULL
)
2873 SamCloseHandle(UserHandle
);
2875 if (RelativeIds
!= NULL
)
2876 SamFreeMemory(RelativeIds
);
2881 if (AccountDomainHandle
!= NULL
)
2882 SamCloseHandle(AccountDomainHandle
);
2884 if (ServerHandle
!= NULL
)
2885 SamCloseHandle(ServerHandle
);
2887 *bufptr
= (LPBYTE
)Buffer
;
2893 /************************************************************
2894 * NetUserGetLocalGroups (NETAPI32.@)
2898 NetUserGetLocalGroups(LPCWSTR servername
,
2904 LPDWORD entriesread
,
2905 LPDWORD totalentries
)
2907 UNICODE_STRING ServerName
;
2908 UNICODE_STRING UserName
;
2909 SAM_HANDLE ServerHandle
= NULL
;
2910 SAM_HANDLE BuiltinDomainHandle
= NULL
;
2911 SAM_HANDLE AccountDomainHandle
= NULL
;
2912 PSID AccountDomainSid
= NULL
;
2913 PSID UserSid
= NULL
;
2914 PULONG RelativeIds
= NULL
;
2915 PSID_NAME_USE Use
= NULL
;
2916 ULONG BuiltinMemberCount
= 0;
2917 ULONG AccountMemberCount
= 0;
2918 PULONG BuiltinAliases
= NULL
;
2919 PULONG AccountAliases
= NULL
;
2920 PUNICODE_STRING BuiltinNames
= NULL
;
2921 PUNICODE_STRING AccountNames
= NULL
;
2922 PLOCALGROUP_USERS_INFO_0 Buffer
= NULL
;
2928 NET_API_STATUS ApiStatus
= NERR_Success
;
2929 NTSTATUS Status
= STATUS_SUCCESS
;
2931 TRACE("(%s, %s, %d, %08x, %p %d, %p, %p) stub!\n",
2932 debugstr_w(servername
), debugstr_w(username
), level
, flags
, bufptr
,
2933 prefmaxlen
, entriesread
, totalentries
);
2936 return ERROR_INVALID_LEVEL
;
2938 if (flags
& ~LG_INCLUDE_INDIRECT
)
2939 return ERROR_INVALID_PARAMETER
;
2941 if (flags
& LG_INCLUDE_INDIRECT
)
2943 WARN("The flag LG_INCLUDE_INDIRECT is not supported yet!\n");
2946 if (servername
!= NULL
)
2947 RtlInitUnicodeString(&ServerName
, servername
);
2949 RtlInitUnicodeString(&UserName
, username
);
2951 /* Connect to the SAM Server */
2952 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
2954 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
2956 if (!NT_SUCCESS(Status
))
2958 ERR("SamConnect failed (Status %08lx)\n", Status
);
2959 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2963 /* Open the Builtin Domain */
2964 Status
= OpenBuiltinDomain(ServerHandle
,
2965 DOMAIN_LOOKUP
| DOMAIN_GET_ALIAS_MEMBERSHIP
,
2966 &BuiltinDomainHandle
);
2967 if (!NT_SUCCESS(Status
))
2969 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
2970 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2974 /* Get the Account Domain SID */
2975 Status
= GetAccountDomainSid((servername
!= NULL
) ? &ServerName
: NULL
,
2977 if (!NT_SUCCESS(Status
))
2979 ERR("GetAccountDomainSid failed (Status %08lx)\n", Status
);
2980 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2984 /* Open the Account Domain */
2985 Status
= SamOpenDomain(ServerHandle
,
2986 DOMAIN_LOOKUP
| DOMAIN_GET_ALIAS_MEMBERSHIP
,
2988 &AccountDomainHandle
);
2989 if (!NT_SUCCESS(Status
))
2991 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
2992 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2996 /* Get the RID for the given user name */
2997 Status
= SamLookupNamesInDomain(AccountDomainHandle
,
3002 if (!NT_SUCCESS(Status
))
3004 ERR("SamLookupNamesInDomain failed (Status %08lx)\n", Status
);
3005 if (Status
== STATUS_NONE_MAPPED
)
3006 ApiStatus
= NERR_UserNotFound
;
3008 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3012 /* Fail, if it is not a user account */
3013 if (Use
[0] != SidTypeUser
)
3015 ERR("Account is not a User!\n");
3016 ApiStatus
= NERR_UserNotFound
;
3020 /* Build the User SID from the Account Domain SID and the users RID */
3021 ApiStatus
= BuildSidFromSidAndRid(AccountDomainSid
,
3024 if (ApiStatus
!= NERR_Success
)
3026 ERR("BuildSidFromSidAndRid failed!\n");
3030 /* Get alias memberships in the Builtin Domain */
3031 Status
= SamGetAliasMembership(BuiltinDomainHandle
,
3034 &BuiltinMemberCount
,
3036 if (!NT_SUCCESS(Status
))
3038 ERR("SamGetAliasMembership failed (Status %08lx)\n", Status
);
3039 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3043 if (BuiltinMemberCount
> 0)
3045 /* Get the Names of the builtin alias members */
3046 Status
= SamLookupIdsInDomain(BuiltinDomainHandle
,
3051 if (!NT_SUCCESS(Status
))
3053 ERR("SamLookupIdsInDomain failed (Status %08lx)\n", Status
);
3054 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3059 /* Get alias memberships in the Account Domain */
3060 Status
= SamGetAliasMembership(AccountDomainHandle
,
3063 &AccountMemberCount
,
3065 if (!NT_SUCCESS(Status
))
3067 ERR("SamGetAliasMembership failed (Status %08lx)\n", Status
);
3068 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3072 if (AccountMemberCount
> 0)
3074 /* Get the Names of the builtin alias members */
3075 Status
= SamLookupIdsInDomain(AccountDomainHandle
,
3080 if (!NT_SUCCESS(Status
))
3082 ERR("SamLookupIdsInDomain failed (Status %08lx)\n", Status
);
3083 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3088 /* Calculate the required buffer size */
3091 for (i
= 0; i
< BuiltinMemberCount
; i
++)
3093 if (BuiltinNames
[i
].Length
> 0)
3095 Size
+= (sizeof(LOCALGROUP_USERS_INFO_0
) + BuiltinNames
[i
].Length
+ sizeof(UNICODE_NULL
));
3100 for (i
= 0; i
< AccountMemberCount
; i
++)
3102 if (AccountNames
[i
].Length
> 0)
3104 Size
+= (sizeof(LOCALGROUP_USERS_INFO_0
) + AccountNames
[i
].Length
+ sizeof(UNICODE_NULL
));
3111 ApiStatus
= NERR_Success
;
3115 /* Allocate buffer */
3116 ApiStatus
= NetApiBufferAllocate(Size
, (LPVOID
*)&Buffer
);
3117 if (ApiStatus
!= NERR_Success
)
3120 ZeroMemory(Buffer
, Size
);
3122 StrPtr
= (LPWSTR
)((INT_PTR
)Buffer
+ Count
* sizeof(LOCALGROUP_USERS_INFO_0
));
3124 /* Copy data to the allocated buffer */
3126 for (i
= 0; i
< BuiltinMemberCount
; i
++)
3128 if (BuiltinNames
[i
].Length
> 0)
3131 BuiltinNames
[i
].Buffer
,
3132 BuiltinNames
[i
].Length
);
3133 Buffer
[Index
].lgrui0_name
= StrPtr
;
3135 StrPtr
= (LPWSTR
)((INT_PTR
)StrPtr
+ BuiltinNames
[i
].Length
+ sizeof(UNICODE_NULL
));
3140 for (i
= 0; i
< AccountMemberCount
; i
++)
3142 if (AccountNames
[i
].Length
> 0)
3145 AccountNames
[i
].Buffer
,
3146 AccountNames
[i
].Length
);
3147 Buffer
[Index
].lgrui0_name
= StrPtr
;
3149 StrPtr
= (LPWSTR
)((INT_PTR
)StrPtr
+ AccountNames
[i
].Length
+ sizeof(UNICODE_NULL
));
3155 if (AccountNames
!= NULL
)
3156 SamFreeMemory(AccountNames
);
3158 if (BuiltinNames
!= NULL
)
3159 SamFreeMemory(BuiltinNames
);
3161 if (AccountAliases
!= NULL
)
3162 SamFreeMemory(AccountAliases
);
3164 if (BuiltinAliases
!= NULL
)
3165 SamFreeMemory(BuiltinAliases
);
3167 if (RelativeIds
!= NULL
)
3168 SamFreeMemory(RelativeIds
);
3173 if (UserSid
!= NULL
)
3174 NetApiBufferFree(UserSid
);
3176 if (AccountDomainSid
!= NULL
)
3177 RtlFreeHeap(RtlGetProcessHeap(), 0, AccountDomainSid
);
3179 if (AccountDomainHandle
!= NULL
)
3180 SamCloseHandle(AccountDomainHandle
);
3182 if (BuiltinDomainHandle
!= NULL
)
3183 SamCloseHandle(BuiltinDomainHandle
);
3185 if (ServerHandle
!= NULL
)
3186 SamCloseHandle(ServerHandle
);
3188 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_MORE_DATA
)
3195 *entriesread
= Count
;
3196 *totalentries
= Count
;
3199 *bufptr
= (LPBYTE
)Buffer
;
3205 /******************************************************************************
3206 * NetUserModalsGet (NETAPI32.@)
3208 * Retrieves global information for all users and global groups in the security
3212 * servername [I] Specifies the DNS or the NetBIOS name of the remote server
3213 * on which the function is to execute.
3214 * level [I] Information level of the data.
3215 * 0 Return global passwords parameters. bufptr points to a
3216 * USER_MODALS_INFO_0 struct.
3217 * 1 Return logon server and domain controller information. bufptr
3218 * points to a USER_MODALS_INFO_1 struct.
3219 * 2 Return domain name and identifier. bufptr points to a
3220 * USER_MODALS_INFO_2 struct.
3221 * 3 Return lockout information. bufptr points to a USER_MODALS_INFO_3
3223 * bufptr [O] Buffer that receives the data.
3226 * Success: NERR_Success.
3228 * ERROR_ACCESS_DENIED - the user does not have access to the info.
3229 * NERR_InvalidComputer - computer name is invalid.
3233 NetUserModalsGet(LPCWSTR servername
,
3237 UNICODE_STRING ServerName
;
3238 SAM_HANDLE ServerHandle
= NULL
;
3239 SAM_HANDLE DomainHandle
= NULL
;
3240 PSID DomainSid
= NULL
;
3241 PDOMAIN_PASSWORD_INFORMATION PasswordInfo
= NULL
;
3242 PDOMAIN_LOGOFF_INFORMATION LogoffInfo
= NULL
;
3243 PDOMAIN_SERVER_ROLE_INFORMATION ServerRoleInfo
= NULL
;
3244 PDOMAIN_REPLICATION_INFORMATION ReplicationInfo
= NULL
;
3245 PDOMAIN_NAME_INFORMATION NameInfo
= NULL
;
3246 PDOMAIN_LOCKOUT_INFORMATION LockoutInfo
= NULL
;
3247 ULONG DesiredAccess
;
3249 PUSER_MODALS_INFO_0 umi0
;
3250 PUSER_MODALS_INFO_1 umi1
;
3251 PUSER_MODALS_INFO_2 umi2
;
3252 PUSER_MODALS_INFO_3 umi3
;
3253 NET_API_STATUS ApiStatus
= NERR_Success
;
3254 NTSTATUS Status
= STATUS_SUCCESS
;
3256 TRACE("(%s %d %p)\n", debugstr_w(servername
), level
, bufptr
);
3260 if (servername
!= NULL
)
3261 RtlInitUnicodeString(&ServerName
, servername
);
3263 /* Connect to the SAM Server */
3264 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
3266 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
3268 if (!NT_SUCCESS(Status
))
3270 ERR("SamConnect failed (Status %08lx)\n", Status
);
3271 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3275 /* Get the Account Domain SID */
3276 Status
= GetAccountDomainSid((servername
!= NULL
) ? &ServerName
: NULL
,
3278 if (!NT_SUCCESS(Status
))
3280 ERR("GetAccountDomainSid failed (Status %08lx)\n", Status
);
3281 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3288 DesiredAccess
= DOMAIN_READ_OTHER_PARAMETERS
| DOMAIN_READ_PASSWORD_PARAMETERS
;
3292 DesiredAccess
= DOMAIN_READ_OTHER_PARAMETERS
;
3296 DesiredAccess
= DOMAIN_READ_OTHER_PARAMETERS
;
3300 DesiredAccess
= DOMAIN_READ_PASSWORD_PARAMETERS
;
3304 ApiStatus
= ERROR_INVALID_LEVEL
;
3308 /* Open the Account Domain */
3309 Status
= SamOpenDomain(ServerHandle
,
3313 if (!NT_SUCCESS(Status
))
3315 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
3316 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3323 /* return global passwords parameters */
3324 Status
= SamQueryInformationDomain(DomainHandle
,
3325 DomainPasswordInformation
,
3326 (PVOID
*)&PasswordInfo
);
3327 if (!NT_SUCCESS(Status
))
3329 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3333 Status
= SamQueryInformationDomain(DomainHandle
,
3334 DomainLogoffInformation
,
3335 (PVOID
*)&LogoffInfo
);
3336 if (!NT_SUCCESS(Status
))
3338 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3342 BufferSize
= sizeof(USER_MODALS_INFO_0
);
3346 /* return logon server and domain controller info */
3347 Status
= SamQueryInformationDomain(DomainHandle
,
3348 DomainServerRoleInformation
,
3349 (PVOID
*)&ServerRoleInfo
);
3350 if (!NT_SUCCESS(Status
))
3352 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3356 Status
= SamQueryInformationDomain(DomainHandle
,
3357 DomainReplicationInformation
,
3358 (PVOID
*)&ReplicationInfo
);
3359 if (!NT_SUCCESS(Status
))
3361 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3365 BufferSize
= sizeof(USER_MODALS_INFO_1
) +
3366 ReplicationInfo
->ReplicaSourceNodeName
.Length
+ sizeof(WCHAR
);
3370 /* return domain name and identifier */
3371 Status
= SamQueryInformationDomain(DomainHandle
,
3372 DomainNameInformation
,
3374 if (!NT_SUCCESS(Status
))
3376 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3380 BufferSize
= sizeof( USER_MODALS_INFO_2
) +
3381 NameInfo
->DomainName
.Length
+ sizeof(WCHAR
) +
3382 RtlLengthSid(DomainSid
);
3386 /* return lockout information */
3387 Status
= SamQueryInformationDomain(DomainHandle
,
3388 DomainLockoutInformation
,
3389 (PVOID
*)&LockoutInfo
);
3390 if (!NT_SUCCESS(Status
))
3392 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3396 BufferSize
= sizeof(USER_MODALS_INFO_3
);
3400 TRACE("Invalid level %d is specified\n", level
);
3401 ApiStatus
= ERROR_INVALID_LEVEL
;
3406 ApiStatus
= NetApiBufferAllocate(BufferSize
,
3408 if (ApiStatus
!= NERR_Success
)
3410 WARN("NetApiBufferAllocate() failed\n");
3417 umi0
= (PUSER_MODALS_INFO_0
)*bufptr
;
3419 umi0
->usrmod0_min_passwd_len
= PasswordInfo
->MinPasswordLength
;
3420 umi0
->usrmod0_max_passwd_age
= (ULONG
)(-PasswordInfo
->MaxPasswordAge
.QuadPart
/ 10000000);
3421 umi0
->usrmod0_min_passwd_age
=
3422 DeltaTimeToSeconds(PasswordInfo
->MinPasswordAge
);
3423 umi0
->usrmod0_force_logoff
=
3424 DeltaTimeToSeconds(LogoffInfo
->ForceLogoff
);
3425 umi0
->usrmod0_password_hist_len
= PasswordInfo
->PasswordHistoryLength
;
3429 umi1
= (PUSER_MODALS_INFO_1
)*bufptr
;
3431 switch (ServerRoleInfo
->DomainServerRole
)
3433 case DomainServerRolePrimary
:
3434 umi1
->usrmod1_role
= UAS_ROLE_PRIMARY
;
3437 case DomainServerRoleBackup
:
3438 umi1
->usrmod1_role
= UAS_ROLE_BACKUP
;
3442 ApiStatus
= NERR_InternalError
;
3446 umi1
->usrmod1_primary
= (LPWSTR
)(*bufptr
+ sizeof(USER_MODALS_INFO_1
));
3447 RtlCopyMemory(umi1
->usrmod1_primary
,
3448 ReplicationInfo
->ReplicaSourceNodeName
.Buffer
,
3449 ReplicationInfo
->ReplicaSourceNodeName
.Length
);
3450 umi1
->usrmod1_primary
[ReplicationInfo
->ReplicaSourceNodeName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
3454 umi2
= (PUSER_MODALS_INFO_2
)*bufptr
;
3456 umi2
->usrmod2_domain_name
= (LPWSTR
)(*bufptr
+ sizeof(USER_MODALS_INFO_2
));
3457 RtlCopyMemory(umi2
->usrmod2_domain_name
,
3458 NameInfo
->DomainName
.Buffer
,
3459 NameInfo
->DomainName
.Length
);
3460 umi2
->usrmod2_domain_name
[NameInfo
->DomainName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
3462 umi2
->usrmod2_domain_id
= *bufptr
+
3463 sizeof(USER_MODALS_INFO_2
) +
3464 NameInfo
->DomainName
.Length
+ sizeof(WCHAR
);
3465 RtlCopyMemory(umi2
->usrmod2_domain_id
,
3467 RtlLengthSid(DomainSid
));
3471 umi3
= (PUSER_MODALS_INFO_3
)*bufptr
;
3472 umi3
->usrmod3_lockout_duration
=
3473 DeltaTimeToSeconds(LockoutInfo
->LockoutDuration
);
3474 umi3
->usrmod3_lockout_observation_window
=
3475 DeltaTimeToSeconds(LockoutInfo
->LockoutObservationWindow
);
3476 umi3
->usrmod3_lockout_threshold
= LockoutInfo
->LockoutThreshold
;
3481 if (LockoutInfo
!= NULL
)
3482 SamFreeMemory(LockoutInfo
);
3484 if (NameInfo
!= NULL
)
3485 SamFreeMemory(NameInfo
);
3487 if (ReplicationInfo
!= NULL
)
3488 SamFreeMemory(ReplicationInfo
);
3490 if (ServerRoleInfo
!= NULL
)
3491 SamFreeMemory(ServerRoleInfo
);
3493 if (LogoffInfo
!= NULL
)
3494 SamFreeMemory(LogoffInfo
);
3496 if (PasswordInfo
!= NULL
)
3497 SamFreeMemory(PasswordInfo
);
3499 if (DomainSid
!= NULL
)
3500 RtlFreeHeap(RtlGetProcessHeap(), 0, DomainSid
);
3502 if (DomainHandle
!= NULL
)
3503 SamCloseHandle(DomainHandle
);
3505 if (ServerHandle
!= NULL
)
3506 SamCloseHandle(ServerHandle
);
3512 /******************************************************************************
3513 * NetUserModalsSet (NETAPI32.@)
3517 NetUserModalsSet(IN LPCWSTR servername
,
3520 OUT LPDWORD parm_err
)
3522 FIXME("(%s %d %p %p)\n", debugstr_w(servername
), level
, buf
, parm_err
);
3523 return ERROR_ACCESS_DENIED
;
3527 /******************************************************************************
3528 * NetUserSetGroups (NETAPI32.@)
3532 NetUserSetGroups(LPCWSTR servername
,
3538 FIXME("(%s %s %lu %p %lu)\n",
3539 debugstr_w(servername
), debugstr_w(username
), level
, buf
, num_entries
);
3540 return ERROR_ACCESS_DENIED
;
3544 /******************************************************************************
3545 * NetUserSetInfo (NETAPI32.@)
3549 NetUserSetInfo(LPCWSTR servername
,
3555 UNICODE_STRING ServerName
;
3556 UNICODE_STRING UserName
;
3557 SAM_HANDLE ServerHandle
= NULL
;
3558 SAM_HANDLE AccountDomainHandle
= NULL
;
3559 SAM_HANDLE UserHandle
= NULL
;
3560 NET_API_STATUS ApiStatus
= NERR_Success
;
3561 NTSTATUS Status
= STATUS_SUCCESS
;
3563 TRACE("(%s %s %lu %p %p)\n",
3564 debugstr_w(servername
), debugstr_w(username
), level
, buf
, parm_err
);
3566 if (parm_err
!= NULL
)
3567 *parm_err
= PARM_ERROR_NONE
;
3569 /* Check the info level */
3601 return ERROR_INVALID_LEVEL
;
3604 if (servername
!= NULL
)
3605 RtlInitUnicodeString(&ServerName
, servername
);
3607 RtlInitUnicodeString(&UserName
, username
);
3609 /* Connect to the SAM Server */
3610 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
3612 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
3614 if (!NT_SUCCESS(Status
))
3616 ERR("SamConnect failed (Status %08lx)\n", Status
);
3617 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3621 /* Open the Account Domain */
3622 Status
= OpenAccountDomain(ServerHandle
,
3623 (servername
!= NULL
) ? &ServerName
: NULL
,
3624 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
| DOMAIN_READ_PASSWORD_PARAMETERS
,
3625 &AccountDomainHandle
);
3626 if (!NT_SUCCESS(Status
))
3628 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
3629 ApiStatus
= NetpNtStatusToApiStatus(Status
);
3633 /* Open the User Account */
3634 ApiStatus
= OpenUserByName(AccountDomainHandle
,
3638 if (ApiStatus
!= NERR_Success
)
3640 ERR("OpenUserByName failed (ApiStatus %lu)\n", ApiStatus
);
3644 /* Set user information */
3645 ApiStatus
= SetUserInfo(UserHandle
,
3648 if (ApiStatus
!= NERR_Success
)
3650 ERR("SetUserInfo failed (Status %lu)\n", ApiStatus
);
3654 if (UserHandle
!= NULL
)
3655 SamCloseHandle(UserHandle
);
3657 if (AccountDomainHandle
!= NULL
)
3658 SamCloseHandle(AccountDomainHandle
);
3660 if (ServerHandle
!= NULL
)
3661 SamCloseHandle(ServerHandle
);