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 NetUserChangePassword
24 * Implement NetUserGetGroups
25 * Implement NetUserSetGroups
26 * NetUserGetLocalGroups does not support LG_INCLUDE_INDIRECT yet.
27 * Add missing information levels.
33 WINE_DEFAULT_DEBUG_CHANNEL(netapi32
);
36 typedef struct _ENUM_CONTEXT
38 SAM_HANDLE ServerHandle
;
39 SAM_HANDLE BuiltinDomainHandle
;
40 SAM_HANDLE AccountDomainHandle
;
42 SAM_ENUMERATE_HANDLE EnumerationContext
;
43 PSAM_RID_ENUMERATION Buffer
;
48 } ENUM_CONTEXT
, *PENUM_CONTEXT
;
53 GetAccountFlags(ULONG AccountControl
)
55 ULONG Flags
= UF_SCRIPT
;
57 if (AccountControl
& USER_ACCOUNT_DISABLED
)
58 Flags
|= UF_ACCOUNTDISABLE
;
60 if (AccountControl
& USER_HOME_DIRECTORY_REQUIRED
)
61 Flags
|= UF_HOMEDIR_REQUIRED
;
63 if (AccountControl
& USER_PASSWORD_NOT_REQUIRED
)
64 Flags
|= UF_PASSWD_NOTREQD
;
66 // UF_PASSWD_CANT_CHANGE
68 if (AccountControl
& USER_ACCOUNT_AUTO_LOCKED
)
71 if (AccountControl
& USER_DONT_EXPIRE_PASSWORD
)
72 Flags
|= UF_DONT_EXPIRE_PASSWD
;
75 if (AccountControl & USER_ENCRYPTED_TEXT_PASSWORD_ALLOWED)
76 Flags |= UF_ENCRYPTED_TEXT_PASSWORD_ALLOWED;
78 if (AccountControl & USER_SMARTCARD_REQUIRED)
79 Flags |= UF_SMARTCARD_REQUIRED;
81 if (AccountControl & USER_TRUSTED_FOR_DELEGATION)
82 Flags |= UF_TRUSTED_FOR_DELEGATION;
84 if (AccountControl & USER_NOT_DELEGATED)
85 Flags |= UF_NOT_DELEGATED;
87 if (AccountControl & USER_USE_DES_KEY_ONLY)
88 Flags |= UF_USE_DES_KEY_ONLY;
90 if (AccountControl & USER_DONT_REQUIRE_PREAUTH)
91 Flags |= UF_DONT_REQUIRE_PREAUTH;
93 if (AccountControl & USER_PASSWORD_EXPIRED)
94 Flags |= UF_PASSWORD_EXPIRED;
97 /* Set account type flags */
98 if (AccountControl
& USER_TEMP_DUPLICATE_ACCOUNT
)
99 Flags
|= UF_TEMP_DUPLICATE_ACCOUNT
;
100 else if (AccountControl
& USER_NORMAL_ACCOUNT
)
101 Flags
|= UF_NORMAL_ACCOUNT
;
102 else if (AccountControl
& USER_INTERDOMAIN_TRUST_ACCOUNT
)
103 Flags
|= UF_INTERDOMAIN_TRUST_ACCOUNT
;
104 else if (AccountControl
& USER_WORKSTATION_TRUST_ACCOUNT
)
105 Flags
|= UF_WORKSTATION_TRUST_ACCOUNT
;
106 else if (AccountControl
& USER_SERVER_TRUST_ACCOUNT
)
107 Flags
|= UF_SERVER_TRUST_ACCOUNT
;
115 BuildUserInfoBuffer(PUSER_ACCOUNT_INFORMATION UserInfo
,
120 LPVOID LocalBuffer
= NULL
;
121 PUSER_INFO_0 UserInfo0
;
122 PUSER_INFO_1 UserInfo1
;
123 PUSER_INFO_2 UserInfo2
;
124 PUSER_INFO_3 UserInfo3
;
125 PUSER_INFO_10 UserInfo10
;
126 PUSER_INFO_20 UserInfo20
;
127 PUSER_INFO_23 UserInfo23
;
130 NET_API_STATUS ApiStatus
= NERR_Success
;
137 Size
= sizeof(USER_INFO_0
) +
138 UserInfo
->UserName
.Length
+ sizeof(WCHAR
);
142 Size
= sizeof(USER_INFO_1
) +
143 UserInfo
->UserName
.Length
+ sizeof(WCHAR
);
145 if (UserInfo
->HomeDirectory
.Length
> 0)
146 Size
+= UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
);
148 if (UserInfo
->AdminComment
.Length
> 0)
149 Size
+= UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
151 if (UserInfo
->ScriptPath
.Length
> 0)
152 Size
+= UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
);
156 Size
= sizeof(USER_INFO_2
) +
157 UserInfo
->UserName
.Length
+ sizeof(WCHAR
);
159 if (UserInfo
->HomeDirectory
.Length
> 0)
160 Size
+= UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
);
162 if (UserInfo
->AdminComment
.Length
> 0)
163 Size
+= UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
165 if (UserInfo
->ScriptPath
.Length
> 0)
166 Size
+= UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
);
168 if (UserInfo
->FullName
.Length
> 0)
169 Size
+= UserInfo
->FullName
.Length
+ sizeof(WCHAR
);
171 /* FIXME: usri2_usr_comment */
172 /* FIXME: usri2_parms */
174 if (UserInfo
->WorkStations
.Length
> 0)
175 Size
+= UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
);
177 /* FIXME: usri2_logon_hours */
178 /* FIXME: usri2_logon_server */
182 Size
= sizeof(USER_INFO_3
) +
183 UserInfo
->UserName
.Length
+ sizeof(WCHAR
);
185 if (UserInfo
->HomeDirectory
.Length
> 0)
186 Size
+= UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
);
188 if (UserInfo
->AdminComment
.Length
> 0)
189 Size
+= UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
191 if (UserInfo
->ScriptPath
.Length
> 0)
192 Size
+= UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
);
194 if (UserInfo
->FullName
.Length
> 0)
195 Size
+= UserInfo
->FullName
.Length
+ sizeof(WCHAR
);
197 /* FIXME: usri3_usr_comment */
198 /* FIXME: usri3_parms */
200 if (UserInfo
->WorkStations
.Length
> 0)
201 Size
+= UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
);
203 /* FIXME: usri3_logon_hours */
204 /* FIXME: usri3_logon_server */
206 if (UserInfo
->ProfilePath
.Length
> 0)
207 Size
+= UserInfo
->ProfilePath
.Length
+ sizeof(WCHAR
);
209 if (UserInfo
->HomeDirectoryDrive
.Length
> 0)
210 Size
+= UserInfo
->HomeDirectoryDrive
.Length
+ sizeof(WCHAR
);
216 Size
= sizeof(USER_INFO_10
) +
217 UserInfo
->UserName
.Length
+ sizeof(WCHAR
);
219 if (UserInfo
->AdminComment
.Length
> 0)
220 Size
+= UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
222 /* FIXME: usri10_usr_comment */
224 if (UserInfo
->FullName
.Length
> 0)
225 Size
+= UserInfo
->FullName
.Length
+ sizeof(WCHAR
);
231 Size
= sizeof(USER_INFO_20
) +
232 UserInfo
->UserName
.Length
+ sizeof(WCHAR
);
234 if (UserInfo
->FullName
.Length
> 0)
235 Size
+= UserInfo
->FullName
.Length
+ sizeof(WCHAR
);
237 if (UserInfo
->AdminComment
.Length
> 0)
238 Size
+= UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
242 Size
= sizeof(USER_INFO_23
) +
243 UserInfo
->UserName
.Length
+ sizeof(WCHAR
);
245 if (UserInfo
->FullName
.Length
> 0)
246 Size
+= UserInfo
->FullName
.Length
+ sizeof(WCHAR
);
248 if (UserInfo
->AdminComment
.Length
> 0)
249 Size
+= UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
251 /* FIXME: usri23_user_sid */
255 ApiStatus
= ERROR_INVALID_LEVEL
;
259 ApiStatus
= NetApiBufferAllocate(Size
, &LocalBuffer
);
260 if (ApiStatus
!= NERR_Success
)
263 ZeroMemory(LocalBuffer
, Size
);
268 UserInfo0
= (PUSER_INFO_0
)LocalBuffer
;
270 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo0
+ sizeof(USER_INFO_0
));
271 UserInfo0
->usri0_name
= Ptr
;
273 memcpy(UserInfo0
->usri0_name
,
274 UserInfo
->UserName
.Buffer
,
275 UserInfo
->UserName
.Length
);
276 UserInfo0
->usri0_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
280 UserInfo1
= (PUSER_INFO_1
)LocalBuffer
;
282 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo1
+ sizeof(USER_INFO_1
));
284 UserInfo1
->usri1_name
= Ptr
;
286 memcpy(UserInfo1
->usri1_name
,
287 UserInfo
->UserName
.Buffer
,
288 UserInfo
->UserName
.Length
);
289 UserInfo1
->usri1_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
291 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
293 UserInfo1
->usri1_password
= NULL
;
295 /* FIXME: UserInfo1->usri1_password_age */
296 /* FIXME: UserInfo1->usri1_priv */
298 if (UserInfo
->HomeDirectory
.Length
> 0)
300 UserInfo1
->usri1_home_dir
= Ptr
;
302 memcpy(UserInfo1
->usri1_home_dir
,
303 UserInfo
->HomeDirectory
.Buffer
,
304 UserInfo
->HomeDirectory
.Length
);
305 UserInfo1
->usri1_home_dir
[UserInfo
->HomeDirectory
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
307 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
));
310 if (UserInfo
->AdminComment
.Length
> 0)
312 UserInfo1
->usri1_comment
= Ptr
;
314 memcpy(UserInfo1
->usri1_comment
,
315 UserInfo
->AdminComment
.Buffer
,
316 UserInfo
->AdminComment
.Length
);
317 UserInfo1
->usri1_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
319 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
322 UserInfo1
->usri1_flags
= GetAccountFlags(UserInfo
->UserAccountControl
);
324 if (UserInfo
->ScriptPath
.Length
> 0)
326 UserInfo1
->usri1_script_path
= Ptr
;
328 memcpy(UserInfo1
->usri1_script_path
,
329 UserInfo
->ScriptPath
.Buffer
,
330 UserInfo
->ScriptPath
.Length
);
331 UserInfo1
->usri1_script_path
[UserInfo
->ScriptPath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
336 UserInfo2
= (PUSER_INFO_2
)LocalBuffer
;
338 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo2
+ sizeof(USER_INFO_2
));
340 UserInfo2
->usri2_name
= Ptr
;
342 memcpy(UserInfo2
->usri2_name
,
343 UserInfo
->UserName
.Buffer
,
344 UserInfo
->UserName
.Length
);
345 UserInfo2
->usri2_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
347 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
349 /* FIXME: usri2_password_age */
350 /* FIXME: usri2_priv */
352 if (UserInfo
->HomeDirectory
.Length
> 0)
354 UserInfo2
->usri2_home_dir
= Ptr
;
356 memcpy(UserInfo2
->usri2_home_dir
,
357 UserInfo
->HomeDirectory
.Buffer
,
358 UserInfo
->HomeDirectory
.Length
);
359 UserInfo2
->usri2_home_dir
[UserInfo
->HomeDirectory
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
361 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
));
364 if (UserInfo
->AdminComment
.Length
> 0)
366 UserInfo2
->usri2_comment
= Ptr
;
368 memcpy(UserInfo2
->usri2_comment
,
369 UserInfo
->AdminComment
.Buffer
,
370 UserInfo
->AdminComment
.Length
);
371 UserInfo2
->usri2_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
373 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
376 UserInfo2
->usri2_flags
= GetAccountFlags(UserInfo
->UserAccountControl
);
378 if (UserInfo
->ScriptPath
.Length
> 0)
380 UserInfo2
->usri2_script_path
= Ptr
;
382 memcpy(UserInfo2
->usri2_script_path
,
383 UserInfo
->ScriptPath
.Buffer
,
384 UserInfo
->ScriptPath
.Length
);
385 UserInfo2
->usri2_script_path
[UserInfo
->ScriptPath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
387 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
));
390 /* FIXME: usri2_auth_flags */
392 if (UserInfo
->FullName
.Length
> 0)
394 UserInfo2
->usri2_full_name
= Ptr
;
396 memcpy(UserInfo2
->usri2_full_name
,
397 UserInfo
->FullName
.Buffer
,
398 UserInfo
->FullName
.Length
);
399 UserInfo2
->usri2_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
401 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
404 /* FIXME: usri2_usr_comment */
405 /* FIXME: usri2_parms */
407 if (UserInfo
->WorkStations
.Length
> 0)
409 UserInfo2
->usri2_workstations
= Ptr
;
411 memcpy(UserInfo2
->usri2_workstations
,
412 UserInfo
->WorkStations
.Buffer
,
413 UserInfo
->WorkStations
.Length
);
414 UserInfo2
->usri2_workstations
[UserInfo
->WorkStations
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
416 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
));
419 RtlTimeToSecondsSince1970(&UserInfo
->LastLogon
,
420 &UserInfo2
->usri2_last_logon
);
422 RtlTimeToSecondsSince1970(&UserInfo
->LastLogoff
,
423 &UserInfo2
->usri2_last_logoff
);
425 RtlTimeToSecondsSince1970(&UserInfo
->AccountExpires
,
426 &UserInfo2
->usri2_acct_expires
);
428 UserInfo2
->usri2_max_storage
= USER_MAXSTORAGE_UNLIMITED
;
430 /* FIXME: usri2_units_per_week */
431 /* FIXME: usri2_logon_hours */
433 UserInfo2
->usri2_bad_pw_count
= UserInfo
->BadPasswordCount
;
434 UserInfo2
->usri2_num_logons
= UserInfo
->LogonCount
;
436 /* FIXME: usri2_logon_server */
437 /* FIXME: usri2_country_code */
438 /* FIXME: usri2_code_page */
443 UserInfo3
= (PUSER_INFO_3
)LocalBuffer
;
445 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo3
+ sizeof(USER_INFO_3
));
447 UserInfo3
->usri3_name
= Ptr
;
449 memcpy(UserInfo3
->usri3_name
,
450 UserInfo
->UserName
.Buffer
,
451 UserInfo
->UserName
.Length
);
452 UserInfo3
->usri3_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
454 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
456 /* FIXME: usri3_password_age */
457 /* FIXME: usri3_priv */
459 if (UserInfo
->HomeDirectory
.Length
> 0)
461 UserInfo3
->usri3_home_dir
= Ptr
;
463 memcpy(UserInfo3
->usri3_home_dir
,
464 UserInfo
->HomeDirectory
.Buffer
,
465 UserInfo
->HomeDirectory
.Length
);
466 UserInfo3
->usri3_home_dir
[UserInfo
->HomeDirectory
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
468 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectory
.Length
+ sizeof(WCHAR
));
471 if (UserInfo
->AdminComment
.Length
> 0)
473 UserInfo3
->usri3_comment
= Ptr
;
475 memcpy(UserInfo3
->usri3_comment
,
476 UserInfo
->AdminComment
.Buffer
,
477 UserInfo
->AdminComment
.Length
);
478 UserInfo3
->usri3_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
480 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
483 UserInfo3
->usri3_flags
= GetAccountFlags(UserInfo
->UserAccountControl
);
485 if (UserInfo
->ScriptPath
.Length
> 0)
487 UserInfo3
->usri3_script_path
= Ptr
;
489 memcpy(UserInfo3
->usri3_script_path
,
490 UserInfo
->ScriptPath
.Buffer
,
491 UserInfo
->ScriptPath
.Length
);
492 UserInfo3
->usri3_script_path
[UserInfo
->ScriptPath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
494 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->ScriptPath
.Length
+ sizeof(WCHAR
));
497 /* FIXME: usri3_auth_flags */
499 if (UserInfo
->FullName
.Length
> 0)
501 UserInfo3
->usri3_full_name
= Ptr
;
503 memcpy(UserInfo3
->usri3_full_name
,
504 UserInfo
->FullName
.Buffer
,
505 UserInfo
->FullName
.Length
);
506 UserInfo3
->usri3_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
508 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
511 /* FIXME: usri3_usr_comment */
512 /* FIXME: usri3_parms */
514 if (UserInfo
->WorkStations
.Length
> 0)
516 UserInfo3
->usri3_workstations
= Ptr
;
518 memcpy(UserInfo3
->usri3_workstations
,
519 UserInfo
->WorkStations
.Buffer
,
520 UserInfo
->WorkStations
.Length
);
521 UserInfo3
->usri3_workstations
[UserInfo
->WorkStations
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
523 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->WorkStations
.Length
+ sizeof(WCHAR
));
526 RtlTimeToSecondsSince1970(&UserInfo
->LastLogon
,
527 &UserInfo3
->usri3_last_logon
);
529 RtlTimeToSecondsSince1970(&UserInfo
->LastLogoff
,
530 &UserInfo3
->usri3_last_logoff
);
532 RtlTimeToSecondsSince1970(&UserInfo
->AccountExpires
,
533 &UserInfo3
->usri3_acct_expires
);
535 UserInfo3
->usri3_max_storage
= USER_MAXSTORAGE_UNLIMITED
;
537 /* FIXME: usri3_units_per_week */
538 /* FIXME: usri3_logon_hours */
540 UserInfo3
->usri3_bad_pw_count
= UserInfo
->BadPasswordCount
;
541 UserInfo3
->usri3_num_logons
= UserInfo
->LogonCount
;
543 /* FIXME: usri3_logon_server */
544 /* FIXME: usri3_country_code */
545 /* FIXME: usri3_code_page */
547 UserInfo3
->usri3_user_id
= RelativeId
;
548 UserInfo3
->usri3_primary_group_id
= UserInfo
->PrimaryGroupId
;
550 if (UserInfo
->ProfilePath
.Length
> 0)
552 UserInfo3
->usri3_profile
= Ptr
;
554 memcpy(UserInfo3
->usri3_profile
,
555 UserInfo
->ProfilePath
.Buffer
,
556 UserInfo
->ProfilePath
.Length
);
557 UserInfo3
->usri3_profile
[UserInfo
->ProfilePath
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
559 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->ProfilePath
.Length
+ sizeof(WCHAR
));
562 if (UserInfo
->HomeDirectoryDrive
.Length
> 0)
564 UserInfo3
->usri3_home_dir_drive
= Ptr
;
566 memcpy(UserInfo3
->usri3_home_dir_drive
,
567 UserInfo
->HomeDirectoryDrive
.Buffer
,
568 UserInfo
->HomeDirectoryDrive
.Length
);
569 UserInfo3
->usri3_home_dir_drive
[UserInfo
->HomeDirectoryDrive
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
571 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->HomeDirectoryDrive
.Length
+ sizeof(WCHAR
));
574 UserInfo3
->usri3_password_expired
= (UserInfo
->UserAccountControl
& USER_PASSWORD_EXPIRED
);
580 UserInfo10
= (PUSER_INFO_10
)LocalBuffer
;
582 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo10
+ sizeof(USER_INFO_10
));
584 UserInfo10
->usri10_name
= Ptr
;
586 memcpy(UserInfo10
->usri10_name
,
587 UserInfo
->UserName
.Buffer
,
588 UserInfo
->UserName
.Length
);
589 UserInfo10
->usri10_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
591 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
593 if (UserInfo
->AdminComment
.Length
> 0)
595 UserInfo10
->usri10_comment
= Ptr
;
597 memcpy(UserInfo10
->usri10_comment
,
598 UserInfo
->AdminComment
.Buffer
,
599 UserInfo
->AdminComment
.Length
);
600 UserInfo10
->usri10_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
602 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
605 /* FIXME: usri10_usr_comment */
607 if (UserInfo
->FullName
.Length
> 0)
609 UserInfo10
->usri10_full_name
= Ptr
;
611 memcpy(UserInfo10
->usri10_full_name
,
612 UserInfo
->FullName
.Buffer
,
613 UserInfo
->FullName
.Length
);
614 UserInfo10
->usri10_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
616 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
623 UserInfo20
= (PUSER_INFO_20
)LocalBuffer
;
625 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo20
+ sizeof(USER_INFO_20
));
627 UserInfo20
->usri20_name
= Ptr
;
629 memcpy(UserInfo20
->usri20_name
,
630 UserInfo
->UserName
.Buffer
,
631 UserInfo
->UserName
.Length
);
632 UserInfo20
->usri20_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
634 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
636 if (UserInfo
->FullName
.Length
> 0)
638 UserInfo20
->usri20_full_name
= Ptr
;
640 memcpy(UserInfo20
->usri20_full_name
,
641 UserInfo
->FullName
.Buffer
,
642 UserInfo
->FullName
.Length
);
643 UserInfo20
->usri20_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
645 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
648 if (UserInfo
->AdminComment
.Length
> 0)
650 UserInfo20
->usri20_comment
= Ptr
;
652 memcpy(UserInfo20
->usri20_comment
,
653 UserInfo
->AdminComment
.Buffer
,
654 UserInfo
->AdminComment
.Length
);
655 UserInfo20
->usri20_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
657 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
660 UserInfo20
->usri20_flags
= GetAccountFlags(UserInfo
->UserAccountControl
);
662 UserInfo20
->usri20_user_id
= RelativeId
;
666 UserInfo23
= (PUSER_INFO_23
)LocalBuffer
;
668 Ptr
= (LPWSTR
)((ULONG_PTR
)UserInfo23
+ sizeof(USER_INFO_23
));
670 UserInfo23
->usri23_name
= Ptr
;
672 memcpy(UserInfo23
->usri23_name
,
673 UserInfo
->UserName
.Buffer
,
674 UserInfo
->UserName
.Length
);
675 UserInfo23
->usri23_name
[UserInfo
->UserName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
677 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->UserName
.Length
+ sizeof(WCHAR
));
679 if (UserInfo
->FullName
.Length
> 0)
681 UserInfo23
->usri23_full_name
= Ptr
;
683 memcpy(UserInfo23
->usri23_full_name
,
684 UserInfo
->FullName
.Buffer
,
685 UserInfo
->FullName
.Length
);
686 UserInfo23
->usri23_full_name
[UserInfo
->FullName
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
688 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->FullName
.Length
+ sizeof(WCHAR
));
691 if (UserInfo
->AdminComment
.Length
> 0)
693 UserInfo23
->usri23_comment
= Ptr
;
695 memcpy(UserInfo23
->usri23_comment
,
696 UserInfo
->AdminComment
.Buffer
,
697 UserInfo
->AdminComment
.Length
);
698 UserInfo23
->usri23_comment
[UserInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
700 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ UserInfo
->AdminComment
.Length
+ sizeof(WCHAR
));
703 UserInfo23
->usri23_flags
= GetAccountFlags(UserInfo
->UserAccountControl
);
705 /* FIXME: usri23_user_sid */
710 if (ApiStatus
== NERR_Success
)
712 *Buffer
= LocalBuffer
;
716 if (LocalBuffer
!= NULL
)
717 NetApiBufferFree(LocalBuffer
);
726 FreeUserInfo(PUSER_ACCOUNT_INFORMATION UserInfo
)
728 if (UserInfo
->UserName
.Buffer
!= NULL
)
729 SamFreeMemory(UserInfo
->UserName
.Buffer
);
731 if (UserInfo
->FullName
.Buffer
!= NULL
)
732 SamFreeMemory(UserInfo
->FullName
.Buffer
);
734 if (UserInfo
->HomeDirectory
.Buffer
!= NULL
)
735 SamFreeMemory(UserInfo
->HomeDirectory
.Buffer
);
737 if (UserInfo
->HomeDirectoryDrive
.Buffer
!= NULL
)
738 SamFreeMemory(UserInfo
->HomeDirectoryDrive
.Buffer
);
740 if (UserInfo
->ScriptPath
.Buffer
!= NULL
)
741 SamFreeMemory(UserInfo
->ScriptPath
.Buffer
);
743 if (UserInfo
->ProfilePath
.Buffer
!= NULL
)
744 SamFreeMemory(UserInfo
->ProfilePath
.Buffer
);
746 if (UserInfo
->AdminComment
.Buffer
!= NULL
)
747 SamFreeMemory(UserInfo
->AdminComment
.Buffer
);
749 if (UserInfo
->WorkStations
.Buffer
!= NULL
)
750 SamFreeMemory(UserInfo
->WorkStations
.Buffer
);
752 if (UserInfo
->LogonHours
.LogonHours
!= NULL
)
753 SamFreeMemory(UserInfo
->LogonHours
.LogonHours
);
755 SamFreeMemory(UserInfo
);
761 SetUserInfo(SAM_HANDLE UserHandle
,
765 USER_ALL_INFORMATION UserAllInfo
;
766 PUSER_INFO_0 UserInfo0
;
767 PUSER_INFO_1 UserInfo1
;
768 PUSER_INFO_2 UserInfo2
;
769 PUSER_INFO_3 UserInfo3
;
770 PUSER_INFO_1003 UserInfo1003
;
771 PUSER_INFO_1006 UserInfo1006
;
772 PUSER_INFO_1007 UserInfo1007
;
773 PUSER_INFO_1009 UserInfo1009
;
774 PUSER_INFO_1011 UserInfo1011
;
775 PUSER_INFO_1012 UserInfo1012
;
776 PUSER_INFO_1013 UserInfo1013
;
777 PUSER_INFO_1014 UserInfo1014
;
778 PUSER_INFO_1052 UserInfo1052
;
779 PUSER_INFO_1053 UserInfo1053
;
780 NET_API_STATUS ApiStatus
= NERR_Success
;
781 NTSTATUS Status
= STATUS_SUCCESS
;
783 ZeroMemory(&UserAllInfo
, sizeof(USER_ALL_INFORMATION
));
788 UserInfo0
= (PUSER_INFO_0
)UserInfo
;
790 RtlInitUnicodeString(&UserAllInfo
.UserName
,
791 UserInfo0
->usri0_name
);
793 UserAllInfo
.WhichFields
|= USER_ALL_USERNAME
;
797 UserInfo1
= (PUSER_INFO_1
)UserInfo
;
799 // usri1_name ignored
801 if (UserInfo1
->usri1_password
!= NULL
)
803 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
804 UserInfo1
->usri1_password
);
805 UserAllInfo
.NtPasswordPresent
= TRUE
;
806 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
809 // usri1_password_age ignored
811 // UserInfo1->usri1_priv
813 if (UserInfo1
->usri1_home_dir
!= NULL
)
815 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
816 UserInfo1
->usri1_home_dir
);
817 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
820 if (UserInfo1
->usri1_comment
!= NULL
)
822 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
823 UserInfo1
->usri1_comment
);
824 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
827 // UserInfo1->usri1_flags
828 // UserAllInfo.WhichFields |= USER_ALL_USERACCOUNTCONTROL;
830 if (UserInfo1
->usri1_script_path
!= NULL
)
832 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
833 UserInfo1
->usri1_script_path
);
834 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
839 UserInfo2
= (PUSER_INFO_2
)UserInfo
;
841 // usri2_name ignored
843 if (UserInfo2
->usri2_password
!= NULL
)
845 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
846 UserInfo2
->usri2_password
);
847 UserAllInfo
.NtPasswordPresent
= TRUE
;
848 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
851 // usri2_password_age ignored
853 // UserInfo2->usri2_priv;
855 if (UserInfo2
->usri2_home_dir
!= NULL
)
857 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
858 UserInfo2
->usri2_home_dir
);
859 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
862 if (UserInfo2
->usri2_comment
!= NULL
)
864 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
865 UserInfo2
->usri2_comment
);
866 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
869 // UserInfo2->usri2_flags;
871 if (UserInfo2
->usri2_script_path
!= NULL
)
873 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
874 UserInfo2
->usri2_script_path
);
875 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
878 // UserInfo2->usri2_auth_flags;
880 if (UserInfo2
->usri2_full_name
!= NULL
)
882 RtlInitUnicodeString(&UserAllInfo
.FullName
,
883 UserInfo2
->usri2_full_name
);
884 UserAllInfo
.WhichFields
|= USER_ALL_FULLNAME
;
887 if (UserInfo2
->usri2_usr_comment
!= NULL
)
889 RtlInitUnicodeString(&UserAllInfo
.UserComment
,
890 UserInfo2
->usri2_usr_comment
);
891 UserAllInfo
.WhichFields
|= USER_ALL_USERCOMMENT
;
894 if (UserInfo2
->usri2_parms
!= NULL
)
896 RtlInitUnicodeString(&UserAllInfo
.Parameters
,
897 UserInfo2
->usri2_parms
);
898 UserAllInfo
.WhichFields
|= USER_ALL_PARAMETERS
;
901 if (UserInfo2
->usri2_workstations
!= NULL
)
903 RtlInitUnicodeString(&UserAllInfo
.WorkStations
,
904 UserInfo2
->usri2_workstations
);
905 UserAllInfo
.WhichFields
|= USER_ALL_WORKSTATIONS
;
908 // usri2_last_logon ignored
909 // usri2_last_logoff ignored
911 // UserInfo2->usri2_acct_expires;
912 // UserInfo2->usri2_max_storage;
913 // UserInfo2->usri2_units_per_week;
914 // UserInfo2->usri2_logon_hours;
916 // usri2_bad_pw_count ignored
917 // usri2_num_logons ignored
918 // usri2_logon_server ignored
920 // UserInfo2->usri2_country_code;
921 // UserInfo2->usri2_code_page;
925 UserInfo3
= (PUSER_INFO_3
)UserInfo
;
927 // usri3_name ignored
929 if (UserInfo3
->usri3_password
!= NULL
)
931 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
932 UserInfo3
->usri3_password
);
933 UserAllInfo
.NtPasswordPresent
= TRUE
;
934 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
937 // usri3_password_age ignored
939 // UserInfo3->usri3_priv;
941 if (UserInfo3
->usri3_home_dir
!= NULL
)
943 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
944 UserInfo3
->usri3_home_dir
);
945 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
948 if (UserInfo3
->usri3_comment
!= NULL
)
950 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
951 UserInfo3
->usri3_comment
);
952 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
955 // UserInfo3->usri3_flags;
956 // UserAllInfo.WhichFields |= USER_ALL_USERACCOUNTCONTROL;
958 if (UserInfo3
->usri3_script_path
!= NULL
)
960 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
961 UserInfo3
->usri3_script_path
);
962 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
965 // UserInfo3->usri3_auth_flags;
967 if (UserInfo3
->usri3_full_name
!= NULL
)
969 RtlInitUnicodeString(&UserAllInfo
.FullName
,
970 UserInfo3
->usri3_full_name
);
971 UserAllInfo
.WhichFields
|= USER_ALL_FULLNAME
;
974 if (UserInfo3
->usri3_usr_comment
!= NULL
)
976 RtlInitUnicodeString(&UserAllInfo
.UserComment
,
977 UserInfo3
->usri3_usr_comment
);
978 UserAllInfo
.WhichFields
|= USER_ALL_USERCOMMENT
;
981 if (UserInfo3
->usri3_parms
!= NULL
)
983 RtlInitUnicodeString(&UserAllInfo
.Parameters
,
984 UserInfo3
->usri3_parms
);
985 UserAllInfo
.WhichFields
|= USER_ALL_PARAMETERS
;
988 if (UserInfo3
->usri3_workstations
!= NULL
)
990 RtlInitUnicodeString(&UserAllInfo
.WorkStations
,
991 UserInfo3
->usri3_workstations
);
992 UserAllInfo
.WhichFields
|= USER_ALL_WORKSTATIONS
;
995 // usri3_last_logon ignored
996 // usri3_last_logoff ignored
998 // UserInfo3->usri3_acct_expires;
999 // UserInfo3->usri3_max_storage;
1000 // UserInfo3->usri3_units_per_week;
1001 // UserInfo3->usri3_logon_hours;
1003 // usri3_bad_pw_count ignored
1004 // usri3_num_logons ignored
1005 // usri3_logon_server ignored
1007 // UserInfo3->usri3_country_code;
1008 // UserInfo3->usri3_code_page;
1010 // usri3_user_id ignored
1012 // UserInfo3->usri3_primary_group_id;
1014 if (UserInfo3
->usri3_profile
!= NULL
)
1016 RtlInitUnicodeString(&UserAllInfo
.ProfilePath
,
1017 UserInfo3
->usri3_profile
);
1018 UserAllInfo
.WhichFields
|= USER_ALL_PROFILEPATH
;
1021 if (UserInfo3
->usri3_home_dir_drive
!= NULL
)
1023 RtlInitUnicodeString(&UserAllInfo
.HomeDirectoryDrive
,
1024 UserInfo3
->usri3_home_dir_drive
);
1025 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORYDRIVE
;
1028 // UserInfo3->usri3_password_expired;
1036 UserInfo1003
= (PUSER_INFO_1003
)UserInfo
;
1038 if (UserInfo1003
->usri1003_password
!= NULL
)
1040 RtlInitUnicodeString(&UserAllInfo
.NtPassword
,
1041 UserInfo1003
->usri1003_password
);
1042 UserAllInfo
.NtPasswordPresent
= TRUE
;
1043 UserAllInfo
.WhichFields
|= USER_ALL_NTPASSWORDPRESENT
;
1050 UserInfo1006
= (PUSER_INFO_1006
)UserInfo
;
1052 if (UserInfo1006
->usri1006_home_dir
!= NULL
)
1054 RtlInitUnicodeString(&UserAllInfo
.HomeDirectory
,
1055 UserInfo1006
->usri1006_home_dir
);
1056 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORY
;
1061 UserInfo1007
= (PUSER_INFO_1007
)UserInfo
;
1063 if (UserInfo1007
->usri1007_comment
!= NULL
)
1065 RtlInitUnicodeString(&UserAllInfo
.AdminComment
,
1066 UserInfo1007
->usri1007_comment
);
1067 UserAllInfo
.WhichFields
|= USER_ALL_ADMINCOMMENT
;
1074 UserInfo1009
= (PUSER_INFO_1009
)UserInfo
;
1076 if (UserInfo1009
->usri1009_script_path
!= NULL
)
1078 RtlInitUnicodeString(&UserAllInfo
.ScriptPath
,
1079 UserInfo1009
->usri1009_script_path
);
1080 UserAllInfo
.WhichFields
|= USER_ALL_SCRIPTPATH
;
1087 UserInfo1011
= (PUSER_INFO_1011
)UserInfo
;
1089 if (UserInfo1011
->usri1011_full_name
!= NULL
)
1091 RtlInitUnicodeString(&UserAllInfo
.FullName
,
1092 UserInfo1011
->usri1011_full_name
);
1093 UserAllInfo
.WhichFields
|= USER_ALL_FULLNAME
;
1098 UserInfo1012
= (PUSER_INFO_1012
)UserInfo
;
1100 if (UserInfo1012
->usri1012_usr_comment
!= NULL
)
1102 RtlInitUnicodeString(&UserAllInfo
.UserComment
,
1103 UserInfo1012
->usri1012_usr_comment
);
1104 UserAllInfo
.WhichFields
|= USER_ALL_USERCOMMENT
;
1109 UserInfo1013
= (PUSER_INFO_1013
)UserInfo
;
1111 if (UserInfo1013
->usri1013_parms
!= NULL
)
1113 RtlInitUnicodeString(&UserAllInfo
.Parameters
,
1114 UserInfo1013
->usri1013_parms
);
1115 UserAllInfo
.WhichFields
|= USER_ALL_PARAMETERS
;
1120 UserInfo1014
= (PUSER_INFO_1014
)UserInfo
;
1122 if (UserInfo1014
->usri1014_workstations
!= NULL
)
1124 RtlInitUnicodeString(&UserAllInfo
.WorkStations
,
1125 UserInfo1014
->usri1014_workstations
);
1126 UserAllInfo
.WhichFields
|= USER_ALL_WORKSTATIONS
;
1136 UserInfo1052
= (PUSER_INFO_1052
)UserInfo
;
1138 if (UserInfo1052
->usri1052_profile
!= NULL
)
1140 RtlInitUnicodeString(&UserAllInfo
.ProfilePath
,
1141 UserInfo1052
->usri1052_profile
);
1142 UserAllInfo
.WhichFields
|= USER_ALL_PROFILEPATH
;
1147 UserInfo1053
= (PUSER_INFO_1053
)UserInfo
;
1149 if (UserInfo1053
->usri1053_home_dir_drive
!= NULL
)
1151 RtlInitUnicodeString(&UserAllInfo
.HomeDirectoryDrive
,
1152 UserInfo1053
->usri1053_home_dir_drive
);
1153 UserAllInfo
.WhichFields
|= USER_ALL_HOMEDIRECTORYDRIVE
;
1158 ERR("Unsupported level %lu!\n", Level
);
1159 return ERROR_INVALID_PARAMETER
;
1162 Status
= SamSetInformationUser(UserHandle
,
1165 if (!NT_SUCCESS(Status
))
1167 ERR("SamSetInformationUser failed (Status %08lx)\n", Status
);
1168 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1179 OpenUserByName(SAM_HANDLE DomainHandle
,
1180 PUNICODE_STRING UserName
,
1181 ULONG DesiredAccess
,
1182 PSAM_HANDLE UserHandle
)
1184 PULONG RelativeIds
= NULL
;
1185 PSID_NAME_USE Use
= NULL
;
1186 NET_API_STATUS ApiStatus
= NERR_Success
;
1187 NTSTATUS Status
= STATUS_SUCCESS
;
1189 /* Get the RID for the given user name */
1190 Status
= SamLookupNamesInDomain(DomainHandle
,
1195 if (!NT_SUCCESS(Status
))
1197 ERR("SamLookupNamesInDomain failed (Status %08lx)\n", Status
);
1198 return NetpNtStatusToApiStatus(Status
);
1201 /* Fail, if it is not an alias account */
1202 if (Use
[0] != SidTypeUser
)
1204 ERR("Object is not a user!\n");
1205 ApiStatus
= NERR_GroupNotFound
;
1209 /* Open the alias account */
1210 Status
= SamOpenUser(DomainHandle
,
1214 if (!NT_SUCCESS(Status
))
1216 ERR("SamOpenUser failed (Status %08lx)\n", Status
);
1217 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1222 if (RelativeIds
!= NULL
)
1223 SamFreeMemory(RelativeIds
);
1232 /************************************************************
1233 * NetUserAdd (NETAPI32.@)
1237 NetUserAdd(LPCWSTR servername
,
1242 UNICODE_STRING ServerName
;
1243 UNICODE_STRING UserName
;
1244 SAM_HANDLE ServerHandle
= NULL
;
1245 SAM_HANDLE DomainHandle
= NULL
;
1246 SAM_HANDLE UserHandle
= NULL
;
1247 ULONG GrantedAccess
;
1249 NET_API_STATUS ApiStatus
= NERR_Success
;
1250 NTSTATUS Status
= STATUS_SUCCESS
;
1252 TRACE("(%s, %d, %p, %p)\n", debugstr_w(servername
), level
, bufptr
, parm_err
);
1254 /* Check the info level */
1264 return ERROR_INVALID_LEVEL
;
1267 if (servername
!= NULL
)
1268 RtlInitUnicodeString(&ServerName
, servername
);
1270 /* Connect to the SAM Server */
1271 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1273 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1275 if (!NT_SUCCESS(Status
))
1277 ERR("SamConnect failed (Status %08lx)\n", Status
);
1278 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1282 /* Open the Account Domain */
1283 Status
= OpenAccountDomain(ServerHandle
,
1284 (servername
!= NULL
) ? &ServerName
: NULL
,
1285 DOMAIN_CREATE_USER
| DOMAIN_LOOKUP
,
1287 if (!NT_SUCCESS(Status
))
1289 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1290 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1294 /* Initialize the user name string */
1295 RtlInitUnicodeString(&UserName
,
1296 ((PUSER_INFO_1
)bufptr
)->usri1_name
);
1298 /* Create the user account */
1299 Status
= SamCreateUser2InDomain(DomainHandle
,
1301 USER_NORMAL_ACCOUNT
,
1302 USER_ALL_ACCESS
| DELETE
| WRITE_DAC
,
1306 if (!NT_SUCCESS(Status
))
1308 ERR("SamCreateUser2InDomain failed (Status %08lx)\n", Status
);
1309 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1313 /* Set user information */
1314 ApiStatus
= SetUserInfo(UserHandle
,
1317 if (ApiStatus
!= NERR_Success
)
1319 ERR("SetUserInfo failed (Status %lu)\n", ApiStatus
);
1324 if (UserHandle
!= NULL
)
1325 SamCloseHandle(UserHandle
);
1327 if (DomainHandle
!= NULL
)
1328 SamCloseHandle(DomainHandle
);
1330 if (ServerHandle
!= NULL
)
1331 SamCloseHandle(ServerHandle
);
1337 /******************************************************************************
1338 * NetUserChangePassword (NETAPI32.@)
1340 * domainname [I] Optional. Domain on which the user resides or the logon
1341 * domain of the current user if NULL.
1342 * username [I] Optional. Username to change the password for or the name
1343 * of the current user if NULL.
1344 * oldpassword [I] The user's current password.
1345 * newpassword [I] The password that the user will be changed to using.
1348 * Success: NERR_Success.
1349 * Failure: NERR_* failure code or win error code.
1354 NetUserChangePassword(LPCWSTR domainname
,
1356 LPCWSTR oldpassword
,
1357 LPCWSTR newpassword
)
1359 TRACE("(%s, %s, ..., ...)\n", debugstr_w(domainname
), debugstr_w(username
));
1360 return NERR_Success
;
1364 /************************************************************
1365 * NetUserDel (NETAPI32.@)
1369 NetUserDel(LPCWSTR servername
,
1372 UNICODE_STRING ServerName
;
1373 UNICODE_STRING UserName
;
1374 SAM_HANDLE ServerHandle
= NULL
;
1375 SAM_HANDLE DomainHandle
= NULL
;
1376 SAM_HANDLE UserHandle
= NULL
;
1377 NET_API_STATUS ApiStatus
= NERR_Success
;
1378 NTSTATUS Status
= STATUS_SUCCESS
;
1380 TRACE("(%s, %s)\n", debugstr_w(servername
), debugstr_w(username
));
1382 if (servername
!= NULL
)
1383 RtlInitUnicodeString(&ServerName
, servername
);
1385 RtlInitUnicodeString(&UserName
, username
);
1387 /* Connect to the SAM Server */
1388 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1390 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1392 if (!NT_SUCCESS(Status
))
1394 ERR("SamConnect failed (Status %08lx)\n", Status
);
1395 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1399 /* Open the Builtin Domain */
1400 Status
= OpenBuiltinDomain(ServerHandle
,
1403 if (!NT_SUCCESS(Status
))
1405 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
1406 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1410 /* Open the user account in the builtin domain */
1411 ApiStatus
= OpenUserByName(DomainHandle
,
1415 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_NONE_MAPPED
)
1417 TRACE("OpenUserByName failed (ApiStatus %lu)\n", ApiStatus
);
1421 if (UserHandle
== NULL
)
1423 if (DomainHandle
!= NULL
)
1425 SamCloseHandle(DomainHandle
);
1426 DomainHandle
= NULL
;
1429 /* Open the Acount Domain */
1430 Status
= OpenAccountDomain(ServerHandle
,
1431 (servername
!= NULL
) ? &ServerName
: NULL
,
1434 if (!NT_SUCCESS(Status
))
1436 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1437 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1441 /* Open the user account in the account domain */
1442 ApiStatus
= OpenUserByName(DomainHandle
,
1446 if (ApiStatus
!= NERR_Success
)
1448 ERR("OpenUserByName failed (ApiStatus %lu)\n", ApiStatus
);
1449 if (ApiStatus
== ERROR_NONE_MAPPED
)
1450 ApiStatus
= NERR_GroupNotFound
;
1455 /* Delete the user */
1456 Status
= SamDeleteUser(UserHandle
);
1457 if (!NT_SUCCESS(Status
))
1459 ERR("SamDeleteUser failed (Status %08lx)\n", Status
);
1460 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1465 if (UserHandle
!= NULL
)
1466 SamCloseHandle(UserHandle
);
1468 if (DomainHandle
!= NULL
)
1469 SamCloseHandle(DomainHandle
);
1471 if (ServerHandle
!= NULL
)
1472 SamCloseHandle(ServerHandle
);
1478 /************************************************************
1479 * NetUserEnum (NETAPI32.@)
1483 NetUserEnum(LPCWSTR servername
,
1488 LPDWORD entriesread
,
1489 LPDWORD totalentries
,
1490 LPDWORD resume_handle
)
1492 UNICODE_STRING ServerName
;
1493 PSAM_RID_ENUMERATION CurrentUser
;
1494 PENUM_CONTEXT EnumContext
= NULL
;
1495 LPVOID Buffer
= NULL
;
1497 SAM_HANDLE UserHandle
= NULL
;
1498 PUSER_ACCOUNT_INFORMATION UserInfo
= NULL
;
1500 NET_API_STATUS ApiStatus
= NERR_Success
;
1501 NTSTATUS Status
= STATUS_SUCCESS
;
1503 TRACE("(%s %d 0x%d %p %d %p %p %p)\n", debugstr_w(servername
), level
,
1504 filter
, bufptr
, prefmaxlen
, entriesread
, totalentries
, resume_handle
);
1510 if (servername
!= NULL
)
1511 RtlInitUnicodeString(&ServerName
, servername
);
1513 if (resume_handle
!= NULL
&& *resume_handle
!= 0)
1515 EnumContext
= (PENUM_CONTEXT
)*resume_handle
;
1519 ApiStatus
= NetApiBufferAllocate(sizeof(ENUM_CONTEXT
), (PVOID
*)&EnumContext
);
1520 if (ApiStatus
!= NERR_Success
)
1523 EnumContext
->EnumerationContext
= 0;
1524 EnumContext
->Buffer
= NULL
;
1525 EnumContext
->Count
= 0;
1526 EnumContext
->Index
= 0;
1527 EnumContext
->BuiltinDone
= FALSE
;
1529 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1530 &EnumContext
->ServerHandle
,
1531 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1533 if (!NT_SUCCESS(Status
))
1535 ERR("SamConnect failed (Status %08lx)\n", Status
);
1536 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1540 Status
= OpenAccountDomain(EnumContext
->ServerHandle
,
1541 (servername
!= NULL
) ? &ServerName
: NULL
,
1542 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
1543 &EnumContext
->AccountDomainHandle
);
1544 if (!NT_SUCCESS(Status
))
1546 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1547 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1551 Status
= OpenBuiltinDomain(EnumContext
->ServerHandle
,
1552 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
1553 &EnumContext
->BuiltinDomainHandle
);
1554 if (!NT_SUCCESS(Status
))
1556 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
1557 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1564 TRACE("EnumContext->Index: %lu\n", EnumContext
->Index
);
1565 TRACE("EnumContext->Count: %lu\n", EnumContext
->Count
);
1567 if (EnumContext
->Index
>= EnumContext
->Count
)
1569 // if (EnumContext->BuiltinDone == TRUE)
1571 // ApiStatus = NERR_Success;
1575 TRACE("Calling SamEnumerateUsersInDomain\n");
1576 Status
= SamEnumerateUsersInDomain(EnumContext
->AccountDomainHandle
, //BuiltinDomainHandle,
1577 &EnumContext
->EnumerationContext
,
1579 (PVOID
*)&EnumContext
->Buffer
,
1581 &EnumContext
->Count
);
1583 TRACE("SamEnumerateUsersInDomain returned (Status %08lx)\n", Status
);
1584 if (!NT_SUCCESS(Status
))
1586 ERR("SamEnumerateUsersInDomain failed (Status %08lx)\n", Status
);
1587 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1591 if (Status
== STATUS_MORE_ENTRIES
)
1593 ApiStatus
= NERR_BufTooSmall
;
1598 EnumContext
->BuiltinDone
= TRUE
;
1602 TRACE("EnumContext: %lu\n", EnumContext
);
1603 TRACE("EnumContext->Count: %lu\n", EnumContext
->Count
);
1604 TRACE("EnumContext->Buffer: %p\n", EnumContext
->Buffer
);
1606 /* Get a pointer to the current user */
1607 CurrentUser
= &EnumContext
->Buffer
[EnumContext
->Index
];
1609 TRACE("RID: %lu\n", CurrentUser
->RelativeId
);
1611 Status
= SamOpenUser(EnumContext
->AccountDomainHandle
, //BuiltinDomainHandle,
1612 USER_READ_GENERAL
| USER_READ_PREFERENCES
| USER_READ_LOGON
| USER_READ_ACCOUNT
,
1613 CurrentUser
->RelativeId
,
1615 if (!NT_SUCCESS(Status
))
1617 ERR("SamOpenUser failed (Status %08lx)\n", Status
);
1618 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1622 Status
= SamQueryInformationUser(UserHandle
,
1623 UserAccountInformation
,
1624 (PVOID
*)&UserInfo
);
1625 if (!NT_SUCCESS(Status
))
1627 ERR("SamQueryInformationUser failed (Status %08lx)\n", Status
);
1628 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1632 SamCloseHandle(UserHandle
);
1635 ApiStatus
= BuildUserInfoBuffer(UserInfo
,
1637 CurrentUser
->RelativeId
,
1639 if (ApiStatus
!= NERR_Success
)
1641 ERR("BuildUserInfoBuffer failed (ApiStatus %lu)\n", ApiStatus
);
1645 if (UserInfo
!= NULL
)
1647 FreeUserInfo(UserInfo
);
1651 EnumContext
->Index
++;
1657 if (ApiStatus
== NERR_Success
&& EnumContext
->Index
< EnumContext
->Count
)
1658 ApiStatus
= ERROR_MORE_DATA
;
1660 if (EnumContext
!= NULL
)
1661 *totalentries
= EnumContext
->Count
;
1663 if (resume_handle
== NULL
|| ApiStatus
!= ERROR_MORE_DATA
)
1665 if (EnumContext
!= NULL
)
1667 if (EnumContext
->BuiltinDomainHandle
!= NULL
)
1668 SamCloseHandle(EnumContext
->BuiltinDomainHandle
);
1670 if (EnumContext
->AccountDomainHandle
!= NULL
)
1671 SamCloseHandle(EnumContext
->AccountDomainHandle
);
1673 if (EnumContext
->ServerHandle
!= NULL
)
1674 SamCloseHandle(EnumContext
->ServerHandle
);
1676 if (EnumContext
->Buffer
!= NULL
)
1678 for (i
= 0; i
< EnumContext
->Count
; i
++)
1680 SamFreeMemory(EnumContext
->Buffer
[i
].Name
.Buffer
);
1683 SamFreeMemory(EnumContext
->Buffer
);
1686 NetApiBufferFree(EnumContext
);
1691 if (UserHandle
!= NULL
)
1692 SamCloseHandle(UserHandle
);
1694 if (UserInfo
!= NULL
)
1695 FreeUserInfo(UserInfo
);
1697 if (resume_handle
!= NULL
)
1698 *resume_handle
= (DWORD_PTR
)EnumContext
;
1700 *bufptr
= (LPBYTE
)Buffer
;
1702 TRACE("return %lu\n", ApiStatus
);
1708 /************************************************************
1709 * NetUserGetGroups (NETAPI32.@)
1713 NetUserGetGroups(LPCWSTR servername
,
1718 LPDWORD entriesread
,
1719 LPDWORD totalentries
)
1721 FIXME("%s %s %d %p %d %p %p stub\n", debugstr_w(servername
),
1722 debugstr_w(username
), level
, bufptr
, prefixmaxlen
, entriesread
,
1729 return ERROR_INVALID_LEVEL
;
1733 /************************************************************
1734 * NetUserGetInfo (NETAPI32.@)
1738 NetUserGetInfo(LPCWSTR servername
,
1743 UNICODE_STRING ServerName
;
1744 UNICODE_STRING UserName
;
1745 SAM_HANDLE ServerHandle
= NULL
;
1746 SAM_HANDLE AccountDomainHandle
= NULL
;
1747 SAM_HANDLE UserHandle
= NULL
;
1748 PULONG RelativeIds
= NULL
;
1749 PSID_NAME_USE Use
= NULL
;
1750 PUSER_ACCOUNT_INFORMATION UserInfo
= NULL
;
1751 LPVOID Buffer
= NULL
;
1752 NET_API_STATUS ApiStatus
= NERR_Success
;
1753 NTSTATUS Status
= STATUS_SUCCESS
;
1755 TRACE("(%s, %s, %d, %p)\n", debugstr_w(servername
),
1756 debugstr_w(username
), level
, bufptr
);
1758 if (servername
!= NULL
)
1759 RtlInitUnicodeString(&ServerName
, servername
);
1761 RtlInitUnicodeString(&UserName
, username
);
1763 /* Connect to the SAM Server */
1764 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1766 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1768 if (!NT_SUCCESS(Status
))
1770 ERR("SamConnect failed (Status %08lx)\n", Status
);
1771 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1775 /* Open the Account Domain */
1776 Status
= OpenAccountDomain(ServerHandle
,
1777 (servername
!= NULL
) ? &ServerName
: NULL
,
1778 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
1779 &AccountDomainHandle
);
1780 if (!NT_SUCCESS(Status
))
1782 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1783 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1787 /* Get the RID for the given user name */
1788 Status
= SamLookupNamesInDomain(AccountDomainHandle
,
1793 if (!NT_SUCCESS(Status
))
1795 ERR("SamOpenDomain failed (Status %08lx)\n", Status
);
1796 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1800 /* Check if the account is a user account */
1801 if (Use
[0] != SidTypeUser
)
1803 ERR("No user found!\n");
1804 ApiStatus
= NERR_UserNotFound
;
1808 TRACE("RID: %lu\n", RelativeIds
[0]);
1810 /* Open the user object */
1811 Status
= SamOpenUser(AccountDomainHandle
,
1812 USER_READ_GENERAL
| USER_READ_PREFERENCES
| USER_READ_LOGON
| USER_READ_ACCOUNT
,
1815 if (!NT_SUCCESS(Status
))
1817 ERR("SamOpenUser failed (Status %08lx)\n", Status
);
1818 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1822 Status
= SamQueryInformationUser(UserHandle
,
1823 UserAccountInformation
,
1824 (PVOID
*)&UserInfo
);
1825 if (!NT_SUCCESS(Status
))
1827 ERR("SamQueryInformationUser failed (Status %08lx)\n", Status
);
1828 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1832 ApiStatus
= BuildUserInfoBuffer(UserInfo
,
1836 if (ApiStatus
!= NERR_Success
)
1838 ERR("BuildUserInfoBuffer failed (ApiStatus %08lu)\n", ApiStatus
);
1843 if (UserInfo
!= NULL
)
1844 FreeUserInfo(UserInfo
);
1846 if (UserHandle
!= NULL
)
1847 SamCloseHandle(UserHandle
);
1849 if (RelativeIds
!= NULL
)
1850 SamFreeMemory(RelativeIds
);
1855 if (AccountDomainHandle
!= NULL
)
1856 SamCloseHandle(AccountDomainHandle
);
1858 if (ServerHandle
!= NULL
)
1859 SamCloseHandle(ServerHandle
);
1861 *bufptr
= (LPBYTE
)Buffer
;
1867 /************************************************************
1868 * NetUserGetLocalGroups (NETAPI32.@)
1872 NetUserGetLocalGroups(LPCWSTR servername
,
1878 LPDWORD entriesread
,
1879 LPDWORD totalentries
)
1881 UNICODE_STRING ServerName
;
1882 UNICODE_STRING UserName
;
1883 SAM_HANDLE ServerHandle
= NULL
;
1884 SAM_HANDLE BuiltinDomainHandle
= NULL
;
1885 SAM_HANDLE AccountDomainHandle
= NULL
;
1886 PSID AccountDomainSid
= NULL
;
1887 PSID UserSid
= NULL
;
1888 PULONG RelativeIds
= NULL
;
1889 PSID_NAME_USE Use
= NULL
;
1890 ULONG BuiltinMemberCount
= 0;
1891 ULONG AccountMemberCount
= 0;
1892 PULONG BuiltinAliases
= NULL
;
1893 PULONG AccountAliases
= NULL
;
1894 PUNICODE_STRING BuiltinNames
= NULL
;
1895 PUNICODE_STRING AccountNames
= NULL
;
1896 PLOCALGROUP_USERS_INFO_0 Buffer
= NULL
;
1902 NET_API_STATUS ApiStatus
= NERR_Success
;
1903 NTSTATUS Status
= STATUS_SUCCESS
;
1905 TRACE("(%s, %s, %d, %08x, %p %d, %p, %p) stub!\n",
1906 debugstr_w(servername
), debugstr_w(username
), level
, flags
, bufptr
,
1907 prefmaxlen
, entriesread
, totalentries
);
1910 return ERROR_INVALID_LEVEL
;
1912 if (flags
& ~LG_INCLUDE_INDIRECT
)
1913 return ERROR_INVALID_PARAMETER
;
1915 if (flags
& LG_INCLUDE_INDIRECT
)
1917 WARN("The flag LG_INCLUDE_INDIRECT is not supported yet!\n");
1920 if (servername
!= NULL
)
1921 RtlInitUnicodeString(&ServerName
, servername
);
1923 RtlInitUnicodeString(&UserName
, username
);
1925 /* Connect to the SAM Server */
1926 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1928 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1930 if (!NT_SUCCESS(Status
))
1932 ERR("SamConnect failed (Status %08lx)\n", Status
);
1933 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1937 /* Open the Builtin Domain */
1938 Status
= OpenBuiltinDomain(ServerHandle
,
1939 DOMAIN_LOOKUP
| DOMAIN_GET_ALIAS_MEMBERSHIP
,
1940 &BuiltinDomainHandle
);
1941 if (!NT_SUCCESS(Status
))
1943 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
1944 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1948 /* Get the Account Domain SID */
1949 Status
= GetAccountDomainSid((servername
!= NULL
) ? &ServerName
: NULL
,
1951 if (!NT_SUCCESS(Status
))
1953 ERR("GetAccountDomainSid failed (Status %08lx)\n", Status
);
1954 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1958 /* Open the Account Domain */
1959 Status
= SamOpenDomain(ServerHandle
,
1960 DOMAIN_LOOKUP
| DOMAIN_GET_ALIAS_MEMBERSHIP
,
1962 &AccountDomainHandle
);
1963 if (!NT_SUCCESS(Status
))
1965 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1966 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1970 /* Get the RID for the given user name */
1971 Status
= SamLookupNamesInDomain(AccountDomainHandle
,
1976 if (!NT_SUCCESS(Status
))
1978 ERR("SamLookupNamesInDomain failed (Status %08lx)\n", Status
);
1979 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1983 /* Fail, if it is not a user account */
1984 if (Use
[0] != SidTypeUser
)
1986 ERR("Account is not a User!\n");
1987 ApiStatus
= NERR_UserNotFound
;
1991 /* Build the User SID from the Account Domain SID and the users RID */
1992 ApiStatus
= BuildSidFromSidAndRid(AccountDomainSid
,
1995 if (ApiStatus
!= NERR_Success
)
1997 ERR("BuildSidFromSidAndRid failed!\n");
2001 /* Get alias memberships in the Builtin Domain */
2002 Status
= SamGetAliasMembership(BuiltinDomainHandle
,
2005 &BuiltinMemberCount
,
2007 if (!NT_SUCCESS(Status
))
2009 ERR("SamGetAliasMembership failed (Status %08lx)\n", Status
);
2010 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2014 if (BuiltinMemberCount
> 0)
2016 /* Get the Names of the builtin alias members */
2017 Status
= SamLookupIdsInDomain(BuiltinDomainHandle
,
2022 if (!NT_SUCCESS(Status
))
2024 ERR("SamLookupIdsInDomain failed (Status %08lx)\n", Status
);
2025 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2030 /* Get alias memberships in the Account Domain */
2031 Status
= SamGetAliasMembership(AccountDomainHandle
,
2034 &AccountMemberCount
,
2036 if (!NT_SUCCESS(Status
))
2038 ERR("SamGetAliasMembership failed (Status %08lx)\n", Status
);
2039 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2043 if (AccountMemberCount
> 0)
2045 /* Get the Names of the builtin alias members */
2046 Status
= SamLookupIdsInDomain(AccountDomainHandle
,
2051 if (!NT_SUCCESS(Status
))
2053 ERR("SamLookupIdsInDomain failed (Status %08lx)\n", Status
);
2054 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2059 /* Calculate the required buffer size */
2062 for (i
= 0; i
< BuiltinMemberCount
; i
++)
2064 if (BuiltinNames
[i
].Length
> 0)
2066 Size
+= (sizeof(LOCALGROUP_USERS_INFO_0
) + BuiltinNames
[i
].Length
+ sizeof(UNICODE_NULL
));
2071 for (i
= 0; i
< AccountMemberCount
; i
++)
2073 if (BuiltinNames
[i
].Length
> 0)
2075 Size
+= (sizeof(LOCALGROUP_USERS_INFO_0
) + AccountNames
[i
].Length
+ sizeof(UNICODE_NULL
));
2082 ApiStatus
= NERR_Success
;
2086 /* Allocate buffer */
2087 ApiStatus
= NetApiBufferAllocate(Size
, (LPVOID
*)&Buffer
);
2088 if (ApiStatus
!= NERR_Success
)
2091 ZeroMemory(Buffer
, Size
);
2093 StrPtr
= (LPWSTR
)((INT_PTR
)Buffer
+ Count
* sizeof(LOCALGROUP_USERS_INFO_0
));
2095 /* Copy data to the allocated buffer */
2097 for (i
= 0; i
< BuiltinMemberCount
; i
++)
2099 if (BuiltinNames
[i
].Length
> 0)
2102 BuiltinNames
[i
].Buffer
,
2103 BuiltinNames
[i
].Length
);
2104 Buffer
[Index
].lgrui0_name
= StrPtr
;
2106 StrPtr
= (LPWSTR
)((INT_PTR
)StrPtr
+ BuiltinNames
[i
].Length
+ sizeof(UNICODE_NULL
));
2111 for (i
= 0; i
< AccountMemberCount
; i
++)
2113 if (AccountNames
[i
].Length
> 0)
2116 AccountNames
[i
].Buffer
,
2117 AccountNames
[i
].Length
);
2118 Buffer
[Index
].lgrui0_name
= StrPtr
;
2120 StrPtr
= (LPWSTR
)((INT_PTR
)StrPtr
+ AccountNames
[i
].Length
+ sizeof(UNICODE_NULL
));
2126 if (AccountNames
!= NULL
)
2127 SamFreeMemory(AccountNames
);
2129 if (BuiltinNames
!= NULL
)
2130 SamFreeMemory(BuiltinNames
);
2132 if (AccountAliases
!= NULL
)
2133 SamFreeMemory(AccountAliases
);
2135 if (BuiltinAliases
!= NULL
)
2136 SamFreeMemory(BuiltinAliases
);
2138 if (RelativeIds
!= NULL
)
2139 SamFreeMemory(RelativeIds
);
2144 if (UserSid
!= NULL
)
2145 NetApiBufferFree(UserSid
);
2147 if (AccountDomainSid
!= NULL
)
2148 RtlFreeHeap(RtlGetProcessHeap(), 0, AccountDomainSid
);
2150 if (AccountDomainHandle
!= NULL
)
2151 SamCloseHandle(AccountDomainHandle
);
2153 if (BuiltinDomainHandle
!= NULL
)
2154 SamCloseHandle(BuiltinDomainHandle
);
2156 if (ServerHandle
!= NULL
)
2157 SamCloseHandle(ServerHandle
);
2159 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_MORE_DATA
)
2166 *entriesread
= Count
;
2167 *totalentries
= Count
;
2170 *bufptr
= (LPBYTE
)Buffer
;
2176 /******************************************************************************
2177 * NetUserSetGroups (NETAPI32.@)
2181 NetUserSetGroups(LPCWSTR servername
,
2187 FIXME("(%s %s %lu %p %lu)\n",
2188 debugstr_w(servername
), debugstr_w(username
), level
, buf
, num_entries
);
2189 return ERROR_ACCESS_DENIED
;
2193 /******************************************************************************
2194 * NetUserSetInfo (NETAPI32.@)
2198 NetUserSetInfo(LPCWSTR servername
,
2204 UNICODE_STRING ServerName
;
2205 UNICODE_STRING UserName
;
2206 SAM_HANDLE ServerHandle
= NULL
;
2207 SAM_HANDLE AccountDomainHandle
= NULL
;
2208 SAM_HANDLE UserHandle
= NULL
;
2209 NET_API_STATUS ApiStatus
= NERR_Success
;
2210 NTSTATUS Status
= STATUS_SUCCESS
;
2212 TRACE("(%s %s %lu %p %p)\n",
2213 debugstr_w(servername
), debugstr_w(username
), level
, buf
, parm_err
);
2215 /* Check the info level */
2245 return ERROR_INVALID_LEVEL
;
2248 if (servername
!= NULL
)
2249 RtlInitUnicodeString(&ServerName
, servername
);
2251 RtlInitUnicodeString(&UserName
, username
);
2253 /* Connect to the SAM Server */
2254 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
2256 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
2258 if (!NT_SUCCESS(Status
))
2260 ERR("SamConnect failed (Status %08lx)\n", Status
);
2261 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2265 /* Open the Account Domain */
2266 Status
= OpenAccountDomain(ServerHandle
,
2267 (servername
!= NULL
) ? &ServerName
: NULL
,
2268 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
2269 &AccountDomainHandle
);
2270 if (!NT_SUCCESS(Status
))
2272 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
2273 ApiStatus
= NetpNtStatusToApiStatus(Status
);
2277 /* Open the User Account */
2278 ApiStatus
= OpenUserByName(AccountDomainHandle
,
2282 if (ApiStatus
!= NERR_Success
)
2284 ERR("OpenUserByName failed (ApiStatus %lu)\n", ApiStatus
);
2288 /* Set user information */
2289 ApiStatus
= SetUserInfo(UserHandle
,
2292 if (ApiStatus
!= NERR_Success
)
2294 ERR("SetUserInfo failed (Status %lu)\n", ApiStatus
);
2298 if (UserHandle
!= NULL
)
2299 SamCloseHandle(UserHandle
);
2301 if (AccountDomainHandle
!= NULL
)
2302 SamCloseHandle(AccountDomainHandle
);
2304 if (ServerHandle
!= NULL
)
2305 SamCloseHandle(ServerHandle
);