comparison src/w32.c @ 97875:a77c2abc7237

(init_user_info): Allocate buf[] with xmalloc using the size needed by GetTokenInformation. (w32_system_process_attributes): Check return values of all system APIs.
author Eli Zaretskii <eliz@gnu.org>
date Sat, 30 Aug 2008 16:46:06 +0000
parents 1f8e4a26957e
children 038d7d21b786
comparison
equal deleted inserted replaced
97874:9468eeadf007 97875:a77c2abc7237
905 Use the relative portion of the identifier authority value from 905 Use the relative portion of the identifier authority value from
906 the user-sid as the user id value (same for group id using the 906 the user-sid as the user id value (same for group id using the
907 primary group sid from the process token). */ 907 primary group sid from the process token). */
908 908
909 char uname[UNLEN+1], gname[GNLEN+1], domain[1025]; 909 char uname[UNLEN+1], gname[GNLEN+1], domain[1025];
910 DWORD ulength = sizeof (uname), dlength = sizeof (domain), trash; 910 DWORD ulength = sizeof (uname), dlength = sizeof (domain), needed;
911 DWORD glength = sizeof (gname); 911 DWORD glength = sizeof (gname);
912 HANDLE token = NULL; 912 HANDLE token = NULL;
913 SID_NAME_USE user_type; 913 SID_NAME_USE user_type;
914 unsigned char buf[1024]; 914 unsigned char *buf = NULL;
915 DWORD blen = 0;
915 TOKEN_USER user_token; 916 TOKEN_USER user_token;
916 TOKEN_PRIMARY_GROUP group_token; 917 TOKEN_PRIMARY_GROUP group_token;
917 918 BOOL result;
918 if (open_process_token (GetCurrentProcess (), TOKEN_QUERY, &token) 919
919 && get_token_information (token, TokenUser, 920 result = open_process_token (GetCurrentProcess (), TOKEN_QUERY, &token);
920 (PVOID)buf, sizeof (buf), &trash) 921 if (result)
921 && (memcpy (&user_token, buf, sizeof (user_token)), 922 {
922 lookup_account_sid (NULL, user_token.User.Sid, uname, &ulength, 923 result = get_token_information (token, TokenUser, NULL, 0, &blen);
923 domain, &dlength, &user_type))) 924 if (!result && GetLastError () == ERROR_INSUFFICIENT_BUFFER)
925 {
926 buf = xmalloc (blen);
927 result = get_token_information (token, TokenUser,
928 (LPVOID)buf, blen, &needed);
929 if (result)
930 {
931 memcpy (&user_token, buf, sizeof (user_token));
932 result = lookup_account_sid (NULL, user_token.User.Sid,
933 uname, &ulength,
934 domain, &dlength, &user_type);
935 }
936 }
937 else
938 result = FALSE;
939 }
940 if (result)
924 { 941 {
925 strcpy (dflt_passwd.pw_name, uname); 942 strcpy (dflt_passwd.pw_name, uname);
926 /* Determine a reasonable uid value. */ 943 /* Determine a reasonable uid value. */
927 if (xstrcasecmp ("administrator", uname) == 0) 944 if (xstrcasecmp ("administrator", uname) == 0)
928 { 945 {
934 /* Use the last sub-authority value of the RID, the relative 951 /* Use the last sub-authority value of the RID, the relative
935 portion of the SID, as user/group ID. */ 952 portion of the SID, as user/group ID. */
936 dflt_passwd.pw_uid = get_rid (user_token.User.Sid); 953 dflt_passwd.pw_uid = get_rid (user_token.User.Sid);
937 954
938 /* Get group id and name. */ 955 /* Get group id and name. */
939 if (get_token_information (token, TokenPrimaryGroup, 956 result = get_token_information (token, TokenPrimaryGroup,
940 (PVOID)buf, sizeof (buf), &trash)) 957 (LPVOID)buf, blen, &needed);
958 if (!result && GetLastError () == ERROR_INSUFFICIENT_BUFFER)
959 {
960 buf = xrealloc (buf, blen = needed);
961 result = get_token_information (token, TokenPrimaryGroup,
962 (LPVOID)buf, blen, &needed);
963 }
964 if (result)
941 { 965 {
942 memcpy (&group_token, buf, sizeof (group_token)); 966 memcpy (&group_token, buf, sizeof (group_token));
943 dflt_passwd.pw_gid = get_rid (group_token.PrimaryGroup); 967 dflt_passwd.pw_gid = get_rid (group_token.PrimaryGroup);
944 dlength = sizeof (domain); 968 dlength = sizeof (domain);
969 /* If we can get at the real Primary Group name, use that.
970 Otherwise, the default group name was already set to
971 "None" in globals_of_w32. */
945 if (lookup_account_sid (NULL, group_token.PrimaryGroup, 972 if (lookup_account_sid (NULL, group_token.PrimaryGroup,
946 gname, &glength, NULL, &dlength, 973 gname, &glength, NULL, &dlength,
947 &user_type)) 974 &user_type))
948 strcpy (dflt_group_name, gname); 975 strcpy (dflt_group_name, gname);
949 } 976 }
950 else 977 else
951 dflt_passwd.pw_gid = dflt_passwd.pw_uid; 978 dflt_passwd.pw_gid = dflt_passwd.pw_uid;
952 } 979 }
953 } 980 }
954 /* If security calls are not supported (presumably because we 981 /* If security calls are not supported (presumably because we
955 are running under Windows 95), fallback to this. */ 982 are running under Windows 9X), fallback to this: */
956 else if (GetUserName (uname, &ulength)) 983 else if (GetUserName (uname, &ulength))
957 { 984 {
958 strcpy (dflt_passwd.pw_name, uname); 985 strcpy (dflt_passwd.pw_name, uname);
959 if (xstrcasecmp ("administrator", uname) == 0) 986 if (xstrcasecmp ("administrator", uname) == 0)
960 dflt_passwd.pw_uid = 0; 987 dflt_passwd.pw_uid = 0;
978 1005
979 /* Set dir and shell from environment variables. */ 1006 /* Set dir and shell from environment variables. */
980 strcpy (dflt_passwd.pw_dir, getenv ("HOME")); 1007 strcpy (dflt_passwd.pw_dir, getenv ("HOME"));
981 strcpy (dflt_passwd.pw_shell, getenv ("SHELL")); 1008 strcpy (dflt_passwd.pw_shell, getenv ("SHELL"));
982 1009
1010 xfree (buf);
983 if (token) 1011 if (token)
984 CloseHandle (token); 1012 CloseHandle (token);
985 } 1013 }
986 1014
987 int 1015 int
3808 Lisp_Object cmd_str, decoded_cmd, tem; 3836 Lisp_Object cmd_str, decoded_cmd, tem;
3809 HANDLE h_snapshot, h_proc; 3837 HANDLE h_snapshot, h_proc;
3810 DWORD proc_id; 3838 DWORD proc_id;
3811 int found_proc = 0; 3839 int found_proc = 0;
3812 char uname[UNLEN+1], gname[GNLEN+1], domain[1025]; 3840 char uname[UNLEN+1], gname[GNLEN+1], domain[1025];
3813 DWORD ulength = sizeof (uname), dlength = sizeof (domain), trash; 3841 DWORD ulength = sizeof (uname), dlength = sizeof (domain), needed;
3814 DWORD glength = sizeof (gname); 3842 DWORD glength = sizeof (gname);
3815 HANDLE token = NULL; 3843 HANDLE token = NULL;
3816 SID_NAME_USE user_type; 3844 SID_NAME_USE user_type;
3817 unsigned char buf[1024]; 3845 unsigned char *buf = NULL;
3846 DWORD blen = 0;
3818 TOKEN_USER user_token; 3847 TOKEN_USER user_token;
3819 TOKEN_PRIMARY_GROUP group_token; 3848 TOKEN_PRIMARY_GROUP group_token;
3820 int euid; 3849 int euid;
3821 int egid; 3850 int egid;
3822 DWORD sess; 3851 DWORD sess;
3826 MEMORYSTATUS memst; 3855 MEMORYSTATUS memst;
3827 MEMORY_STATUS_EX memstex; 3856 MEMORY_STATUS_EX memstex;
3828 double totphys = 0.0; 3857 double totphys = 0.0;
3829 Lisp_Object ctime, stime, utime, etime; 3858 Lisp_Object ctime, stime, utime, etime;
3830 double pcpu; 3859 double pcpu;
3860 BOOL result = FALSE;
3831 3861
3832 CHECK_NUMBER_OR_FLOAT (pid); 3862 CHECK_NUMBER_OR_FLOAT (pid);
3833 proc_id = FLOATP (pid) ? XFLOAT_DATA (pid) : XINT (pid); 3863 proc_id = FLOATP (pid) ? XFLOAT_DATA (pid) : XINT (pid);
3834 3864
3835 h_snapshot = create_toolhelp32_snapshot (TH32CS_SNAPPROCESS, 0); 3865 h_snapshot = create_toolhelp32_snapshot (TH32CS_SNAPPROCESS, 0);
3896 FALSE, proc_id); 3926 FALSE, proc_id);
3897 restore_privilege (&priv_current); 3927 restore_privilege (&priv_current);
3898 revert_to_self (); 3928 revert_to_self ();
3899 } 3929 }
3900 } 3930 }
3901 if (h_proc 3931 if (h_proc)
3902 && open_process_token (h_proc, TOKEN_QUERY, &token) 3932 {
3903 && get_token_information (token, TokenUser, 3933 result = open_process_token (h_proc, TOKEN_QUERY, &token);
3904 (PVOID)buf, sizeof (buf), &trash)) 3934 if (result)
3905 { 3935 {
3906 memcpy (&user_token, buf, sizeof (user_token)); 3936 result = get_token_information (token, TokenUser, NULL, 0, &blen);
3907 if (w32_cached_id (user_token.User.Sid, &euid, uname)) 3937 if (!result && GetLastError () == ERROR_INSUFFICIENT_BUFFER)
3908 ulength = strlen (uname); 3938 {
3939 buf = xmalloc (blen);
3940 result = get_token_information (token, TokenUser,
3941 (LPVOID)buf, blen, &needed);
3942 if (result)
3943 {
3944 memcpy (&user_token, buf, sizeof (user_token));
3945 if (!w32_cached_id (user_token.User.Sid, &euid, uname))
3946 {
3947 euid = get_rid (user_token.User.Sid);
3948 result = lookup_account_sid (NULL, user_token.User.Sid,
3949 uname, &ulength,
3950 domain, &dlength,
3951 &user_type);
3952 if (result)
3953 w32_add_to_cache (user_token.User.Sid, euid, uname);
3954 else
3955 {
3956 strcpy (uname, "unknown");
3957 result = TRUE;
3958 }
3959 }
3960 ulength = strlen (uname);
3961 }
3962 }
3963 }
3964 if (result)
3965 {
3966 /* Determine a reasonable euid and gid values. */
3967 if (xstrcasecmp ("administrator", uname) == 0)
3968 {
3969 euid = 500; /* well-known Administrator uid */
3970 egid = 513; /* well-known None gid */
3971 }
3972 else
3973 {
3974 /* Get group id and name. */
3975 result = get_token_information (token, TokenPrimaryGroup,
3976 (LPVOID)buf, blen, &needed);
3977 if (!result && GetLastError () == ERROR_INSUFFICIENT_BUFFER)
3978 {
3979 buf = xrealloc (buf, blen = needed);
3980 result = get_token_information (token, TokenPrimaryGroup,
3981 (LPVOID)buf, blen, &needed);
3982 }
3983 if (result)
3984 {
3985 memcpy (&group_token, buf, sizeof (group_token));
3986 if (!w32_cached_id (group_token.PrimaryGroup, &egid, gname))
3987 {
3988 egid = get_rid (group_token.PrimaryGroup);
3989 dlength = sizeof (domain);
3990 result =
3991 lookup_account_sid (NULL, group_token.PrimaryGroup,
3992 gname, &glength, NULL, &dlength,
3993 &user_type);
3994 if (result)
3995 w32_add_to_cache (group_token.PrimaryGroup,
3996 egid, gname);
3997 else
3998 {
3999 strcpy (gname, "None");
4000 result = TRUE;
4001 }
4002 }
4003 glength = strlen (gname);
4004 }
4005 }
4006 }
4007 if (buf)
4008 xfree (buf);
4009 }
4010 if (!result)
4011 {
4012 if (!is_windows_9x ())
4013 {
4014 /* We couldn't open the process token, presumably because of
4015 insufficient access rights. Assume this process is run
4016 by the system. */
4017 strcpy (uname, "SYSTEM");
4018 strcpy (gname, "None");
4019 euid = 18; /* SYSTEM */
4020 egid = 513; /* None */
4021 glength = strlen (gname);
4022 ulength = strlen (uname);
4023 }
4024 /* If we are running under Windows 9X, where security calls are
4025 not supported, we assume all processes are run by the current
4026 user. */
4027 else if (GetUserName (uname, &ulength))
4028 {
4029 if (xstrcasecmp ("administrator", uname) == 0)
4030 euid = 0;
4031 else
4032 euid = 123;
4033 egid = euid;
4034 strcpy (gname, "None");
4035 glength = strlen (gname);
4036 ulength = strlen (uname);
4037 }
3909 else 4038 else
3910 { 4039 {
3911 lookup_account_sid (NULL, user_token.User.Sid, uname, &ulength, 4040 euid = 123;
3912 domain, &dlength, &user_type); 4041 egid = 123;
3913 euid = get_rid (user_token.User.Sid); 4042 strcpy (uname, "administrator");
3914 w32_add_to_cache (user_token.User.Sid, euid, uname); 4043 ulength = strlen (uname);
3915 } 4044 strcpy (gname, "None");
3916 /* Determine a reasonable euid and gid values. */ 4045 glength = strlen (gname);
3917 if (xstrcasecmp ("administrator", uname) == 0) 4046 }
3918 { 4047 if (token)
3919 euid = 500; /* well-known Administrator uid */ 4048 CloseHandle (token);
3920 egid = 513; /* well-known None gid */ 4049 }
3921 }
3922 else
3923 {
3924 /* Get group id and name. */
3925 if (get_token_information (token, TokenPrimaryGroup,
3926 (PVOID)buf, sizeof (buf), &trash))
3927 {
3928 memcpy (&group_token, buf, sizeof (group_token));
3929 if (w32_cached_id (group_token.PrimaryGroup, &egid, gname))
3930 glength = strlen (gname);
3931 else
3932 {
3933 dlength = sizeof (domain);
3934 lookup_account_sid (NULL, group_token.PrimaryGroup,
3935 gname, &glength, NULL, &dlength,
3936 &user_type);
3937 egid = get_rid (group_token.PrimaryGroup);
3938 w32_add_to_cache (group_token.PrimaryGroup, egid, gname);
3939 }
3940 }
3941 else
3942 egid = euid;
3943 }
3944 }
3945 else if (!is_windows_9x ())
3946 {
3947 /* We couldn't open the process token, presumably because of
3948 insufficient access rights. Assume this process is run by
3949 the system. */
3950 strcpy (uname, "SYSTEM");
3951 strcpy (gname, "None");
3952 euid = 18; /* SYSTEM */
3953 egid = 513; /* None */
3954 glength = strlen (gname);
3955 ulength = strlen (uname);
3956 }
3957 /* If we are running under Windows 9X, where security calls are not
3958 supported, we assume all processes are run by the current
3959 user. */
3960 else if (GetUserName (uname, &ulength))
3961 {
3962 if (xstrcasecmp ("administrator", uname) == 0)
3963 euid = 0;
3964 else
3965 euid = 123;
3966 egid = euid;
3967 strcpy (gname, "None");
3968 glength = strlen (gname);
3969 ulength = strlen (uname);
3970 }
3971 else
3972 {
3973 euid = 123;
3974 egid = 123;
3975 strcpy (uname, "administrator");
3976 ulength = strlen (uname);
3977 strcpy (gname, "None");
3978 glength = strlen (gname);
3979 }
3980 if (token)
3981 CloseHandle (token);
3982 4050
3983 attrs = Fcons (Fcons (Qeuid, make_fixnum_or_float (euid)), attrs); 4051 attrs = Fcons (Fcons (Qeuid, make_fixnum_or_float (euid)), attrs);
3984 tem = make_unibyte_string (uname, ulength); 4052 tem = make_unibyte_string (uname, ulength);
3985 attrs = Fcons (Fcons (Quser, 4053 attrs = Fcons (Fcons (Quser,
3986 code_convert_string_norecord (tem, Vlocale_coding_system, 0)), 4054 code_convert_string_norecord (tem, Vlocale_coding_system, 0)),