1 /*
2 // Copyright (c) 2018 Intel Corporation
3 //
4 // Licensed under the Apache License, Version 2.0 (the "License");
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 //      http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 */
16 #pragma once
17 #include <ipmid/api.h>
18 
19 #include <bitset>
20 #include <string>
21 
22 namespace ipmi
23 {
24 
25 // TODO: Has to be replaced with proper channel number assignment logic
26 /**
27  * @enum Channel Id
28  */
29 enum class EChannelID : uint8_t
30 {
31     chanLan1 = 0x01
32 };
33 
34 static constexpr uint8_t invalidUserId = 0xFF;
35 static constexpr uint8_t reservedUserId = 0x0;
36 static constexpr uint8_t ipmiMaxUserName = 16;
37 static constexpr uint8_t ipmiMaxUsers = 15;
38 static constexpr uint8_t ipmiMaxChannels = 16;
39 static constexpr uint8_t maxIpmi20PasswordSize = 20;
40 static constexpr uint8_t maxIpmi15PasswordSize = 16;
41 static constexpr uint8_t payloadsPerByte = 8;
42 
43 /** @struct PrivAccess
44  *
45  *  User privilege related access data as per IPMI specification.(refer spec
46  * sec 22.26)
47  */
48 struct PrivAccess
49 {
50 #if BYTE_ORDER == LITTLE_ENDIAN
51     uint8_t privilege : 4;
52     uint8_t ipmiEnabled : 1;
53     uint8_t linkAuthEnabled : 1;
54     uint8_t accessCallback : 1;
55     uint8_t reserved : 1;
56 #endif
57 #if BYTE_ORDER == BIG_ENDIAN
58     uint8_t reserved : 1;
59     uint8_t accessCallback : 1;
60     uint8_t linkAuthEnabled : 1;
61     uint8_t ipmiEnabled : 1;
62     uint8_t privilege : 4;
63 #endif
64 } __attribute__((packed));
65 
66 /** @struct UserPayloadAccess
67  *
68  *  Structure to denote payload access restrictions applicable for a
69  *  given user and channel. (refer spec sec 24.6)
70  */
71 struct PayloadAccess
72 {
73     std::bitset<payloadsPerByte> stdPayloadEnables1;
74     std::bitset<payloadsPerByte> stdPayloadEnables2Reserved;
75     std::bitset<payloadsPerByte> oemPayloadEnables1;
76     std::bitset<payloadsPerByte> oemPayloadEnables2Reserved;
77 };
78 
79 /** @brief initializes user management
80  *
81  *  @return IPMI_CC_OK for success, others for failure.
82  */
83 ipmi_ret_t ipmiUserInit();
84 
85 /** @brief The ipmi get user password layer call
86  *
87  *  @param[in] userName - user name
88  *
89  *  @return password or empty string
90  */
91 std::string ipmiUserGetPassword(const std::string& userName);
92 
93 /** @brief The IPMI call to clear password entry associated with specified
94  * username
95  *
96  *  @param[in] userName - user name to be removed
97  *
98  *  @return 0 on success, non-zero otherwise.
99  */
100 ipmi_ret_t ipmiClearUserEntryPassword(const std::string& userName);
101 
102 /** @brief The IPMI call to reuse password entry for the renamed user
103  *  to another one
104  *
105  *  @param[in] userName - user name which has to be renamed
106  *  @param[in] newUserName - new user name
107  *
108  *  @return 0 on success, non-zero otherwise.
109  */
110 ipmi_ret_t ipmiRenameUserEntryPassword(const std::string& userName,
111                                        const std::string& newUserName);
112 
113 /** @brief determines valid userId
114  *
115  *  @param[in] userId - user id
116  *
117  *  @return true if valid, false otherwise
118  */
119 bool ipmiUserIsValidUserId(const uint8_t userId);
120 
121 /** @brief determines valid privilege level
122  *
123  *  @param[in] priv - privilege level
124  *
125  *  @return true if valid, false otherwise
126  */
127 bool ipmiUserIsValidPrivilege(const uint8_t priv);
128 
129 /** @brief get user id corresponding to the user name
130  *
131  *  @param[in] userName - user name
132  *
133  *  @return userid. Will return 0xff if no user id found
134  */
135 uint8_t ipmiUserGetUserId(const std::string& userName);
136 
137 /** @brief set's user name
138  *
139  *  @param[in] userId - user id
140  *  @param[in] userName - user name
141  *
142  *  @return IPMI_CC_OK for success, others for failure.
143  */
144 ipmi_ret_t ipmiUserSetUserName(const uint8_t userId, const char* userName);
145 
146 /** @brief set user password
147  *
148  *  @param[in] userId - user id
149  *  @param[in] userPassword - New Password
150  *
151  *  @return IPMI_CC_OK for success, others for failure.
152  */
153 ipmi_ret_t ipmiUserSetUserPassword(const uint8_t userId,
154                                    const char* userPassword);
155 
156 /** @brief set special user password (non-ipmi accounts)
157  *
158  *  @param[in] userName - user name
159  *  @param[in] userPassword - New Password
160  *
161  *  @return IPMI_CC_OK for success, others for failure.
162  */
163 ipmi_ret_t ipmiSetSpecialUserPassword(const std::string& userName,
164                                       const std::string& userPassword);
165 
166 /** @brief get user name
167  *
168  *  @param[in] userId - user id
169  *  @param[out] userName - user name
170  *
171  *  @return IPMI_CC_OK for success, others for failure.
172  */
173 ipmi_ret_t ipmiUserGetUserName(const uint8_t userId, std::string& userName);
174 
175 /** @brief provides available fixed, max, and enabled user counts
176  *
177  *  @param[out] maxChUsers - max channel users
178  *  @param[out] enabledUsers - enabled user count
179  *  @param[out] fixedUsers - fixed user count
180  *
181  *  @return IPMI_CC_OK for success, others for failure.
182  */
183 ipmi_ret_t ipmiUserGetAllCounts(uint8_t& maxChUsers, uint8_t& enabledUsers,
184                                 uint8_t& fixedUsers);
185 
186 /** @brief function to update user enabled state
187  *
188  *  @param[in] userId - user id
189  *..@param[in] state - state of the user to be updated, true - user enabled.
190  *
191  *  @return IPMI_CC_OK for success, others for failure.
192  */
193 ipmi_ret_t ipmiUserUpdateEnabledState(const uint8_t userId, const bool& state);
194 
195 /** @brief determines whether user is enabled
196  *
197  *  @param[in] userId - user id
198  *..@param[out] state - state of the user
199  *
200  *  @return IPMI_CC_OK for success, others for failure.
201  */
202 ipmi_ret_t ipmiUserCheckEnabled(const uint8_t userId, bool& state);
203 
204 /** @brief provides user privilege access data
205  *
206  *  @param[in] userId - user id
207  *  @param[in] chNum - channel number
208  *  @param[out] privAccess - privilege access data
209  *
210  *  @return IPMI_CC_OK for success, others for failure.
211  */
212 ipmi_ret_t ipmiUserGetPrivilegeAccess(const uint8_t userId, const uint8_t chNum,
213                                       PrivAccess& privAccess);
214 
215 /** @brief sets user privilege access data
216  *
217  *  @param[in] userId - user id
218  *  @param[in] chNum - channel number
219  *  @param[in] privAccess - privilege access data
220  *  @param[in] otherPrivUpdate - flags to indicate other fields update
221  *
222  *  @return IPMI_CC_OK for success, others for failure.
223  */
224 ipmi_ret_t ipmiUserSetPrivilegeAccess(const uint8_t userId, const uint8_t chNum,
225                                       const PrivAccess& privAccess,
226                                       const bool& otherPrivUpdate);
227 
228 /** @brief check for user pam authentication. This is to determine, whether user
229  * is already locked out for failed login attempt
230  *
231  *  @param[in] username - username
232  *  @param[in] password - password
233  *
234  *  @return status
235  */
236 bool ipmiUserPamAuthenticate(std::string_view userName,
237                              std::string_view userPassword);
238 
239 /** @brief sets user payload access data
240  *
241  *  @param[in] chNum - channel number
242  *  @param[in] operation - ENABLE / DISABLE operation
243  *  @param[in] userId - user id
244  *  @param[in] payloadAccess - payload access data
245  *
246  *  @return IPMI_CC_OK for success, others for failure.
247  */
248 ipmi_ret_t ipmiUserSetUserPayloadAccess(const uint8_t chNum,
249                                         const uint8_t operation,
250                                         const uint8_t userId,
251                                         const PayloadAccess& payloadAccess);
252 
253 /** @brief provides user payload access data
254  *
255  *  @param[in] chNum - channel number
256  *  @param[in] userId - user id
257  *  @param[out] payloadAccess - payload access data
258  *
259  *  @return IPMI_CC_OK for success, others for failure.
260  */
261 ipmi_ret_t ipmiUserGetUserPayloadAccess(const uint8_t chNum,
262                                         const uint8_t userId,
263                                         PayloadAccess& payloadAccess);
264 
265 } // namespace ipmi
266