aboutsummaryrefslogtreecommitdiffstats
path: root/src/w32.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/w32.c')
-rw-r--r--src/w32.c149
1 files changed, 124 insertions, 25 deletions
diff --git a/src/w32.c b/src/w32.c
index 5a8289789da..2395c236769 100644
--- a/src/w32.c
+++ b/src/w32.c
@@ -120,6 +120,8 @@ static BOOL g_b_init_open_process_token;
120static BOOL g_b_init_get_token_information; 120static BOOL g_b_init_get_token_information;
121static BOOL g_b_init_lookup_account_sid; 121static BOOL g_b_init_lookup_account_sid;
122static BOOL g_b_init_get_sid_identifier_authority; 122static BOOL g_b_init_get_sid_identifier_authority;
123static BOOL g_b_init_get_sid_sub_authority;
124static BOOL g_b_init_get_sid_sub_authority_count;
123 125
124/* 126/*
125 BEGIN: Wrapper functions around OpenProcessToken 127 BEGIN: Wrapper functions around OpenProcessToken
@@ -161,6 +163,12 @@ typedef BOOL (WINAPI * LookupAccountSid_Proc) (
161 PSID_NAME_USE peUse); 163 PSID_NAME_USE peUse);
162typedef PSID_IDENTIFIER_AUTHORITY (WINAPI * GetSidIdentifierAuthority_Proc) ( 164typedef PSID_IDENTIFIER_AUTHORITY (WINAPI * GetSidIdentifierAuthority_Proc) (
163 PSID pSid); 165 PSID pSid);
166typedef PDWORD (WINAPI * GetSidSubAuthority_Proc) (
167 PSID pSid,
168 DWORD n);
169typedef PUCHAR (WINAPI * GetSidSubAuthorityCount_Proc) (
170 PSID pSid);
171
164 172
165 /* ** A utility function ** */ 173 /* ** A utility function ** */
166static BOOL 174static BOOL
@@ -349,6 +357,57 @@ PSID_IDENTIFIER_AUTHORITY WINAPI get_sid_identifier_authority (
349 return (s_pfn_Get_Sid_Identifier_Authority (pSid)); 357 return (s_pfn_Get_Sid_Identifier_Authority (pSid));
350} 358}
351 359
360PDWORD WINAPI get_sid_sub_authority (
361 PSID pSid,
362 DWORD n)
363{
364 static GetSidSubAuthority_Proc s_pfn_Get_Sid_Sub_Authority = NULL;
365 static DWORD zero = 0U;
366 HMODULE hm_advapi32 = NULL;
367 if (is_windows_9x () == TRUE)
368 {
369 return &zero;
370 }
371 if (g_b_init_get_sid_sub_authority == 0)
372 {
373 g_b_init_get_sid_sub_authority = 1;
374 hm_advapi32 = LoadLibrary ("Advapi32.dll");
375 s_pfn_Get_Sid_Sub_Authority =
376 (GetSidSubAuthority_Proc) GetProcAddress (
377 hm_advapi32, "GetSidSubAuthority");
378 }
379 if (s_pfn_Get_Sid_Sub_Authority == NULL)
380 {
381 return &zero;
382 }
383 return (s_pfn_Get_Sid_Sub_Authority (pSid, n));
384}
385
386PUCHAR WINAPI get_sid_sub_authority_count (
387 PSID pSid)
388{
389 static GetSidSubAuthorityCount_Proc s_pfn_Get_Sid_Sub_Authority_Count = NULL;
390 static UCHAR zero = 0U;
391 HMODULE hm_advapi32 = NULL;
392 if (is_windows_9x () == TRUE)
393 {
394 return &zero;
395 }
396 if (g_b_init_get_sid_sub_authority_count == 0)
397 {
398 g_b_init_get_sid_sub_authority_count = 1;
399 hm_advapi32 = LoadLibrary ("Advapi32.dll");
400 s_pfn_Get_Sid_Sub_Authority_Count =
401 (GetSidSubAuthorityCount_Proc) GetProcAddress (
402 hm_advapi32, "GetSidSubAuthorityCount");
403 }
404 if (s_pfn_Get_Sid_Sub_Authority_Count == NULL)
405 {
406 return &zero;
407 }
408 return (s_pfn_Get_Sid_Sub_Authority_Count (pSid));
409}
410
352/* 411/*
353 END: Wrapper functions around OpenProcessToken 412 END: Wrapper functions around OpenProcessToken
354 and other functions in advapi32.dll that are only 413 and other functions in advapi32.dll that are only
@@ -547,39 +606,47 @@ init_user_info ()
547 domain, &dlength, &user_type)) 606 domain, &dlength, &user_type))
548 { 607 {
549 strcpy (the_passwd.pw_name, name); 608 strcpy (the_passwd.pw_name, name);
550 /* Determine a reasonable uid value. */ 609 /* Determine a reasonable uid value. */
551 if (stricmp ("administrator", name) == 0) 610 if (stricmp ("administrator", name) == 0)
552 { 611 {
553 the_passwd.pw_uid = 0; 612 the_passwd.pw_uid = 500; /* well-known Administrator uid */
554 the_passwd.pw_gid = 0; 613 the_passwd.pw_gid = 513; /* well-known None gid */
555 } 614 }
556 else 615 else
557 { 616 {
558 SID_IDENTIFIER_AUTHORITY * pSIA; 617 /* Use the last sub-authority value of the RID, the relative
559 618 portion of the SID, as user/group ID. */
560 pSIA = get_sid_identifier_authority (*((PSID *) user_sid)); 619 DWORD n_subauthorities =
561 /* I believe the relative portion is the last 4 bytes (of 6) 620 *get_sid_sub_authority_count (*((PSID *) user_sid));
562 with msb first. */ 621
563 the_passwd.pw_uid = ((pSIA->Value[2] << 24) + 622 if (n_subauthorities < 1)
564 (pSIA->Value[3] << 16) + 623 the_passwd.pw_uid = 0; /* the "World" RID */
565 (pSIA->Value[4] << 8) + 624 else
566 (pSIA->Value[5] << 0)); 625 {
567 /* restrict to conventional uid range for normal users */ 626 the_passwd.pw_uid =
568 the_passwd.pw_uid = the_passwd.pw_uid % 60001; 627 *get_sid_sub_authority (*((PSID *) user_sid),
628 n_subauthorities - 1);
629 /* Restrict to conventional uid range for normal users. */
630 the_passwd.pw_uid %= 60001;
631 }
569 632
570 /* Get group id */ 633 /* Get group id */
571 if (get_token_information (token, TokenPrimaryGroup, 634 if (get_token_information (token, TokenPrimaryGroup,
572 (PVOID) user_sid, sizeof (user_sid), &trash)) 635 (PVOID) user_sid, sizeof (user_sid), &trash))
573 { 636 {
574 SID_IDENTIFIER_AUTHORITY * pSIA; 637 n_subauthorities =
575 638 *get_sid_sub_authority_count (*((PSID *) user_sid));
576 pSIA = get_sid_identifier_authority (*((PSID *) user_sid)); 639
577 the_passwd.pw_gid = ((pSIA->Value[2] << 24) + 640 if (n_subauthorities < 1)
578 (pSIA->Value[3] << 16) + 641 the_passwd.pw_gid = 0; /* the "World" RID */
579 (pSIA->Value[4] << 8) + 642 else
580 (pSIA->Value[5] << 0)); 643 {
581 /* I don't know if this is necessary, but for safety... */ 644 the_passwd.pw_gid =
582 the_passwd.pw_gid = the_passwd.pw_gid % 60001; 645 *get_sid_sub_authority (*((PSID *) user_sid),
646 n_subauthorities - 1);
647 /* I don't know if this is necessary, but for safety... */
648 the_passwd.pw_gid %= 60001;
649 }
583 } 650 }
584 else 651 else
585 the_passwd.pw_gid = the_passwd.pw_uid; 652 the_passwd.pw_gid = the_passwd.pw_uid;
@@ -1938,6 +2005,36 @@ unc_volume_file_attributes (const char *path)
1938 return attrs; 2005 return attrs;
1939} 2006}
1940 2007
2008/* Ensure a network connection is authenticated. */
2009static void
2010logon_network_drive (const char *path)
2011{
2012 NETRESOURCE resource;
2013 char share[MAX_PATH];
2014 int i, n_slashes;
2015
2016 /* Only logon to networked drives. */
2017 if (!IS_DIRECTORY_SEP (path[0]) || !IS_DIRECTORY_SEP (path[1]))
2018 return;
2019 n_slashes = 2;
2020 strncpy (share, path, MAX_PATH);
2021 /* Truncate to just server and share name. */
2022 for (i = 2; i < MAX_PATH; i++)
2023 {
2024 if (IS_DIRECTORY_SEP (share[i]) && ++n_slashes > 3)
2025 {
2026 share[i] = '\0';
2027 break;
2028 }
2029 }
2030
2031 resource.dwType = RESOURCETYPE_DISK;
2032 resource.lpLocalName = NULL;
2033 resource.lpRemoteName = share;
2034 resource.lpProvider = NULL;
2035
2036 WNetAddConnection2 (&resource, NULL, NULL, CONNECT_INTERACTIVE);
2037}
1941 2038
1942/* Shadow some MSVC runtime functions to map requests for long filenames 2039/* Shadow some MSVC runtime functions to map requests for long filenames
1943 to reasonable short names if necessary. This was originally added to 2040 to reasonable short names if necessary. This was originally added to
@@ -2495,6 +2592,8 @@ stat (const char * path, struct stat * buf)
2495 } 2592 }
2496 else 2593 else
2497 { 2594 {
2595 logon_network_drive (name);
2596
2498 fh = FindFirstFile (name, &wfd); 2597 fh = FindFirstFile (name, &wfd);
2499 if (fh == INVALID_HANDLE_VALUE) 2598 if (fh == INVALID_HANDLE_VALUE)
2500 { 2599 {
@@ -2668,8 +2767,8 @@ fstat (int desc, struct stat * buf)
2668 buf->st_ino = fake_inode; 2767 buf->st_ino = fake_inode;
2669 2768
2670 /* consider files to belong to current user */ 2769 /* consider files to belong to current user */
2671 buf->st_uid = 0; 2770 buf->st_uid = the_passwd.pw_uid;
2672 buf->st_gid = 0; 2771 buf->st_gid = the_passwd.pw_gid;
2673 2772
2674 buf->st_dev = info.dwVolumeSerialNumber; 2773 buf->st_dev = info.dwVolumeSerialNumber;
2675 buf->st_rdev = info.dwVolumeSerialNumber; 2774 buf->st_rdev = info.dwVolumeSerialNumber;