Author: Kamil Kowalski kamil.kowalski@intel.com
Primary assignee: Kamil Kowalski
Other contributors: None
Created: June 7, 2019
Redfish API presented by BMCWeb allows user to authenticate using quite a few methods, eg. BasicAuth, Sessions, etc. In addition to those user can gain access to nodes by providing certificate upon negotiating HTTPS connection for identifications. The design and principles behind this solution are described below.
Redfish currently lacks support for modern authentication methods. Certificate based auth would allow for more secure and controllable access control. Using SSL certificates provides validity periods, ability to revoke access from CA level, and many other security features.
Reference documents:
Redfish API - Redfish API as defined by DMTF Redfish - Redfish API implementation in BMCWeb
Adding this would benefit WebUI's and Redfish API's security greatly, and would push it towards modern security standards compliance.
Whenever CA
's certificate changes User
shall provide Redfish
with it. After that is completed, user should request a CSR (Certificate Signing Request) from Redfish
to get a request allowing to generate proper user
's certificate from CA
. After this certificate is acquired, User
can use this certificate when initializing HTTPS sessions.
┌──┐ ┌────┐ ┌───────┐ │CA│ │User│ │Redfish│ └┬─┘ └─┬──┘ └───┬───┘ │ Request CA's certificate │ │ │ <────────────────────────────── │ │ │ │ │ Return CA's certificate │ │ │ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─> │ │ │ │ │ │ Upload CA Certificate │ │ │ ───────────────────────────────────────> │ │ │ │ ──────────┐ │ │ │ Generate CSR │ │ <─────────┘ │ │ │ │ │ Request certificate using CSR │ │ │ <────────────────────────────── │ │ │ │ │ Return User's certificate │ │ │ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─> │ │ │ │ │ │ │ │ ╔═══════╤═══╪════════════════════════════════════════╪════╗ │ ║ LOOP │ Typical runtime │ ║ │ ╟───────┘ │ │ ║ │ ║ │ Initiate HTTPS Session │ ║ │ ║ │ ───────────────────────────────────────> ║ │ ║ │ │ ║ │ ║ │ Request TLS client authentication │ ║ │ ║ │ <─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ║ │ ║ │ │ ║ │ ║ │ Provide certificate │ ║ │ ║ │ ───────────────────────────────────────> ║ │ ║ │ │ ║ │ ║ │ Return requested data │ ║ │ ║ │ <─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ─ ║ │ ╚═══════════╪════════════════════════════════════════╪════╝ ┌┴─┐ ┌─┴──┐ ┌───┴───┐ │CA│ │User│ │Redfish│ └──┘ └────┘ └───────┘
CA's certificates for user authentication are kept at /redfish/v1/AccountService/TLSAuth/Certificates
. There can be more than one, so user must use certificate that is signed by any CA that have their valid certificate stored there. New certificates can be uploaded by POSTing new certificate object on CertificateCollection.
Example POST payload:
{ "CertificateString": "... <Certificate String> ...", "CertificateType": "PEM" }
Should CA certificate get invalid (compromised, out-of-date, etc.) it is recommended to use #CertificateService.ReplaceCertificate
action at /redfish/v1/CertificateService
, to avoid wasting space and performance unnecessarily for processing invalid certificates.
Example #CertificateService.ReplaceCertificate
action payload executed on /redfish/v1/CertificateService/Actions/CertificateService.ReplaceCertificate
:
{ "CertificateUri": "/redfish/v1/AccountService/TLSAuth/Certificates/1", "CertificateString": "... <Certificate String> ...", "CertificateType": "PEM" }
User can generate CSR in any way that is convenient to him.
+-+ +++ | V +------------+------------+ Yes | | +---------+ Is certificate valid | | | and signed by known CA? | | | | | +------------+------------+ | | | | No | V | +-----------+-----------+ | Yes | | +----------+ Is URI whitelisted? | | | | | +-----------+-----------+ | | | | No | V | +-----------+-----------+ | Yes | | +----------+ Is X-Token provided? | | | | | +-----------+-----------+ | | | | No | V | +-----------+-----------+ | Yes | | +----------+ Is cookie provided? | | | | | +-----------+-----------+ | | | | No | V | +-----------+-----------+ | Yes | | +----------+ Is Token provided? | | | | | +-----------+-----------+ | | | | No | V | +---------------+--------------+ | Yes | | No +------+ Is Basic auth data provided? +------+ | | | | | +------------------------------+ | V V +-------------+--------------+ +-------------+--------------+ | | | | | Create session | | Return authorization error | | | | | +-------------+--------------+ +-------------+--------------+ | | | +-+ | +--------------------->*<--------------------+ +-+
Certificate based authentication has the highest priority, because of the design of Boost.Beast/Boost.ASIO/OpenSSL as the certificate verification is being done at the very beginning of HTTPS request processing. OpenSSL library is responsible for determining whether certificate is valid or not. For certificate to be marked as valid, it (and every certificate in chain) has to meet these conditions:
After these checks a callback is invoked providing result of user<->CA matching status. There, in case of success Redfish extracts username from CommonName
and verifies if user does exist in the system.
As can be seen on the flow diagram, Redfish will use the first valid credentials according to processing sequence. It is recommended for user to use only one set of credentials/authentication data in a single request to be sure what will be used, otherwise there is no certainty which credential are used during operation.
User can configure which methods are available in /redfish/v1/AccountService
OEM schema. The sequence of credential verification stays the same regardless of configuration. Whitelist verification is always-on, because of Redfish specification and other accessibility requirements.
User certificate does not have to be signed by the exact CAs whose certificates are stored, but instead it can be done in a chain (Redfish guarantees support for chain depth up to 5, but greater ones may work as well). It is recommended to use at least 2048bit RSA or 256/384bit elliptic curve keys. Certificate has to be in its validity period in the moment of session initialization.
User identified by any of methods described above, goes through process of examining whether user actually exists, and what privileges, groups, etc. should be provided. Current base is BasicAuth as it should be used for creating sessions which can be used in following connections, and it is executed by BMCWeb through PAM library usage. Other auth methods have access only to user's login credentials without password, so verification of user existence cannot be directly done through classic PAM flow, and should be done in other way. This also applies for certificate based auth, so all non BasicAuth methods should verify whether user exists and is not locked out of the system on any login attempt.
None.
Current auth methods will not be impacted. This proposition is based on locally stored CA certificates, so it does not guarantee automated measures against situations where certificates have been revoked, and user/admin has not yet updated certificates on BMC.
Testing should be conducted on currently supported auth methods beside TLS, to confirm that their behavior did not change, and did not suffer any regression.
As for TLS auth itself: