/*
// Copyright (c) 2018 Intel Corporation
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
*/

#include "usercommands.hpp"

#include "apphandler.hpp"
#include "channel_layer.hpp"
#include "user_layer.hpp"

#include <security/pam_appl.h>

#include <ipmid/api.hpp>
#include <phosphor-logging/lg2.hpp>

#include <regex>

namespace ipmi
{

static constexpr uint8_t enableOperation = 0x00;
static constexpr uint8_t disableOperation = 0x01;

/** @brief implements the set user access command
 *  @param ctx - IPMI context pointer (for channel)
 *  @param channel - channel number
 *  @param ipmiEnabled - indicates ipmi messaging state
 *  @param linkAuthEnabled - indicates link authentication state
 *  @param accessCallback - indicates callback state
 *  @param bitsUpdate - indicates update request
 *  @param userId - user id
 *  @param reserved1 - skip 2 bits
 *  @param privilege - user privilege
 *  @param reserved2 - skip 4 bits
 *  @param sessionLimit - optional - unused for now
 *
 *  @returns ipmi completion code
 */
ipmi::RspType<> ipmiSetUserAccess(ipmi::Context::ptr ctx, uint4_t channel,
                                  uint1_t ipmiEnabled, uint1_t linkAuthEnabled,
                                  uint1_t accessCallback, uint1_t bitsUpdate,

                                  uint6_t userId, uint2_t reserved1,

                                  uint4_t privilege, uint4_t reserved2,

                                  std::optional<uint8_t> sessionLimit)
{
    uint8_t sessLimit = sessionLimit.value_or(0);
    if (reserved1 || reserved2 || sessLimit ||
        !ipmiUserIsValidPrivilege(static_cast<uint8_t>(privilege)))
    {
        lg2::debug("Set user access - Invalid field in request");
        return ipmi::responseInvalidFieldRequest();
    }

    uint8_t chNum = convertCurrentChannelNum(static_cast<uint8_t>(channel),
                                             ctx->channel);
    if (!isValidChannel(chNum))
    {
        lg2::debug("Set user access - Invalid channel request");
        return ipmi::response(invalidChannel);
    }
    if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
    {
        lg2::debug("Set user access - No support on channel");
        return ipmi::response(ccActionNotSupportedForChannel);
    }
    if (!ipmiUserIsValidUserId(static_cast<uint8_t>(userId)))
    {
        lg2::debug("Set user access - Parameter out of range");
        return ipmi::responseParmOutOfRange();
    }

    PrivAccess privAccess = {};
    if (bitsUpdate)
    {
        privAccess.ipmiEnabled = static_cast<uint8_t>(ipmiEnabled);
        privAccess.linkAuthEnabled = static_cast<uint8_t>(linkAuthEnabled);
        privAccess.accessCallback = static_cast<uint8_t>(accessCallback);
    }
    privAccess.privilege = static_cast<uint8_t>(privilege);
    return ipmi::response(
        ipmiUserSetPrivilegeAccess(static_cast<uint8_t>(userId), chNum,
                                   privAccess, static_cast<bool>(bitsUpdate)));
}

/** @brief implements the set user access command
 *  @param ctx - IPMI context pointer (for channel)
 *  @param channel - channel number
 *  @param reserved1 - skip 4 bits
 *  @param userId - user id
 *  @param reserved2 - skip 2 bits
 *
 *  @returns ipmi completion code plus response data
 *   - maxChUsers - max channel users
 *   - reserved1 - skip 2 bits
 *   - enabledUsers - enabled users count
 *   - enabledStatus - enabled status
 *   - fixedUsers - fixed users count
 *   - reserved2 - skip 2 bits
 *   - privilege - user privilege
 *   - ipmiEnabled - ipmi messaging state
 *   - linkAuthEnabled - link authenticatin state
 *   - accessCallback - callback state
 *   - reserved - skip 1 bit
 */
ipmi::RspType<uint6_t, // max channel users
              uint2_t, // reserved1

              uint6_t, // enabled users count
              uint2_t, // enabled status

              uint6_t, // fixed users count
              uint2_t, // reserved2

              uint4_t, // privilege
              uint1_t, // ipmi messaging state
              uint1_t, // link authentication state
              uint1_t, // access callback state
              uint1_t  // reserved3
              >
    ipmiGetUserAccess(ipmi::Context::ptr ctx, uint4_t channel,
                      uint4_t reserved1,

                      uint6_t userId, uint2_t reserved2)
{
    uint8_t chNum = convertCurrentChannelNum(static_cast<uint8_t>(channel),
                                             ctx->channel);

    if (reserved1 || reserved2 || !isValidChannel(chNum))
    {
        lg2::debug("Get user access - Invalid field in request");
        return ipmi::responseInvalidFieldRequest();
    }

    if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
    {
        lg2::debug("Get user access - No support on channel");
        return ipmi::response(ccActionNotSupportedForChannel);
    }
    if (!ipmiUserIsValidUserId(static_cast<uint8_t>(userId)))
    {
        lg2::debug("Get user access - Parameter out of range");
        return ipmi::responseParmOutOfRange();
    }

    uint8_t maxChUsers = 0, enabledUsers = 0, fixedUsers = 0;
    ipmi::Cc retStatus;
    retStatus = ipmiUserGetAllCounts(maxChUsers, enabledUsers, fixedUsers);
    if (retStatus != ccSuccess)
    {
        return ipmi::response(retStatus);
    }

    bool enabledState = false;
    retStatus = ipmiUserCheckEnabled(static_cast<uint8_t>(userId),
                                     enabledState);
    if (retStatus != ccSuccess)
    {
        return ipmi::response(retStatus);
    }

    uint2_t enabledStatus = enabledState ? userIdEnabledViaSetPassword
                                         : userIdDisabledViaSetPassword;
    PrivAccess privAccess{};
    retStatus = ipmiUserGetPrivilegeAccess(static_cast<uint8_t>(userId), chNum,
                                           privAccess);
    if (retStatus != ccSuccess)
    {
        return ipmi::response(retStatus);
    }
    constexpr uint2_t res2Bits = 0;
    return ipmi::responseSuccess(
        static_cast<uint6_t>(maxChUsers), res2Bits,

        static_cast<uint6_t>(enabledUsers), enabledStatus,

        static_cast<uint6_t>(fixedUsers), res2Bits,

        static_cast<uint4_t>(privAccess.privilege),
        static_cast<uint1_t>(privAccess.ipmiEnabled),
        static_cast<uint1_t>(privAccess.linkAuthEnabled),
        static_cast<uint1_t>(privAccess.accessCallback),
        static_cast<uint1_t>(privAccess.reserved));
}

/** @brief implementes the get user name command
 *  @param[in] ctx - ipmi command context
 *  @param[in] userId - 6-bit user ID
 *  @param[in] reserved - 2-bits reserved
 *  @param[in] name - 16-byte array for username

 *  @returns ipmi response
 */
ipmi::RspType<>
    ipmiSetUserName([[maybe_unused]] ipmi::Context::ptr ctx, uint6_t id,
                    uint2_t reserved,
                    const std::array<uint8_t, ipmi::ipmiMaxUserName>& name)
{
    if (reserved)
    {
        return ipmi::responseInvalidFieldRequest();
    }
    uint8_t userId = static_cast<uint8_t>(id);
    if (!ipmiUserIsValidUserId(userId))
    {
        lg2::debug("Set user name - Invalid user id");
        return ipmi::responseParmOutOfRange();
    }

    size_t nameLen = strnlen(reinterpret_cast<const char*>(name.data()),
                             ipmi::ipmiMaxUserName);
    const std::string strUserName(reinterpret_cast<const char*>(name.data()),
                                  nameLen);

    ipmi::Cc res = ipmiUserSetUserName(userId, strUserName);
    return ipmi::response(res);
}

/** @brief implementes the get user name command
 *  @param[in] ctx - ipmi command context
 *  @param[in] userId - 6-bit user ID
 *  @param[in] reserved - 2-bits reserved

 *  @returns ipmi response with 16-byte username
 */
ipmi::RspType<std::array<uint8_t, ipmi::ipmiMaxUserName>> // user name
    ipmiGetUserName([[maybe_unused]] ipmi::Context::ptr ctx, uint6_t id,
                    uint2_t reserved)
{
    if (reserved)
    {
        return ipmi::responseInvalidFieldRequest();
    }

    uint8_t userId = static_cast<uint8_t>(id);
    std::string userName;
    if (ipmiUserGetUserName(userId, userName) != ccSuccess)
    { // Invalid User ID
        lg2::debug("User Name not found, user Id: {USER_ID}", "USER_ID",
                   userId);
        return ipmi::responseParmOutOfRange();
    }
    // copy the std::string into a fixed array
    if (userName.size() > ipmi::ipmiMaxUserName)
    {
        return ipmi::responseUnspecifiedError();
    }
    std::array<uint8_t, ipmi::ipmiMaxUserName> userNameFixed;
    std::fill(userNameFixed.begin(), userNameFixed.end(), 0);
    std::copy(userName.begin(), userName.end(), userNameFixed.begin());
    return ipmi::responseSuccess(std::move(userNameFixed));
}

/** @brief implementes the get user name command
 *  @param[in] ctx - ipmi command context
 *  @param[in] userId - 6-bit user ID
 *  @param[in] reserved - 2-bits reserved

 *  @returns ipmi response with 16-byte username
 */
ipmi::RspType<> // user name
    ipmiSetUserPassword([[maybe_unused]] ipmi::Context::ptr ctx, uint6_t id,
                        bool reserved1, bool pwLen20, uint2_t operation,
                        uint6_t reserved2, SecureBuffer& userPassword)
{
    if (reserved1 || reserved2)
    {
        lg2::debug("Invalid data field in request");
        return ipmi::responseInvalidFieldRequest();
    }

    static constexpr uint2_t opDisableUser = 0x00;
    static constexpr uint2_t opEnableUser = 0x01;
    static constexpr uint2_t opSetPassword = 0x02;
    static constexpr uint2_t opTestPassword = 0x03;

    // If set / test password operation then password size has to be 16 or 20
    // bytes based on the password size bit
    if (((operation == opSetPassword) || (operation == opTestPassword)) &&
        ((pwLen20 && (userPassword.size() != maxIpmi20PasswordSize)) ||
         (!pwLen20 && (userPassword.size() != maxIpmi15PasswordSize))))
    {
        lg2::debug("Invalid Length");
        return ipmi::responseReqDataLenInvalid();
    }

    size_t passwordLength = userPassword.size();

    uint8_t userId = static_cast<uint8_t>(id);
    std::string userName;
    if (ipmiUserGetUserName(userId, userName) != ccSuccess)
    {
        lg2::debug("User Name not found, user Id: {USER_ID}", "USER_ID",
                   userId);
        return ipmi::responseParmOutOfRange();
    }

    if (operation == opSetPassword)
    {
        // turn the non-nul terminated SecureBuffer into a SecureString
        SecureString password(
            reinterpret_cast<const char*>(userPassword.data()), passwordLength);
        ipmi::Cc res = ipmiUserSetUserPassword(userId, password.data());
        return ipmi::response(res);
    }
    else if (operation == opEnableUser || operation == opDisableUser)
    {
        ipmi::Cc res = ipmiUserUpdateEnabledState(userId,
                                                  static_cast<bool>(operation));
        return ipmi::response(res);
    }
    else if (operation == opTestPassword)
    {
        SecureString password = ipmiUserGetPassword(userName);
        // extend with zeros, if needed
        if (password.size() < passwordLength)
        {
            password.resize(passwordLength, '\0');
        }
        SecureString testPassword(
            reinterpret_cast<const char*>(userPassword.data()), passwordLength);
        // constant time string compare: always compare exactly as many bytes
        // as the length of the input, resizing the actual password to match,
        // maintaining a knowledge if the sizes differed originally
        static const std::array<char, maxIpmi20PasswordSize> empty = {'\0'};
        size_t cmpLen = testPassword.size();
        bool pwLenDiffers = password.size() != cmpLen;
        const char* cmpPassword = nullptr;
        if (pwLenDiffers)
        {
            cmpPassword = empty.data();
        }
        else
        {
            cmpPassword = password.data();
        }
        bool pwBad = CRYPTO_memcmp(cmpPassword, testPassword.data(), cmpLen);
        pwBad |= pwLenDiffers;
        if (pwBad)
        {
            lg2::debug("Test password failed, user Id: {USER_ID}", "USER_ID",
                       userId);
            static constexpr ipmi::Cc ipmiCCPasswdFailMismatch = 0x80;
            return ipmi::response(ipmiCCPasswdFailMismatch);
        }
        return ipmi::responseSuccess();
    }
    return ipmi::responseInvalidFieldRequest();
}

/** @brief implements the get channel authentication command
 *  @param ctx - IPMI context pointer (for channel)
 *  @param extData - get IPMI 2.0 extended data
 *  @param reserved1 - skip 3 bits
 *  @param chNum - channel number to get info about
 *  @param reserved2 - skip 4 bits
 *  @param privLevel - requested privilege level

 *  @returns ipmi completion code plus response data
 *   - channel number
 *   - rmcpAuthTypes - RMCP auth types (IPMI 1.5)
 *   - reserved1
 *   - extDataSupport - true for IPMI 2.0 extensions
 *   - anonymousLogin - true for anonymous login enabled
 *   - nullUsers - true for null user names enabled
 *   - nonNullUsers - true for non-null usernames enabled
 *   - userAuth - false for user authentication enabled
 *   - perMessageAuth - false for per message authentication enabled
 *   - KGStatus - true for Kg required for authentication
 *   - reserved2
 *   - rmcp - RMCP (IPMI 1.5) connection support
 *   - rmcpp - RMCP+ (IPMI 2.0) connection support
 *   - reserved3
 *   - oemID - OEM IANA of any OEM auth support
 *   - oemAuxillary - OEM data for auth
 */
ipmi::RspType<uint8_t,  // channel number
              uint6_t,  // rmcpAuthTypes
              bool,     // reserved1
              bool,     // extDataSupport
              bool,     // anonymousLogin
              bool,     // nullUsers
              bool,     // nonNullUsers
              bool,     // userAuth
              bool,     // perMessageAuth
              bool,     // KGStatus
              uint2_t,  // reserved2
              bool,     // rmcp
              bool,     // rmcpp
              uint6_t,  // reserved3
              uint24_t, // oemID
              uint8_t   // oemAuxillary
              >
    ipmiGetChannelAuthenticationCapabilities(ipmi::Context::ptr ctx,
                                             uint4_t chNum, uint3_t reserved1,
                                             [[maybe_unused]] bool extData,
                                             uint4_t privLevel,
                                             uint4_t reserved2)
{
    uint8_t channel = convertCurrentChannelNum(static_cast<uint8_t>(chNum),
                                               ctx->channel);

    if (reserved1 || reserved2 || !isValidChannel(channel) ||
        !isValidPrivLimit(static_cast<uint8_t>(privLevel)))
    {
        lg2::debug("Get channel auth capabilities - Invalid field in request");
        return ipmi::responseInvalidFieldRequest();
    }

    if (getChannelSessionSupport(channel) == EChannelSessSupported::none)
    {
        lg2::debug("Get channel auth capabilities - No support on channel");
        return ipmi::response(ccActionNotSupportedForChannel);
    }

    constexpr bool extDataSupport = true; // true for IPMI 2.0 extensions
    constexpr bool reserved3 = false;
    constexpr uint6_t rmcpAuthTypes = 0;  // IPMI 1.5 auth types - not supported
    constexpr uint2_t reserved4 = 0;
    constexpr bool KGStatus = false;      // Not supporting now.
    constexpr bool perMessageAuth = false; // Per message auth - enabled
    constexpr bool userAuth = false;       // User authentication - enabled
    constexpr bool nullUsers = false;      // Null user names - not supported
    constexpr bool anonymousLogin = false; // Anonymous login - not supported
    constexpr uint6_t reserved5 = 0;
    constexpr bool rmcpp = true;           // IPMI 2.0 - supported
    constexpr bool rmcp = false;           // IPMI 1.5 - not supported
    constexpr uint24_t oemID = 0;
    constexpr uint8_t oemAuxillary = 0;

    bool nonNullUsers = 0;
    uint8_t maxChUsers = 0, enabledUsers = 0, fixedUsers = 0;
    ipmi::ipmiUserGetAllCounts(maxChUsers, enabledUsers, fixedUsers);
    nonNullUsers = enabledUsers > 0;

    return ipmi::responseSuccess(
        channel, rmcpAuthTypes, reserved3, extDataSupport, anonymousLogin,
        nullUsers, nonNullUsers, userAuth, perMessageAuth, KGStatus, reserved4,
        rmcp, rmcpp, reserved5, oemID, oemAuxillary);
}

/** @brief implements the set user payload access command.
 *  @param ctx - IPMI context pointer (for channel)
 *  @param channel - channel number (4 bits)
 *  @param reserved1 - skip 4 bits
 *  @param userId - user id (6 bits)
 *  @param operation - access ENABLE /DISABLE. (2 bits)
 *  @param stdPayload0 - IPMI - reserved. (1 bit)
 *  @param stdPayload1 - SOL.             (1 bit)
 *  @param stdPayload2 -                  (1 bit)
 *  @param stdPayload3 -                  (1 bit)
 *  @param stdPayload4 -                  (1 bit)
 *  @param stdPayload5 -                  (1 bit)
 *  @param stdPayload6 -                  (1 bit)
 *  @param stdPayload7 -                  (1 bit)
 *  @param stdPayloadEnables2Reserved -   (8 bits)
 *  @param oemPayload0 -                  (1 bit)
 *  @param oemPayload1 -                  (1 bit)
 *  @param oemPayload2 -                  (1 bit)
 *  @param oemPayload3 -                  (1 bit)
 *  @param oemPayload4 -                  (1 bit)
 *  @param oemPayload5 -                  (1 bit)
 *  @param oemPayload6 -                  (1 bit)
 *  @param oemPayload7 -                  (1 bit)
 *  @param oemPayloadEnables2Reserved -   (8 bits)
 *
 *  @returns IPMI completion code
 */
ipmi::RspType<> ipmiSetUserPayloadAccess(
    ipmi::Context::ptr ctx,

    uint4_t channel, uint4_t reserved,

    uint6_t userId, uint2_t operation,

    bool stdPayload0ipmiReserved, bool stdPayload1SOL, bool stdPayload2,
    bool stdPayload3, bool stdPayload4, bool stdPayload5, bool stdPayload6,
    bool stdPayload7,

    uint8_t stdPayloadEnables2Reserved,

    bool oemPayload0, bool oemPayload1, bool oemPayload2, bool oemPayload3,
    bool oemPayload4, bool oemPayload5, bool oemPayload6, bool oemPayload7,

    uint8_t oemPayloadEnables2Reserved)
{
    auto chNum = convertCurrentChannelNum(static_cast<uint8_t>(channel),
                                          ctx->channel);
    // Validate the reserved args. Only SOL payload is supported as on date.
    if (reserved || stdPayload0ipmiReserved || stdPayload2 || stdPayload3 ||
        stdPayload4 || stdPayload5 || stdPayload6 || stdPayload7 ||
        oemPayload0 || oemPayload1 || oemPayload2 || oemPayload3 ||
        oemPayload4 || oemPayload5 || oemPayload6 || oemPayload7 ||
        stdPayloadEnables2Reserved || oemPayloadEnables2Reserved ||
        !isValidChannel(chNum))
    {
        return ipmi::responseInvalidFieldRequest();
    }

    if ((operation != enableOperation && operation != disableOperation))
    {
        return ipmi::responseInvalidFieldRequest();
    }
    if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
    {
        return ipmi::response(ccActionNotSupportedForChannel);
    }
    if (!ipmiUserIsValidUserId(static_cast<uint8_t>(userId)))
    {
        return ipmi::responseParmOutOfRange();
    }

    PayloadAccess payloadAccess = {};
    payloadAccess.stdPayloadEnables1[1] = stdPayload1SOL;

    return ipmi::response(ipmiUserSetUserPayloadAccess(
        chNum, static_cast<uint8_t>(operation), static_cast<uint8_t>(userId),
        payloadAccess));
}

/** @brief implements the get user payload access command
 *  This command returns information about user payload enable settings
 *  that were set using the 'Set User Payload Access' Command.
 *
 *  @param ctx - IPMI context pointer (for channel)
 *  @param channel - channel number
 *  @param reserved1 - skip 4 bits
 *  @param userId - user id
 *  @param reserved2 - skip 2 bits
 *
 *  @returns IPMI completion code plus response data
 *   - stdPayload0ipmiReserved - IPMI payload (reserved).
 *   - stdPayload1SOL - SOL payload
 *   - stdPayload2
 *   - stdPayload3
 *   - stdPayload4
 *   - stdPayload5
 *   - stdPayload6
 *   - stdPayload7

 *   - stdPayloadEnables2Reserved - Reserved.

 *   - oemPayload0
 *   - oemPayload1
 *   - oemPayload2
 *   - oemPayload3
 *   - oemPayload4
 *   - oemPayload5
 *   - oemPayload6
 *   - oemPayload7

 *  - oemPayloadEnables2Reserved - Reserved
 */
ipmi::RspType<bool,    // stdPayload0ipmiReserved
              bool,    // stdPayload1SOL
              bool,    // stdPayload2
              bool,    // stdPayload3
              bool,    // stdPayload4
              bool,    // stdPayload5
              bool,    // stdPayload6
              bool,    // stdPayload7

              uint8_t, // stdPayloadEnables2Reserved

              bool,    // oemPayload0
              bool,    // oemPayload1
              bool,    // oemPayload2
              bool,    // oemPayload3
              bool,    // oemPayload4
              bool,    // oemPayload5
              bool,    // oemPayload6
              bool,    // oemPayload7

              uint8_t  // oemPayloadEnables2Reserved
              >
    ipmiGetUserPayloadAccess(ipmi::Context::ptr ctx,

                             uint4_t channel, uint4_t reserved1,

                             uint6_t userId, uint2_t reserved2)
{
    uint8_t chNum = convertCurrentChannelNum(static_cast<uint8_t>(channel),
                                             ctx->channel);

    if (reserved1 || reserved2 || !isValidChannel(chNum))
    {
        return ipmi::responseInvalidFieldRequest();
    }
    if (getChannelSessionSupport(chNum) == EChannelSessSupported::none)
    {
        return ipmi::response(ccActionNotSupportedForChannel);
    }
    if (!ipmiUserIsValidUserId(static_cast<uint8_t>(userId)))
    {
        return ipmi::responseParmOutOfRange();
    }

    ipmi::Cc retStatus;
    PayloadAccess payloadAccess = {};
    retStatus = ipmiUserGetUserPayloadAccess(
        chNum, static_cast<uint8_t>(userId), payloadAccess);
    if (retStatus != ccSuccess)
    {
        return ipmi::response(retStatus);
    }
    constexpr uint8_t res8bits = 0;
    return ipmi::responseSuccess(payloadAccess.stdPayloadEnables1.test(0),
                                 payloadAccess.stdPayloadEnables1.test(1),
                                 payloadAccess.stdPayloadEnables1.test(2),
                                 payloadAccess.stdPayloadEnables1.test(3),
                                 payloadAccess.stdPayloadEnables1.test(4),
                                 payloadAccess.stdPayloadEnables1.test(5),
                                 payloadAccess.stdPayloadEnables1.test(6),
                                 payloadAccess.stdPayloadEnables1.test(7),

                                 res8bits,

                                 payloadAccess.oemPayloadEnables1.test(0),
                                 payloadAccess.oemPayloadEnables1.test(1),
                                 payloadAccess.oemPayloadEnables1.test(2),
                                 payloadAccess.oemPayloadEnables1.test(3),
                                 payloadAccess.oemPayloadEnables1.test(4),
                                 payloadAccess.oemPayloadEnables1.test(5),
                                 payloadAccess.oemPayloadEnables1.test(6),
                                 payloadAccess.oemPayloadEnables1.test(7),

                                 res8bits);
}

void registerUserIpmiFunctions() __attribute__((constructor));
void registerUserIpmiFunctions()
{
    post_work([]() { ipmiUserInit(); });
    ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
                          ipmi::app::cmdSetUserAccessCommand,
                          ipmi::Privilege::Admin, ipmiSetUserAccess);

    ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
                          ipmi::app::cmdGetUserAccessCommand,
                          ipmi::Privilege::Admin, ipmiGetUserAccess);

    ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
                          ipmi::app::cmdGetUserNameCommand,
                          ipmi::Privilege::Admin, ipmiGetUserName);

    ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
                          ipmi::app::cmdSetUserName, ipmi::Privilege::Admin,
                          ipmiSetUserName);

    ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
                          ipmi::app::cmdSetUserPasswordCommand,
                          ipmi::Privilege::Admin, ipmiSetUserPassword);

    ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
                          ipmi::app::cmdGetChannelAuthCapabilities,
                          ipmi::Privilege::Callback,
                          ipmiGetChannelAuthenticationCapabilities);

    ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
                          ipmi::app::cmdSetUserPayloadAccess,
                          ipmi::Privilege::Admin, ipmiSetUserPayloadAccess);

    ipmi::registerHandler(ipmi::prioOpenBmcBase, ipmi::netFnApp,
                          ipmi::app::cmdGetUserPayloadAccess,
                          ipmi::Privilege::Operator, ipmiGetUserPayloadAccess);

    return;
}
} // namespace ipmi
