Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-05-10 08:44:50

0001 /**
0002  * \file hmac_drbg.h
0003  *
0004  * \brief The HMAC_DRBG pseudorandom generator.
0005  *
0006  * This module implements the HMAC_DRBG pseudorandom generator described
0007  * in <em>NIST SP 800-90A: Recommendation for Random Number Generation Using
0008  * Deterministic Random Bit Generators</em>.
0009  */
0010 /*
0011  *  Copyright The Mbed TLS Contributors
0012  *  SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
0013  */
0014 #ifndef MBEDTLS_HMAC_DRBG_H
0015 #define MBEDTLS_HMAC_DRBG_H
0016 #include "mbedtls/private_access.h"
0017 
0018 #include "tf-psa-crypto/build_info.h"
0019 
0020 #include "mbedtls/md.h"
0021 
0022 #if defined(MBEDTLS_THREADING_C)
0023 #include "mbedtls/threading.h"
0024 #endif
0025 
0026 /*
0027  * Error codes
0028  */
0029 /** Too many random requested in single call. */
0030 #define MBEDTLS_ERR_HMAC_DRBG_REQUEST_TOO_BIG              -0x0003
0031 /** Input too large (Entropy + additional). */
0032 #define MBEDTLS_ERR_HMAC_DRBG_INPUT_TOO_BIG                -0x0005
0033 /** Read/write error in file. */
0034 #define MBEDTLS_ERR_HMAC_DRBG_FILE_IO_ERROR                -0x0007
0035 /** The entropy source failed. */
0036 #define MBEDTLS_ERR_HMAC_DRBG_ENTROPY_SOURCE_FAILED        -0x0009
0037 
0038 /**
0039  * \name SECTION: Module settings
0040  *
0041  * The configuration options you can set for this module are in this section.
0042  * Either change them in mbedtls_config.h or define them on the compiler command line.
0043  * \{
0044  */
0045 
0046 #if !defined(MBEDTLS_PSA_RNG_RESEED_INTERVAL)
0047 #define MBEDTLS_PSA_RNG_RESEED_INTERVAL   10000   /**< Interval before reseed is performed by default */
0048 #endif
0049 
0050 #define MBEDTLS_HMAC_DRBG_MAX_INPUT         256     /**< Maximum number of additional input bytes */
0051 #define MBEDTLS_HMAC_DRBG_MAX_REQUEST       1024    /**< Maximum number of requested bytes per call */
0052 #define MBEDTLS_HMAC_DRBG_MAX_SEED_INPUT    384     /**< Maximum size of (re)seed buffer */
0053 
0054 /** \} name SECTION: Module settings */
0055 
0056 #define MBEDTLS_HMAC_DRBG_PR_OFF   0   /**< No prediction resistance       */
0057 #define MBEDTLS_HMAC_DRBG_PR_ON    1   /**< Prediction resistance enabled  */
0058 
0059 #ifdef __cplusplus
0060 extern "C" {
0061 #endif
0062 
0063 /**
0064  * HMAC_DRBG context.
0065  */
0066 typedef struct mbedtls_hmac_drbg_context {
0067     /* Working state: the key K is not stored explicitly,
0068      * but is implied by the HMAC context */
0069     mbedtls_md_context_t MBEDTLS_PRIVATE(md_ctx);                    /*!< HMAC context (inc. K)  */
0070     unsigned char MBEDTLS_PRIVATE(V)[MBEDTLS_MD_MAX_SIZE];  /*!< V in the spec          */
0071     int MBEDTLS_PRIVATE(reseed_counter);                     /*!< reseed counter         */
0072 
0073     /* Administrative state */
0074     size_t MBEDTLS_PRIVATE(entropy_len);         /*!< entropy bytes grabbed on each (re)seed */
0075     int MBEDTLS_PRIVATE(prediction_resistance);  /*!< enable prediction resistance (Automatic
0076                                                     reseed before every random generation) */
0077     int MBEDTLS_PRIVATE(reseed_interval);        /*!< reseed interval   */
0078 
0079     /* Callbacks */
0080     int(*MBEDTLS_PRIVATE(f_entropy))(void *, unsigned char *, size_t);  /*!< entropy function */
0081     void *MBEDTLS_PRIVATE(p_entropy);            /*!< context for the entropy function        */
0082 
0083 #if defined(MBEDTLS_THREADING_C)
0084     /* Invariant: the mutex is initialized if and only if
0085      * md_ctx->md_info != NULL. This means that the mutex is initialized
0086      * during the initial seeding in mbedtls_hmac_drbg_seed() or
0087      * mbedtls_hmac_drbg_seed_buf() and freed in mbedtls_ctr_drbg_free().
0088      *
0089      * Note that this invariant may change without notice. Do not rely on it
0090      * and do not access the mutex directly in application code.
0091      */
0092     mbedtls_threading_mutex_t MBEDTLS_PRIVATE(mutex);
0093 #endif
0094 } mbedtls_hmac_drbg_context;
0095 
0096 /**
0097  * \brief               HMAC_DRBG context initialization.
0098  *
0099  * This function makes the context ready for mbedtls_hmac_drbg_seed(),
0100  * mbedtls_hmac_drbg_seed_buf() or mbedtls_hmac_drbg_free().
0101  *
0102  * \note                The reseed interval is #MBEDTLS_PSA_RNG_RESEED_INTERVAL
0103  *                      by default. Override this value by calling
0104  *                      mbedtls_hmac_drbg_set_reseed_interval().
0105  *
0106  * \param ctx           HMAC_DRBG context to be initialized.
0107  */
0108 void mbedtls_hmac_drbg_init(mbedtls_hmac_drbg_context *ctx);
0109 
0110 /**
0111  * \brief               HMAC_DRBG initial seeding.
0112  *
0113  * Set the initial seed and set up the entropy source for future reseeds.
0114  *
0115  * A typical choice for the \p f_entropy and \p p_entropy parameters is
0116  * to use the entropy module:
0117  * - \p f_entropy is mbedtls_entropy_func();
0118  * - \p p_entropy is an instance of ::mbedtls_entropy_context initialized
0119  *   with mbedtls_entropy_init() (which registers the platform's default
0120  *   entropy sources).
0121  *
0122  * You can provide a personalization string in addition to the
0123  * entropy source, to make this instantiation as unique as possible.
0124  *
0125  * \note                By default, the security strength as defined by NIST is:
0126  *                      - 128 bits if \p md_info is SHA-1;
0127  *                      - 192 bits if \p md_info is SHA-224;
0128  *                      - 256 bits if \p md_info is SHA-256, SHA-384 or SHA-512.
0129  *                      Note that SHA-256 is just as efficient as SHA-224.
0130  *                      The security strength can be reduced if a smaller
0131  *                      entropy length is set with
0132  *                      mbedtls_hmac_drbg_set_entropy_len().
0133  *
0134  * \note                The default entropy length is the security strength
0135  *                      (converted from bits to bytes). You can override
0136  *                      it by calling mbedtls_hmac_drbg_set_entropy_len().
0137  *
0138  * \note                During the initial seeding, this function calls
0139  *                      the entropy source to obtain a nonce
0140  *                      whose length is half the entropy length.
0141  */
0142 #if defined(MBEDTLS_THREADING_C)
0143 /**
0144  * \note                When Mbed TLS is built with threading support,
0145  *                      after this function returns successfully,
0146  *                      it is safe to call mbedtls_hmac_drbg_random()
0147  *                      from multiple threads. Other operations, including
0148  *                      reseeding, are not thread-safe.
0149  */
0150 #endif /* MBEDTLS_THREADING_C */
0151 /**
0152  * \param ctx           HMAC_DRBG context to be seeded.
0153  * \param md_info       MD algorithm to use for HMAC_DRBG.
0154  * \param f_entropy     The entropy callback, taking as arguments the
0155  *                      \p p_entropy context, the buffer to fill, and the
0156  *                      length of the buffer.
0157  *                      \p f_entropy is always called with a length that is
0158  *                      less than or equal to the entropy length.
0159  * \param p_entropy     The entropy context to pass to \p f_entropy.
0160  * \param custom        The personalization string.
0161  *                      This can be \c NULL, in which case the personalization
0162  *                      string is empty regardless of the value of \p len.
0163  * \param len           The length of the personalization string.
0164  *                      This must be at most #MBEDTLS_HMAC_DRBG_MAX_INPUT
0165  *                      and also at most
0166  *                      #MBEDTLS_HMAC_DRBG_MAX_SEED_INPUT - \c entropy_len * 3 / 2
0167  *                      where \c entropy_len is the entropy length
0168  *                      described above.
0169  *
0170  * \return              \c 0 if successful.
0171  * \return              #MBEDTLS_ERR_MD_BAD_INPUT_DATA if \p md_info is
0172  *                      invalid.
0173  * \return              #MBEDTLS_ERR_MD_ALLOC_FAILED if there was not enough
0174  *                      memory to allocate context data.
0175  * \return              #MBEDTLS_ERR_HMAC_DRBG_ENTROPY_SOURCE_FAILED
0176  *                      if the call to \p f_entropy failed.
0177  */
0178 int mbedtls_hmac_drbg_seed(mbedtls_hmac_drbg_context *ctx,
0179                            const mbedtls_md_info_t *md_info,
0180                            int (*f_entropy)(void *, unsigned char *, size_t),
0181                            void *p_entropy,
0182                            const unsigned char *custom,
0183                            size_t len);
0184 
0185 /**
0186  * \brief               Initialisation of simplified HMAC_DRBG (never reseeds).
0187  *
0188  * This function is meant for use in algorithms that need a pseudorandom
0189  * input such as deterministic ECDSA.
0190  */
0191 #if defined(MBEDTLS_THREADING_C)
0192 /**
0193  * \note                When Mbed TLS is built with threading support,
0194  *                      after this function returns successfully,
0195  *                      it is safe to call mbedtls_hmac_drbg_random()
0196  *                      from multiple threads. Other operations, including
0197  *                      reseeding, are not thread-safe.
0198  */
0199 #endif /* MBEDTLS_THREADING_C */
0200 /**
0201  * \param ctx           HMAC_DRBG context to be initialised.
0202  * \param md_info       MD algorithm to use for HMAC_DRBG.
0203  * \param data          Concatenation of the initial entropy string and
0204  *                      the additional data.
0205  * \param data_len      Length of \p data in bytes.
0206  *
0207  * \return              \c 0 if successful. or
0208  * \return              #MBEDTLS_ERR_MD_BAD_INPUT_DATA if \p md_info is
0209  *                      invalid.
0210  * \return              #MBEDTLS_ERR_MD_ALLOC_FAILED if there was not enough
0211  *                      memory to allocate context data.
0212  */
0213 int mbedtls_hmac_drbg_seed_buf(mbedtls_hmac_drbg_context *ctx,
0214                                const mbedtls_md_info_t *md_info,
0215                                const unsigned char *data, size_t data_len);
0216 
0217 /**
0218  * \brief               This function turns prediction resistance on or off.
0219  *                      The default value is off.
0220  *
0221  * \note                If enabled, entropy is gathered at the beginning of
0222  *                      every call to mbedtls_hmac_drbg_random_with_add()
0223  *                      or mbedtls_hmac_drbg_random().
0224  *                      Only use this if your entropy source has sufficient
0225  *                      throughput.
0226  *
0227  * \param ctx           The HMAC_DRBG context.
0228  * \param resistance    #MBEDTLS_HMAC_DRBG_PR_ON or #MBEDTLS_HMAC_DRBG_PR_OFF.
0229  */
0230 void mbedtls_hmac_drbg_set_prediction_resistance(mbedtls_hmac_drbg_context *ctx,
0231                                                  int resistance);
0232 
0233 /**
0234  * \brief               This function sets the amount of entropy grabbed on each
0235  *                      seed or reseed.
0236  *
0237  * See the documentation of mbedtls_hmac_drbg_seed() for the default value.
0238  *
0239  * \param ctx           The HMAC_DRBG context.
0240  * \param len           The amount of entropy to grab, in bytes.
0241  */
0242 void mbedtls_hmac_drbg_set_entropy_len(mbedtls_hmac_drbg_context *ctx,
0243                                        size_t len);
0244 
0245 /**
0246  * \brief               Set the reseed interval.
0247  *
0248  * The reseed interval is the number of calls to mbedtls_hmac_drbg_random()
0249  * or mbedtls_hmac_drbg_random_with_add() after which the entropy function
0250  * is called again.
0251  *
0252  * The default value is #MBEDTLS_PSA_RNG_RESEED_INTERVAL.
0253  *
0254  * \param ctx           The HMAC_DRBG context.
0255  * \param interval      The reseed interval.
0256  */
0257 void mbedtls_hmac_drbg_set_reseed_interval(mbedtls_hmac_drbg_context *ctx,
0258                                            int interval);
0259 
0260 /**
0261  * \brief               This function updates the state of the HMAC_DRBG context.
0262  *
0263  * \note                This function is not thread-safe. It is not safe
0264  *                      to call this function if another thread might be
0265  *                      concurrently obtaining random numbers from the same
0266  *                      context or updating or reseeding the same context.
0267  *
0268  * \param ctx           The HMAC_DRBG context.
0269  * \param additional    The data to update the state with.
0270  *                      If this is \c NULL, there is no additional data.
0271  * \param add_len       Length of \p additional in bytes.
0272  *                      Unused if \p additional is \c NULL.
0273  *
0274  * \return              \c 0 on success, or an error from the underlying
0275  *                      hash calculation.
0276  */
0277 int mbedtls_hmac_drbg_update(mbedtls_hmac_drbg_context *ctx,
0278                              const unsigned char *additional, size_t add_len);
0279 
0280 /**
0281  * \brief               This function reseeds the HMAC_DRBG context, that is
0282  *                      extracts data from the entropy source.
0283  *
0284  * \note                This function is not thread-safe. It is not safe
0285  *                      to call this function if another thread might be
0286  *                      concurrently obtaining random numbers from the same
0287  *                      context or updating or reseeding the same context.
0288  *
0289  * \param ctx           The HMAC_DRBG context.
0290  * \param additional    Additional data to add to the state.
0291  *                      If this is \c NULL, there is no additional data
0292  *                      and \p len should be \c 0.
0293  * \param len           The length of the additional data.
0294  *                      This must be at most #MBEDTLS_HMAC_DRBG_MAX_INPUT
0295  *                      and also at most
0296  *                      #MBEDTLS_HMAC_DRBG_MAX_SEED_INPUT - \c entropy_len
0297  *                      where \c entropy_len is the entropy length
0298  *                      (see mbedtls_hmac_drbg_set_entropy_len()).
0299  *
0300  * \return              \c 0 if successful.
0301  * \return              #MBEDTLS_ERR_HMAC_DRBG_ENTROPY_SOURCE_FAILED
0302  *                      if a call to the entropy function failed.
0303  */
0304 int mbedtls_hmac_drbg_reseed(mbedtls_hmac_drbg_context *ctx,
0305                              const unsigned char *additional, size_t len);
0306 
0307 /**
0308  * \brief   This function updates an HMAC_DRBG instance with additional
0309  *          data and uses it to generate random data.
0310  *
0311  * This function automatically reseeds if the reseed counter is exceeded
0312  * or prediction resistance is enabled.
0313  *
0314  * \note                This function is not thread-safe. It is not safe
0315  *                      to call this function if another thread might be
0316  *                      concurrently obtaining random numbers from the same
0317  *                      context or updating or reseeding the same context.
0318  *
0319  * \param p_rng         The HMAC_DRBG context. This must be a pointer to a
0320  *                      #mbedtls_hmac_drbg_context structure.
0321  * \param output        The buffer to fill.
0322  * \param output_len    The length of the buffer in bytes.
0323  *                      This must be at most #MBEDTLS_HMAC_DRBG_MAX_REQUEST.
0324  * \param additional    Additional data to update with.
0325  *                      If this is \c NULL, there is no additional data
0326  *                      and \p add_len should be \c 0.
0327  * \param add_len       The length of the additional data.
0328  *                      This must be at most #MBEDTLS_HMAC_DRBG_MAX_INPUT.
0329  *
0330  * \return              \c 0 if successful.
0331  * \return              #MBEDTLS_ERR_HMAC_DRBG_ENTROPY_SOURCE_FAILED
0332  *                      if a call to the entropy source failed.
0333  * \return              #MBEDTLS_ERR_HMAC_DRBG_REQUEST_TOO_BIG if
0334  *                      \p output_len > #MBEDTLS_HMAC_DRBG_MAX_REQUEST.
0335  * \return              #MBEDTLS_ERR_HMAC_DRBG_INPUT_TOO_BIG if
0336  *                      \p add_len > #MBEDTLS_HMAC_DRBG_MAX_INPUT.
0337  */
0338 int mbedtls_hmac_drbg_random_with_add(void *p_rng,
0339                                       unsigned char *output, size_t output_len,
0340                                       const unsigned char *additional,
0341                                       size_t add_len);
0342 
0343 /**
0344  * \brief   This function uses HMAC_DRBG to generate random data.
0345  *
0346  * This function automatically reseeds if the reseed counter is exceeded
0347  * or prediction resistance is enabled.
0348  */
0349 #if defined(MBEDTLS_THREADING_C)
0350 /**
0351  * \note                When Mbed TLS is built with threading support,
0352  *                      it is safe to call mbedtls_ctr_drbg_random()
0353  *                      from multiple threads. Other operations, including
0354  *                      reseeding, are not thread-safe.
0355  */
0356 #endif /* MBEDTLS_THREADING_C */
0357 /**
0358  * \param p_rng         The HMAC_DRBG context. This must be a pointer to a
0359  *                      #mbedtls_hmac_drbg_context structure.
0360  * \param output        The buffer to fill.
0361  * \param out_len       The length of the buffer in bytes.
0362  *                      This must be at most #MBEDTLS_HMAC_DRBG_MAX_REQUEST.
0363  *
0364  * \return              \c 0 if successful.
0365  * \return              #MBEDTLS_ERR_HMAC_DRBG_ENTROPY_SOURCE_FAILED
0366  *                      if a call to the entropy source failed.
0367  * \return              #MBEDTLS_ERR_HMAC_DRBG_REQUEST_TOO_BIG if
0368  *                      \p out_len > #MBEDTLS_HMAC_DRBG_MAX_REQUEST.
0369  */
0370 int mbedtls_hmac_drbg_random(void *p_rng, unsigned char *output, size_t out_len);
0371 
0372 /**
0373  * \brief               This function resets HMAC_DRBG context to the state immediately
0374  *                      after initial call of mbedtls_hmac_drbg_init().
0375  *
0376  * \param ctx           The HMAC_DRBG context to free.
0377  */
0378 void mbedtls_hmac_drbg_free(mbedtls_hmac_drbg_context *ctx);
0379 
0380 #if defined(MBEDTLS_FS_IO)
0381 /**
0382  * \brief               This function writes a seed file.
0383  *
0384  * \param ctx           The HMAC_DRBG context.
0385  * \param path          The name of the file.
0386  *
0387  * \return              \c 0 on success.
0388  * \return              #MBEDTLS_ERR_HMAC_DRBG_FILE_IO_ERROR on file error.
0389  * \return              #MBEDTLS_ERR_HMAC_DRBG_ENTROPY_SOURCE_FAILED on reseed
0390  *                      failure.
0391  */
0392 int mbedtls_hmac_drbg_write_seed_file(mbedtls_hmac_drbg_context *ctx, const char *path);
0393 
0394 /**
0395  * \brief               This function reads and updates a seed file. The seed
0396  *                      is added to this instance.
0397  *
0398  * \param ctx           The HMAC_DRBG context.
0399  * \param path          The name of the file.
0400  *
0401  * \return              \c 0 on success.
0402  * \return              #MBEDTLS_ERR_HMAC_DRBG_FILE_IO_ERROR on file error.
0403  * \return              #MBEDTLS_ERR_HMAC_DRBG_ENTROPY_SOURCE_FAILED on
0404  *                      reseed failure.
0405  * \return              #MBEDTLS_ERR_HMAC_DRBG_INPUT_TOO_BIG if the existing
0406  *                      seed file is too large.
0407  */
0408 int mbedtls_hmac_drbg_update_seed_file(mbedtls_hmac_drbg_context *ctx, const char *path);
0409 #endif /* MBEDTLS_FS_IO */
0410 
0411 
0412 #if defined(MBEDTLS_SELF_TEST)
0413 /**
0414  * \brief               The HMAC_DRBG Checkup routine.
0415  *
0416  * \return              \c 0 if successful.
0417  * \return              \c 1 if the test failed.
0418  */
0419 int mbedtls_hmac_drbg_self_test(int verbose);
0420 #endif
0421 
0422 #ifdef __cplusplus
0423 }
0424 #endif
0425 
0426 #endif /* hmac_drbg.h */