2 This driver manages user information and produces user manager protocol.
4 Copyright (c) 2009 - 2018, Intel Corporation. All rights reserved.<BR>
5 (C) Copyright 2018 Hewlett Packard Enterprise Development LP<BR>
6 This program and the accompanying materials
7 are licensed and made available under the terms and conditions of the BSD License
8 which accompanies this distribution. The full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
16 #include "UserIdentifyManager.h"
21 CHAR16 mUserName
[] = L
"Administrator";
24 // Points to the user profile database.
26 USER_PROFILE_DB
*mUserProfileDb
= NULL
;
29 // Points to the credential providers found in system.
31 CREDENTIAL_PROVIDER_INFO
*mProviderDb
= NULL
;
34 // Current user shared in multi function.
36 EFI_USER_PROFILE_HANDLE mCurrentUser
= NULL
;
39 // Flag indicates a user is identified.
41 BOOLEAN mIdentified
= FALSE
;
42 USER_MANAGER_CALLBACK_INFO
*mCallbackInfo
= NULL
;
43 HII_VENDOR_DEVICE_PATH mHiiVendorDevicePath
= {
49 (UINT8
) (sizeof (VENDOR_DEVICE_PATH
)),
50 (UINT8
) ((sizeof (VENDOR_DEVICE_PATH
)) >> 8)
53 USER_IDENTIFY_MANAGER_GUID
57 END_ENTIRE_DEVICE_PATH_SUBTYPE
,
59 (UINT8
) (END_DEVICE_PATH_LENGTH
),
60 (UINT8
) ((END_DEVICE_PATH_LENGTH
) >> 8)
66 EFI_USER_MANAGER_PROTOCOL gUserIdentifyManager
= {
76 UserProfileDeleteInfo
,
77 UserProfileGetNextInfo
,
82 Find the specified user in the user database.
84 This function searches the specified user from the beginning of the user database.
85 And if NextUser is TRUE, return the next User in the user database.
87 @param[in, out] User On entry, points to the user profile entry to search.
88 On return, points to the user profile entry or NULL if not found.
89 @param[in] NextUser If FALSE, find the user in user profile database specifyed by User
90 If TRUE, find the next user in user profile database specifyed
92 @param[out] ProfileIndex A pointer to the index of user profile database that matches the
93 user specifyed by User.
95 @retval EFI_NOT_FOUND User was NULL, or User was not found, or the next user was not found.
96 @retval EFI_SUCCESS User or the next user are found in user profile database
101 IN OUT USER_PROFILE_ENTRY
**User
,
103 OUT UINTN
*ProfileIndex OPTIONAL
111 if ((mUserProfileDb
== NULL
) || (User
== NULL
)) {
112 return EFI_NOT_FOUND
;
116 // Check whether the user profile is in the user profile database.
118 for (Index
= 0; Index
< mUserProfileDb
->UserProfileNum
; Index
++) {
119 if (mUserProfileDb
->UserProfile
[Index
] == *User
) {
120 if (ProfileIndex
!= NULL
) {
121 *ProfileIndex
= Index
;
129 // Find the next user profile.
132 if (Index
< mUserProfileDb
->UserProfileNum
) {
133 *User
= mUserProfileDb
->UserProfile
[Index
];
134 } else if (Index
== mUserProfileDb
->UserProfileNum
) {
136 return EFI_NOT_FOUND
;
138 if ((mUserProfileDb
->UserProfileNum
> 0) && (*User
== NULL
)) {
139 *User
= mUserProfileDb
->UserProfile
[0];
142 return EFI_NOT_FOUND
;
145 } else if (Index
== mUserProfileDb
->UserProfileNum
) {
146 return EFI_NOT_FOUND
;
153 Find the specified user information record in the specified User profile.
155 This function searches the specified user information record from the beginning of the user
156 profile. And if NextInfo is TRUE, return the next info in the user profile.
158 @param[in] User Points to the user profile entry.
159 @param[in, out] Info On entry, points to the user information record or NULL to start
160 searching with the first user information record.
161 On return, points to the user information record or NULL if not found.
162 @param[in] NextInfo If FALSE, find the user information record in profile specifyed by User.
163 If TRUE, find the next user information record in profile specifyed
165 @param[out] Offset A pointer to the offset of the information record in the user profile.
167 @retval EFI_INVALID_PARAMETER Info is NULL
168 @retval EFI_NOT_FOUND Info was not found, or the next Info was not found.
169 @retval EFI_SUCCESS Info or the next info are found in user profile.
174 IN USER_PROFILE_ENTRY
* User
,
175 IN OUT EFI_USER_INFO
**Info
,
177 OUT UINTN
*Offset OPTIONAL
181 EFI_USER_INFO
*UserInfo
;
185 return EFI_INVALID_PARAMETER
;
189 // Check user profile entry
191 Status
= FindUserProfile (&User
, FALSE
, NULL
);
192 if (EFI_ERROR (Status
)) {
197 // Find user information in the specified user record.
200 while (InfoLen
< User
->UserProfileSize
) {
201 UserInfo
= (EFI_USER_INFO
*) (User
->ProfileInfo
+ InfoLen
);
202 if (UserInfo
== *Info
) {
203 if (Offset
!= NULL
) {
208 InfoLen
+= ALIGN_VARIABLE (UserInfo
->InfoSize
);
212 // Check whether to find the next user information.
215 if (InfoLen
< User
->UserProfileSize
) {
216 UserInfo
= (EFI_USER_INFO
*) (User
->ProfileInfo
+ InfoLen
);
217 InfoLen
+= ALIGN_VARIABLE (UserInfo
->InfoSize
);
218 if (InfoLen
< User
->UserProfileSize
) {
219 *Info
= (EFI_USER_INFO
*) (User
->ProfileInfo
+ InfoLen
);
220 if (Offset
!= NULL
) {
223 } else if (InfoLen
== User
->UserProfileSize
) {
225 return EFI_NOT_FOUND
;
229 *Info
= (EFI_USER_INFO
*) User
->ProfileInfo
;
230 if (Offset
!= NULL
) {
235 return EFI_NOT_FOUND
;
238 } else if (InfoLen
== User
->UserProfileSize
) {
239 return EFI_NOT_FOUND
;
246 Find a user infomation record by the information record type.
248 This function searches all user information records of User. The search starts with the
249 user information record following Info and continues until either the information is found
250 or there are no more user infomation record.
251 A match occurs when a Info.InfoType field matches the user information record type.
253 @param[in] User Points to the user profile record to search.
254 @param[in, out] Info On entry, points to the user information record or NULL to start
255 searching with the first user information record.
256 On return, points to the user information record or NULL if not found.
257 @param[in] InfoType The infomation type to be searched.
259 @retval EFI_SUCCESS User information was found. Info points to the user information record.
260 @retval EFI_NOT_FOUND User information was not found.
261 @retval EFI_INVALID_PARAMETER User is NULL or Info is NULL.
266 IN USER_PROFILE_ENTRY
*User
,
267 IN OUT EFI_USER_INFO
**Info
,
272 EFI_USER_INFO
*UserInfo
;
276 return EFI_INVALID_PARAMETER
;
280 // Check whether the user has the specified user information.
284 Status
= FindUserProfile (&User
, FALSE
, NULL
);
286 Status
= FindUserInfo (User
, Info
, TRUE
, &InfoLen
);
289 if (EFI_ERROR (Status
)) {
290 return EFI_NOT_FOUND
;
293 while (InfoLen
< User
->UserProfileSize
) {
294 UserInfo
= (EFI_USER_INFO
*) (User
->ProfileInfo
+ InfoLen
);
295 if (UserInfo
->InfoType
== InfoType
) {
296 if (UserInfo
!= *Info
) {
302 InfoLen
+= ALIGN_VARIABLE (UserInfo
->InfoSize
);
306 return EFI_NOT_FOUND
;
310 Find a user using a user information record.
312 This function searches all user profiles for the specified user information record. The
313 search starts with the user information record handle following UserInfo and continues
314 until either the information is found or there are no more user profiles.
315 A match occurs when the Info.InfoType field matches the user information record type and the
316 user information record data matches the portion of Info passed the EFI_USER_INFO header.
318 @param[in, out] User On entry, points to the previously returned user profile record,
319 or NULL to start searching with the first user profile.
320 On return, points to the user profile entry, or NULL if not found.
321 @param[in, out] UserInfo On entry, points to the previously returned user information record,
322 or NULL to start searching with the first.
323 On return, points to the user information record, or NULL if not found.
324 @param[in] Info Points to the buffer containing the user information to be compared
325 to the user information record.
326 @param[in] InfoSize The size of Info, in bytes. Same as Info->InfoSize.
328 @retval EFI_SUCCESS User information was found. User points to the user profile record,
329 and UserInfo points to the user information record.
330 @retval EFI_NOT_FOUND User information was not found.
331 @retval EFI_INVALID_PARAMETER User is NULL; Info is NULL; or, InfoSize is too small.
335 FindUserProfileByInfo (
336 IN OUT USER_PROFILE_ENTRY
**User
,
337 IN OUT EFI_USER_INFO
**UserInfo
, OPTIONAL
338 IN EFI_USER_INFO
*Info
,
343 EFI_USER_INFO
*InfoEntry
;
346 if ((User
== NULL
) || (Info
== NULL
)) {
347 return EFI_INVALID_PARAMETER
;
350 if (InfoSize
< sizeof (EFI_USER_INFO
)) {
351 return EFI_INVALID_PARAMETER
;
354 if (UserInfo
!= NULL
) {
355 InfoEntry
= *UserInfo
;
360 // Find user profile according to information.
363 *User
= mUserProfileDb
->UserProfile
[0];
367 // Check user profile handle.
369 Status
= FindUserProfile (User
, FALSE
, NULL
);
371 while (!EFI_ERROR (Status
)) {
373 // Find the user information in a user profile.
376 Status
= FindUserInfoByType (*User
, &InfoEntry
, Info
->InfoType
);
377 if (EFI_ERROR (Status
)) {
381 if (InfoSize
== Info
->InfoSize
) {
382 if (CompareMem ((UINT8
*) (InfoEntry
+ 1), (UINT8
*) (Info
+ 1), InfoSize
- sizeof (EFI_USER_INFO
)) == 0) {
384 // Found the infomation record.
386 if (UserInfo
!= NULL
) {
387 *UserInfo
= InfoEntry
;
395 // Get next user profile.
398 Status
= FindUserProfile (User
, TRUE
, NULL
);
401 return EFI_NOT_FOUND
;
406 Check whether the access policy is valid.
408 @param[in] PolicyInfo Point to the access policy.
409 @param[in] InfoLen The policy length.
411 @retval TRUE The policy is a valid access policy.
412 @retval FALSE The access policy is not a valid access policy.
417 IN UINT8
*PolicyInfo
,
424 EFI_USER_INFO_ACCESS_CONTROL Access
;
425 EFI_DEVICE_PATH_PROTOCOL
*Path
;
429 while (TotalLen
< InfoLen
) {
431 // Check access policy according to type.
433 CopyMem (&Access
, PolicyInfo
+ TotalLen
, sizeof (Access
));
434 ValueLen
= Access
.Size
- sizeof (EFI_USER_INFO_ACCESS_CONTROL
);
435 switch (Access
.Type
) {
436 case EFI_USER_INFO_ACCESS_FORBID_LOAD
:
437 case EFI_USER_INFO_ACCESS_PERMIT_LOAD
:
438 case EFI_USER_INFO_ACCESS_FORBID_CONNECT
:
439 case EFI_USER_INFO_ACCESS_PERMIT_CONNECT
:
441 while (OffSet
< ValueLen
) {
442 Path
= (EFI_DEVICE_PATH_PROTOCOL
*) (PolicyInfo
+ TotalLen
+ sizeof (Access
) + OffSet
);
443 PathSize
= GetDevicePathSize (Path
);
446 if (OffSet
!= ValueLen
) {
451 case EFI_USER_INFO_ACCESS_SETUP
:
452 if (ValueLen
% sizeof (EFI_GUID
) != 0) {
457 case EFI_USER_INFO_ACCESS_BOOT_ORDER
:
458 if (ValueLen
% sizeof (EFI_USER_INFO_ACCESS_BOOT_ORDER_HDR
) != 0) {
463 case EFI_USER_INFO_ACCESS_ENROLL_SELF
:
464 case EFI_USER_INFO_ACCESS_ENROLL_OTHERS
:
465 case EFI_USER_INFO_ACCESS_MANAGE
:
476 TotalLen
+= Access
.Size
;
479 if (TotalLen
!= InfoLen
) {
488 Check whether the identity policy is valid.
490 @param[in] PolicyInfo Point to the identity policy.
491 @param[in] InfoLen The policy length.
493 @retval TRUE The policy is a valid identity policy.
494 @retval FALSE The access policy is not a valid identity policy.
498 CheckIdentityPolicy (
499 IN UINT8
*PolicyInfo
,
505 EFI_USER_INFO_IDENTITY_POLICY
*Identity
;
510 // Check each part of policy expression.
512 while (TotalLen
< InfoLen
) {
514 // Check access polisy according to type.
516 Identity
= (EFI_USER_INFO_IDENTITY_POLICY
*) (PolicyInfo
+ TotalLen
);
517 ValueLen
= Identity
->Length
- sizeof (EFI_USER_INFO_IDENTITY_POLICY
);
518 switch (Identity
->Type
) {
520 // Check False option.
522 case EFI_USER_INFO_IDENTITY_FALSE
:
529 // Check True option.
531 case EFI_USER_INFO_IDENTITY_TRUE
:
538 // Check negative operation.
540 case EFI_USER_INFO_IDENTITY_NOT
:
547 // Check and operation.
549 case EFI_USER_INFO_IDENTITY_AND
:
556 // Check or operation.
558 case EFI_USER_INFO_IDENTITY_OR
:
565 // Check credential provider by type.
567 case EFI_USER_INFO_IDENTITY_CREDENTIAL_TYPE
:
568 if (ValueLen
!= sizeof (EFI_GUID
)) {
574 // Check credential provider by ID.
576 case EFI_USER_INFO_IDENTITY_CREDENTIAL_PROVIDER
:
577 if (ValueLen
!= sizeof (EFI_GUID
)) {
587 TotalLen
+= Identity
->Length
;
590 if (TotalLen
!= InfoLen
) {
599 Check whether the user information is a valid user information record.
601 @param[in] Info points to the user information.
603 @retval TRUE The info is a valid user information record.
604 @retval FALSE The info is not a valid user information record.
609 IN CONST EFI_USER_INFO
*Info
618 // Check user information according to information type.
620 InfoLen
= Info
->InfoSize
- sizeof (EFI_USER_INFO
);
621 switch (Info
->InfoType
) {
622 case EFI_USER_INFO_EMPTY_RECORD
:
628 case EFI_USER_INFO_NAME_RECORD
:
629 case EFI_USER_INFO_CREDENTIAL_TYPE_NAME_RECORD
:
630 case EFI_USER_INFO_CREDENTIAL_PROVIDER_NAME_RECORD
:
633 case EFI_USER_INFO_CREATE_DATE_RECORD
:
634 case EFI_USER_INFO_USAGE_DATE_RECORD
:
635 if (InfoLen
!= sizeof (EFI_TIME
)) {
640 case EFI_USER_INFO_USAGE_COUNT_RECORD
:
641 if (InfoLen
!= sizeof (UINT64
)) {
646 case EFI_USER_INFO_IDENTIFIER_RECORD
:
652 case EFI_USER_INFO_CREDENTIAL_TYPE_RECORD
:
653 case EFI_USER_INFO_CREDENTIAL_PROVIDER_RECORD
:
654 case EFI_USER_INFO_GUID_RECORD
:
655 if (InfoLen
!= sizeof (EFI_GUID
)) {
660 case EFI_USER_INFO_PKCS11_RECORD
:
661 case EFI_USER_INFO_CBEFF_RECORD
:
664 case EFI_USER_INFO_FAR_RECORD
:
665 case EFI_USER_INFO_RETRY_RECORD
:
671 case EFI_USER_INFO_ACCESS_POLICY_RECORD
:
672 if(!CheckAccessPolicy ((UINT8
*) (Info
+ 1), InfoLen
)) {
677 case EFI_USER_INFO_IDENTITY_POLICY_RECORD
:
678 if (!CheckIdentityPolicy ((UINT8
*) (Info
+ 1), InfoLen
)) {
693 Check the user profile data format to be added.
695 @param[in] UserProfileInfo Points to the user profile data.
696 @param[in] UserProfileSize The length of user profile data.
698 @retval TRUE It is a valid user profile.
699 @retval FALSE It is not a valid user profile.
704 IN UINT8
*UserProfileInfo
,
705 IN UINTN UserProfileSize
711 if (UserProfileInfo
== NULL
) {
716 // Check user profile information length.
719 while (ChkLen
< UserProfileSize
) {
720 Info
= (EFI_USER_INFO
*) (UserProfileInfo
+ ChkLen
);
722 // Check user information format.
724 if (!CheckUserInfo (Info
)) {
728 ChkLen
+= ALIGN_VARIABLE (Info
->InfoSize
);
731 if (ChkLen
!= UserProfileSize
) {
740 Find the specified RightType in current user profile.
742 @param[in] RightType Could be EFI_USER_INFO_ACCESS_MANAGE,
743 EFI_USER_INFO_ACCESS_ENROLL_OTHERS or
744 EFI_USER_INFO_ACCESS_ENROLL_SELF.
746 @retval TRUE Find the specified RightType in current user profile.
747 @retval FALSE Can't find the right in the profile.
751 CheckCurrentUserAccessRight (
759 EFI_USER_INFO_ACCESS_CONTROL Access
;
762 // Get user access right information.
765 Status
= FindUserInfoByType (
766 (USER_PROFILE_ENTRY
*) mCurrentUser
,
768 EFI_USER_INFO_ACCESS_POLICY_RECORD
770 if (EFI_ERROR (Status
)) {
774 ASSERT (Info
!= NULL
);
775 TotalLen
= Info
->InfoSize
- sizeof (EFI_USER_INFO
);
777 while (CheckLen
< TotalLen
) {
779 // Check right according to access type.
781 CopyMem (&Access
, (UINT8
*) (Info
+ 1) + CheckLen
, sizeof (Access
));
782 if (Access
.Type
== RightType
) {
786 CheckLen
+= Access
.Size
;
794 Create a unique user identifier.
796 @param[out] Identifier This points to the identifier.
801 OUT UINT8
*Identifier
805 UINT64 MonotonicCount
;
806 UINT32
*MonotonicPointer
;
810 // Create a unique user identifier.
812 gRT
->GetTime (&Time
, NULL
);
813 CopyMem (Identifier
, &Time
, sizeof (EFI_TIME
));
817 for (Index
= 0; Index
< sizeof (EFI_TIME
); Index
++) {
818 if (Identifier
[Index
] == 0) {
819 Identifier
[Index
] = 0x5a;
823 MonotonicPointer
= (UINT32
*) Identifier
;
824 gBS
->GetNextMonotonicCount (&MonotonicCount
);
825 MonotonicPointer
[0] += (UINT32
) MonotonicCount
;
826 MonotonicPointer
[1] += (UINT32
) MonotonicCount
;
827 MonotonicPointer
[2] += (UINT32
) MonotonicCount
;
828 MonotonicPointer
[3] += (UINT32
) MonotonicCount
;
833 Generate unique user ID.
835 @param[out] UserId Points to the user identifer.
844 USER_PROFILE_ENTRY
*UserProfile
;
845 EFI_USER_INFO
*UserInfo
;
849 // Generate unique user ID
852 GenerateIdentifier (UserId
);
854 // Check whether it's unique in user profile database.
856 if (mUserProfileDb
== NULL
) {
860 for (Index
= 0; Index
< mUserProfileDb
->UserProfileNum
; Index
++) {
861 UserProfile
= (USER_PROFILE_ENTRY
*) (mUserProfileDb
->UserProfile
[Index
]);
863 Status
= FindUserInfoByType (UserProfile
, &UserInfo
, EFI_USER_INFO_IDENTIFIER_RECORD
);
864 if (EFI_ERROR (Status
)) {
868 if (CompareMem ((UINT8
*) (UserInfo
+ 1), UserId
, sizeof (EFI_USER_INFO_IDENTIFIER
)) == 0) {
873 if (Index
== mUserProfileDb
->UserProfileNum
) {
881 Expand user profile database.
883 @retval TRUE Success to expand user profile database.
884 @retval FALSE Fail to expand user profile database.
888 ExpandUsermUserProfileDb (
893 USER_PROFILE_DB
*NewDataBase
;
896 // Create new user profile database.
898 if (mUserProfileDb
== NULL
) {
899 MaxNum
= USER_NUMBER_INC
;
901 MaxNum
= mUserProfileDb
->MaxProfileNum
+ USER_NUMBER_INC
;
904 NewDataBase
= AllocateZeroPool (
905 sizeof (USER_PROFILE_DB
) - sizeof (EFI_USER_PROFILE_HANDLE
) +
906 MaxNum
* sizeof (EFI_USER_PROFILE_HANDLE
)
908 if (NewDataBase
== NULL
) {
912 NewDataBase
->MaxProfileNum
= MaxNum
;
915 // Copy old user profile database value
917 if (mUserProfileDb
== NULL
) {
918 NewDataBase
->UserProfileNum
= 0;
920 NewDataBase
->UserProfileNum
= mUserProfileDb
->UserProfileNum
;
922 NewDataBase
->UserProfile
,
923 mUserProfileDb
->UserProfile
,
924 NewDataBase
->UserProfileNum
* sizeof (EFI_USER_PROFILE_HANDLE
)
926 FreePool (mUserProfileDb
);
929 mUserProfileDb
= NewDataBase
;
937 @param[in] User Points to user profile.
938 @param[in] ExpandSize The size of user profile.
940 @retval TRUE Success to expand user profile size.
941 @retval FALSE Fail to expand user profile size.
946 IN USER_PROFILE_ENTRY
*User
,
954 // Allocate new memory.
957 User
->MaxProfileSize
+= ((ExpandSize
+ InfoSizeInc
- 1) / InfoSizeInc
) * InfoSizeInc
;
958 Info
= AllocateZeroPool (User
->MaxProfileSize
);
964 // Copy exist information.
966 if (User
->UserProfileSize
> 0) {
967 CopyMem (Info
, User
->ProfileInfo
, User
->UserProfileSize
);
968 FreePool (User
->ProfileInfo
);
971 User
->ProfileInfo
= Info
;
977 Save the user profile to non-volatile memory, or delete it from non-volatile memory.
979 @param[in] User Point to the user profile
980 @param[in] Delete If TRUE, delete the found user profile.
981 If FALSE, save the user profile.
982 @retval EFI_SUCCESS Save or delete user profile successfully.
983 @retval Others Fail to change the profile.
988 IN USER_PROFILE_ENTRY
*User
,
995 // Check user profile entry.
997 Status
= FindUserProfile (&User
, FALSE
, NULL
);
998 if (EFI_ERROR (Status
)) {
1003 // Save the user profile to non-volatile memory.
1005 Status
= gRT
->SetVariable (
1007 &gUserIdentifyManagerGuid
,
1008 EFI_VARIABLE_NON_VOLATILE
| EFI_VARIABLE_BOOTSERVICE_ACCESS
,
1009 Delete
? 0 : User
->UserProfileSize
,
1016 Add one new user info into the user's profile.
1018 @param[in] User point to the user profile
1019 @param[in] Info Points to the user information payload.
1020 @param[in] InfoSize The size of the user information payload, in bytes.
1021 @param[out] UserInfo Point to the new info in user profile
1022 @param[in] Save If TRUE, save the profile to NV flash.
1023 If FALSE, don't need to save the profile to NV flash.
1025 @retval EFI_SUCCESS Add user info to user profile successfully.
1026 @retval Others Fail to add user info to user profile.
1031 IN USER_PROFILE_ENTRY
*User
,
1034 OUT EFI_USER_INFO
**UserInfo
, OPTIONAL
1040 if ((Info
== NULL
) || (User
== NULL
)) {
1041 return EFI_INVALID_PARAMETER
;
1045 // Check user profile handle.
1047 Status
= FindUserProfile (&User
, FALSE
, NULL
);
1048 if (EFI_ERROR (Status
)) {
1053 // Check user information memory size.
1055 if (User
->MaxProfileSize
- User
->UserProfileSize
< ALIGN_VARIABLE (InfoSize
)) {
1056 if (!ExpandUserProfile (User
, ALIGN_VARIABLE (InfoSize
))) {
1057 return EFI_OUT_OF_RESOURCES
;
1062 // Add new user information.
1064 CopyMem (User
->ProfileInfo
+ User
->UserProfileSize
, Info
, InfoSize
);
1065 if (UserInfo
!= NULL
) {
1066 *UserInfo
= (EFI_USER_INFO
*) (User
->ProfileInfo
+ User
->UserProfileSize
);
1068 User
->UserProfileSize
+= ALIGN_VARIABLE (InfoSize
);
1071 // Save user profile information.
1074 Status
= SaveNvUserProfile (User
, FALSE
);
1082 Get the user info from the specified user info handle.
1084 @param[in] User Point to the user profile.
1085 @param[in] UserInfo Point to the user information record to get.
1086 @param[out] Info On entry, points to a buffer of at least *InfoSize bytes.
1087 On exit, holds the user information.
1088 @param[in, out] InfoSize On entry, points to the size of Info.
1089 On return, points to the size of the user information.
1090 @param[in] ChkRight If TRUE, check the user info attribute.
1091 If FALSE, don't check the user info attribute.
1094 @retval EFI_ACCESS_DENIED The information cannot be accessed by the current user.
1095 @retval EFI_INVALID_PARAMETER InfoSize is NULL or UserInfo is NULL.
1096 @retval EFI_BUFFER_TOO_SMALL The number of bytes specified by *InfoSize is too small to hold the
1097 returned data. The actual size required is returned in *InfoSize.
1098 @retval EFI_SUCCESS Information returned successfully.
1103 IN USER_PROFILE_ENTRY
*User
,
1104 IN EFI_USER_INFO
*UserInfo
,
1105 OUT EFI_USER_INFO
*Info
,
1106 IN OUT UINTN
*InfoSize
,
1112 if ((InfoSize
== NULL
) || (UserInfo
== NULL
)) {
1113 return EFI_INVALID_PARAMETER
;
1116 if ((*InfoSize
!= 0) && (Info
== NULL
)) {
1117 return EFI_INVALID_PARAMETER
;
1121 // Find the user information to get.
1123 Status
= FindUserInfo (User
, &UserInfo
, FALSE
, NULL
);
1124 if (EFI_ERROR (Status
)) {
1129 // Check information attributes.
1132 switch (UserInfo
->InfoAttribs
& EFI_USER_INFO_ACCESS
) {
1133 case EFI_USER_INFO_PRIVATE
:
1134 case EFI_USER_INFO_PROTECTED
:
1135 if (User
!= mCurrentUser
) {
1136 return EFI_ACCESS_DENIED
;
1140 case EFI_USER_INFO_PUBLIC
:
1144 return EFI_INVALID_PARAMETER
;
1150 // Get user information.
1152 if (UserInfo
->InfoSize
> *InfoSize
) {
1153 *InfoSize
= UserInfo
->InfoSize
;
1154 return EFI_BUFFER_TOO_SMALL
;
1157 *InfoSize
= UserInfo
->InfoSize
;
1159 CopyMem (Info
, UserInfo
, *InfoSize
);
1167 Delete the specified user information from user profile.
1169 @param[in] User Point to the user profile.
1170 @param[in] Info Point to the user information record to delete.
1171 @param[in] Save If TRUE, save the profile to NV flash.
1172 If FALSE, don't need to save the profile to NV flash.
1174 @retval EFI_SUCCESS Delete user info from user profile successfully.
1175 @retval Others Fail to delete user info from user profile.
1180 IN USER_PROFILE_ENTRY
*User
,
1181 IN EFI_USER_INFO
*Info
,
1190 // Check user information handle.
1192 Status
= FindUserInfo (User
, &Info
, FALSE
, &Offset
);
1193 if (EFI_ERROR (Status
)) {
1197 if (Info
->InfoType
== EFI_USER_INFO_IDENTIFIER_RECORD
) {
1198 return EFI_ACCESS_DENIED
;
1202 // Delete the specified user information.
1204 NextOffset
= Offset
+ ALIGN_VARIABLE (Info
->InfoSize
);
1205 User
->UserProfileSize
-= ALIGN_VARIABLE (Info
->InfoSize
);
1206 if (Offset
< User
->UserProfileSize
) {
1207 CopyMem (User
->ProfileInfo
+ Offset
, User
->ProfileInfo
+ NextOffset
, User
->UserProfileSize
- Offset
);
1211 Status
= SaveNvUserProfile (User
, FALSE
);
1219 Add or update user information.
1221 @param[in] User Point to the user profile.
1222 @param[in, out] UserInfo On entry, points to the user information to modify,
1223 or NULL to add a new UserInfo.
1224 On return, points to the modified user information.
1225 @param[in] Info Points to the new user information.
1226 @param[in] InfoSize The size of Info,in bytes.
1228 @retval EFI_INVALID_PARAMETER UserInfo is NULL or Info is NULL.
1229 @retval EFI_ACCESS_DENIED The record is exclusive.
1230 @retval EFI_SUCCESS User information was successfully changed/added.
1235 IN USER_PROFILE_ENTRY
*User
,
1236 IN OUT EFI_USER_INFO
**UserInfo
,
1237 IN CONST EFI_USER_INFO
*Info
,
1243 EFI_USER_INFO
*OldInfo
;
1245 if ((UserInfo
== NULL
) || (Info
== NULL
)) {
1246 return EFI_INVALID_PARAMETER
;
1249 if (InfoSize
< sizeof (EFI_USER_INFO
) || InfoSize
!= Info
->InfoSize
) {
1250 return EFI_INVALID_PARAMETER
;
1254 // Check user information.
1256 if (Info
->InfoType
== EFI_USER_INFO_IDENTIFIER_RECORD
) {
1257 return EFI_ACCESS_DENIED
;
1260 if (!CheckUserInfo (Info
)) {
1261 return EFI_INVALID_PARAMETER
;
1265 if (*UserInfo
== NULL
) {
1267 // Add new user information.
1271 Status
= FindUserInfoByType (User
, &OldInfo
, Info
->InfoType
);
1272 if (EFI_ERROR (Status
)) {
1275 ASSERT (OldInfo
!= NULL
);
1277 if (((OldInfo
->InfoAttribs
& EFI_USER_INFO_EXCLUSIVE
) != 0) ||
1278 ((Info
->InfoAttribs
& EFI_USER_INFO_EXCLUSIVE
) != 0)) {
1280 // Same type can not co-exist for exclusive information.
1282 return EFI_ACCESS_DENIED
;
1286 // Check whether it exists in DB.
1288 if (Info
->InfoSize
!= OldInfo
->InfoSize
) {
1292 if (!CompareGuid (&OldInfo
->Credential
, &Info
->Credential
)) {
1296 PayloadLen
= Info
->InfoSize
- sizeof (EFI_USER_INFO
);
1297 if (PayloadLen
== 0) {
1301 if (CompareMem ((UINT8
*)(OldInfo
+ 1), (UINT8
*)(Info
+ 1), PayloadLen
) != 0) {
1306 // Yes. The new info is as same as the one in profile.
1309 } while (!EFI_ERROR (Status
));
1311 Status
= AddUserInfo (User
, (UINT8
*) Info
, InfoSize
, UserInfo
, TRUE
);
1316 // Modify existing user information.
1318 OldInfo
= *UserInfo
;
1319 if (OldInfo
->InfoType
!= Info
->InfoType
) {
1320 return EFI_INVALID_PARAMETER
;
1323 if (((Info
->InfoAttribs
& EFI_USER_INFO_EXCLUSIVE
) != 0) &&
1324 (OldInfo
->InfoAttribs
& EFI_USER_INFO_EXCLUSIVE
) == 0) {
1326 // Try to add exclusive attrib in new info.
1327 // Check whether there is another information with the same type in profile.
1331 Status
= FindUserInfoByType (User
, &OldInfo
, Info
->InfoType
);
1332 if (EFI_ERROR (Status
)) {
1335 if (OldInfo
!= *UserInfo
) {
1337 // There is another information with the same type in profile.
1338 // Therefore, can't modify existing user information to add exclusive attribute.
1340 return EFI_ACCESS_DENIED
;
1345 Status
= DelUserInfo (User
, *UserInfo
, FALSE
);
1346 if (EFI_ERROR (Status
)) {
1350 return AddUserInfo (User
, (UINT8
*) Info
, InfoSize
, UserInfo
, TRUE
);
1355 Delete the user profile from non-volatile memory and database.
1357 @param[in] User Points to the user profile.
1359 @retval EFI_SUCCESS Delete user from the user profile successfully.
1360 @retval Others Fail to delete user from user profile
1365 IN USER_PROFILE_ENTRY
*User
1372 // Check whether it is in the user profile database.
1374 Status
= FindUserProfile (&User
, FALSE
, &Index
);
1375 if (EFI_ERROR (Status
)) {
1376 return EFI_INVALID_PARAMETER
;
1380 // Check whether it is the current user.
1382 if (User
== mCurrentUser
) {
1383 return EFI_ACCESS_DENIED
;
1387 // Delete user profile from the non-volatile memory.
1389 Status
= SaveNvUserProfile (mUserProfileDb
->UserProfile
[mUserProfileDb
->UserProfileNum
- 1], TRUE
);
1390 if (EFI_ERROR (Status
)) {
1393 mUserProfileDb
->UserProfileNum
--;
1396 // Modify user profile database.
1398 if (Index
!= mUserProfileDb
->UserProfileNum
) {
1399 mUserProfileDb
->UserProfile
[Index
] = mUserProfileDb
->UserProfile
[mUserProfileDb
->UserProfileNum
];
1401 ((USER_PROFILE_ENTRY
*) mUserProfileDb
->UserProfile
[Index
])->UserVarName
,
1403 sizeof (User
->UserVarName
)
1405 Status
= SaveNvUserProfile (mUserProfileDb
->UserProfile
[Index
], FALSE
);
1406 if (EFI_ERROR (Status
)) {
1411 // Delete user profile information.
1413 if (User
->ProfileInfo
!= NULL
) {
1414 FreePool (User
->ProfileInfo
);
1423 Add user profile to user profile database.
1425 @param[out] UserProfile Point to the newly added user profile.
1426 @param[in] ProfileSize The size of the user profile.
1427 @param[in] ProfileInfo Point to the user profie data.
1428 @param[in] Save If TRUE, save the new added profile to NV flash.
1429 If FALSE, don't save the profile to NV flash.
1431 @retval EFI_SUCCESS Add user profile to user profile database successfully.
1432 @retval Others Fail to add user profile to user profile database.
1437 OUT USER_PROFILE_ENTRY
**UserProfile
, OPTIONAL
1438 IN UINTN ProfileSize
,
1439 IN UINT8
*ProfileInfo
,
1444 USER_PROFILE_ENTRY
*User
;
1447 // Check the data format to be added.
1449 if (!CheckProfileInfo (ProfileInfo
, ProfileSize
)) {
1450 return EFI_SECURITY_VIOLATION
;
1454 // Create user profile entry.
1456 User
= AllocateZeroPool (sizeof (USER_PROFILE_ENTRY
));
1458 return EFI_OUT_OF_RESOURCES
;
1461 // Add the entry to the user profile database.
1463 if (mUserProfileDb
->UserProfileNum
== mUserProfileDb
->MaxProfileNum
) {
1464 if (!ExpandUsermUserProfileDb ()) {
1466 return EFI_OUT_OF_RESOURCES
;
1472 sizeof (User
->UserVarName
),
1474 mUserProfileDb
->UserProfileNum
1476 User
->UserProfileSize
= 0;
1477 User
->MaxProfileSize
= 0;
1478 User
->ProfileInfo
= NULL
;
1479 mUserProfileDb
->UserProfile
[mUserProfileDb
->UserProfileNum
] = (EFI_USER_PROFILE_HANDLE
) User
;
1480 mUserProfileDb
->UserProfileNum
++;
1483 // Add user profile information.
1485 Status
= AddUserInfo (User
, ProfileInfo
, ProfileSize
, NULL
, Save
);
1486 if (EFI_ERROR (Status
)) {
1487 DelUserProfile (User
);
1491 // Set new user profile handle.
1493 if (UserProfile
!= NULL
) {
1494 *UserProfile
= User
;
1502 This function creates a new user profile with only a new user identifier
1503 attached and returns its handle. The user profile is non-volatile, but the
1504 handle User can change across reboots.
1506 @param[out] User Handle of a new user profile.
1508 @retval EFI_SUCCESS User profile was successfully created.
1509 @retval Others Fail to create user profile
1514 OUT USER_PROFILE_ENTRY
**User
1518 EFI_USER_INFO
*UserInfo
;
1521 return EFI_INVALID_PARAMETER
;
1524 // Generate user id information.
1526 UserInfo
= AllocateZeroPool (sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_IDENTIFIER
));
1527 if (UserInfo
== NULL
) {
1528 return EFI_OUT_OF_RESOURCES
;
1531 UserInfo
->InfoType
= EFI_USER_INFO_IDENTIFIER_RECORD
;
1532 UserInfo
->InfoSize
= sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_IDENTIFIER
);
1533 UserInfo
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PUBLIC
| EFI_USER_INFO_EXCLUSIVE
;
1534 GenerateUserId ((UINT8
*) (UserInfo
+ 1));
1537 // Add user profile to the user profile database.
1539 Status
= AddUserProfile (User
, UserInfo
->InfoSize
, (UINT8
*) UserInfo
, TRUE
);
1540 FreePool (UserInfo
);
1546 Add a default user profile to user profile database.
1548 @retval EFI_SUCCESS A default user profile is added successfully.
1549 @retval Others Fail to add a default user profile
1553 AddDefaultUserProfile (
1558 USER_PROFILE_ENTRY
*User
;
1559 EFI_USER_INFO
*Info
;
1560 EFI_USER_INFO
*NewInfo
;
1561 EFI_USER_INFO_CREATE_DATE CreateDate
;
1562 EFI_USER_INFO_USAGE_COUNT UsageCount
;
1563 EFI_USER_INFO_ACCESS_CONTROL
*Access
;
1564 EFI_USER_INFO_IDENTITY_POLICY
*Policy
;
1567 // Create a user profile.
1569 Status
= CreateUserProfile (&User
);
1570 if (EFI_ERROR (Status
)) {
1575 // Allocate a buffer to add all default user information.
1577 Info
= AllocateZeroPool (sizeof (EFI_USER_INFO
) + INFO_PAYLOAD_SIZE
);
1579 return EFI_OUT_OF_RESOURCES
;
1585 Info
->InfoType
= EFI_USER_INFO_NAME_RECORD
;
1586 Info
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PUBLIC
| EFI_USER_INFO_EXCLUSIVE
;
1587 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + sizeof (mUserName
);
1588 CopyMem ((UINT8
*) (Info
+ 1), mUserName
, sizeof (mUserName
));
1590 Status
= ModifyUserInfo (User
, &NewInfo
, Info
, Info
->InfoSize
);
1591 if (EFI_ERROR (Status
)) {
1596 // Add user profile create date record.
1598 Info
->InfoType
= EFI_USER_INFO_CREATE_DATE_RECORD
;
1599 Info
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PUBLIC
| EFI_USER_INFO_EXCLUSIVE
;
1600 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_CREATE_DATE
);
1601 Status
= gRT
->GetTime (&CreateDate
, NULL
);
1602 if (EFI_ERROR (Status
)) {
1606 CopyMem ((UINT8
*) (Info
+ 1), &CreateDate
, sizeof (EFI_USER_INFO_CREATE_DATE
));
1608 Status
= ModifyUserInfo (User
, &NewInfo
, Info
, Info
->InfoSize
);
1609 if (EFI_ERROR (Status
)) {
1614 // Add user profile usage count record.
1616 Info
->InfoType
= EFI_USER_INFO_USAGE_COUNT_RECORD
;
1617 Info
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PUBLIC
| EFI_USER_INFO_EXCLUSIVE
;
1618 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_USAGE_COUNT
);
1620 CopyMem ((UINT8
*) (Info
+ 1), &UsageCount
, sizeof (EFI_USER_INFO_USAGE_COUNT
));
1622 Status
= ModifyUserInfo (User
, &NewInfo
, Info
, Info
->InfoSize
);
1623 if (EFI_ERROR (Status
)) {
1628 // Add user access right.
1630 Info
->InfoType
= EFI_USER_INFO_ACCESS_POLICY_RECORD
;
1631 Info
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PUBLIC
| EFI_USER_INFO_EXCLUSIVE
;
1632 Access
= (EFI_USER_INFO_ACCESS_CONTROL
*) (Info
+ 1);
1633 Access
->Type
= EFI_USER_INFO_ACCESS_MANAGE
;
1634 Access
->Size
= sizeof (EFI_USER_INFO_ACCESS_CONTROL
);
1635 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + Access
->Size
;
1637 Status
= ModifyUserInfo (User
, &NewInfo
, Info
, Info
->InfoSize
);
1638 if (EFI_ERROR (Status
)) {
1643 // Add user identity policy.
1645 Info
->InfoType
= EFI_USER_INFO_IDENTITY_POLICY_RECORD
;
1646 Info
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PRIVATE
| EFI_USER_INFO_EXCLUSIVE
;
1647 Policy
= (EFI_USER_INFO_IDENTITY_POLICY
*) (Info
+ 1);
1648 Policy
->Type
= EFI_USER_INFO_IDENTITY_TRUE
;
1649 Policy
->Length
= sizeof (EFI_USER_INFO_IDENTITY_POLICY
);
1650 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + Policy
->Length
;
1652 Status
= ModifyUserInfo (User
, &NewInfo
, Info
, Info
->InfoSize
);
1661 Publish current user information into EFI System Configuration Table.
1663 By UEFI spec, the User Identity Manager will publish the current user profile
1664 into the EFI System Configuration Table. Currently, only the user identifier and user
1667 @retval EFI_SUCCESS Current user information is published successfully.
1668 @retval Others Fail to publish current user information
1677 EFI_CONFIGURATION_TABLE
*EfiConfigurationTable
;
1678 EFI_USER_INFO_TABLE
*UserInfoTable
;
1679 EFI_USER_INFO
*IdInfo
;
1680 EFI_USER_INFO
*NameInfo
;
1682 Status
= EfiGetSystemConfigurationTable (
1683 &gEfiUserManagerProtocolGuid
,
1684 (VOID
**) &EfiConfigurationTable
1686 if (!EFI_ERROR (Status
)) {
1688 // The table existed!
1694 // Get user ID information.
1697 Status
= FindUserInfoByType (mCurrentUser
, &IdInfo
, EFI_USER_INFO_IDENTIFIER_RECORD
);
1698 if (EFI_ERROR (Status
)) {
1703 // Get user name information.
1706 Status
= FindUserInfoByType (mCurrentUser
, &NameInfo
, EFI_USER_INFO_NAME_RECORD
);
1707 if (EFI_ERROR (Status
)) {
1712 // Allocate a buffer for user information table.
1714 UserInfoTable
= (EFI_USER_INFO_TABLE
*) AllocateRuntimePool (
1715 sizeof (EFI_USER_INFO_TABLE
) +
1719 if (UserInfoTable
== NULL
) {
1720 Status
= EFI_OUT_OF_RESOURCES
;
1724 UserInfoTable
->Size
= sizeof (EFI_USER_INFO_TABLE
);
1727 // Append the user information to the user info table
1729 CopyMem ((UINT8
*) UserInfoTable
+ UserInfoTable
->Size
, (UINT8
*) IdInfo
, IdInfo
->InfoSize
);
1730 UserInfoTable
->Size
+= IdInfo
->InfoSize
;
1732 CopyMem ((UINT8
*) UserInfoTable
+ UserInfoTable
->Size
, (UINT8
*) NameInfo
, NameInfo
->InfoSize
);
1733 UserInfoTable
->Size
+= NameInfo
->InfoSize
;
1735 Status
= gBS
->InstallConfigurationTable (&gEfiUserManagerProtocolGuid
, (VOID
*) UserInfoTable
);
1741 Get the user's identity type.
1743 The identify manager only supports the identity policy in which the credential
1744 provider handles are connected by the operator 'AND' or 'OR'.
1747 @param[in] User Handle of a user profile.
1748 @param[out] PolicyType Point to the identity type.
1750 @retval EFI_SUCCESS Get user's identity type successfully.
1751 @retval Others Fail to get user's identity type.
1756 IN EFI_USER_PROFILE_HANDLE User
,
1757 OUT UINT8
*PolicyType
1761 EFI_USER_INFO
*IdentifyInfo
;
1763 EFI_USER_INFO_IDENTITY_POLICY
*Identity
;
1766 // Get user identify policy information.
1768 IdentifyInfo
= NULL
;
1769 Status
= FindUserInfoByType (User
, &IdentifyInfo
, EFI_USER_INFO_IDENTITY_POLICY_RECORD
);
1770 if (EFI_ERROR (Status
)) {
1773 ASSERT (IdentifyInfo
!= NULL
);
1776 // Search the user identify policy according to type.
1779 *PolicyType
= EFI_USER_INFO_IDENTITY_FALSE
;
1780 while (TotalLen
< IdentifyInfo
->InfoSize
- sizeof (EFI_USER_INFO
)) {
1781 Identity
= (EFI_USER_INFO_IDENTITY_POLICY
*) ((UINT8
*) (IdentifyInfo
+ 1) + TotalLen
);
1782 if (Identity
->Type
== EFI_USER_INFO_IDENTITY_AND
) {
1783 *PolicyType
= EFI_USER_INFO_IDENTITY_AND
;
1787 if (Identity
->Type
== EFI_USER_INFO_IDENTITY_OR
) {
1788 *PolicyType
= EFI_USER_INFO_IDENTITY_OR
;
1791 TotalLen
+= Identity
->Length
;
1798 Identify the User by the specfied provider.
1800 @param[in] User Handle of a user profile.
1801 @param[in] Provider Points to the identifier of credential provider.
1803 @retval EFI_INVALID_PARAMETER Provider is NULL.
1804 @retval EFI_NOT_FOUND Fail to identify the specified user.
1805 @retval EFI_SUCCESS User is identified successfully.
1809 IdentifyByProviderId (
1810 IN EFI_USER_PROFILE_HANDLE User
,
1811 IN EFI_GUID
*Provider
1815 EFI_USER_INFO_IDENTIFIER UserId
;
1817 EFI_CREDENTIAL_LOGON_FLAGS AutoLogon
;
1818 EFI_HII_HANDLE HiiHandle
;
1821 EFI_USER_CREDENTIAL2_PROTOCOL
*UserCredential
;
1823 if (Provider
== NULL
) {
1824 return EFI_INVALID_PARAMETER
;
1828 // Check the user ID identified by the specified credential provider.
1830 for (Index
= 0; Index
< mProviderDb
->Count
; Index
++) {
1832 // Check credential provider class.
1834 UserCredential
= mProviderDb
->Provider
[Index
];
1835 if (CompareGuid (&UserCredential
->Identifier
, Provider
)) {
1836 Status
= UserCredential
->Select (UserCredential
, &AutoLogon
);
1837 if (EFI_ERROR (Status
)) {
1841 if ((AutoLogon
& EFI_CREDENTIAL_LOGON_FLAG_AUTO
) == 0) {
1843 // Get credential provider form.
1845 Status
= UserCredential
->Form (
1851 if (!EFI_ERROR (Status
)) {
1853 // Send form to get user input.
1855 Status
= mCallbackInfo
->FormBrowser2
->SendForm (
1856 mCallbackInfo
->FormBrowser2
,
1864 if (EFI_ERROR (Status
)) {
1870 Status
= UserCredential
->User (UserCredential
, User
, &UserId
);
1871 if (EFI_ERROR (Status
)) {
1875 Status
= UserCredential
->Deselect (UserCredential
);
1876 if (EFI_ERROR (Status
)) {
1884 return EFI_NOT_FOUND
;
1889 Update user information when user is logon on successfully.
1891 @param[in] User Points to user profile.
1893 @retval EFI_SUCCESS Update user information successfully.
1894 @retval Others Fail to update user information.
1899 IN USER_PROFILE_ENTRY
*User
1903 EFI_USER_INFO
*Info
;
1904 EFI_USER_INFO
*NewInfo
;
1905 EFI_USER_INFO_CREATE_DATE Date
;
1906 EFI_USER_INFO_USAGE_COUNT UsageCount
;
1910 // Allocate a buffer to update user's date record and usage record.
1912 InfoLen
= MAX (sizeof (EFI_USER_INFO_CREATE_DATE
), sizeof (EFI_USER_INFO_USAGE_COUNT
));
1913 Info
= AllocateZeroPool (sizeof (EFI_USER_INFO
) + InfoLen
);
1915 return EFI_OUT_OF_RESOURCES
;
1919 // Check create date record.
1922 Status
= FindUserInfoByType (User
, &NewInfo
, EFI_USER_INFO_CREATE_DATE_RECORD
);
1923 if (Status
== EFI_NOT_FOUND
) {
1924 Info
->InfoType
= EFI_USER_INFO_CREATE_DATE_RECORD
;
1925 Info
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PUBLIC
| EFI_USER_INFO_EXCLUSIVE
;
1926 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_CREATE_DATE
);
1927 Status
= gRT
->GetTime (&Date
, NULL
);
1928 if (EFI_ERROR (Status
)) {
1933 CopyMem ((UINT8
*) (Info
+ 1), &Date
, sizeof (EFI_USER_INFO_CREATE_DATE
));
1935 Status
= ModifyUserInfo (User
, &NewInfo
, Info
, Info
->InfoSize
);
1936 if (EFI_ERROR (Status
)) {
1943 // Update usage date record.
1946 Status
= FindUserInfoByType (User
, &NewInfo
, EFI_USER_INFO_USAGE_DATE_RECORD
);
1947 if ((Status
== EFI_SUCCESS
) || (Status
== EFI_NOT_FOUND
)) {
1948 Info
->InfoType
= EFI_USER_INFO_USAGE_DATE_RECORD
;
1949 Info
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PUBLIC
| EFI_USER_INFO_EXCLUSIVE
;
1950 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_USAGE_DATE
);
1951 Status
= gRT
->GetTime (&Date
, NULL
);
1952 if (EFI_ERROR (Status
)) {
1957 CopyMem ((UINT8
*) (Info
+ 1), &Date
, sizeof (EFI_USER_INFO_USAGE_DATE
));
1958 Status
= ModifyUserInfo (User
, &NewInfo
, Info
, Info
->InfoSize
);
1959 if (EFI_ERROR (Status
)) {
1966 // Update usage count record.
1970 Status
= FindUserInfoByType (User
, &NewInfo
, EFI_USER_INFO_USAGE_COUNT_RECORD
);
1974 if (Status
== EFI_SUCCESS
) {
1975 CopyMem (&UsageCount
, (UINT8
*) (NewInfo
+ 1), sizeof (EFI_USER_INFO_USAGE_COUNT
));
1979 if ((Status
== EFI_SUCCESS
) || (Status
== EFI_NOT_FOUND
)) {
1980 Info
->InfoType
= EFI_USER_INFO_USAGE_COUNT_RECORD
;
1981 Info
->InfoAttribs
= EFI_USER_INFO_STORAGE_PLATFORM_NV
| EFI_USER_INFO_PUBLIC
| EFI_USER_INFO_EXCLUSIVE
;
1982 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_USAGE_COUNT
);
1983 CopyMem ((UINT8
*) (Info
+ 1), &UsageCount
, sizeof (EFI_USER_INFO_USAGE_COUNT
));
1984 Status
= ModifyUserInfo (User
, &NewInfo
, Info
, Info
->InfoSize
);
1985 if (EFI_ERROR (Status
)) {
1997 Add a credenetial provider item in form.
1999 @param[in] ProviderGuid Points to the identifir of credential provider.
2000 @param[in] OpCodeHandle Points to container for dynamic created opcodes.
2004 AddProviderSelection (
2005 IN EFI_GUID
*ProviderGuid
,
2006 IN VOID
*OpCodeHandle
2009 EFI_HII_HANDLE HiiHandle
;
2010 EFI_STRING_ID ProvID
;
2013 EFI_USER_CREDENTIAL2_PROTOCOL
*UserCredential
;
2015 for (Index
= 0; Index
< mProviderDb
->Count
; Index
++) {
2016 UserCredential
= mProviderDb
->Provider
[Index
];
2017 if (CompareGuid (&UserCredential
->Identifier
, ProviderGuid
)) {
2019 // Add credential provider selection.
2021 UserCredential
->Title (UserCredential
, &HiiHandle
, &ProvID
);
2022 ProvStr
= HiiGetString (HiiHandle
, ProvID
, NULL
);
2023 if (ProvStr
== NULL
) {
2026 ProvID
= HiiSetString (mCallbackInfo
->HiiHandle
, 0, ProvStr
, NULL
);
2028 HiiCreateActionOpCode (
2029 OpCodeHandle
, // Container for dynamic created opcodes
2030 (EFI_QUESTION_ID
)(LABEL_PROVIDER_NAME
+ Index
), // Question ID
2031 ProvID
, // Prompt text
2032 STRING_TOKEN (STR_NULL_STRING
), // Help text
2033 EFI_IFR_FLAG_CALLBACK
, // Question flag
2034 0 // Action String ID
2043 Add a username item in form.
2045 @param[in] Index The index of the user in the user name list.
2046 @param[in] User Points to the user profile whose username is added.
2047 @param[in] OpCodeHandle Points to container for dynamic created opcodes.
2049 @retval EFI_SUCCESS Add a username successfully.
2050 @retval Others Fail to add a username.
2056 IN USER_PROFILE_ENTRY
*User
,
2057 IN VOID
*OpCodeHandle
2060 EFI_STRING_ID UserName
;
2062 EFI_USER_INFO
*UserInfo
;
2065 Status
= FindUserInfoByType (User
, &UserInfo
, EFI_USER_INFO_NAME_RECORD
);
2066 if (EFI_ERROR (Status
)) {
2071 // Add user name selection.
2073 UserName
= HiiSetString (mCallbackInfo
->HiiHandle
, 0, (EFI_STRING
) (UserInfo
+ 1), NULL
);
2074 if (UserName
== 0) {
2075 return EFI_OUT_OF_RESOURCES
;
2078 HiiCreateGotoOpCode (
2079 OpCodeHandle
, // Container for dynamic created opcodes
2080 FORMID_PROVIDER_FORM
, // Target Form ID
2081 UserName
, // Prompt text
2082 STRING_TOKEN (STR_NULL_STRING
), // Help text
2083 EFI_IFR_FLAG_CALLBACK
, // Question flag
2084 (UINT16
) Index
// Question ID
2092 Identify the user whose identity policy does not contain the operator 'OR'.
2094 @param[in] User Points to the user profile.
2096 @retval EFI_SUCCESS The specified user is identified successfully.
2097 @retval Others Fail to identify the user.
2101 IdentifyAndTypeUser (
2102 IN USER_PROFILE_ENTRY
*User
2106 EFI_USER_INFO
*IdentifyInfo
;
2110 EFI_USER_INFO_IDENTITY_POLICY
*Identity
;
2113 // Get user identify policy information.
2115 IdentifyInfo
= NULL
;
2116 Status
= FindUserInfoByType (User
, &IdentifyInfo
, EFI_USER_INFO_IDENTITY_POLICY_RECORD
);
2117 if (EFI_ERROR (Status
)) {
2120 ASSERT (IdentifyInfo
!= NULL
);
2123 // Check each part of identification policy expression.
2127 while (TotalLen
< IdentifyInfo
->InfoSize
- sizeof (EFI_USER_INFO
)) {
2128 Identity
= (EFI_USER_INFO_IDENTITY_POLICY
*) ((UINT8
*) (IdentifyInfo
+ 1) + TotalLen
);
2129 ValueLen
= Identity
->Length
- sizeof (EFI_USER_INFO_IDENTITY_POLICY
);
2130 switch (Identity
->Type
) {
2132 case EFI_USER_INFO_IDENTITY_FALSE
:
2134 // Check False option.
2139 case EFI_USER_INFO_IDENTITY_TRUE
:
2141 // Check True option.
2146 case EFI_USER_INFO_IDENTITY_NOT
:
2148 // Check negative operation.
2152 case EFI_USER_INFO_IDENTITY_AND
:
2154 // Check and operation.
2157 return EFI_NOT_READY
;
2163 case EFI_USER_INFO_IDENTITY_OR
:
2165 // Check or operation.
2172 case EFI_USER_INFO_IDENTITY_CREDENTIAL_TYPE
:
2174 // Check credential provider by type.
2178 case EFI_USER_INFO_IDENTITY_CREDENTIAL_PROVIDER
:
2180 // Check credential provider by ID.
2182 if (ValueLen
!= sizeof (EFI_GUID
)) {
2183 return EFI_INVALID_PARAMETER
;
2186 Status
= IdentifyByProviderId (User
, (EFI_GUID
*) (Identity
+ 1));
2187 if (EFI_ERROR (Status
)) {
2195 return EFI_INVALID_PARAMETER
;
2199 TotalLen
+= Identity
->Length
;
2202 if (TotalLen
!= IdentifyInfo
->InfoSize
- sizeof (EFI_USER_INFO
)) {
2203 return EFI_INVALID_PARAMETER
;
2207 return EFI_NOT_READY
;
2215 Identify the user whose identity policy does not contain the operator 'AND'.
2217 @param[in] User Points to the user profile.
2219 @retval EFI_SUCCESS The specified user is identified successfully.
2220 @retval Others Fail to identify the user.
2224 IdentifyOrTypeUser (
2225 IN USER_PROFILE_ENTRY
*User
2229 EFI_USER_INFO
*IdentifyInfo
;
2232 EFI_USER_INFO_IDENTITY_POLICY
*Identity
;
2233 VOID
*StartOpCodeHandle
;
2234 VOID
*EndOpCodeHandle
;
2235 EFI_IFR_GUID_LABEL
*StartLabel
;
2236 EFI_IFR_GUID_LABEL
*EndLabel
;
2239 // Get user identify policy information.
2241 IdentifyInfo
= NULL
;
2242 Status
= FindUserInfoByType (User
, &IdentifyInfo
, EFI_USER_INFO_IDENTITY_POLICY_RECORD
);
2243 if (EFI_ERROR (Status
)) {
2246 ASSERT (IdentifyInfo
!= NULL
);
2249 // Initialize the container for dynamic opcodes.
2251 StartOpCodeHandle
= HiiAllocateOpCodeHandle ();
2252 ASSERT (StartOpCodeHandle
!= NULL
);
2254 EndOpCodeHandle
= HiiAllocateOpCodeHandle ();
2255 ASSERT (EndOpCodeHandle
!= NULL
);
2258 // Create Hii Extend Label OpCode.
2260 StartLabel
= (EFI_IFR_GUID_LABEL
*) HiiCreateGuidOpCode (
2264 sizeof (EFI_IFR_GUID_LABEL
)
2266 StartLabel
->ExtendOpCode
= EFI_IFR_EXTEND_OP_LABEL
;
2267 StartLabel
->Number
= LABEL_PROVIDER_NAME
;
2269 EndLabel
= (EFI_IFR_GUID_LABEL
*) HiiCreateGuidOpCode (
2273 sizeof (EFI_IFR_GUID_LABEL
)
2275 EndLabel
->ExtendOpCode
= EFI_IFR_EXTEND_OP_LABEL
;
2276 EndLabel
->Number
= LABEL_END
;
2279 // Add the providers that exists in the user's policy.
2282 while (TotalLen
< IdentifyInfo
->InfoSize
- sizeof (EFI_USER_INFO
)) {
2283 Identity
= (EFI_USER_INFO_IDENTITY_POLICY
*) ((UINT8
*) (IdentifyInfo
+ 1) + TotalLen
);
2284 ValueLen
= Identity
->Length
- sizeof (EFI_USER_INFO_IDENTITY_POLICY
);
2285 if (Identity
->Type
== EFI_USER_INFO_IDENTITY_CREDENTIAL_PROVIDER
) {
2286 AddProviderSelection ((EFI_GUID
*) (Identity
+ 1), StartOpCodeHandle
);
2289 TotalLen
+= Identity
->Length
;
2293 mCallbackInfo
->HiiHandle
, // HII handle
2294 &gUserIdentifyManagerGuid
,// Formset GUID
2295 FORMID_PROVIDER_FORM
, // Form ID
2296 StartOpCodeHandle
, // Label for where to insert opcodes
2297 EndOpCodeHandle
// Replace data
2300 HiiFreeOpCodeHandle (StartOpCodeHandle
);
2301 HiiFreeOpCodeHandle (EndOpCodeHandle
);
2308 This function processes the results of changes in configuration.
2310 @param This Points to the EFI_HII_CONFIG_ACCESS_PROTOCOL.
2311 @param Action Specifies the type of action taken by the browser.
2312 @param QuestionId A unique value which is sent to the original
2313 exporting driver so that it can identify the type
2315 @param Type The type of value for the question.
2316 @param Value A pointer to the data being sent to the original
2318 @param ActionRequest On return, points to the action requested by the
2321 @retval EFI_SUCCESS The callback successfully handled the action.
2322 @retval Others Fail to handle the action.
2327 UserIdentifyManagerCallback (
2328 IN CONST EFI_HII_CONFIG_ACCESS_PROTOCOL
*This
,
2329 IN EFI_BROWSER_ACTION Action
,
2330 IN EFI_QUESTION_ID QuestionId
,
2332 IN EFI_IFR_TYPE_VALUE
*Value
,
2333 OUT EFI_BROWSER_ACTION_REQUEST
*ActionRequest
2337 USER_PROFILE_ENTRY
*User
;
2340 VOID
*StartOpCodeHandle
;
2341 VOID
*EndOpCodeHandle
;
2342 EFI_IFR_GUID_LABEL
*StartLabel
;
2343 EFI_IFR_GUID_LABEL
*EndLabel
;
2345 Status
= EFI_SUCCESS
;
2348 case EFI_BROWSER_ACTION_FORM_OPEN
:
2351 // Update user Form when user Form is opened.
2352 // This will be done only in FORM_OPEN CallBack of question with FORM_OPEN_QUESTION_ID from user Form.
2354 if (QuestionId
!= FORM_OPEN_QUESTION_ID
) {
2359 // Initialize the container for dynamic opcodes.
2361 StartOpCodeHandle
= HiiAllocateOpCodeHandle ();
2362 ASSERT (StartOpCodeHandle
!= NULL
);
2364 EndOpCodeHandle
= HiiAllocateOpCodeHandle ();
2365 ASSERT (EndOpCodeHandle
!= NULL
);
2368 // Create Hii Extend Label OpCode.
2370 StartLabel
= (EFI_IFR_GUID_LABEL
*) HiiCreateGuidOpCode (
2374 sizeof (EFI_IFR_GUID_LABEL
)
2376 StartLabel
->ExtendOpCode
= EFI_IFR_EXTEND_OP_LABEL
;
2377 StartLabel
->Number
= LABEL_USER_NAME
;
2379 EndLabel
= (EFI_IFR_GUID_LABEL
*) HiiCreateGuidOpCode (
2383 sizeof (EFI_IFR_GUID_LABEL
)
2385 EndLabel
->ExtendOpCode
= EFI_IFR_EXTEND_OP_LABEL
;
2386 EndLabel
->Number
= LABEL_END
;
2389 // Add all the user profile in the user profile database.
2391 for (Index
= 0; Index
< mUserProfileDb
->UserProfileNum
; Index
++) {
2392 User
= (USER_PROFILE_ENTRY
*) mUserProfileDb
->UserProfile
[Index
];
2393 AddUserSelection ((UINT16
)(LABEL_USER_NAME
+ Index
), User
, StartOpCodeHandle
);
2397 mCallbackInfo
->HiiHandle
, // HII handle
2398 &gUserIdentifyManagerGuid
,// Formset GUID
2399 FORMID_USER_FORM
, // Form ID
2400 StartOpCodeHandle
, // Label for where to insert opcodes
2401 EndOpCodeHandle
// Replace data
2404 HiiFreeOpCodeHandle (StartOpCodeHandle
);
2405 HiiFreeOpCodeHandle (EndOpCodeHandle
);
2411 case EFI_BROWSER_ACTION_FORM_CLOSE
:
2412 Status
= EFI_SUCCESS
;
2415 case EFI_BROWSER_ACTION_CHANGED
:
2416 if (QuestionId
>= LABEL_PROVIDER_NAME
) {
2418 // QuestionId comes from the second Form (Select a Credential Provider if identity
2419 // policy is OR type). Identify the user by the selected provider.
2421 Status
= IdentifyByProviderId (mCurrentUser
, &mProviderDb
->Provider
[QuestionId
& 0xFFF]->Identifier
);
2422 if (Status
== EFI_SUCCESS
) {
2424 *ActionRequest
= EFI_BROWSER_ACTION_REQUEST_EXIT
;
2430 case EFI_BROWSER_ACTION_CHANGING
:
2432 // QuestionId comes from the first Form (Select a user to identify).
2434 if (QuestionId
>= LABEL_PROVIDER_NAME
) {
2438 User
= (USER_PROFILE_ENTRY
*) mUserProfileDb
->UserProfile
[QuestionId
& 0xFFF];
2439 Status
= GetIdentifyType (User
, &PolicyType
);
2440 if (EFI_ERROR (Status
)) {
2444 if (PolicyType
== EFI_USER_INFO_IDENTITY_OR
) {
2446 // Identify the user by "OR" logical.
2448 Status
= IdentifyOrTypeUser (User
);
2449 if (EFI_ERROR (Status
)) {
2453 mCurrentUser
= (EFI_USER_PROFILE_HANDLE
) User
;
2456 // Identify the user by "AND" logical.
2458 Status
= IdentifyAndTypeUser (User
);
2459 if (EFI_ERROR (Status
)) {
2463 mCurrentUser
= (EFI_USER_PROFILE_HANDLE
) User
;
2465 if (Type
== EFI_IFR_TYPE_REF
) {
2466 Value
->ref
.FormId
= FORMID_INVALID_FORM
;
2473 // All other action return unsupported.
2475 Status
= EFI_UNSUPPORTED
;
2485 This function construct user profile database from user data saved in the Flash.
2486 If no user is found in Flash, add one default user "administrator" in the user
2489 @retval EFI_SUCCESS Init user profile database successfully.
2490 @retval Others Fail to init user profile database.
2506 if (mUserProfileDb
!= NULL
) {
2508 // The user profiles had been already initialized.
2514 // Init user profile database structure.
2516 if (!ExpandUsermUserProfileDb ()) {
2517 return EFI_OUT_OF_RESOURCES
;
2520 CurVarSize
= DEFAULT_PROFILE_SIZE
;
2521 VarData
= AllocateZeroPool (CurVarSize
);
2522 if (VarData
== NULL
) {
2523 return EFI_OUT_OF_RESOURCES
;
2527 // Get all user proifle entries.
2532 // Get variable name.
2543 // Get variable value.
2545 VarSize
= CurVarSize
;
2546 Status
= gRT
->GetVariable (VarName
, &gUserIdentifyManagerGuid
, &VarAttr
, &VarSize
, VarData
);
2547 if (Status
== EFI_BUFFER_TOO_SMALL
) {
2549 VarData
= AllocatePool (VarSize
);
2550 if (VarData
== NULL
) {
2551 Status
= EFI_OUT_OF_RESOURCES
;
2555 CurVarSize
= VarSize
;
2556 Status
= gRT
->GetVariable (VarName
, &gUserIdentifyManagerGuid
, &VarAttr
, &VarSize
, VarData
);
2559 if (EFI_ERROR (Status
)) {
2560 if (Status
== EFI_NOT_FOUND
) {
2561 Status
= EFI_SUCCESS
;
2567 // Check variable attributes.
2569 if (VarAttr
!= (EFI_VARIABLE_NON_VOLATILE
| EFI_VARIABLE_BOOTSERVICE_ACCESS
)) {
2570 Status
= gRT
->SetVariable (VarName
, &gUserIdentifyManagerGuid
, VarAttr
, 0, NULL
);
2575 // Add user profile to the user profile database.
2577 Status
= AddUserProfile (NULL
, VarSize
, VarData
, FALSE
);
2578 if (EFI_ERROR (Status
)) {
2579 if (Status
== EFI_SECURITY_VIOLATION
) {
2581 // Delete invalid user profile
2583 gRT
->SetVariable (VarName
, &gUserIdentifyManagerGuid
, VarAttr
, 0, NULL
);
2584 } else if (Status
== EFI_OUT_OF_RESOURCES
) {
2589 // Delete and save the profile again if some invalid profiles are deleted.
2591 if (mUserProfileDb
->UserProfileNum
< Index
) {
2592 gRT
->SetVariable (VarName
, &gUserIdentifyManagerGuid
, VarAttr
, 0, NULL
);
2593 SaveNvUserProfile (mUserProfileDb
->UserProfile
[mUserProfileDb
->UserProfileNum
- 1], FALSE
);
2598 if (VarData
!= NULL
) {
2602 if (EFI_ERROR (Status
)) {
2607 // Check whether the user profile database is empty.
2609 if (mUserProfileDb
->UserProfileNum
== 0) {
2610 Status
= AddDefaultUserProfile ();
2618 This function collects all the credential providers and saves to mProviderDb.
2620 @retval EFI_SUCCESS Collect credential providers successfully.
2621 @retval Others Fail to collect credential providers.
2631 EFI_HANDLE
*HandleBuf
;
2634 if (mProviderDb
!= NULL
) {
2636 // The credential providers had been collected before.
2642 // Try to find all the user credential provider driver.
2646 Status
= gBS
->LocateHandleBuffer (
2648 &gEfiUserCredential2ProtocolGuid
,
2653 if (EFI_ERROR (Status
)) {
2658 // Get provider infomation.
2660 mProviderDb
= AllocateZeroPool (
2661 sizeof (CREDENTIAL_PROVIDER_INFO
) -
2662 sizeof (EFI_USER_CREDENTIAL2_PROTOCOL
*) +
2663 HandleCount
* sizeof (EFI_USER_CREDENTIAL2_PROTOCOL
*)
2665 if (mProviderDb
== NULL
) {
2666 FreePool (HandleBuf
);
2667 return EFI_OUT_OF_RESOURCES
;
2670 mProviderDb
->Count
= HandleCount
;
2671 for (Index
= 0; Index
< HandleCount
; Index
++) {
2672 Status
= gBS
->HandleProtocol (
2674 &gEfiUserCredential2ProtocolGuid
,
2675 (VOID
**) &mProviderDb
->Provider
[Index
]
2677 if (EFI_ERROR (Status
)) {
2678 FreePool (HandleBuf
);
2679 FreePool (mProviderDb
);
2685 FreePool (HandleBuf
);
2691 This function allows a caller to extract the current configuration for one
2692 or more named elements from the target driver.
2695 @param This Points to the EFI_HII_CONFIG_ACCESS_PROTOCOL.
2696 @param Request A null-terminated Unicode string in <ConfigRequest> format.
2697 @param Progress On return, points to a character in the Request string.
2698 Points to the string's null terminator if request was successful.
2699 Points to the most recent '&' before the first failing name/value
2700 pair (or the beginning of the string if the failure is in the
2701 first name/value pair) if the request was not successful.
2702 @param Results A null-terminated Unicode string in <ConfigAltResp> format which
2703 has all values filled in for the names in the Request string.
2704 String to be allocated by the called function.
2706 @retval EFI_SUCCESS The Results is filled with the requested values.
2707 @retval EFI_OUT_OF_RESOURCES Not enough memory to store the results.
2708 @retval EFI_INVALID_PARAMETER Request is illegal syntax, or unknown name.
2709 @retval EFI_NOT_FOUND Routing data doesn't match any storage in this driver.
2715 IN CONST EFI_HII_CONFIG_ACCESS_PROTOCOL
*This
,
2716 IN CONST EFI_STRING Request
,
2717 OUT EFI_STRING
*Progress
,
2718 OUT EFI_STRING
*Results
2721 if (Progress
== NULL
|| Results
== NULL
) {
2722 return EFI_INVALID_PARAMETER
;
2724 *Progress
= Request
;
2725 return EFI_NOT_FOUND
;
2729 This function processes the results of changes in configuration.
2732 @param This Points to the EFI_HII_CONFIG_ACCESS_PROTOCOL.
2733 @param Configuration A null-terminated Unicode string in <ConfigResp> format.
2734 @param Progress A pointer to a string filled in with the offset of the most
2735 recent '&' before the first failing name/value pair (or the
2736 beginning of the string if the failure is in the first
2737 name/value pair) or the terminating NULL if all was successful.
2739 @retval EFI_SUCCESS The Results is processed successfully.
2740 @retval EFI_INVALID_PARAMETER Configuration is NULL.
2741 @retval EFI_NOT_FOUND Routing data doesn't match any storage in this driver.
2747 IN CONST EFI_HII_CONFIG_ACCESS_PROTOCOL
*This
,
2748 IN CONST EFI_STRING Configuration
,
2749 OUT EFI_STRING
*Progress
2752 if (Configuration
== NULL
|| Progress
== NULL
) {
2753 return EFI_INVALID_PARAMETER
;
2756 *Progress
= Configuration
;
2758 return EFI_NOT_FOUND
;
2763 This function initialize the data mainly used in form browser.
2765 @retval EFI_SUCCESS Initialize form data successfully.
2766 @retval Others Fail to Initialize form data.
2775 USER_MANAGER_CALLBACK_INFO
*CallbackInfo
;
2776 EFI_HII_DATABASE_PROTOCOL
*HiiDatabase
;
2777 EFI_HII_STRING_PROTOCOL
*HiiString
;
2778 EFI_FORM_BROWSER2_PROTOCOL
*FormBrowser2
;
2781 // Initialize driver private data.
2783 CallbackInfo
= AllocateZeroPool (sizeof (USER_MANAGER_CALLBACK_INFO
));
2784 if (CallbackInfo
== NULL
) {
2785 return EFI_OUT_OF_RESOURCES
;
2788 CallbackInfo
->Signature
= USER_MANAGER_SIGNATURE
;
2789 CallbackInfo
->ConfigAccess
.ExtractConfig
= FakeExtractConfig
;
2790 CallbackInfo
->ConfigAccess
.RouteConfig
= FakeRouteConfig
;
2791 CallbackInfo
->ConfigAccess
.Callback
= UserIdentifyManagerCallback
;
2794 // Locate Hii Database protocol.
2796 Status
= gBS
->LocateProtocol (&gEfiHiiDatabaseProtocolGuid
, NULL
, (VOID
**) &HiiDatabase
);
2797 if (EFI_ERROR (Status
)) {
2800 CallbackInfo
->HiiDatabase
= HiiDatabase
;
2803 // Locate HiiString protocol.
2805 Status
= gBS
->LocateProtocol (&gEfiHiiStringProtocolGuid
, NULL
, (VOID
**) &HiiString
);
2806 if (EFI_ERROR (Status
)) {
2809 CallbackInfo
->HiiString
= HiiString
;
2812 // Locate Formbrowser2 protocol.
2814 Status
= gBS
->LocateProtocol (&gEfiFormBrowser2ProtocolGuid
, NULL
, (VOID
**) &FormBrowser2
);
2815 if (EFI_ERROR (Status
)) {
2819 CallbackInfo
->FormBrowser2
= FormBrowser2
;
2820 CallbackInfo
->DriverHandle
= NULL
;
2823 // Install Device Path Protocol and Config Access protocol to driver handle.
2825 Status
= gBS
->InstallMultipleProtocolInterfaces (
2826 &CallbackInfo
->DriverHandle
,
2827 &gEfiDevicePathProtocolGuid
,
2828 &mHiiVendorDevicePath
,
2829 &gEfiHiiConfigAccessProtocolGuid
,
2830 &CallbackInfo
->ConfigAccess
,
2833 ASSERT_EFI_ERROR (Status
);
2836 // Publish HII data.
2838 CallbackInfo
->HiiHandle
= HiiAddPackages (
2839 &gUserIdentifyManagerGuid
,
2840 CallbackInfo
->DriverHandle
,
2841 UserIdentifyManagerStrings
,
2842 UserIdentifyManagerVfrBin
,
2845 if (CallbackInfo
->HiiHandle
== NULL
) {
2846 return EFI_OUT_OF_RESOURCES
;
2849 mCallbackInfo
= CallbackInfo
;
2856 Identify the user whose identification policy supports auto logon.
2858 @param[in] ProviderIndex The provider index in the provider list.
2859 @param[out] User Points to user user profile if a user is identified successfully.
2861 @retval EFI_SUCCESS Identify a user with the specified provider successfully.
2862 @retval Others Fail to identify a user.
2866 IdentifyAutoLogonUser (
2867 IN UINTN ProviderIndex
,
2868 OUT USER_PROFILE_ENTRY
**User
2872 EFI_USER_INFO
*Info
;
2875 Info
= AllocateZeroPool (sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_IDENTIFIER
));
2877 return EFI_OUT_OF_RESOURCES
;
2880 Info
->InfoType
= EFI_USER_INFO_IDENTIFIER_RECORD
;
2881 Info
->InfoSize
= sizeof (EFI_USER_INFO
) + sizeof (EFI_USER_INFO_IDENTIFIER
);
2884 // Identify the specified credential provider's auto logon user.
2886 Status
= mProviderDb
->Provider
[ProviderIndex
]->User (
2887 mProviderDb
->Provider
[ProviderIndex
],
2889 (EFI_USER_INFO_IDENTIFIER
*) (Info
+ 1)
2891 if (EFI_ERROR (Status
)) {
2897 // Find user with the specified user ID.
2900 Status
= FindUserProfileByInfo (User
, NULL
, Info
, Info
->InfoSize
);
2902 if (EFI_ERROR (Status
)) {
2906 Status
= GetIdentifyType ((EFI_USER_PROFILE_HANDLE
) * User
, &PolicyType
);
2907 if (PolicyType
== EFI_USER_INFO_IDENTITY_AND
) {
2909 // The identified user need also identified by other credential provider.
2910 // This can handle through select user.
2912 return EFI_NOT_READY
;
2920 Check whether the given console is ready.
2922 @param[in] ProtocolGuid Points to the protocol guid of sonsole .
2924 @retval TRUE The given console is ready.
2925 @retval FALSE The given console is not ready.
2930 EFI_GUID
*ProtocolGuid
2935 EFI_HANDLE
*HandleBuf
;
2937 EFI_DEVICE_PATH_PROTOCOL
*DevicePath
;
2940 // Try to find all the handle driver.
2944 Status
= gBS
->LocateHandleBuffer (
2951 if (EFI_ERROR (Status
)) {
2955 for (Index
= 0; Index
< HandleCount
; Index
++) {
2956 DevicePath
= DevicePathFromHandle (HandleBuf
[Index
]);
2957 if (DevicePath
!= NULL
) {
2958 FreePool (HandleBuf
);
2962 FreePool (HandleBuf
);
2968 Check whether the console is ready.
2970 @retval TRUE The console is ready.
2971 @retval FALSE The console is not ready.
2979 if (!CheckConsole (&gEfiSimpleTextOutProtocolGuid
)) {
2983 if (!CheckConsole (&gEfiSimpleTextInProtocolGuid
)) {
2984 if (!CheckConsole (&gEfiSimpleTextInputExProtocolGuid
)) {
2994 Identify a user to logon.
2996 @param[out] User Points to user user profile if a user is identified successfully.
2998 @retval EFI_SUCCESS Identify a user successfully.
3003 OUT USER_PROFILE_ENTRY
**User
3008 EFI_CREDENTIAL_LOGON_FLAGS AutoLogon
;
3009 EFI_USER_INFO
*IdentifyInfo
;
3010 EFI_USER_INFO_IDENTITY_POLICY
*Identity
;
3011 EFI_USER_CREDENTIAL2_PROTOCOL
*UserCredential
;
3012 USER_PROFILE_ENTRY
*UserEntry
;
3015 // Initialize credential providers.
3017 InitProviderInfo ();
3020 // Initialize user profile database.
3022 InitUserProfileDb ();
3025 // If only one user in system, and its identify policy is TRUE, then auto logon.
3027 if (mUserProfileDb
->UserProfileNum
== 1) {
3028 UserEntry
= (USER_PROFILE_ENTRY
*) mUserProfileDb
->UserProfile
[0];
3029 IdentifyInfo
= NULL
;
3030 Status
= FindUserInfoByType (UserEntry
, &IdentifyInfo
, EFI_USER_INFO_IDENTITY_POLICY_RECORD
);
3031 if (EFI_ERROR (Status
)) {
3034 ASSERT (IdentifyInfo
!= NULL
);
3036 Identity
= (EFI_USER_INFO_IDENTITY_POLICY
*) ((UINT8
*) (IdentifyInfo
+ 1));
3037 if (Identity
->Type
== EFI_USER_INFO_IDENTITY_TRUE
) {
3038 mCurrentUser
= (EFI_USER_PROFILE_HANDLE
) UserEntry
;
3039 UpdateUserInfo (UserEntry
);
3046 // Find and login the default & AutoLogon user.
3048 for (Index
= 0; Index
< mProviderDb
->Count
; Index
++) {
3049 UserCredential
= mProviderDb
->Provider
[Index
];
3050 Status
= UserCredential
->Default (UserCredential
, &AutoLogon
);
3051 if (EFI_ERROR (Status
)) {
3055 if ((AutoLogon
& (EFI_CREDENTIAL_LOGON_FLAG_DEFAULT
| EFI_CREDENTIAL_LOGON_FLAG_AUTO
)) != 0) {
3056 Status
= IdentifyAutoLogonUser (Index
, &UserEntry
);
3057 if (Status
== EFI_SUCCESS
) {
3058 mCurrentUser
= (EFI_USER_PROFILE_HANDLE
) UserEntry
;
3059 UpdateUserInfo (UserEntry
);
3066 if (!IsConsoleReady ()) {
3068 // The console is still not ready for user selection.
3070 return EFI_ACCESS_DENIED
;
3074 // Select a user and identify it.
3076 mCallbackInfo
->FormBrowser2
->SendForm (
3077 mCallbackInfo
->FormBrowser2
,
3078 &mCallbackInfo
->HiiHandle
,
3080 &gUserIdentifyManagerGuid
,
3087 *User
= (USER_PROFILE_ENTRY
*) mCurrentUser
;
3088 UpdateUserInfo (*User
);
3092 return EFI_ACCESS_DENIED
;
3097 An empty function to pass error checking of CreateEventEx ().
3099 @param Event Event whose notification function is being invoked.
3100 @param Context Pointer to the notification function's context,
3101 which is implementation-dependent.
3106 InternalEmptyFuntion (
3115 Create, Signal, and Close the User Profile Changed event.
3119 SignalEventUserProfileChanged (
3126 Status
= gBS
->CreateEventEx (
3129 InternalEmptyFuntion
,
3131 &gEfiEventUserProfileChangedGuid
,
3134 ASSERT_EFI_ERROR (Status
);
3135 gBS
->SignalEvent (Event
);
3136 gBS
->CloseEvent (Event
);
3141 Create a new user profile.
3143 This function creates a new user profile with only a new user identifier attached and returns
3144 its handle. The user profile is non-volatile, but the handle User can change across reboots.
3146 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3147 @param[out] User On return, points to the new user profile handle.
3148 The user profile handle is unique only during this boot.
3150 @retval EFI_SUCCESS User profile was successfully created.
3151 @retval EFI_ACCESS_DENIED Current user does not have sufficient permissions to create a
3153 @retval EFI_UNSUPPORTED Creation of new user profiles is not supported.
3154 @retval EFI_INVALID_PARAMETER The User parameter is NULL.
3160 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3161 OUT EFI_USER_PROFILE_HANDLE
*User
3166 if ((This
== NULL
) || (User
== NULL
)) {
3167 return EFI_INVALID_PARAMETER
;
3171 // Check the right of the current user.
3173 if (!CheckCurrentUserAccessRight (EFI_USER_INFO_ACCESS_MANAGE
)) {
3174 if (!CheckCurrentUserAccessRight (EFI_USER_INFO_ACCESS_ENROLL_OTHERS
)) {
3175 return EFI_ACCESS_DENIED
;
3180 // Create new user profile
3182 Status
= CreateUserProfile ((USER_PROFILE_ENTRY
**) User
);
3183 if (EFI_ERROR (Status
)) {
3184 return EFI_ACCESS_DENIED
;
3191 Delete an existing user profile.
3193 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3194 @param[in] User User profile handle.
3196 @retval EFI_SUCCESS User profile was successfully deleted.
3197 @retval EFI_ACCESS_DENIED Current user does not have sufficient permissions to delete a user
3198 profile or there is only one user profile.
3199 @retval EFI_UNSUPPORTED Deletion of new user profiles is not supported.
3200 @retval EFI_INVALID_PARAMETER User does not refer to a valid user profile.
3206 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3207 IN EFI_USER_PROFILE_HANDLE User
3213 return EFI_INVALID_PARAMETER
;
3217 // Check the right of the current user.
3219 if (!CheckCurrentUserAccessRight (EFI_USER_INFO_ACCESS_MANAGE
)) {
3220 return EFI_ACCESS_DENIED
;
3224 // Delete user profile.
3226 Status
= DelUserProfile (User
);
3227 if (EFI_ERROR (Status
)) {
3228 if (Status
!= EFI_INVALID_PARAMETER
) {
3229 return EFI_ACCESS_DENIED
;
3231 return EFI_INVALID_PARAMETER
;
3239 Enumerate all of the enrolled users on the platform.
3241 This function returns the next enrolled user profile. To retrieve the first user profile handle,
3242 point User at a NULL. Each subsequent call will retrieve another user profile handle until there
3243 are no more, at which point User will point to NULL.
3245 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3246 @param[in, out] User On entry, points to the previous user profile handle or NULL to
3247 start enumeration. On exit, points to the next user profile handle
3248 or NULL if there are no more user profiles.
3250 @retval EFI_SUCCESS Next enrolled user profile successfully returned.
3251 @retval EFI_ACCESS_DENIED Next enrolled user profile was not successfully returned.
3252 @retval EFI_INVALID_PARAMETER The User parameter is NULL.
3256 UserProfileGetNext (
3257 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3258 IN OUT EFI_USER_PROFILE_HANDLE
*User
3263 if ((This
== NULL
) || (User
== NULL
)) {
3264 return EFI_INVALID_PARAMETER
;
3267 Status
= FindUserProfile ((USER_PROFILE_ENTRY
**) User
, TRUE
, NULL
);
3268 if (EFI_ERROR (Status
)) {
3269 return EFI_ACCESS_DENIED
;
3276 Return the current user profile handle.
3278 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3279 @param[out] CurrentUser On return, points to the current user profile handle.
3281 @retval EFI_SUCCESS Current user profile handle returned successfully.
3282 @retval EFI_INVALID_PARAMETER The CurrentUser parameter is NULL.
3287 UserProfileCurrent (
3288 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3289 OUT EFI_USER_PROFILE_HANDLE
*CurrentUser
3293 // Get current user profile.
3295 if ((This
== NULL
) || (CurrentUser
== NULL
)) {
3296 return EFI_INVALID_PARAMETER
;
3299 *CurrentUser
= mCurrentUser
;
3307 Identify the user and, if authenticated, returns the user handle and changes the current
3308 user profile. All user information marked as private in a previously selected profile
3309 is no longer available for inspection.
3310 Whenever the current user profile is changed then the an event with the GUID
3311 EFI_EVENT_GROUP_USER_PROFILE_CHANGED is signaled.
3313 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3314 @param[out] User On return, points to the user profile handle for the current
3317 @retval EFI_SUCCESS User was successfully identified.
3318 @retval EFI_ACCESS_DENIED User was not successfully identified.
3319 @retval EFI_INVALID_PARAMETER The User parameter is NULL.
3324 UserProfileIdentify (
3325 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3326 OUT EFI_USER_PROFILE_HANDLE
*User
3331 if ((This
== NULL
) || (User
== NULL
)) {
3332 return EFI_INVALID_PARAMETER
;
3335 if (mCurrentUser
!= NULL
) {
3336 *User
= mCurrentUser
;
3343 Status
= IdentifyUser ((USER_PROFILE_ENTRY
**) User
);
3344 if (EFI_ERROR (Status
)) {
3345 return EFI_ACCESS_DENIED
;
3349 // Publish the user info into the EFI system configuration table.
3351 PublishUserTable ();
3354 // Signal User Profile Changed event.
3356 SignalEventUserProfileChanged ();
3361 Find a user using a user information record.
3363 This function searches all user profiles for the specified user information record.
3364 The search starts with the user information record handle following UserInfo and
3365 continues until either the information is found or there are no more user profiles.
3366 A match occurs when the Info.InfoType field matches the user information record
3367 type and the user information record data matches the portion of Info.
3369 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3370 @param[in, out] User On entry, points to the previously returned user profile
3371 handle, or NULL to start searching with the first user profile.
3372 On return, points to the user profile handle, or NULL if not
3374 @param[in, out] UserInfo On entry, points to the previously returned user information
3375 handle, or NULL to start searching with the first. On return,
3376 points to the user information handle of the user information
3377 record, or NULL if not found. Can be NULL, in which case only
3378 one user information record per user can be returned.
3379 @param[in] Info Points to the buffer containing the user information to be
3380 compared to the user information record. If the user information
3381 record data is empty, then only the user information record type
3382 is compared. If InfoSize is 0, then the user information record
3385 @param[in] InfoSize The size of Info, in bytes.
3387 @retval EFI_SUCCESS User information was found. User points to the user profile
3388 handle, and UserInfo points to the user information handle.
3389 @retval EFI_NOT_FOUND User information was not found. User points to NULL, and
3390 UserInfo points to NULL.
3391 @retval EFI_INVALID_PARAMETER User is NULL. Or Info is NULL.
3397 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3398 IN OUT EFI_USER_PROFILE_HANDLE
*User
,
3399 IN OUT EFI_USER_INFO_HANDLE
*UserInfo OPTIONAL
,
3400 IN CONST EFI_USER_INFO
*Info
,
3407 if ((This
== NULL
) || (User
== NULL
) || (Info
== NULL
)) {
3408 return EFI_INVALID_PARAMETER
;
3411 if (InfoSize
== 0) {
3413 // If InfoSize is 0, then the user information record must be empty.
3415 if (Info
->InfoSize
!= sizeof (EFI_USER_INFO
)) {
3416 return EFI_INVALID_PARAMETER
;
3419 if (InfoSize
!= Info
->InfoSize
) {
3420 return EFI_INVALID_PARAMETER
;
3423 Size
= Info
->InfoSize
;
3426 // Find user profile accdoring to user information.
3428 Status
= FindUserProfileByInfo (
3429 (USER_PROFILE_ENTRY
**) User
,
3430 (EFI_USER_INFO
**) UserInfo
,
3431 (EFI_USER_INFO
*) Info
,
3434 if (EFI_ERROR (Status
)) {
3436 if (UserInfo
!= NULL
) {
3439 return EFI_NOT_FOUND
;
3447 Return information attached to the user.
3449 This function returns user information. The format of the information is described in User
3450 Information. The function may return EFI_ACCESS_DENIED if the information is marked private
3451 and the handle specified by User is not the current user profile. The function may return
3452 EFI_ACCESS_DENIED if the information is marked protected and the information is associated
3453 with a credential provider for which the user has not been authenticated.
3455 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3456 @param[in] User Handle of the user whose profile will be retrieved.
3457 @param[in] UserInfo Handle of the user information data record.
3458 @param[out] Info On entry, points to a buffer of at least *InfoSize bytes. On exit,
3459 holds the user information. If the buffer is too small to hold the
3460 information, then EFI_BUFFER_TOO_SMALL is returned and InfoSize is
3461 updated to contain the number of bytes actually required.
3462 @param[in, out] InfoSize On entry, points to the size of Info. On return, points to the size
3463 of the user information.
3465 @retval EFI_SUCCESS Information returned successfully.
3466 @retval EFI_ACCESS_DENIED The information about the specified user cannot be accessed by the
3468 @retval EFI_BUFFER_TOO_SMALL The number of bytes specified by *InfoSize is too small to hold the
3469 returned data. The actual size required is returned in *InfoSize.
3470 @retval EFI_NOT_FOUND User does not refer to a valid user profile or UserInfo does not refer
3471 to a valid user info handle.
3472 @retval EFI_INVALID_PARAMETER Info is NULL or InfoSize is NULL.
3477 UserProfileGetInfo (
3478 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3479 IN EFI_USER_PROFILE_HANDLE User
,
3480 IN EFI_USER_INFO_HANDLE UserInfo
,
3481 OUT EFI_USER_INFO
*Info
,
3482 IN OUT UINTN
*InfoSize
3487 if ((This
== NULL
) || (InfoSize
== NULL
)) {
3488 return EFI_INVALID_PARAMETER
;
3491 if ((*InfoSize
!= 0) && (Info
== NULL
)) {
3492 return EFI_INVALID_PARAMETER
;
3495 if ((User
== NULL
) || (UserInfo
== NULL
)) {
3496 return EFI_NOT_FOUND
;
3499 Status
= GetUserInfo (User
, UserInfo
, Info
, InfoSize
, TRUE
);
3500 if (EFI_ERROR (Status
)) {
3501 if (Status
== EFI_BUFFER_TOO_SMALL
) {
3502 return EFI_BUFFER_TOO_SMALL
;
3504 return EFI_ACCESS_DENIED
;
3511 Add or update user information.
3513 This function changes user information. If NULL is pointed to by UserInfo, then a new user
3514 information record is created and its handle is returned in UserInfo. Otherwise, the existing
3516 If EFI_USER_INFO_IDENITTY_POLICY_RECORD is changed, it is the caller's responsibility to keep
3517 it to be synced with the information on credential providers.
3518 If EFI_USER_INFO_EXCLUSIVE is specified in Info and a user information record of the same
3519 type already exists in the user profile, then EFI_ACCESS_DENIED will be returned and UserInfo
3520 will point to the handle of the existing record.
3522 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3523 @param[in] User Handle of the user whose profile will be retrieved.
3524 @param[in, out] UserInfo Handle of the user information data record.
3525 @param[in] Info On entry, points to a buffer of at least *InfoSize bytes. On exit,
3526 holds the user information. If the buffer is too small to hold the
3527 information, then EFI_BUFFER_TOO_SMALL is returned and InfoSize is
3528 updated to contain the number of bytes actually required.
3529 @param[in] InfoSize On entry, points to the size of Info. On return, points to the size
3530 of the user information.
3532 @retval EFI_SUCCESS Information returned successfully.
3533 @retval EFI_ACCESS_DENIED The record is exclusive.
3534 @retval EFI_SECURITY_VIOLATION The current user does not have permission to change the specified
3535 user profile or user information record.
3536 @retval EFI_NOT_FOUND User does not refer to a valid user profile or UserInfo does not
3537 refer to a valid user info handle.
3538 @retval EFI_INVALID_PARAMETER UserInfo is NULL or Info is NULL.
3542 UserProfileSetInfo (
3543 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3544 IN EFI_USER_PROFILE_HANDLE User
,
3545 IN OUT EFI_USER_INFO_HANDLE
*UserInfo
,
3546 IN CONST EFI_USER_INFO
*Info
,
3552 if ((This
== NULL
) || (User
== NULL
) || (UserInfo
== NULL
) || (Info
== NULL
)) {
3553 return EFI_INVALID_PARAMETER
;
3557 // Check the right of the current user.
3559 if (User
!= mCurrentUser
) {
3560 if (!CheckCurrentUserAccessRight (EFI_USER_INFO_ACCESS_MANAGE
)) {
3561 if (*UserInfo
!= NULL
) {
3563 // Can't update info in other profiles without MANAGE right.
3565 return EFI_SECURITY_VIOLATION
;
3568 if (!CheckCurrentUserAccessRight (EFI_USER_INFO_ACCESS_ENROLL_OTHERS
)) {
3570 // Can't add info into other profiles.
3572 return EFI_SECURITY_VIOLATION
;
3577 if (User
== mCurrentUser
) {
3578 if (CheckCurrentUserAccessRight (EFI_USER_INFO_ACCESS_ENROLL_SELF
)) {
3580 // Only identify policy can be added/updated.
3582 if (Info
->InfoType
!= EFI_USER_INFO_IDENTITY_POLICY_RECORD
) {
3583 return EFI_SECURITY_VIOLATION
;
3589 // Modify user information.
3591 Status
= ModifyUserInfo (User
, (EFI_USER_INFO
**) UserInfo
, Info
, InfoSize
);
3592 if (EFI_ERROR (Status
)) {
3593 if (Status
== EFI_ACCESS_DENIED
) {
3594 return EFI_ACCESS_DENIED
;
3596 return EFI_SECURITY_VIOLATION
;
3603 Called by credential provider to notify of information change.
3605 This function allows the credential provider to notify the User Identity Manager when user status
3607 If the User Identity Manager doesn't support asynchronous changes in credentials, then this function
3608 should return EFI_UNSUPPORTED.
3609 If current user does not exist, and the credential provider can identify a user, then make the user
3610 to be current user and signal the EFI_EVENT_GROUP_USER_PROFILE_CHANGED event.
3611 If current user already exists, and the credential provider can identify another user, then switch
3612 current user to the newly identified user, and signal the EFI_EVENT_GROUP_USER_PROFILE_CHANGED event.
3613 If current user was identified by this credential provider and now the credential provider cannot identify
3614 current user, then logout current user and signal the EFI_EVENT_GROUP_USER_PROFILE_CHANGED event.
3616 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3617 @param[in] Changed Handle on which is installed an instance of the EFI_USER_CREDENTIAL2_PROTOCOL
3618 where the user has changed.
3620 @retval EFI_SUCCESS The User Identity Manager has handled the notification.
3621 @retval EFI_NOT_READY The function was called while the specified credential provider was not selected.
3622 @retval EFI_UNSUPPORTED The User Identity Manager doesn't support asynchronous notifications.
3628 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3629 IN EFI_HANDLE Changed
3632 return EFI_UNSUPPORTED
;
3637 Delete user information.
3639 Delete the user information attached to the user profile specified by the UserInfo.
3641 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3642 @param[in] User Handle of the user whose information will be deleted.
3643 @param[in] UserInfo Handle of the user information to remove.
3645 @retval EFI_SUCCESS User information deleted successfully.
3646 @retval EFI_NOT_FOUND User information record UserInfo does not exist in the user profile.
3647 @retval EFI_ACCESS_DENIED The current user does not have permission to delete this user information.
3652 UserProfileDeleteInfo (
3653 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3654 IN EFI_USER_PROFILE_HANDLE User
,
3655 IN EFI_USER_INFO_HANDLE UserInfo
3661 return EFI_INVALID_PARAMETER
;
3665 // Check the right of the current user.
3667 if (User
!= mCurrentUser
) {
3668 if (!CheckCurrentUserAccessRight (EFI_USER_INFO_ACCESS_MANAGE
)) {
3669 return EFI_ACCESS_DENIED
;
3674 // Delete user information.
3676 Status
= DelUserInfo (User
, UserInfo
, TRUE
);
3677 if (EFI_ERROR (Status
)) {
3678 if (Status
== EFI_NOT_FOUND
) {
3679 return EFI_NOT_FOUND
;
3681 return EFI_ACCESS_DENIED
;
3688 Enumerate user information of all the enrolled users on the platform.
3690 This function returns the next user information record. To retrieve the first user
3691 information record handle, point UserInfo at a NULL. Each subsequent call will retrieve
3692 another user information record handle until there are no more, at which point UserInfo
3695 @param[in] This Points to this instance of the EFI_USER_MANAGER_PROTOCOL.
3696 @param[in] User Handle of the user whose information will be deleted.
3697 @param[in, out] UserInfo Handle of the user information to remove.
3699 @retval EFI_SUCCESS User information returned.
3700 @retval EFI_NOT_FOUND No more user information found.
3701 @retval EFI_INVALID_PARAMETER UserInfo is NULL.
3706 UserProfileGetNextInfo (
3707 IN CONST EFI_USER_MANAGER_PROTOCOL
*This
,
3708 IN EFI_USER_PROFILE_HANDLE User
,
3709 IN OUT EFI_USER_INFO_HANDLE
*UserInfo
3712 if ((This
== NULL
) || (UserInfo
== NULL
)) {
3713 return EFI_INVALID_PARAMETER
;
3716 // Get next user information entry.
3718 return FindUserInfo (User
, (EFI_USER_INFO
**) UserInfo
, TRUE
, NULL
);
3723 Main entry for this driver.
3725 @param[in] ImageHandle Image handle this driver.
3726 @param[in] SystemTable Pointer to SystemTable.
3728 @retval EFI_SUCESS This function always complete successfully.
3733 UserIdentifyManagerInit (
3734 IN EFI_HANDLE ImageHandle
,
3735 IN EFI_SYSTEM_TABLE
*SystemTable
3742 // It is NOT robust enough to be included in production.
3744 #error "This implementation is just a sample, please comment this line if you really want to use this driver."
3747 // Initiate form browser.
3752 // Install protocol interfaces for the User Identity Manager.
3754 Status
= gBS
->InstallProtocolInterface (
3755 &mCallbackInfo
->DriverHandle
,
3756 &gEfiUserManagerProtocolGuid
,
3757 EFI_NATIVE_INTERFACE
,
3758 &gUserIdentifyManager
3760 ASSERT_EFI_ERROR (Status
);
3762 LoadDeferredImageInit (ImageHandle
);