base/fs/m_fs_info_win.c
/* Get the user/group and their sids from a security descriptor.
 * \param sd The security descriptor to read the user/group/sids from.
 * \param user[out] The user for the sd. This will return alloced memory that must be freed.
 * \param user_sid[out] A buffer to hold the user's sid.
 * \param user_sid_len The length of the user sid buffer.
 * \param group[out] The group for the sid. This will return alloced memory that must be freed.
 * \param group_sid[out] A buffer to hold the group's sid.
 * \param group_sid_len The length of the group sid buffer.
 * \return Result.
 */
Get the user/group and their sids from a security descriptor.
\param sd The security descriptor to read the user/group/sids from.
\param user[out] The user for the sd. This will return alloced memory that must be freed.
\param user_sid[out] A buffer to hold the user's sid.
\param user_sid_len The length of the user sid buffer.
\param group[out] The group for the sid. This will return alloced memory that must be freed.
\param group_sid[out] A buffer to hold the group's sid.
\param group_sid_len The length of the group sid buffer.
\return Result.
Get the user / group and their sids from a security descriptor . \ param sd The security descriptor to read the user / group / sids from . \ param user [ out ] The user for the sd . This will return alloced memory that must be freed . \ param user_sid [ out ] A buffer to hold the user ' s sid . \ param user_sid_len The length of the user sid buffer . \ param group [ out ] The group for the sid . This will return alloced memory that must be freed . \ param group_sid [ out ] A buffer to hold the group ' s sid . \ param group_sid_len The length of the group sid buffer . \ return Result .
static M_fs_error_t M_fs_info_get_file_user_group(PSECURITY_DESCRIPTOR sd, char **user, PSID user_sid, DWORD user_sid_len, char **group, PSID group_sid, DWORD group_sid_len)
{
	PSID          myuser_sid;
	PSID          mygroup_sid = NULL;
	DWORD         user_len    = 0;
	DWORD         group_len   = 0;
	char          domain[DNLEN+1];
	DWORD         domain_len;
	SID_NAME_USE  sid_use     = SidTypeUnknown;
	BOOL          defaulted;
	LPSTR         sstr;
	if (user != NULL) {
		*user  = NULL;
	}
	if (group != NULL) {
		*group = NULL;
	}
	if (sd == NULL || user == NULL || user_sid == NULL || user_sid_len == 0 || group == NULL || group_sid == NULL || group_sid_len == 0) {
		return M_FS_ERROR_INVALID;
	}
	if (!GetSecurityDescriptorOwner(sd, &myuser_sid, &defaulted)) {
		return M_fs_error_from_syserr(GetLastError());
	}
	if (!GetSecurityDescriptorGroup(sd, &mygroup_sid, &defaulted)) {
		return M_fs_error_from_syserr(GetLastError());
	}
	ConvertSidToStringSid(mygroup_sid, &sstr);
	if (M_str_eq_start(sstr, "S-1-5-21-") && M_str_eq_end(sstr, "513")) {
		mygroup_sid = NULL;
	}
	LocalFree(sstr);
	domain_len = sizeof(domain);
	LookupAccountSid(NULL, myuser_sid, NULL, &user_len, domain, &domain_len, &sid_use);
	if (user_len == 0) {
		return M_fs_error_from_syserr(GetLastError());
	}
	if (mygroup_sid != NULL) {
		domain_len = sizeof(domain);
		LookupAccountSid(NULL, mygroup_sid, NULL, &group_len, domain, &domain_len, &sid_use);
	}
	if (IsValidSid(myuser_sid)) {
		*user = M_malloc(sizeof(**user)*user_len);
		domain_len = sizeof(domain);
		if (!LookupAccountSid(NULL, myuser_sid, *user, &user_len, domain, &domain_len, &sid_use)) {
			M_free(*user);
			*user = NULL;
			return M_fs_error_from_syserr(GetLastError());
		}
		if (sid_use != SidTypeUser && sid_use != SidTypeAlias && sid_use != SidTypeDeletedAccount && sid_use != SidTypeWellKnownGroup) {
			M_free(*user);
			*user = NULL;
			return M_FS_ERROR_INVALID;
		}
		CopySid(user_sid_len, user_sid, myuser_sid);
	} else {
		return M_FS_ERROR_INVALID;
	}
	if (mygroup_sid != NULL && group_len != 0 && IsValidSid(mygroup_sid)) {
		*group = M_malloc(sizeof(**group)*group_len);
		domain_len = sizeof(domain);
		if (LookupAccountSid(NULL, mygroup_sid, *group, &group_len, domain, &domain_len, &sid_use) && (sid_use == SidTypeGroup || sid_use == SidTypeWellKnownGroup)) {
			CopySid(group_sid_len, group_sid, mygroup_sid);
		} else {
			M_free(*group);
			*group = NULL;
		}
	}
	return M_FS_ERROR_SUCCESS;
}
static M_fs_error_t M_fs_info_get_file_user_group ( PSECURITY_DESCRIPTOR sd , char * * user , PSID user_sid , DWORD user_sid_len , char * * group , PSID group_sid , DWORD group_sid_len ) { PSID myuser_sid ; PSID mygroup_sid = NULL ; DWORD user_len = 0 ; DWORD group_len = 0 ; char domain [ DNLEN + 1 ] ; DWORD domain_len ; SID_NAME_USE sid_use = SidTypeUnknown ; BOOL defaulted ; LPSTR sstr ; if ( user != NULL ) { * user = NULL ; } if ( group != NULL ) { * group = NULL ; } if ( sd == NULL || user == NULL || user_sid == NULL || user_sid_len == 0 || group == NULL || group_sid == NULL || group_sid_len == 0 ) { return M_FS_ERROR_INVALID ; } if ( ! GetSecurityDescriptorOwner ( sd , & myuser_sid , & defaulted ) ) { return M_fs_error_from_syserr ( GetLastError ( ) ) ; } if ( ! GetSecurityDescriptorGroup ( sd , & mygroup_sid , & defaulted ) ) { return M_fs_error_from_syserr ( GetLastError ( ) ) ; } ConvertSidToStringSid ( mygroup_sid , & sstr ) ; if ( M_str_eq_start ( sstr , " " ) && M_str_eq_end ( sstr , " " ) ) { mygroup_sid = NULL ; } LocalFree ( sstr ) ; domain_len = sizeof ( domain ) ; LookupAccountSid ( NULL , myuser_sid , NULL , & user_len , domain , & domain_len , & sid_use ) ; if ( user_len == 0 ) { return M_fs_error_from_syserr ( GetLastError ( ) ) ; } if ( mygroup_sid != NULL ) { domain_len = sizeof ( domain ) ; LookupAccountSid ( NULL , mygroup_sid , NULL , & group_len , domain , & domain_len , & sid_use ) ; } if ( IsValidSid ( myuser_sid ) ) { * user = M_malloc ( sizeof ( * * user ) * user_len ) ; domain_len = sizeof ( domain ) ; if ( ! LookupAccountSid ( NULL , myuser_sid , * user , & user_len , domain , & domain_len , & sid_use ) ) { M_free ( * user ) ; * user = NULL ; return M_fs_error_from_syserr ( GetLastError ( ) ) ; } if ( sid_use != SidTypeUser && sid_use != SidTypeAlias && sid_use != SidTypeDeletedAccount && sid_use != SidTypeWellKnownGroup ) { M_free ( * user ) ; * user = NULL ; return M_FS_ERROR_INVALID ; } CopySid ( user_sid_len , user_sid , myuser_sid ) ; } else { return M_FS_ERROR_INVALID ; } if ( mygroup_sid != NULL && group_len != 0 && IsValidSid ( mygroup_sid ) ) { * group = M_malloc ( sizeof ( * * group ) * group_len ) ; domain_len = sizeof ( domain ) ; if ( LookupAccountSid ( NULL , mygroup_sid , * group , & group_len , domain , & domain_len , & sid_use ) && ( sid_use == SidTypeGroup || sid_use == SidTypeWellKnownGroup ) ) { CopySid ( group_sid_len , group_sid , mygroup_sid ) ; } else { M_free ( * group ) ; * group = NULL ; } } return M_FS_ERROR_SUCCESS ; }
Get the user/group and their sids from a security descriptor.
Get the user / group and their sids from a security descriptor .
/* We don't care about the domin but the LookupAccountSid requires a buffer for the domain */ /* Get the user and group sids */ /* Check for the S-1-5-21-<domain>-513 well known group which is a generic group (called None) that every
 	 * user on the system is part of. This isn't an actual group that should have perms read/set. */ /* First get the lengths of the user and group so we know how much memory needs to be allocated to hold them */ /* Find out the length of the user name */ /* Find out the length of the group name */ /* Allocate the memory and call the lookup function again to fill in the user and group names */ /* Verify it looked up the proper type.
		 *
		 * Well known group is included in this check as a valid type because Fat32 doesn't support
		 * user and groups. Windows fills in some default values on this fiel system. It sets the
		 * user sid to 'S-1-1-0' which is 'everyone' and the use to SidTypeWellKnownGroup. We don't
		 * have a way to determine what file system the file/dir is on so we don't have a separate
		 * Fat32 check here. */