hmac-drbg

Pure Haskell HMAC-DRBG (docs.ppad.tech/hmac-drbg).
git clone git://git.ppad.tech/hmac-drbg.git
Log | Files | Refs | README | LICENSE

README.md (4473B)


      1 # hmac-drbg
      2 
      3 [![](https://img.shields.io/hackage/v/ppad-hmac-drbg?color=blue)](https://hackage.haskell.org/package/ppad-hmac-drbg)
      4 ![](https://img.shields.io/badge/license-MIT-brightgreen)
      5 [![](https://img.shields.io/badge/haddock-hmac-drbg-lightblue)](https://docs.ppad.tech/hmac-drbg)
      6 
      7 A pure Haskell implementation of the HMAC-DRBG cryptographically-secure PRNG,
      8 as specified by [NIST SP 800-90A][sp800].
      9 
     10 ## Usage
     11 
     12 A sample GHCi session:
     13 
     14 ```
     15   > -- extensions/b16 import just for illustration here; not required for use
     16   > :set -XOverloadedStrings
     17   > :set -XRankNTypes
     18   > import qualified Data.ByteString.Base16 as B16
     19   >
     20   > -- import qualified
     21   > import qualified Crypto.DRBG.HMAC as DRBG
     22   >
     23   > -- supply your own HMAC function
     24   > import qualified Crypto.Hash.SHA256 as SHA256
     25   >
     26   > -- instantiate a DRBG
     27   > let entropy = "very random"
     28   > let nonce = "very unused"
     29   > let personalization_string = "very personal"
     30   >
     31   > drbg <- DRBG.new SHA256.hmac entropy nonce personalization_string
     32   >
     33   > -- use it to generate some bytes
     34   >
     35   > fmap B16.encode (DRBG.gen mempty 32 drbg)
     36   "e4d17210810c4b343f6eae2c19e3d82395b555294b1b16a85f91dbea67e5f277"
     37   >
     38   > -- reuse the generator to get more; the state is updated automatically
     39   >
     40   > fmap B16.encode (DRBG.gen mempty 16 drbg)
     41   "5d867730d99eb5335f16b1d622f03023"
     42   >
     43   > -- this DRBG was instantiated in the IO monad:
     44   >
     45   > :t drbg
     46   drbg :: DRBG.DRBG ghc-prim:GHC.Prim.RealWorld
     47   >
     48   > -- but you can also use use ST to keep things pure:
     49   >
     50   > import Control.Monad.ST
     51   >
     52   > :{
     53   ghci| let drbg_pure = DRBG.new SHA256.hmac mempty mempty mempty ::
     54   ghci|                   forall s. ST s (DRBG.DRBG s)
     55   ghci| :}
     56   >
     57   > :t drbg_pure
     58   drbg_pure :: ST s (DRBG.DRBG s)
     59   >
     60   > runST $ drbg_pure >>= fmap B16.encode . DRBG.gen mempty 16
     61   "b44299907e4e42aa4fded5d6153e8bac"
     62 ```
     63 
     64 ## Documentation
     65 
     66 Haddocks (API documentation, etc.) are hosted at
     67 [docs.ppad.tech/hmac-drbg][hadoc].
     68 
     69 ## Performance
     70 
     71 The aim is best-in-class performance for pure, highly-auditable Haskell
     72 code.
     73 
     74 Current benchmark figures on an M4 Silicon MacBook Air look like (use
     75 `cabal bench` to run the benchmark suite):
     76 
     77 ```
     78   benchmarking ppad-hmac-drbg/HMAC-SHA256/new
     79   time                 10.46 μs   (10.45 μs .. 10.46 μs)
     80                        1.000 R²   (1.000 R² .. 1.000 R²)
     81   mean                 10.44 μs   (10.44 μs .. 10.46 μs)
     82   std dev              28.45 ns   (19.59 ns .. 46.15 ns)
     83 
     84   benchmarking ppad-hmac-drbg/HMAC-SHA256/reseed
     85   time                 6.917 μs   (6.900 μs .. 6.934 μs)
     86                        1.000 R²   (1.000 R² .. 1.000 R²)
     87   mean                 6.908 μs   (6.893 μs .. 6.921 μs)
     88   std dev              47.40 ns   (27.59 ns .. 84.31 ns)
     89 
     90   benchmarking ppad-hmac-drbg/HMAC-SHA256/gen (32B)
     91   time                 10.55 μs   (10.52 μs .. 10.59 μs)
     92                        1.000 R²   (1.000 R² .. 1.000 R²)
     93   mean                 10.51 μs   (10.50 μs .. 10.53 μs)
     94   std dev              44.48 ns   (25.76 ns .. 78.90 ns)
     95 
     96   benchmarking ppad-hmac-drbg/HMAC-SHA256/gen (256B)
     97   time                 36.08 μs   (34.94 μs .. 37.26 μs)
     98                        0.996 R²   (0.994 R² .. 1.000 R²)
     99   mean                 35.30 μs   (35.09 μs .. 35.96 μs)
    100   std dev              1.085 μs   (488.0 ns .. 2.012 μs)
    101 ```
    102 
    103 ## Security
    104 
    105 This library aims at the maximum security achievable in a
    106 garbage-collected language under an optimizing compiler such as GHC, in
    107 which strict constant-timeness can be [challenging to achieve][const].
    108 
    109 The HMAC-DRBG implementation within has been tested against the
    110 NIST DRBGVS vectors available for SHA-256 and SHA-512, using the
    111 HMAC functions from [ppad-sha256][sh256] and [ppad-sha512][sh512]
    112 respectively.
    113 
    114 If you discover any vulnerabilities, please disclose them via
    115 security@ppad.tech.
    116 
    117 ## Development
    118 
    119 You'll require [Nix][nixos] with [flake][flake] support enabled. Enter a
    120 development shell with:
    121 
    122 ```
    123 $ nix develop
    124 ```
    125 
    126 Then do e.g.:
    127 
    128 ```
    129 $ cabal repl ppad-hmac-drbg
    130 ```
    131 
    132 to get a REPL for the main library.
    133 
    134 [sp800]: https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-90Ar1.pdf
    135 [nixos]: https://nixos.org/
    136 [flake]: https://nixos.org/manual/nix/unstable/command-ref/new-cli/nix3-flake.html
    137 [hadoc]: https://docs.ppad.tech/hmac-drbg
    138 [sh256]: https://git.ppad.tech/sha256
    139 [sh512]: https://git.ppad.tech/sha512
    140 [const]: https://www.chosenplaintext.ca/articles/beginners-guide-constant-time-cryptography.html