Signed-off-by: Anjan Roy <hello@itzmeanjan.in>
Caution
This Kyber implementation is conformant with Kyber specification https://pq-crystals.org/kyber/data/kyber-specification-round3-20210804.pdf and I also try to make it constant-time but be informed that it is not yet audited. If you consider using it in production, be careful !
kyber
CRYSTALS-Kyber: Post-Quantum Public-key Encryption & Key-establishment Algorithm
Motivation
Kyber is being standardized by NIST as post-quantum secure key encapsulation mechanism (KEM), which can be used for key establishment.
Kyber offers an IND-CCA2-secure Key Encapsulation Mechanism - its security is based on the hardness of solving the learning-with-errors (LWE) problem in module (i.e. structured) lattices.
Kyber Key Encapsulation Mechanism is built on top of IND-CPA-secure Kyber Public Key Encryption, where two communicating parties, both generating their key pairs, while publishing their public keys to each other, can encrypt fixed length ( = 32 -bytes ) message using peer's public key. Cipher text can be decrypted by corresponding secret key ( which is private to the keypair owner ) and 32 -bytes message can be recovered back. Then a slightly tweaked Fujisaki–Okamoto (FO) transform is applied on IND-CPA-secure Kyber PKE - giving us the IND-CCA2-secure KEM construction. In KEM scheme, two parties interested in establishing a secure communication channel over public & insecure channel, can generate a shared secret key ( of arbitrary byte length ) from a key derivation function ( i.e. KDF which is SHAKE256 Xof in this context ) which is obtained by both of these parties as result of seeding SHAKE256 Xof with same secret. This secret is 32 -bytes and that's what is communicated by sender to receiver using underlying Kyber PKE scheme.
| Algorithm | Input | Output |
|---|---|---|
| KEM KeyGen | - | Public Key and Secret Key |
| Encapsulation | Public Key | Cipher Text and SHAKE256 KDF |
| Decapsulation | Secret Key and Cipher Text | SHAKE256 KDF |
Note
IND-CCA2-secure Kyber KEM can be used for synchronous secure communication such as TLS.
Here I'm maintaining kyber - a header-only and easy-to-use ( see more in usage ) C++ library implementing Kyber KEM, supporting Kyber-{512, 768, 1024} parameter sets, as defined in table 1 of Kyber specification. sha3 and subtle are two dependencies of this library, which are pinned to specific git commits, using git submodule.
Note
Find Kyber specification https://pq-crystals.org/kyber/data/kyber-specification-round3-20210804.pdf - this is the document that I followed when implementing Kyber. I suggest you go through the specification to get an in-depth understanding of Kyber PQC suite.
Note
Find progress of NIST PQC standardization effort @ https://csrc.nist.gov/projects/post-quantum-cryptography.
Prerequisites
- A C++ compiler with C++20 standard library such as
clang++/g++.
$ clang++ --version
Ubuntu clang version 17.0.2 (1~exp1ubuntu2.1)
Target: x86_64-pc-linux-gnu
Thread model: posix
InstalledDir: /usr/bin
$ g++ --version
g++ (Ubuntu 13.2.0-4ubuntu3) 13.2.0
- Build tools such as
make,cmake.
$ make --version
GNU Make 4.3
$ cmake --version
cmake version 3.25.1
- For testing Kyber KEM implementation, you need to globally install
google-testlibrary and headers. Follow this guide, if you don't have it installed. - For benchmarking Kyber KEM implementation, targeting CPU systems, you'll need to have
google-benchmarkheader and library globally installed. I found guide @ https://github.com/google/benchmark#installation helpful.
Note
If you are on a machine running GNU/Linux kernel and you want to obtain CPU cycle count for KEM routines, you should consider building
google-benchmarklibrary withlibPFMsupport, following https://gist.github.com/itzmeanjan/05dc3e946f635d00c5e0b21aae6203a7, a step-by-step guide. Find more about libPFM @ https://perfmon2.sourceforge.net.
Tip
Git submodule based dependencies will mostly be imported automatically, but in case that doesn't work, you can manually initialize and update them by issuing
$ git submodule update --initfrom inside the root of this repository.
Testing
For testing functional correctness and conformance with Kyber specification, you have to issue
Note
Known Answer Test (KAT) files living in this directory are generated by following (reproducible) steps, described in https://gist.github.com/itzmeanjan/c8f5bc9640d0f0bdd2437dfe364d7710.
make -j
Note: Randomizing tests' orders with a seed of 61247 .
[==========] Running 10 tests from 1 test suite.
[----------] Global test environment set-up.
[----------] 10 tests from KyberKEM
[ RUN ] KyberKEM.ArithmeticOverZq
[ OK ] KyberKEM.ArithmeticOverZq (116 ms)
[ RUN ] KyberKEM.NumberTheoreticTransform
[ OK ] KyberKEM.NumberTheoreticTransform (0 ms)
[ RUN ] KyberKEM.Kyber768KnownAnswerTests
[ OK ] KyberKEM.Kyber768KnownAnswerTests (8 ms)
[ RUN ] KyberKEM.Kyber512KnownAnswerTests
[ OK ] KyberKEM.Kyber512KnownAnswerTests (5 ms)
[ RUN ] KyberKEM.CompressDecompressZq
[ OK ] KyberKEM.CompressDecompressZq (94 ms)
[ RUN ] KyberKEM.Kyber1024KnownAnswerTests
[ OK ] KyberKEM.Kyber1024KnownAnswerTests (13 ms)
[ RUN ] KyberKEM.Kyber768KeygenEncapsDecaps
[ OK ] KyberKEM.Kyber768KeygenEncapsDecaps (0 ms)
[ RUN ] KyberKEM.Kyber512KeygenEncapsDecaps
[ OK ] KyberKEM.Kyber512KeygenEncapsDecaps (0 ms)
[ RUN ] KyberKEM.PolynomialSerialization
[ OK ] KyberKEM.PolynomialSerialization (0 ms)
[ RUN ] KyberKEM.Kyber1024KeygenEncapsDecaps
[ OK ] KyberKEM.Kyber1024KeygenEncapsDecaps (0 ms)
[----------] 10 tests from KyberKEM (238 ms total)
[----------] Global test environment tear-down
[==========] 10 tests from 1 test suite ran. (238 ms total)
[ PASSED ] 10 tests.
Benchmarking
For benchmarking Kyber KEM routines ( i.e. keygen, encaps and decaps ) for various suggested parameter sets, you have to issue.
make benchmark # If you haven't built google-benchmark library with libPFM support.
make perf # If you have built google-benchmark library with libPFM support.
Note
Benchmarking expects presence of
google-benchmarkheader and library in global namespace ( so that it can be found by the compiler ).
Caution
When benchmarking, ensure that you've disabled CPU frequency scaling, by following guide @ https://github.com/google/benchmark/blob/main/docs/reducing_variance.md.
Note
make perf- was issued when collecting following benchmarks. Notice, cycles column, denoting cost of executing Kyber KEM routines in terms of CPU cycles. Follow this for more details.
On 12th Gen Intel(R) Core(TM) i7-1260P ( compiled with GCC-13.2.0 )
2023-12-05T22:33:52+04:00
Running ./build/perf.out
Run on (16 X 504.568 MHz CPU s)
CPU Caches:
L1 Data 48 KiB (x8)
L1 Instruction 32 KiB (x8)
L2 Unified 1280 KiB (x8)
L3 Unified 18432 KiB (x1)
Load Average: 0.44, 0.51, 0.51
----------------------------------------------------------------------------------------------
Benchmark Time CPU Iterations CYCLES items_per_second
----------------------------------------------------------------------------------------------
kyber512/keygen_mean 14.4 us 14.4 us 8 67.3437k 69.4709k/s
kyber512/keygen_median 14.4 us 14.4 us 8 67.4082k 69.3937k/s
kyber512/keygen_stddev 0.042 us 0.043 us 8 176.213 210.232/s
kyber512/keygen_cv 0.29 % 0.30 % 8 0.26% 0.30%
kyber1024/decap_mean 48.5 us 48.5 us 8 226.76k 20.6092k/s
kyber1024/decap_median 48.5 us 48.5 us 8 226.561k 20.6251k/s
kyber1024/decap_stddev 0.165 us 0.157 us 8 426.061 66.8334/s
kyber1024/decap_cv 0.34 % 0.32 % 8 0.19% 0.32%
kyber512/decap_mean 20.7 us 20.6 us 8 96.5275k 48.4359k/s
kyber512/decap_median 20.6 us 20.6 us 8 96.3069k 48.5757k/s
kyber512/decap_stddev 0.134 us 0.135 us 8 582.227 313.68/s
kyber512/decap_cv 0.65 % 0.65 % 8 0.60% 0.65%
kyber768/keygen_mean 24.7 us 24.7 us 8 114.9k 40.5314k/s
kyber768/keygen_median 24.6 us 24.6 us 8 115.106k 40.6451k/s
kyber768/keygen_stddev 0.177 us 0.169 us 8 687.033 274.976/s
kyber768/keygen_cv 0.72 % 0.69 % 8 0.60% 0.68%
kyber768/decap_mean 33.3 us 33.2 us 8 155.52k 30.0789k/s
kyber768/decap_median 33.2 us 33.2 us 8 155.26k 30.0966k/s
kyber768/decap_stddev 0.147 us 0.139 us 8 552.726 125.078/s
kyber768/decap_cv 0.44 % 0.42 % 8 0.36% 0.42%
kyber1024/encap_mean 44.3 us 44.3 us 8 206.579k 22.5924k/s
kyber1024/encap_median 44.3 us 44.3 us 8 206.455k 22.5788k/s
kyber1024/encap_stddev 0.147 us 0.145 us 8 549.686 74.1456/s
kyber1024/encap_cv 0.33 % 0.33 % 8 0.27% 0.33%
kyber512/encap_mean 18.0 us 18.0 us 8 84.133k 55.5064k/s
kyber512/encap_median 18.0 us 18.0 us 8 84.1549k 55.5051k/s
kyber512/encap_stddev 0.064 us 0.061 us 8 151.114 186.754/s
kyber512/encap_cv 0.36 % 0.34 % 8 0.18% 0.34%
kyber768/encap_mean 29.7 us 29.7 us 8 138.837k 33.6446k/s
kyber768/encap_median 29.7 us 29.7 us 8 138.648k 33.7164k/s
kyber768/encap_stddev 0.161 us 0.158 us 8 633.267 178.415/s
kyber768/encap_cv 0.54 % 0.53 % 8 0.46% 0.53%
kyber1024/keygen_mean 38.8 us 38.8 us 8 180.897k 25.7986k/s
kyber1024/keygen_median 38.9 us 38.8 us 8 181.344k 25.7401k/s
kyber1024/keygen_stddev 0.268 us 0.267 us 8 1.09543k 179.632/s
kyber1024/keygen_cv 0.69 % 0.69 % 8 0.61% 0.70%
On 12th Gen Intel(R) Core(TM) i7-1260P ( compiled with Clang-17.0.2 )
2023-12-05T22:32:40+04:00
Running ./build/perf.out
Run on (16 X 1113.91 MHz CPU s)
CPU Caches:
L1 Data 48 KiB (x8)
L1 Instruction 32 KiB (x8)
L2 Unified 1280 KiB (x8)
L3 Unified 18432 KiB (x1)
Load Average: 0.70, 0.54, 0.52
----------------------------------------------------------------------------------------------
Benchmark Time CPU Iterations CYCLES items_per_second
----------------------------------------------------------------------------------------------
kyber1024/encap_mean 39.4 us 39.4 us 8 184.447k 25.3726k/s
kyber1024/encap_median 39.4 us 39.4 us 8 184.349k 25.4044k/s
kyber1024/encap_stddev 0.111 us 0.110 us 8 666.498 70.9216/s
kyber1024/encap_cv 0.28 % 0.28 % 8 0.36% 0.28%
kyber768/encap_mean 25.2 us 25.2 us 8 118.269k 39.6068k/s
kyber768/encap_median 25.2 us 25.2 us 8 118.098k 39.6763k/s
kyber768/encap_stddev 0.190 us 0.191 us 8 944.954 296.817/s
kyber768/encap_cv 0.75 % 0.76 % 8 0.80% 0.75%
kyber768/decap_mean 27.4 us 27.4 us 8 128.276k 36.4705k/s
kyber768/decap_median 27.4 us 27.4 us 8 128.023k 36.5011k/s
kyber768/decap_stddev 0.148 us 0.147 us 8 725.711 194.118/s
kyber768/decap_cv 0.54 % 0.54 % 8 0.57% 0.53%
kyber512/keygen_mean 11.7 us 11.7 us 8 54.4158k 85.6074k/s
kyber512/keygen_median 11.6 us 11.6 us 8 54.4761k 85.8637k/s
kyber512/keygen_stddev 0.157 us 0.157 us 8 230.812 1.1305k/s
kyber512/keygen_cv 1.35 % 1.35 % 8 0.42% 1.32%
kyber1024/keygen_mean 31.2 us 31.2 us 8 146.117k 32.0219k/s
kyber1024/keygen_median 31.3 us 31.3 us 8 146.447k 31.9462k/s
kyber1024/keygen_stddev 0.443 us 0.443 us 8 2.14262k 460.613/s
kyber1024/keygen_cv 1.42 % 1.42 % 8 1.47% 1.44%
kyber512/decap_mean 16.8 us 16.8 us 8 78.599k 59.5481k/s
kyber512/decap_median 16.8 us 16.8 us 8 78.6311k 59.5517k/s
kyber512/decap_stddev 0.154 us 0.154 us 8 750.744 545.456/s
kyber512/decap_cv 0.92 % 0.92 % 8 0.96% 0.92%
kyber512/encap_mean 15.4 us 15.4 us 8 71.9738k 65.0018k/s
kyber512/encap_median 15.3 us 15.3 us 8 71.6988k 65.2546k/s
kyber512/encap_stddev 0.172 us 0.172 us 8 790.241 725.525/s
kyber512/encap_cv 1.12 % 1.12 % 8 1.10% 1.12%
kyber768/keygen_mean 20.5 us 20.5 us 8 95.9542k 48.737k/s
kyber768/keygen_median 20.5 us 20.5 us 8 95.9397k 48.6711k/s
kyber768/keygen_stddev 0.096 us 0.096 us 8 523.379 227.911/s
kyber768/keygen_cv 0.47 % 0.47 % 8 0.55% 0.47%
kyber1024/decap_mean 41.8 us 41.8 us 8 194.826k 23.9134k/s
kyber1024/decap_median 41.7 us 41.7 us 8 194.774k 24.0016k/s
kyber1024/decap_stddev 0.526 us 0.523 us 8 573.604 291.732/s
kyber1024/decap_cv 1.26 % 1.25 % 8 0.29% 1.22%
On ARM Cortex-A72 i.e. Raspberry Pi 4B ( compiled with GCC-13.2.0 )
2023-12-06T00:37:57+05:30
Running ./build/perf.out
Run on (4 X 1800 MHz CPU s)
CPU Caches:
L1 Data 32 KiB (x4)
L1 Instruction 48 KiB (x4)
L2 Unified 1024 KiB (x1)
Load Average: 0.69, 1.28, 1.13
Performance counters not supported.
-----------------------------------------------------------------------------------
Benchmark Time CPU Iterations items_per_second
-----------------------------------------------------------------------------------
kyber1024/encap_mean 220 us 220 us 10 4.53661k/s
kyber1024/encap_median 220 us 220 us 10 4.53843k/s
kyber1024/encap_stddev 0.775 us 0.776 us 10 15.9613/s
kyber1024/encap_cv 0.35 % 0.35 % 10 0.35%
kyber768/encap_mean 147 us 146 us 10 6.82666k/s
kyber768/encap_median 146 us 146 us 10 6.82827k/s
kyber768/encap_stddev 0.370 us 0.357 us 10 16.6515/s
kyber768/encap_cv 0.25 % 0.24 % 10 0.24%
kyber1024/keygen_mean 189 us 189 us 10 5.30215k/s
kyber1024/keygen_median 188 us 188 us 10 5.30614k/s
kyber1024/keygen_stddev 0.588 us 0.590 us 10 16.5559/s
kyber1024/keygen_cv 0.31 % 0.31 % 10 0.31%
kyber512/decap_mean 106 us 106 us 10 9.45067k/s
kyber512/decap_median 106 us 106 us 10 9.45608k/s
kyber512/decap_stddev 0.243 us 0.250 us 10 22.2866/s
kyber512/decap_cv 0.23 % 0.24 % 10 0.24%
kyber768/decap_mean 169 us 169 us 10 5.91167k/s
kyber768/decap_median 169 us 169 us 10 5.91724k/s
kyber768/decap_stddev 0.639 us 0.623 us 10 21.6423/s
kyber768/decap_cv 0.38 % 0.37 % 10 0.37%
kyber512/encap_mean 89.0 us 89.0 us 10 11.236k/s
kyber512/encap_median 89.0 us 89.0 us 10 11.2376k/s
kyber512/encap_stddev 0.216 us 0.222 us 10 28.0647/s
kyber512/encap_cv 0.24 % 0.25 % 10 0.25%
kyber768/keygen_mean 119 us 119 us 10 8.37056k/s
kyber768/keygen_median 119 us 119 us 10 8.38088k/s
kyber768/keygen_stddev 0.623 us 0.615 us 10 42.9127/s
kyber768/keygen_cv 0.52 % 0.51 % 10 0.51%
kyber1024/decap_mean 249 us 249 us 10 4.02233k/s
kyber1024/decap_median 249 us 249 us 10 4.02281k/s
kyber1024/decap_stddev 0.721 us 0.706 us 10 11.4051/s
kyber1024/decap_cv 0.29 % 0.28 % 10 0.28%
kyber512/keygen_mean 70.1 us 70.0 us 10 14.2774k/s
kyber512/keygen_median 70.1 us 70.1 us 10 14.2713k/s
kyber512/keygen_stddev 0.198 us 0.196 us 10 40.0484/s
kyber512/keygen_cv 0.28 % 0.28 % 10 0.28%
On ARM Cortex-A72 i.e. Raspberry Pi 4B ( compiled with Clang-17.0.2 )
2023-12-06T00:36:20+05:30
Running ./build/perf.out
Run on (4 X 1800 MHz CPU s)
CPU Caches:
L1 Data 32 KiB (x4)
L1 Instruction 48 KiB (x4)
L2 Unified 1024 KiB (x1)
Load Average: 0.73, 1.55, 1.20
Performance counters not supported.
-----------------------------------------------------------------------------------
Benchmark Time CPU Iterations items_per_second
-----------------------------------------------------------------------------------
kyber1024/encap_mean 297 us 297 us 10 3.36489k/s
kyber1024/encap_median 297 us 297 us 10 3.36366k/s
kyber1024/encap_stddev 1.08 us 1.09 us 10 12.2899/s
kyber1024/encap_cv 0.36 % 0.37 % 10 0.37%
kyber1024/keygen_mean 254 us 254 us 10 3.93546k/s
kyber1024/keygen_median 254 us 254 us 10 3.93845k/s
kyber1024/keygen_stddev 1.05 us 1.05 us 10 16.2184/s
kyber1024/keygen_cv 0.41 % 0.41 % 10 0.41%
kyber512/decap_mean 129 us 129 us 10 7.72535k/s
kyber512/decap_median 130 us 129 us 10 7.72301k/s
kyber512/decap_stddev 0.293 us 0.284 us 10 16.9731/s
kyber512/decap_cv 0.23 % 0.22 % 10 0.22%
kyber768/encap_mean 193 us 193 us 10 5.16967k/s
kyber768/encap_median 193 us 193 us 10 5.17074k/s
kyber768/encap_stddev 0.416 us 0.426 us 10 11.3712/s
kyber768/encap_cv 0.22 % 0.22 % 10 0.22%
kyber1024/decap_mean 320 us 320 us 10 3.12381k/s
kyber1024/decap_median 320 us 320 us 10 3.12274k/s
kyber1024/decap_stddev 0.813 us 0.805 us 10 7.85819/s
kyber1024/decap_cv 0.25 % 0.25 % 10 0.25%
kyber768/decap_mean 211 us 211 us 10 4.73723k/s
kyber768/decap_median 211 us 211 us 10 4.73735k/s
kyber768/decap_stddev 0.374 us 0.391 us 10 8.77749/s
kyber768/decap_cv 0.18 % 0.19 % 10 0.19%
kyber512/encap_mean 116 us 116 us 10 8.59258k/s
kyber512/encap_median 116 us 116 us 10 8.59042k/s
kyber512/encap_stddev 0.222 us 0.216 us 10 15.9794/s
kyber512/encap_cv 0.19 % 0.19 % 10 0.19%
kyber512/keygen_mean 92.6 us 92.6 us 10 10.7953k/s
kyber512/keygen_median 92.4 us 92.4 us 10 10.8198k/s
kyber512/keygen_stddev 0.692 us 0.695 us 10 79.7935/s
kyber512/keygen_cv 0.75 % 0.75 % 10 0.74%
kyber768/keygen_mean 159 us 159 us 10 6.29988k/s
kyber768/keygen_median 159 us 159 us 10 6.30371k/s
kyber768/keygen_stddev 0.714 us 0.712 us 10 28.124/s
kyber768/keygen_cv 0.45 % 0.45 % 10 0.45%
Usage
kyber is written as a header-only C++ library, majorly targeting 64 -bit platforms and it's pretty easy to get started with. All you need to do is following.
- Clone
kyberrepository.
cd
# Multi-step cloning and importing of submodules
git clone https://github.com/itzmeanjan/kyber.git && pushd kyber && git submodule update --init && popd
# Or do single step cloning and importing of submodules
git clone https://github.com/itzmeanjan/kyber.git --recurse-submodules
- Write your program while including proper header files ( based on which variant of Kyber KEM you want to use, see include directory ), which includes declarations ( and definitions ) of all required KEM routines and constants ( such as byte length of public/ private keys and cipher text ).
// main.cpp
#include "kyber512_kem.hpp"
#include <algorithm>
#include <array>
#include <cassert>
int
main()
{
std::array<uint8_t, 32> d{}; // seed
std::array<uint8_t, 32> z{}; // seed
std::array<uint8_t, kyber512_kem::PKEY_LEN> pkey{};
std::array<uint8_t, kyber512_kem::SKEY_LEN> skey{};
std::array<uint8_t, 32> m{}; // seed
std::array<uint8_t, kyber512_kem::CIPHER_LEN> cipher{};
// Be careful !
//
// Read API documentation in include/prng.hpp
prng::prng_t prng;
prng.read(d);
prng.read(z);
prng.read(m);
kyber512_kem::keygen(d, z, pkey, skey);
auto skdf = kyber512_kem::encapsulate(m, pkey, cipher);
auto rkdf = kyber512_kem::decapsulate(skey, cipher);
std::array<uint8_t, 32> sender_key{};
skdf.squeeze(sender_key);
std::array<uint8_t, 32> receiver_key{};
rkdf.squeeze(receiver_key);
assert(std::ranges::equal(sender_key, receiver_key));
return 0;
}
- When compiling your program, let your compiler know where it can find
kyber,sha3andsubtleheaders, which includes their definitions ( kyber being a header-only library ) too.
# Assuming `kyber` was cloned just under $HOME
KYBER_HEADERS=~/kyber/include
SHA3_HEADERS=~/kyber/sha3/include
SUBTLE_HEADERS=~/kyber/subtle/include
g++ -std=c++20 -Wall -O3 -march=native -I $KYBER_HEADERS -I $SHA3_HEADERS -I $SUBTLE_HEADERS main.cpp
| Kyber KEM Variant | Namespace | Header |
|---|---|---|
| Kyber512 KEM Routines | kyber512_kem:: |
include/kyber512_kem.hpp |
| Kyber768 KEM Routines | kyber768_kem:: |
include/kyber768_kem.hpp |
| Kyber1024 KEM Routines | kyber1024_kem:: |
include/kyber1024_kem.hpp |
Note
Kyber parameter sets are selected from table 1 of Kyber specification https://pq-crystals.org/kyber/data/kyber-specification-round3-20210804.pdf.
See example program, where I show how to use Kyber512 KEM API. You can almost similarly use Kyber768 or Kyber1024 KEM API, by just importing correct header file and using KEM functions/ constants from respective namespace.
g++ -std=c++20 -Wall -Wextra -pedantic -O3 -march=native -I ./include -I ./sha3/include -I ./subtle/include/ examples/kyber512_kem.cpp && ./a.out
Kyber512 KEM
pubkey : 175782d35b2666833aee098617626d88dbcc47091a011882d52105acc218c9287a95276a3259a6a94aa386d8148886abdcc1841f39260ce4754ebacc1fd36102905d4c623d0b27930b4c249ee7380758c0ac5982b0e932eda95184a40f55c451d835861ca2b314dbce97829f1b92752dda592d8960b2540f464988ea1c974c63467c439b1de540490b0af0491a6507951ebc971887bd2b4a11327381d99586f10668c83abe92fb649b113da7ec666729bc1cc38a1de137dd3cc4e3a6abb9881a2ee63e7df3ad6cb680664ba1559ca17448c968b7c867ac5f324911ffd43993b8a7b8f57094c786877c1208fa7f53e51d6f1a46ae71bc81f78ebe5808d48200b7e1bc81ec3d31070a6993aa5db237eb3a4c592aa559a73bd769583a0ad095ec1669b952be4a71fe8603f5d597f007a048cc9d7fea6735383b6b8bbf896b74dc48a21840a92c497a9bc7434b0241a9e42e6428515d477c4e0b3678fab1d619b794f01b828648e7577bb2e5297915b9fdf33cb291a37de51b51c7aca6f07994193bd981134da2340c23a93cda8b68e429ac801d3748b8d112b57e388511e3305e50a51184b623607447468be94351cd0b9111a119b4b3c6f270c1cfea749a2ac89455590280c369163946481dbaeb4693dbb376202db2d8464c61aea6411cd887080f5c59e1587da01510cd1b0e8b030a5c200639ba26376134e88279891b90373cc92e7a76c0aaa33d084ab3f61e175010996652e441300ad5aefda9cc88f17fef2102b643179e0a49a60c47ce06c5b1a0b150b09ca4593e5dd48a9b1979d103ba862c43ed354d2ec99575b70e741808288aa0e1cb792c0a458d4584ddfa1870d7b797e2aac7d4cc08916015401338d8841d226d9656661cda93f53343e0f906b82bce8f25428b02a639a47f7dda5b946a3785656fb6d083df5a5ec7493cc017a2469b1f43c96f2e3bbc9d6cb07bec82d721a4cfba6ca2c59b0e01bda98585692b9da753923f830b52c843b6d963f959ad60189f42d61df7808f4d131c4d233e246c4735193e516452061701e6114cf1587a54c79105f48fdce9c2134bb60550b242945ea011ec54c570054b93d96f072426b7c9b524db8d2f136b7db2d1f38897
seckey : a598a250c2008688af8f71a285abae5b528a19479acf915cd2f92a7365bc757c670accc4b2190aa77b7d0c76355962a0ea9b6a1f4400be77797a6851776815032307913aa475b733a1ba698b2134ea25a57bd9b979e2bcb7d99f24f06ee760227486ae1cdaba79065bc3180d79a0906c514e5b973435c00f34b87e882643ef6b42bcbca4a3b65207abb5dca76e49a9be7a6013d256bc09b1211b70bb28e2151200c6c1e00082e88634600a29e3cf5ff541051c703ac373a91228a6d30491221df6749e22b21429612ed4ba07a7d7789717809e498f2e3a1b8a6a40afe0a7d2460350074a2a5127cc20c0b03446977a612a096324337cd5bc455f77cdbe4600e147b02fe58bc9c383b1e84ea3bc5755d3a87ce515b07c96741a72d9eb702d445acc3374531c70ef221216db2c9198110d83084f7b508da18fd34b8ee9f45d1204a627609d09a89c73e8bfc1f987c6bc906fac0d01720b169061b3d8015a5121a0d3beab454a03cc24a9bc5725e6c4aaf44d8f8b7242443f289c0751226448ec794a02a1ba411caeabb99f7a90510b8812a91a0ad69f1476408940381724a1dbfb7f69642788267b068c585bf41bf3f857fd14bcd9506b95b6a257d7481a07628004944e136a4c97842c13451e960cf4e08a8b6666e17a6aac016d701c1a00c82072939a092397c7104d7fd6332b860034f2ace5191e2792cf10e21f5166304bf329696128d63640b7882809b750f1f89e5d513fa08a8439e1ad5fe0affd887b0f06ab91798c35d48f39261af3dab7ddbc899be21d1f751b8d317b8e280f400b637ac6a471b4065973a6253235c94117e22083562b715ce680fafb78da9113f0f52692c52625ea8e1c24a1d8837beb963a5ab078455c8a43cbab68dc4eaa4c7646c9bb45803442250e935738944c7228aa3f7137567eb1231c63bff7552a7858525b92bdca832a41cb20fb24647a62af1da27e50c41f3cd070ed8c1d1213c22b1540a5c1412d67ab4ff334c2e5217c06a5f8a93c0637bd0fb4736c19591f67c378aa80f7c9587b346bbfe81eff8574c7e0acc3164c3df048019639a80377b97457175782d35b2666833aee098617626d88dbcc47091a011882d52105acc218c9287a95276a3259a6a94aa386d8148886abdcc1841f39260ce4754ebacc1fd36102905d4c623d0b27930b4c249ee7380758c0ac5982b0e932eda95184a40f55c451d835861ca2b314dbce97829f1b92752dda592d8960b2540f464988ea1c974c63467c439b1de540490b0af0491a6507951ebc971887bd2b4a11327381d99586f10668c83abe92fb649b113da7ec666729bc1cc38a1de137dd3cc4e3a6abb9881a2ee63e7df3ad6cb680664ba1559ca17448c968b7c867ac5f324911ffd43993b8a7b8f57094c786877c1208fa7f53e51d6f1a46ae71bc81f78ebe5808d48200b7e1bc81ec3d31070a6993aa5db237eb3a4c592aa559a73bd769583a0ad095ec1669b952be4a71fe8603f5d597f007a048cc9d7fea6735383b6b8bbf896b74dc48a21840a92c497a9bc7434b0241a9e42e6428515d477c4e0b3678fab1d619b794f01b828648e7577bb2e5297915b9fdf33cb291a37de51b51c7aca6f07994193bd981134da2340c23a93cda8b68e429ac801d3748b8d112b57e388511e3305e50a51184b623607447468be94351cd0b9111a119b4b3c6f270c1cfea749a2ac89455590280c369163946481dbaeb4693dbb376202db2d8464c61aea6411cd887080f5c59e1587da01510cd1b0e8b030a5c200639ba26376134e88279891b90373cc92e7a76c0aaa33d084ab3f61e175010996652e441300ad5aefda9cc88f17fef2102b643179e0a49a60c47ce06c5b1a0b150b09ca4593e5dd48a9b1979d103ba862c43ed354d2ec99575b70e741808288aa0e1cb792c0a458d4584ddfa1870d7b797e2aac7d4cc08916015401338d8841d226d9656661cda93f53343e0f906b82bce8f25428b02a639a47f7dda5b946a3785656fb6d083df5a5ec7493cc017a2469b1f43c96f2e3bbc9d6cb07bec82d721a4cfba6ca2c59b0e01bda98585692b9da753923f830b52c843b6d963f959ad60189f42d61df7808f4d131c4d233e246c4735193e516452061701e6114cf1587a54c79105f48fdce9c2134bb60550b242945ea011ec54c570054b93d96f072426b7c9b524db8d2f136b7db2d1f3889778f791d583227a702cdfa4a9f95014df019495f14e02318b3704dc3794af523705be75f29753f47b2888ceef235d82caca9f983b40bf10b29672da272113a973
cipher : bcee459c896ea378dcc458a532c35c029eff6b8cf8adc83f484fb6f9bfe32612f7c936cbf4dbd7c5262288dc3966a0d769f94a0bd57913a60a71efae09321c22c53839d836cef5fb8bf5c630bd3b3d657492eabfc7e67a42a631c95391656f0fce607a181e418144dff3d97f1192a2825a94da5113bcffc2e5f3e043f7583e6159902ddd009f8bcb18046a05695917bdef48accc2e3708f8536aabb420a7fd7989c60bca6c1941af45eac2f03cf71c8506721f8cd69bd3c573f036e3e8ae72b85632d06e0cab6fa1fea078d84aa1a116ac58ee632a0542b2d0e6a7026ae814ceeb46478d1cefd082c9b19efa7bb6ddd7abda8e43eab7b5a5204449273ea056b36d3797371f855d0c7ff0436279b21b831ad0970c26cc39f8627deb932689b8df48e73b1b5893987fa4dbc65571a78287f1573beeb85db52a3edbad6f50725bcbfa40423e3ce1ab00c16ea3922bc42e6782ce224ccfb3c978d8704584b9768a8edb6a950c0208b1c1c9a6a4e0d6300a9cfe788389697460efc41308448e9752d2022dfdecd118440346e2fabb07559b76301943f3b186adaaba09828efb28db1cd4a5e82e01f360451cb3c487f371af05725ea0e7d61932a8dc38108e99182e9b50d2aa828a773a2e18f5271ac75e5a5c50b9221f893e5f7076732beb0ffb9e4b82e1c0648192c9547870372b78c6a3e3a1b00d904a4a1492d5944e0510acee62e40c78cecef97922b04807cdd47d4d403a7bb16316598e6eee760b257382d9648c9920c3395717d8ac829bd37465c0f3e7f0c7e6fc351aac802edb722200776906eb36f622c0b8702958e44317961f583265a83b8cfcd9eed80f15b9ef848ebb7355df9718a60c532e20074854797685b3e4a25f929fce9ad02a5af114f92210abd3b73fddf28f116c2d4c27ceda6428a3892eb0c18fc12b07596e4153f2a3df9aa440957704bc56bbbee06cd99def3218c046344b4c5a811840a088bcbbad76fca4a20b9bf608873b2830afd6097b05022e8b1d42af3e5e4f00303adc9f130a84cdde3fef9335ccd1120b3f2050f17ef0c10fd226268965cbfc13738ada0632
shared secret : 508ac79bf97e90d75267159ba5189b73c48ab41a91aec0f32edd6cd1e66465b5
Caution
Before you consider using Psuedo Random Number Generator which comes with this library implementation, I strongly advice you to go through include/prng.hpp.
Note
Looking at API documentation, in header files, can give you good idea of how to use Kyber KEM API. Note, this library doesn't expose any raw pointer based interface, rather everything is wrapped under statically defined
std::span- which one can easily create fromstd::{array, vector}. I opt for using statically definedstd::spanbased function interfaces because we always know, at compile-time, how many bytes the seeds/ keys/ cipher-texts/ shared-secrets are, for various different Kyber KEM parameters. This gives much better type safety and compile-time error reporting.