Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenaccess.c
Go to the documentation of this file.
00001 /* 00002 * Copyright 2002 Andriy Palamarchuk 00003 * 00004 * netapi32 access functions 00005 * 00006 * This library is free software; you can redistribute it and/or 00007 * modify it under the terms of the GNU Lesser General Public 00008 * License as published by the Free Software Foundation; either 00009 * version 2.1 of the License, or (at your option) any later version. 00010 * 00011 * This library is distributed in the hope that it will be useful, 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00014 * Lesser General Public License for more details. 00015 * 00016 * You should have received a copy of the GNU Lesser General Public 00017 * License along with this library; if not, write to the Free Software 00018 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 00019 */ 00020 00021 #include <stdarg.h> 00022 00023 #include "ntstatus.h" 00024 #define WIN32_NO_STATUS 00025 #include "windef.h" 00026 #include "winbase.h" 00027 #include "winerror.h" 00028 #include "lmcons.h" 00029 #include "lmaccess.h" 00030 #include "lmapibuf.h" 00031 #include "lmerr.h" 00032 #include "lmuse.h" 00033 #include "ntsecapi.h" 00034 #include "wine/debug.h" 00035 #include "wine/unicode.h" 00036 #include "wine/list.h" 00037 00038 WINE_DEFAULT_DEBUG_CHANNEL(netapi32); 00039 00040 /* NOTE: So far, this is implemented to support tests that require user logins, 00041 * but not designed to handle real user databases. Those should probably 00042 * be synced with either the host's user database or with Samba. 00043 * 00044 * FIXME: The user database should hold all the information the USER_INFO_4 struct 00045 * needs, but for the first try, I will just implement the USER_INFO_1 fields. 00046 */ 00047 00048 struct sam_user 00049 { 00050 struct list entry; 00051 WCHAR user_name[LM20_UNLEN+1]; 00052 WCHAR user_password[PWLEN + 1]; 00053 DWORD sec_since_passwd_change; 00054 DWORD user_priv; 00055 LPWSTR home_dir; 00056 LPWSTR user_comment; 00057 DWORD user_flags; 00058 LPWSTR user_logon_script_path; 00059 }; 00060 00061 static struct list user_list = LIST_INIT( user_list ); 00062 00063 BOOL NETAPI_IsLocalComputer(LPCWSTR ServerName); 00064 00065 /************************************************************ 00066 * NETAPI_ValidateServername 00067 * 00068 * Validates server name 00069 */ 00070 static NET_API_STATUS NETAPI_ValidateServername(LPCWSTR ServerName) 00071 { 00072 if (ServerName) 00073 { 00074 if (ServerName[0] == 0) 00075 return ERROR_BAD_NETPATH; 00076 else if ( 00077 ((ServerName[0] == '\\') && 00078 (ServerName[1] != '\\')) 00079 || 00080 ((ServerName[0] == '\\') && 00081 (ServerName[1] == '\\') && 00082 (ServerName[2] == 0)) 00083 ) 00084 return ERROR_INVALID_NAME; 00085 } 00086 return NERR_Success; 00087 } 00088 00089 /************************************************************ 00090 * NETAPI_FindUser 00091 * 00092 * Looks for a user in the user database. 00093 * Returns a pointer to the entry in the user list when the user 00094 * is found, NULL otherwise. 00095 */ 00096 static struct sam_user* NETAPI_FindUser(LPCWSTR UserName) 00097 { 00098 struct sam_user *user; 00099 00100 LIST_FOR_EACH_ENTRY(user, &user_list, struct sam_user, entry) 00101 { 00102 if(lstrcmpW(user->user_name, UserName) == 0) 00103 return user; 00104 } 00105 return NULL; 00106 } 00107 00108 static BOOL NETAPI_IsCurrentUser(LPCWSTR username) 00109 { 00110 LPWSTR curr_user = NULL; 00111 DWORD dwSize; 00112 BOOL ret = FALSE; 00113 00114 dwSize = LM20_UNLEN+1; 00115 curr_user = HeapAlloc(GetProcessHeap(), 0, dwSize * sizeof(WCHAR)); 00116 if(!curr_user) 00117 { 00118 ERR("Failed to allocate memory for user name.\n"); 00119 goto end; 00120 } 00121 if(!GetUserNameW(curr_user, &dwSize)) 00122 { 00123 ERR("Failed to get current user's user name.\n"); 00124 goto end; 00125 } 00126 if (!lstrcmpW(curr_user, username)) 00127 { 00128 ret = TRUE; 00129 } 00130 00131 end: 00132 HeapFree(GetProcessHeap(), 0, curr_user); 00133 return ret; 00134 } 00135 00136 /************************************************************ 00137 * NetUserAdd (NETAPI32.@) 00138 */ 00139 NET_API_STATUS WINAPI NetUserAdd(LPCWSTR servername, 00140 DWORD level, LPBYTE bufptr, LPDWORD parm_err) 00141 { 00142 NET_API_STATUS status; 00143 struct sam_user * su = NULL; 00144 00145 FIXME("(%s, %d, %p, %p) stub!\n", debugstr_w(servername), level, bufptr, parm_err); 00146 00147 if((status = NETAPI_ValidateServername(servername)) != NERR_Success) 00148 return status; 00149 00150 switch(level) 00151 { 00152 /* Level 3 and 4 are identical for the purposes of NetUserAdd */ 00153 case 4: 00154 case 3: 00155 FIXME("Level 3 and 4 not implemented.\n"); 00156 /* Fall through */ 00157 case 2: 00158 FIXME("Level 2 not implemented.\n"); 00159 /* Fall through */ 00160 case 1: 00161 { 00162 PUSER_INFO_1 ui = (PUSER_INFO_1) bufptr; 00163 su = HeapAlloc(GetProcessHeap(), 0, sizeof(struct sam_user)); 00164 if(!su) 00165 { 00166 status = NERR_InternalError; 00167 break; 00168 } 00169 00170 if(lstrlenW(ui->usri1_name) > LM20_UNLEN) 00171 { 00172 status = NERR_BadUsername; 00173 break; 00174 } 00175 00176 /*FIXME: do other checks for a valid username */ 00177 lstrcpyW(su->user_name, ui->usri1_name); 00178 00179 if(lstrlenW(ui->usri1_password) > PWLEN) 00180 { 00181 /* Always return PasswordTooShort on invalid passwords. */ 00182 status = NERR_PasswordTooShort; 00183 break; 00184 } 00185 lstrcpyW(su->user_password, ui->usri1_password); 00186 00187 su->sec_since_passwd_change = ui->usri1_password_age; 00188 su->user_priv = ui->usri1_priv; 00189 su->user_flags = ui->usri1_flags; 00190 00191 /*FIXME: set the other LPWSTRs to NULL for now */ 00192 su->home_dir = NULL; 00193 su->user_comment = NULL; 00194 su->user_logon_script_path = NULL; 00195 00196 list_add_head(&user_list, &su->entry); 00197 return NERR_Success; 00198 } 00199 default: 00200 TRACE("Invalid level %d specified.\n", level); 00201 status = ERROR_INVALID_LEVEL; 00202 break; 00203 } 00204 00205 HeapFree(GetProcessHeap(), 0, su); 00206 00207 return status; 00208 } 00209 00210 /************************************************************ 00211 * NetUserDel (NETAPI32.@) 00212 */ 00213 NET_API_STATUS WINAPI NetUserDel(LPCWSTR servername, LPCWSTR username) 00214 { 00215 NET_API_STATUS status; 00216 struct sam_user *user; 00217 00218 TRACE("(%s, %s)\n", debugstr_w(servername), debugstr_w(username)); 00219 00220 if((status = NETAPI_ValidateServername(servername))!= NERR_Success) 00221 return status; 00222 00223 if ((user = NETAPI_FindUser(username)) == NULL) 00224 return NERR_UserNotFound; 00225 00226 list_remove(&user->entry); 00227 00228 HeapFree(GetProcessHeap(), 0, user->home_dir); 00229 HeapFree(GetProcessHeap(), 0, user->user_comment); 00230 HeapFree(GetProcessHeap(), 0, user->user_logon_script_path); 00231 HeapFree(GetProcessHeap(), 0, user); 00232 00233 return NERR_Success; 00234 } 00235 00236 /************************************************************ 00237 * NetUserGetInfo (NETAPI32.@) 00238 */ 00239 NET_API_STATUS WINAPI 00240 NetUserGetInfo(LPCWSTR servername, LPCWSTR username, DWORD level, 00241 LPBYTE* bufptr) 00242 { 00243 NET_API_STATUS status; 00244 TRACE("(%s, %s, %d, %p)\n", debugstr_w(servername), debugstr_w(username), 00245 level, bufptr); 00246 status = NETAPI_ValidateServername(servername); 00247 if (status != NERR_Success) 00248 return status; 00249 00250 if(!NETAPI_IsLocalComputer(servername)) 00251 { 00252 FIXME("Only implemented for local computer, but remote server" 00253 "%s was requested.\n", debugstr_w(servername)); 00254 return NERR_InvalidComputer; 00255 } 00256 00257 if(!NETAPI_FindUser(username) && !NETAPI_IsCurrentUser(username)) 00258 { 00259 TRACE("User %s is unknown.\n", debugstr_w(username)); 00260 return NERR_UserNotFound; 00261 } 00262 00263 switch (level) 00264 { 00265 case 0: 00266 { 00267 PUSER_INFO_0 ui; 00268 int name_sz; 00269 00270 name_sz = lstrlenW(username) + 1; 00271 00272 /* set up buffer */ 00273 NetApiBufferAllocate(sizeof(USER_INFO_0) + name_sz * sizeof(WCHAR), 00274 (LPVOID *) bufptr); 00275 00276 ui = (PUSER_INFO_0) *bufptr; 00277 ui->usri0_name = (LPWSTR) (*bufptr + sizeof(USER_INFO_0)); 00278 00279 /* get data */ 00280 lstrcpyW(ui->usri0_name, username); 00281 break; 00282 } 00283 00284 case 10: 00285 { 00286 PUSER_INFO_10 ui; 00287 PUSER_INFO_0 ui0; 00288 NET_API_STATUS status; 00289 /* sizes of the field buffers in WCHARS */ 00290 int name_sz, comment_sz, usr_comment_sz, full_name_sz; 00291 00292 comment_sz = 1; 00293 usr_comment_sz = 1; 00294 full_name_sz = 1; 00295 00296 /* get data */ 00297 status = NetUserGetInfo(servername, username, 0, (LPBYTE *) &ui0); 00298 if (status != NERR_Success) 00299 { 00300 NetApiBufferFree(ui0); 00301 return status; 00302 } 00303 name_sz = lstrlenW(ui0->usri0_name) + 1; 00304 00305 /* set up buffer */ 00306 NetApiBufferAllocate(sizeof(USER_INFO_10) + 00307 (name_sz + comment_sz + usr_comment_sz + 00308 full_name_sz) * sizeof(WCHAR), 00309 (LPVOID *) bufptr); 00310 ui = (PUSER_INFO_10) *bufptr; 00311 ui->usri10_name = (LPWSTR) (*bufptr + sizeof(USER_INFO_10)); 00312 ui->usri10_comment = (LPWSTR) ( 00313 ((PBYTE) ui->usri10_name) + name_sz * sizeof(WCHAR)); 00314 ui->usri10_usr_comment = (LPWSTR) ( 00315 ((PBYTE) ui->usri10_comment) + comment_sz * sizeof(WCHAR)); 00316 ui->usri10_full_name = (LPWSTR) ( 00317 ((PBYTE) ui->usri10_usr_comment) + usr_comment_sz * sizeof(WCHAR)); 00318 00319 /* set data */ 00320 lstrcpyW(ui->usri10_name, ui0->usri0_name); 00321 NetApiBufferFree(ui0); 00322 ui->usri10_comment[0] = 0; 00323 ui->usri10_usr_comment[0] = 0; 00324 ui->usri10_full_name[0] = 0; 00325 break; 00326 } 00327 00328 case 1: 00329 { 00330 static const WCHAR homedirW[] = {'H','O','M','E',0}; 00331 PUSER_INFO_1 ui; 00332 PUSER_INFO_0 ui0; 00333 NET_API_STATUS status; 00334 /* sizes of the field buffers in WCHARS */ 00335 int name_sz, password_sz, home_dir_sz, comment_sz, script_path_sz; 00336 00337 password_sz = 1; /* not filled out for security reasons for NetUserGetInfo*/ 00338 comment_sz = 1; 00339 script_path_sz = 1; 00340 00341 /* get data */ 00342 status = NetUserGetInfo(servername, username, 0, (LPBYTE *) &ui0); 00343 if (status != NERR_Success) 00344 { 00345 NetApiBufferFree(ui0); 00346 return status; 00347 } 00348 name_sz = lstrlenW(ui0->usri0_name) + 1; 00349 home_dir_sz = GetEnvironmentVariableW(homedirW, NULL,0); 00350 /* set up buffer */ 00351 NetApiBufferAllocate(sizeof(USER_INFO_1) + 00352 (name_sz + password_sz + home_dir_sz + 00353 comment_sz + script_path_sz) * sizeof(WCHAR), 00354 (LPVOID *) bufptr); 00355 00356 ui = (PUSER_INFO_1) *bufptr; 00357 ui->usri1_name = (LPWSTR) (ui + 1); 00358 ui->usri1_password = ui->usri1_name + name_sz; 00359 ui->usri1_home_dir = ui->usri1_password + password_sz; 00360 ui->usri1_comment = ui->usri1_home_dir + home_dir_sz; 00361 ui->usri1_script_path = ui->usri1_comment + comment_sz; 00362 /* set data */ 00363 lstrcpyW(ui->usri1_name, ui0->usri0_name); 00364 NetApiBufferFree(ui0); 00365 ui->usri1_password[0] = 0; 00366 ui->usri1_password_age = 0; 00367 ui->usri1_priv = 0; 00368 GetEnvironmentVariableW(homedirW, ui->usri1_home_dir,home_dir_sz); 00369 ui->usri1_comment[0] = 0; 00370 ui->usri1_flags = 0; 00371 ui->usri1_script_path[0] = 0; 00372 break; 00373 } 00374 case 2: 00375 case 3: 00376 case 4: 00377 case 11: 00378 case 20: 00379 case 23: 00380 case 1003: 00381 case 1005: 00382 case 1006: 00383 case 1007: 00384 case 1008: 00385 case 1009: 00386 case 1010: 00387 case 1011: 00388 case 1012: 00389 case 1013: 00390 case 1014: 00391 case 1017: 00392 case 1018: 00393 case 1020: 00394 case 1023: 00395 case 1024: 00396 case 1025: 00397 case 1051: 00398 case 1052: 00399 case 1053: 00400 { 00401 FIXME("Level %d is not implemented\n", level); 00402 return NERR_InternalError; 00403 } 00404 default: 00405 TRACE("Invalid level %d is specified\n", level); 00406 return ERROR_INVALID_LEVEL; 00407 } 00408 return NERR_Success; 00409 } 00410 00411 /************************************************************ 00412 * NetUserGetLocalGroups (NETAPI32.@) 00413 */ 00414 NET_API_STATUS WINAPI 00415 NetUserGetLocalGroups(LPCWSTR servername, LPCWSTR username, DWORD level, 00416 DWORD flags, LPBYTE* bufptr, DWORD prefmaxlen, 00417 LPDWORD entriesread, LPDWORD totalentries) 00418 { 00419 NET_API_STATUS status; 00420 const WCHAR admins[] = {'A','d','m','i','n','i','s','t','r','a','t','o','r','s',0}; 00421 LPWSTR currentuser; 00422 LOCALGROUP_USERS_INFO_0* info; 00423 DWORD size; 00424 00425 FIXME("(%s, %s, %d, %08x, %p %d, %p, %p) stub!\n", 00426 debugstr_w(servername), debugstr_w(username), level, flags, bufptr, 00427 prefmaxlen, entriesread, totalentries); 00428 00429 status = NETAPI_ValidateServername(servername); 00430 if (status != NERR_Success) 00431 return status; 00432 00433 size = UNLEN + 1; 00434 NetApiBufferAllocate(size * sizeof(WCHAR), (LPVOID*)¤tuser); 00435 GetUserNameW(currentuser, &size); 00436 00437 if (lstrcmpiW(username, currentuser) && NETAPI_FindUser(username)) 00438 { 00439 NetApiBufferFree(currentuser); 00440 return NERR_UserNotFound; 00441 } 00442 00443 NetApiBufferFree(currentuser); 00444 *totalentries = 1; 00445 size = sizeof(*info) + sizeof(admins); 00446 00447 if(prefmaxlen < size) 00448 status = ERROR_MORE_DATA; 00449 else 00450 status = NetApiBufferAllocate(size, (LPVOID*)&info); 00451 00452 if(status != NERR_Success) 00453 { 00454 *bufptr = NULL; 00455 *entriesread = 0; 00456 return status; 00457 } 00458 00459 info->lgrui0_name = (LPWSTR)((LPBYTE)info + sizeof(*info)); 00460 lstrcpyW(info->lgrui0_name, admins); 00461 00462 *bufptr = (LPBYTE)info; 00463 *entriesread = 1; 00464 00465 return NERR_Success; 00466 } 00467 00468 /************************************************************ 00469 * NetUserEnum (NETAPI32.@) 00470 */ 00471 NET_API_STATUS WINAPI 00472 NetUserEnum(LPCWSTR servername, DWORD level, DWORD filter, LPBYTE* bufptr, 00473 DWORD prefmaxlen, LPDWORD entriesread, LPDWORD totalentries, 00474 LPDWORD resume_handle) 00475 { 00476 FIXME("(%s,%d, 0x%d,%p,%d,%p,%p,%p) stub!\n", debugstr_w(servername), level, 00477 filter, bufptr, prefmaxlen, entriesread, totalentries, resume_handle); 00478 00479 return ERROR_ACCESS_DENIED; 00480 } 00481 00482 /************************************************************ 00483 * ACCESS_QueryAdminDisplayInformation 00484 * 00485 * Creates a buffer with information for the Admin User 00486 */ 00487 static void ACCESS_QueryAdminDisplayInformation(PNET_DISPLAY_USER *buf, PDWORD pdwSize) 00488 { 00489 static const WCHAR sAdminUserName[] = { 00490 'A','d','m','i','n','i','s','t','r','a','t','o','r',0}; 00491 00492 /* sizes of the field buffers in WCHARS */ 00493 int name_sz, comment_sz, full_name_sz; 00494 PNET_DISPLAY_USER usr; 00495 00496 /* set up buffer */ 00497 name_sz = lstrlenW(sAdminUserName) + 1; 00498 comment_sz = 1; 00499 full_name_sz = 1; 00500 00501 *pdwSize = sizeof(NET_DISPLAY_USER); 00502 *pdwSize += (name_sz + comment_sz + full_name_sz) * sizeof(WCHAR); 00503 NetApiBufferAllocate(*pdwSize, (LPVOID *) buf); 00504 00505 usr = *buf; 00506 usr->usri1_name = (LPWSTR) ((PBYTE) usr + sizeof(NET_DISPLAY_USER)); 00507 usr->usri1_comment = (LPWSTR) ( 00508 ((PBYTE) usr->usri1_name) + name_sz * sizeof(WCHAR)); 00509 usr->usri1_full_name = (LPWSTR) ( 00510 ((PBYTE) usr->usri1_comment) + comment_sz * sizeof(WCHAR)); 00511 00512 /* set data */ 00513 lstrcpyW(usr->usri1_name, sAdminUserName); 00514 usr->usri1_comment[0] = 0; 00515 usr->usri1_flags = UF_SCRIPT | UF_NORMAL_ACCOUNT | UF_DONT_EXPIRE_PASSWD; 00516 usr->usri1_full_name[0] = 0; 00517 usr->usri1_user_id = DOMAIN_USER_RID_ADMIN; 00518 usr->usri1_next_index = 0; 00519 } 00520 00521 /************************************************************ 00522 * ACCESS_QueryGuestDisplayInformation 00523 * 00524 * Creates a buffer with information for the Guest User 00525 */ 00526 static void ACCESS_QueryGuestDisplayInformation(PNET_DISPLAY_USER *buf, PDWORD pdwSize) 00527 { 00528 static const WCHAR sGuestUserName[] = { 00529 'G','u','e','s','t',0 }; 00530 00531 /* sizes of the field buffers in WCHARS */ 00532 int name_sz, comment_sz, full_name_sz; 00533 PNET_DISPLAY_USER usr; 00534 00535 /* set up buffer */ 00536 name_sz = lstrlenW(sGuestUserName) + 1; 00537 comment_sz = 1; 00538 full_name_sz = 1; 00539 00540 *pdwSize = sizeof(NET_DISPLAY_USER); 00541 *pdwSize += (name_sz + comment_sz + full_name_sz) * sizeof(WCHAR); 00542 NetApiBufferAllocate(*pdwSize, (LPVOID *) buf); 00543 00544 usr = *buf; 00545 usr->usri1_name = (LPWSTR) ((PBYTE) usr + sizeof(NET_DISPLAY_USER)); 00546 usr->usri1_comment = (LPWSTR) ( 00547 ((PBYTE) usr->usri1_name) + name_sz * sizeof(WCHAR)); 00548 usr->usri1_full_name = (LPWSTR) ( 00549 ((PBYTE) usr->usri1_comment) + comment_sz * sizeof(WCHAR)); 00550 00551 /* set data */ 00552 lstrcpyW(usr->usri1_name, sGuestUserName); 00553 usr->usri1_comment[0] = 0; 00554 usr->usri1_flags = UF_ACCOUNTDISABLE | UF_SCRIPT | UF_NORMAL_ACCOUNT | 00555 UF_DONT_EXPIRE_PASSWD; 00556 usr->usri1_full_name[0] = 0; 00557 usr->usri1_user_id = DOMAIN_USER_RID_GUEST; 00558 usr->usri1_next_index = 0; 00559 } 00560 00561 /************************************************************ 00562 * Copies NET_DISPLAY_USER record. 00563 */ 00564 static void ACCESS_CopyDisplayUser(const NET_DISPLAY_USER *dest, LPWSTR *dest_buf, 00565 PNET_DISPLAY_USER src) 00566 { 00567 LPWSTR str = *dest_buf; 00568 00569 src->usri1_name = str; 00570 lstrcpyW(src->usri1_name, dest->usri1_name); 00571 str = (LPWSTR) ( 00572 ((PBYTE) str) + (lstrlenW(str) + 1) * sizeof(WCHAR)); 00573 00574 src->usri1_comment = str; 00575 lstrcpyW(src->usri1_comment, dest->usri1_comment); 00576 str = (LPWSTR) ( 00577 ((PBYTE) str) + (lstrlenW(str) + 1) * sizeof(WCHAR)); 00578 00579 src->usri1_flags = dest->usri1_flags; 00580 00581 src->usri1_full_name = str; 00582 lstrcpyW(src->usri1_full_name, dest->usri1_full_name); 00583 str = (LPWSTR) ( 00584 ((PBYTE) str) + (lstrlenW(str) + 1) * sizeof(WCHAR)); 00585 00586 src->usri1_user_id = dest->usri1_user_id; 00587 src->usri1_next_index = dest->usri1_next_index; 00588 *dest_buf = str; 00589 } 00590 00591 /************************************************************ 00592 * NetQueryDisplayInformation (NETAPI32.@) 00593 * 00594 * The buffer structure: 00595 * - array of fixed size record of the level type 00596 * - strings, referenced by the record of the level type 00597 */ 00598 NET_API_STATUS WINAPI 00599 NetQueryDisplayInformation( 00600 LPCWSTR ServerName, DWORD Level, DWORD Index, DWORD EntriesRequested, 00601 DWORD PreferredMaximumLength, LPDWORD ReturnedEntryCount, 00602 PVOID *SortedBuffer) 00603 { 00604 TRACE("(%s, %d, %d, %d, %d, %p, %p)\n", debugstr_w(ServerName), 00605 Level, Index, EntriesRequested, PreferredMaximumLength, 00606 ReturnedEntryCount, SortedBuffer); 00607 00608 if(!NETAPI_IsLocalComputer(ServerName)) 00609 { 00610 FIXME("Only implemented on local computer, but requested for " 00611 "remote server %s\n", debugstr_w(ServerName)); 00612 return ERROR_ACCESS_DENIED; 00613 } 00614 00615 switch (Level) 00616 { 00617 case 1: 00618 { 00619 /* current record */ 00620 PNET_DISPLAY_USER inf; 00621 /* current available strings buffer */ 00622 LPWSTR str; 00623 PNET_DISPLAY_USER admin, guest; 00624 DWORD admin_size, guest_size; 00625 LPWSTR name = NULL; 00626 DWORD dwSize; 00627 00628 /* sizes of the field buffers in WCHARS */ 00629 int name_sz, comment_sz, full_name_sz; 00630 00631 /* number of the records, returned in SortedBuffer 00632 3 - for current user, Administrator and Guest users 00633 */ 00634 int records = 3; 00635 00636 FIXME("Level %d partially implemented\n", Level); 00637 *ReturnedEntryCount = records; 00638 comment_sz = 1; 00639 full_name_sz = 1; 00640 00641 /* get data */ 00642 dwSize = UNLEN + 1; 00643 NetApiBufferAllocate(dwSize * sizeof(WCHAR), (LPVOID *) &name); 00644 if (!GetUserNameW(name, &dwSize)) 00645 { 00646 NetApiBufferFree(name); 00647 return ERROR_ACCESS_DENIED; 00648 } 00649 name_sz = dwSize; 00650 ACCESS_QueryAdminDisplayInformation(&admin, &admin_size); 00651 ACCESS_QueryGuestDisplayInformation(&guest, &guest_size); 00652 00653 /* set up buffer */ 00654 dwSize = sizeof(NET_DISPLAY_USER) * records; 00655 dwSize += (name_sz + comment_sz + full_name_sz) * sizeof(WCHAR); 00656 00657 NetApiBufferAllocate(dwSize + 00658 admin_size - sizeof(NET_DISPLAY_USER) + 00659 guest_size - sizeof(NET_DISPLAY_USER), 00660 SortedBuffer); 00661 inf = *SortedBuffer; 00662 str = (LPWSTR) ((PBYTE) inf + sizeof(NET_DISPLAY_USER) * records); 00663 inf->usri1_name = str; 00664 str = (LPWSTR) ( 00665 ((PBYTE) str) + name_sz * sizeof(WCHAR)); 00666 inf->usri1_comment = str; 00667 str = (LPWSTR) ( 00668 ((PBYTE) str) + comment_sz * sizeof(WCHAR)); 00669 inf->usri1_full_name = str; 00670 str = (LPWSTR) ( 00671 ((PBYTE) str) + full_name_sz * sizeof(WCHAR)); 00672 00673 /* set data */ 00674 lstrcpyW(inf->usri1_name, name); 00675 NetApiBufferFree(name); 00676 inf->usri1_comment[0] = 0; 00677 inf->usri1_flags = 00678 UF_SCRIPT | UF_NORMAL_ACCOUNT | UF_DONT_EXPIRE_PASSWD; 00679 inf->usri1_full_name[0] = 0; 00680 inf->usri1_user_id = 0; 00681 inf->usri1_next_index = 0; 00682 00683 inf++; 00684 ACCESS_CopyDisplayUser(admin, &str, inf); 00685 NetApiBufferFree(admin); 00686 00687 inf++; 00688 ACCESS_CopyDisplayUser(guest, &str, inf); 00689 NetApiBufferFree(guest); 00690 break; 00691 } 00692 00693 case 2: 00694 case 3: 00695 { 00696 FIXME("Level %d is not implemented\n", Level); 00697 break; 00698 } 00699 00700 default: 00701 TRACE("Invalid level %d is specified\n", Level); 00702 return ERROR_INVALID_LEVEL; 00703 } 00704 return NERR_Success; 00705 } 00706 00707 /************************************************************ 00708 * NetGetDCName (NETAPI32.@) 00709 * 00710 * Return the name of the primary domain controller (PDC) 00711 */ 00712 00713 NET_API_STATUS WINAPI 00714 NetGetDCName(LPCWSTR servername, LPCWSTR domainname, LPBYTE *bufptr) 00715 { 00716 FIXME("(%s, %s, %p) stub!\n", debugstr_w(servername), 00717 debugstr_w(domainname), bufptr); 00718 return NERR_DCNotFound; /* say we can't find a domain controller */ 00719 } 00720 00721 /************************************************************ 00722 * NetGroupEnum (NETAPI32.@) 00723 * 00724 */ 00725 NET_API_STATUS WINAPI 00726 NetGroupEnum(LPCWSTR servername, DWORD level, LPBYTE *bufptr, DWORD prefmaxlen, 00727 LPDWORD entriesread, LPDWORD totalentries, LPDWORD resume_handle) 00728 { 00729 FIXME("(%s, %d, %p, %d, %p, %p, %p) stub!\n", debugstr_w(servername), 00730 level, bufptr, prefmaxlen, entriesread, totalentries, resume_handle); 00731 return ERROR_ACCESS_DENIED; 00732 } 00733 00734 /************************************************************ 00735 * NetGroupGetInfo (NETAPI32.@) 00736 * 00737 */ 00738 NET_API_STATUS WINAPI NetGroupGetInfo(LPCWSTR servername, LPCWSTR groupname, DWORD level, LPBYTE *bufptr) 00739 { 00740 FIXME("(%s, %s, %d, %p) stub!\n", debugstr_w(servername), debugstr_w(groupname), level, bufptr); 00741 return ERROR_ACCESS_DENIED; 00742 } 00743 00744 /****************************************************************************** 00745 * NetUserModalsGet (NETAPI32.@) 00746 * 00747 * Retrieves global information for all users and global groups in the security 00748 * database. 00749 * 00750 * PARAMS 00751 * szServer [I] Specifies the DNS or the NetBIOS name of the remote server 00752 * on which the function is to execute. 00753 * level [I] Information level of the data. 00754 * 0 Return global passwords parameters. bufptr points to a 00755 * USER_MODALS_INFO_0 struct. 00756 * 1 Return logon server and domain controller information. bufptr 00757 * points to a USER_MODALS_INFO_1 struct. 00758 * 2 Return domain name and identifier. bufptr points to a 00759 * USER_MODALS_INFO_2 struct. 00760 * 3 Return lockout information. bufptr points to a USER_MODALS_INFO_3 00761 * struct. 00762 * pbuffer [I] Buffer that receives the data. 00763 * 00764 * RETURNS 00765 * Success: NERR_Success. 00766 * Failure: 00767 * ERROR_ACCESS_DENIED - the user does not have access to the info. 00768 * NERR_InvalidComputer - computer name is invalid. 00769 */ 00770 NET_API_STATUS WINAPI NetUserModalsGet( 00771 LPCWSTR szServer, DWORD level, LPBYTE *pbuffer) 00772 { 00773 TRACE("(%s %d %p)\n", debugstr_w(szServer), level, pbuffer); 00774 00775 switch (level) 00776 { 00777 case 0: 00778 /* return global passwords parameters */ 00779 FIXME("level 0 not implemented!\n"); 00780 *pbuffer = NULL; 00781 return NERR_InternalError; 00782 case 1: 00783 /* return logon server and domain controller info */ 00784 FIXME("level 1 not implemented!\n"); 00785 *pbuffer = NULL; 00786 return NERR_InternalError; 00787 case 2: 00788 { 00789 /* return domain name and identifier */ 00790 PUSER_MODALS_INFO_2 umi; 00791 LSA_HANDLE policyHandle; 00792 LSA_OBJECT_ATTRIBUTES objectAttributes; 00793 PPOLICY_ACCOUNT_DOMAIN_INFO domainInfo; 00794 NTSTATUS ntStatus; 00795 PSID domainIdentifier = NULL; 00796 int domainNameLen, domainIdLen; 00797 00798 ZeroMemory(&objectAttributes, sizeof(objectAttributes)); 00799 objectAttributes.Length = sizeof(objectAttributes); 00800 00801 ntStatus = LsaOpenPolicy(NULL, &objectAttributes, 00802 POLICY_VIEW_LOCAL_INFORMATION, 00803 &policyHandle); 00804 if (ntStatus != STATUS_SUCCESS) 00805 { 00806 WARN("LsaOpenPolicy failed with NT status %x\n", 00807 LsaNtStatusToWinError(ntStatus)); 00808 return ntStatus; 00809 } 00810 00811 ntStatus = LsaQueryInformationPolicy(policyHandle, 00812 PolicyAccountDomainInformation, 00813 (PVOID *)&domainInfo); 00814 if (ntStatus != STATUS_SUCCESS) 00815 { 00816 WARN("LsaQueryInformationPolicy failed with NT status %x\n", 00817 LsaNtStatusToWinError(ntStatus)); 00818 LsaClose(policyHandle); 00819 return ntStatus; 00820 } 00821 00822 domainIdentifier = domainInfo->DomainSid; 00823 domainIdLen = (domainIdentifier) ? GetLengthSid(domainIdentifier) : 0; 00824 domainNameLen = lstrlenW(domainInfo->DomainName.Buffer) + 1; 00825 LsaClose(policyHandle); 00826 00827 ntStatus = NetApiBufferAllocate(sizeof(USER_MODALS_INFO_2) + 00828 domainIdLen + 00829 domainNameLen * sizeof(WCHAR), 00830 (LPVOID *)pbuffer); 00831 00832 if (ntStatus != NERR_Success) 00833 { 00834 WARN("NetApiBufferAllocate() failed\n"); 00835 LsaFreeMemory(domainInfo); 00836 return ntStatus; 00837 } 00838 00839 umi = (USER_MODALS_INFO_2 *) *pbuffer; 00840 umi->usrmod2_domain_id = (domainIdLen > 0) ? (*pbuffer + sizeof(USER_MODALS_INFO_2)) : NULL; 00841 umi->usrmod2_domain_name = (LPWSTR)(*pbuffer + 00842 sizeof(USER_MODALS_INFO_2) + domainIdLen); 00843 00844 lstrcpynW(umi->usrmod2_domain_name, 00845 domainInfo->DomainName.Buffer, 00846 domainNameLen); 00847 if (domainIdLen > 0) 00848 CopySid(GetLengthSid(domainIdentifier), umi->usrmod2_domain_id, 00849 domainIdentifier); 00850 00851 LsaFreeMemory(domainInfo); 00852 00853 break; 00854 } 00855 case 3: 00856 /* return lockout information */ 00857 FIXME("level 3 not implemented!\n"); 00858 *pbuffer = NULL; 00859 return NERR_InternalError; 00860 default: 00861 TRACE("Invalid level %d is specified\n", level); 00862 *pbuffer = NULL; 00863 return ERROR_INVALID_LEVEL; 00864 } 00865 00866 return NERR_Success; 00867 } 00868 00869 /****************************************************************************** 00870 * NetUserChangePassword (NETAPI32.@) 00871 * PARAMS 00872 * domainname [I] Optional. Domain on which the user resides or the logon 00873 * domain of the current user if NULL. 00874 * username [I] Optional. Username to change the password for or the name 00875 * of the current user if NULL. 00876 * oldpassword [I] The user's current password. 00877 * newpassword [I] The password that the user will be changed to using. 00878 * 00879 * RETURNS 00880 * Success: NERR_Success. 00881 * Failure: NERR_* failure code or win error code. 00882 * 00883 */ 00884 NET_API_STATUS WINAPI NetUserChangePassword(LPCWSTR domainname, LPCWSTR username, 00885 LPCWSTR oldpassword, LPCWSTR newpassword) 00886 { 00887 struct sam_user *user; 00888 00889 TRACE("(%s, %s, ..., ...)\n", debugstr_w(domainname), debugstr_w(username)); 00890 00891 if(domainname) 00892 FIXME("Ignoring domainname %s.\n", debugstr_w(domainname)); 00893 00894 if((user = NETAPI_FindUser(username)) == NULL) 00895 return NERR_UserNotFound; 00896 00897 if(lstrcmpW(user->user_password, oldpassword) != 0) 00898 return ERROR_INVALID_PASSWORD; 00899 00900 if(lstrlenW(newpassword) > PWLEN) 00901 return ERROR_PASSWORD_RESTRICTION; 00902 00903 lstrcpyW(user->user_password, newpassword); 00904 00905 return NERR_Success; 00906 } 00907 00908 NET_API_STATUS WINAPI NetUseAdd(LMSTR servername, DWORD level, LPBYTE bufptr, LPDWORD parm_err) 00909 { 00910 FIXME("%s %d %p %p stub\n", debugstr_w(servername), level, bufptr, parm_err); 00911 return NERR_Success; 00912 } Generated on Sun May 27 2012 04:20:50 for ReactOS by
1.7.6.1
|