Skip to content

Commit fedbedf

Browse files
committed
[skip ci] Fix memory leak in XOF and hash_<g|h|i|j>
Signed-off-by: Ganyu (Bruce) Xu <g66xu@uwaterloo.ca>
1 parent 341e05c commit fedbedf

19 files changed

Lines changed: 61 additions & 4 deletions

File tree

README.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -61,7 +61,7 @@ All names other than `ML-KEM` and `ML-DSA` are subject to change. `liboqs` makes
6161
| BIKE | Not selected by [NIST](https://bikesuite.org/files/v5.1/BIKE_Spec.2022.10.10.1.pdf) | [`awslabs/bike-kem`](https://github.com/awslabs/bike-kem) |
6262
| Classic McEliece | Under [ISO](https://classic.mceliece.org/iso.html) consideration | [`PQClean/PQClean@1eacfda`](https://github.com/PQClean/PQClean/commit/1eacfdafc15ddc5d5759d0b85b4cef26627df181) |
6363
| FrodoKEM | Under [ISO](https://frodokem.org/) consideration | [`microsoft/PQCrypto-LWEKE@a2f9dec`](https://github.com/microsoft/PQCrypto-LWEKE/commit/a2f9dec8917ccc3464b3378d46b140fa7353320d) |
64-
| HQC | Selected by [NIST](https://pqc-hqc.org/doc/hqc_specifications_2025_08_22.pdf) for upcoming standardization | [`xuganyu96/pqc-hqc@37555f2`](https://github.com/xuganyu96/pqc-hqc/commit/37555f24745e93554a10875c66fa5dd30594eefc) |
64+
| HQC | Selected by [NIST](https://pqc-hqc.org/doc/hqc_specifications_2025_08_22.pdf) for upcoming standardization | [`xuganyu96/pqc-hqc@1b45cfa`](https://github.com/xuganyu96/pqc-hqc/commit/1b45cfa0b85f0fcf363b5f2d75dcf3286a551b52) |
6565
| Kyber | Selected by [NIST](https://csrc.nist.gov/CSRC/media/Projects/post-quantum-cryptography/documents/round-3/submissions/Kyber-Round3.zip) as basis for ML-KEM (FIPS 203) | [`pq-crystals/kyber@441c051`](https://github.com/pq-crystals/kyber/commit/441c0519a07e8b86c8d079954a6b10bd31d29efc) |
6666
| ML-KEM | Standardized by [NIST](https://csrc.nist.gov/pubs/fips/203/final) | [`pq-code-package/mlkem-native@d2cae2b`](https://github.com/pq-code-package/mlkem-native/commit/d2cae2be522a67bfae26100fdb520576f1b2ef90) |
6767
| NTRU | Not selected by [NIST](https://csrc.nist.gov/CSRC/media/Projects/post-quantum-cryptography/documents/round-3/submissions/NTRU-Round3.zip), under standardization consideration by [NTT](https://info.isl.ntt.co.jp/crypt/ntru/index.html) | [`PQClean/PQClean@4c9e5a3`](https://github.com/PQClean/PQClean/commit/4c9e5a3aa715cc8d1d0e377e4e6e682ebd7602d6) |

docs/algorithms/kem/hqc.md

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
- **Authors' website**: https://pqc-hqc.org/
88
- **Specification version**: 2025-08-22.
99
- **Primary Source**<a name="primary-source"></a>:
10-
- **Source**: https://github.com/xuganyu96/pqc-hqc/commit/37555f24745e93554a10875c66fa5dd30594eefc
10+
- **Source**: https://github.com/xuganyu96/pqc-hqc/commit/1b45cfa0b85f0fcf363b5f2d75dcf3286a551b52
1111
- **Implementation license (SPDX-Identifier)**: Public domain
1212
- **Ancestors of primary source**:
1313
- https://gitlab.com/pqc-hqc, which takes it from:

docs/algorithms/kem/hqc.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -68,7 +68,7 @@ parameter-sets:
6868
default: true
6969
primary-upstream:
7070
spdx-license-identifier: Public domain
71-
source: https://github.com/xuganyu96/pqc-hqc/commit/37555f24745e93554a10875c66fa5dd30594eefc
71+
source: https://github.com/xuganyu96/pqc-hqc/commit/1b45cfa0b85f0fcf363b5f2d75dcf3286a551b52
7272
default-upstream-id: ref
7373
auxiliary-submitters:
7474
- Carlos Aguilar-Melchor

scripts/copy_from_upstream/copy_from_upstream.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@ upstreams:
33
name: xuganyu96-hqc
44
git_url: https://github.com/xuganyu96/pqc-hqc.git
55
git_branch: liboqs-integration
6-
git_commit: 37555f24745e93554a10875c66fa5dd30594eefc
6+
git_commit: 1b45cfa0b85f0fcf363b5f2d75dcf3286a551b52
77
kem_meta_path: "integrations/{pretty_name_full}_META.yml"
88
kem_scheme_path: .
99
patches: []

src/kem/hqc/xuganyu96-hqc_hqc-1_ref/hqc.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,10 +46,12 @@ void hqc_pke_keygen(uint8_t *ek_pke, uint8_t *dk_pke, uint8_t *seed) {
4646
xof_init(&dk_xof_ctx, seed_dk, SEED_BYTES);
4747
vect_sample_fixed_weight1(&dk_xof_ctx, y, PARAM_OMEGA);
4848
vect_sample_fixed_weight1(&dk_xof_ctx, x, PARAM_OMEGA);
49+
xof_ctx_release(&dk_xof_ctx);
4950

5051
// Compute encryption key
5152
xof_init(&ek_xof_ctx, seed_ek, SEED_BYTES);
5253
vect_set_random(&ek_xof_ctx, h);
54+
xof_ctx_release(&ek_xof_ctx);
5355
vect_mul(s, y, h);
5456
vect_add(s, x, s, VEC_N_SIZE_64);
5557

@@ -113,6 +115,7 @@ void hqc_pke_encrypt(ciphertext_pke_t *c_pke, const uint8_t *ek_pke, const uint6
113115
vect_sample_fixed_weight2(&theta_xof_ctx, r2, PARAM_OMEGA_R);
114116
vect_sample_fixed_weight2(&theta_xof_ctx, e, PARAM_OMEGA_E);
115117
vect_sample_fixed_weight2(&theta_xof_ctx, r1, PARAM_OMEGA_R);
118+
xof_ctx_release(&theta_xof_ctx);
116119

117120
// Compute u = r1 + r2.h
118121
vect_mul(c_pke->u, r2, h);

src/kem/hqc/xuganyu96-hqc_hqc-1_ref/kem.c

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -61,6 +61,7 @@ int crypto_kem_keypair(uint8_t *ek_kem, uint8_t *dk_kem) {
6161
xof_init(&ctx_kem, seed_kem, SEED_BYTES);
6262
xof_get_bytes(&ctx_kem, seed_pke, SEED_BYTES);
6363
xof_get_bytes(&ctx_kem, sigma, PARAM_SECURITY_BYTES);
64+
xof_ctx_release(&ctx_kem);
6465

6566
// Compute HQC-PKE keypair
6667
hqc_pke_keygen(ek_pke, dk_pke, seed_pke);

src/kem/hqc/xuganyu96-hqc_hqc-1_ref/parsing.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ void hqc_dk_pke_from_string(uint64_t *y, const uint8_t *dk_pke) {
2020
shake256_xof_ctx dk_xof_ctx = {0};
2121
xof_init(&dk_xof_ctx, dk_pke, SEED_BYTES);
2222
vect_sample_fixed_weight1(&dk_xof_ctx, y, PARAM_OMEGA);
23+
xof_ctx_release(&dk_xof_ctx);
2324

2425
// Zeroize sensitive data
2526
memset_zero(&dk_xof_ctx, sizeof dk_xof_ctx);
@@ -37,6 +38,7 @@ void hqc_ek_pke_from_string(uint64_t *h, uint64_t *s, const uint8_t *ek_pke) {
3738

3839
xof_init(&ek_xof_ctx, ek_pke, SEED_BYTES);
3940
vect_set_random(&ek_xof_ctx, h);
41+
xof_ctx_release(&ek_xof_ctx);
4042

4143
memcpy(s, ek_pke + SEED_BYTES, VEC_N_SIZE_BYTES);
4244
}

src/kem/hqc/xuganyu96-hqc_hqc-1_ref/symmetric.c

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,13 @@ void xof_get_bytes(shake256_xof_ctx *xof_ctx, uint8_t *output, uint32_t output_s
7575
OQS_SHA3_shake256_inc_squeeze(output, output_size, xof_ctx);
7676
}
7777

78+
/**
79+
* @brief Free heap-allocated memory in the SHAKE256 XOF context
80+
*/
81+
void xof_ctx_release(shake256_xof_ctx *xof_ctx) {
82+
OQS_SHA3_shake256_inc_ctx_release(xof_ctx);
83+
}
84+
7885
/**
7986
* @brief Computes the hash function I (SHA3-512) with domain separation.
8087
*
@@ -91,6 +98,7 @@ void hash_i(uint8_t *output, const uint8_t *seed) {
9198
OQS_SHA3_sha3_512_inc_absorb(&i_hash_ctx, seed, SEED_BYTES);
9299
OQS_SHA3_sha3_512_inc_absorb(&i_hash_ctx, &i_domain, 1);
93100
OQS_SHA3_sha3_512_inc_finalize(output, &i_hash_ctx);
101+
OQS_SHA3_sha3_512_inc_ctx_release(&i_hash_ctx);
94102
}
95103

96104
/**
@@ -106,6 +114,7 @@ void hash_h(uint8_t *output, const uint8_t ek_kem[PUBLIC_KEY_BYTES]) {
106114
OQS_SHA3_sha3_256_inc_absorb(&h_hash_ctx, ek_kem, PUBLIC_KEY_BYTES);
107115
OQS_SHA3_sha3_256_inc_absorb(&h_hash_ctx, &h_domain, 1);
108116
OQS_SHA3_sha3_256_inc_finalize(output, &h_hash_ctx);
117+
OQS_SHA3_sha3_256_inc_ctx_release(&h_hash_ctx);
109118
}
110119

111120
/**
@@ -126,6 +135,7 @@ void hash_g(uint8_t *output, const uint8_t hash_ek_kem[SEED_BYTES], const uint8_
126135
OQS_SHA3_sha3_512_inc_absorb(&g_hash_ctx, salt, SALT_BYTES);
127136
OQS_SHA3_sha3_512_inc_absorb(&g_hash_ctx, &i_domain, 1);
128137
OQS_SHA3_sha3_512_inc_finalize(output, &g_hash_ctx);
138+
OQS_SHA3_sha3_512_inc_ctx_release(&g_hash_ctx);
129139
}
130140

131141
/**
@@ -148,4 +158,5 @@ void hash_j(uint8_t *output, const uint8_t hash_ek_kem[SEED_BYTES], const uint8_
148158
OQS_SHA3_sha3_256_inc_absorb(&k_hash_ctx, c_kem->salt, SALT_BYTES);
149159
OQS_SHA3_sha3_256_inc_absorb(&k_hash_ctx, &k_domain, 1);
150160
OQS_SHA3_sha3_256_inc_finalize(output, &k_hash_ctx);
161+
OQS_SHA3_sha3_256_inc_ctx_release(&k_hash_ctx);
151162
}

src/kem/hqc/xuganyu96-hqc_hqc-1_ref/symmetric.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -73,6 +73,7 @@ typedef OQS_SHA3_shake256_inc_ctx shake256_xof_ctx;
7373
#define prng_get_bytes PQCHQC_NAMESPACE(prng_get_bytes)
7474
#define xof_init PQCHQC_NAMESPACE(xof_init)
7575
#define xof_get_bytes PQCHQC_NAMESPACE(xof_get_bytes)
76+
#define xof_ctx_release PQCHQC_NAMESPACE(xof_ctx_release)
7677
#define hash_g PQCHQC_NAMESPACE(hash_g)
7778
#define hash_h PQCHQC_NAMESPACE(hash_h)
7879
#define hash_i PQCHQC_NAMESPACE(hash_i)
@@ -83,6 +84,7 @@ void prng_get_bytes(uint8_t *output, uint32_t outlen);
8384

8485
void xof_init(shake256_xof_ctx *xof_ctx, const uint8_t *seed, uint32_t seed_size);
8586
void xof_get_bytes(shake256_xof_ctx *xof_ctx, uint8_t *output, uint32_t output_size);
87+
void xof_ctx_release(shake256_xof_ctx *xof_ctx);
8688

8789
void hash_g(uint8_t *output, const uint8_t h_ek[SEED_BYTES], const uint8_t m[VEC_K_SIZE_BYTES],
8890
const uint8_t salt[SALT_BYTES]);

src/kem/hqc/xuganyu96-hqc_hqc-3_ref/hqc.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,10 +46,12 @@ void hqc_pke_keygen(uint8_t *ek_pke, uint8_t *dk_pke, uint8_t *seed) {
4646
xof_init(&dk_xof_ctx, seed_dk, SEED_BYTES);
4747
vect_sample_fixed_weight1(&dk_xof_ctx, y, PARAM_OMEGA);
4848
vect_sample_fixed_weight1(&dk_xof_ctx, x, PARAM_OMEGA);
49+
xof_ctx_release(&dk_xof_ctx);
4950

5051
// Compute encryption key
5152
xof_init(&ek_xof_ctx, seed_ek, SEED_BYTES);
5253
vect_set_random(&ek_xof_ctx, h);
54+
xof_ctx_release(&ek_xof_ctx);
5355
vect_mul(s, y, h);
5456
vect_add(s, x, s, VEC_N_SIZE_64);
5557

@@ -113,6 +115,7 @@ void hqc_pke_encrypt(ciphertext_pke_t *c_pke, const uint8_t *ek_pke, const uint6
113115
vect_sample_fixed_weight2(&theta_xof_ctx, r2, PARAM_OMEGA_R);
114116
vect_sample_fixed_weight2(&theta_xof_ctx, e, PARAM_OMEGA_E);
115117
vect_sample_fixed_weight2(&theta_xof_ctx, r1, PARAM_OMEGA_R);
118+
xof_ctx_release(&theta_xof_ctx);
116119

117120
// Compute u = r1 + r2.h
118121
vect_mul(c_pke->u, r2, h);

0 commit comments

Comments
 (0)