• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

randombit / botan / 25457312714

06 May 2026 07:43PM UTC coverage: 89.331% (-2.3%) from 91.667%
25457312714

push

github

randombit
In TLS 1.3 verification of client certs, check the correct extension for OCSP

This was checking if the client asked us (the server) for OCSP, instead of
checking if we asked the client for OCSP when we sent the CertificateRequest.

107574 of 120422 relevant lines covered (89.33%)

11482758.98 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

97.75
/src/lib/block/seed/seed.cpp
1
/*
2
* SEED
3
* (C) 1999-2007,2020 Jack Lloyd
4
*
5
* Botan is released under the Simplified BSD License (see license.txt)
6
*/
7

8
#include <botan/internal/seed.h>
9

10
#include <botan/internal/loadstor.h>
11
#include <botan/internal/prefetch.h>
12

13
#if defined(BOTAN_HAS_CPUID)
14
   #include <botan/internal/cpuid.h>
15
#endif
16

17
namespace Botan {
18

19
namespace {
20

21
alignas(256) const uint8_t SEED_S0[256] = {
22
   0xA9, 0x85, 0xD6, 0xD3, 0x54, 0x1D, 0xAC, 0x25, 0x5D, 0x43, 0x18, 0x1E, 0x51, 0xFC, 0xCA, 0x63, 0x28, 0x44, 0x20,
23
   0x9D, 0xE0, 0xE2, 0xC8, 0x17, 0xA5, 0x8F, 0x03, 0x7B, 0xBB, 0x13, 0xD2, 0xEE, 0x70, 0x8C, 0x3F, 0xA8, 0x32, 0xDD,
24
   0xF6, 0x74, 0xEC, 0x95, 0x0B, 0x57, 0x5C, 0x5B, 0xBD, 0x01, 0x24, 0x1C, 0x73, 0x98, 0x10, 0xCC, 0xF2, 0xD9, 0x2C,
25
   0xE7, 0x72, 0x83, 0x9B, 0xD1, 0x86, 0xC9, 0x60, 0x50, 0xA3, 0xEB, 0x0D, 0xB6, 0x9E, 0x4F, 0xB7, 0x5A, 0xC6, 0x78,
26
   0xA6, 0x12, 0xAF, 0xD5, 0x61, 0xC3, 0xB4, 0x41, 0x52, 0x7D, 0x8D, 0x08, 0x1F, 0x99, 0x00, 0x19, 0x04, 0x53, 0xF7,
27
   0xE1, 0xFD, 0x76, 0x2F, 0x27, 0xB0, 0x8B, 0x0E, 0xAB, 0xA2, 0x6E, 0x93, 0x4D, 0x69, 0x7C, 0x09, 0x0A, 0xBF, 0xEF,
28
   0xF3, 0xC5, 0x87, 0x14, 0xFE, 0x64, 0xDE, 0x2E, 0x4B, 0x1A, 0x06, 0x21, 0x6B, 0x66, 0x02, 0xF5, 0x92, 0x8A, 0x0C,
29
   0xB3, 0x7E, 0xD0, 0x7A, 0x47, 0x96, 0xE5, 0x26, 0x80, 0xAD, 0xDF, 0xA1, 0x30, 0x37, 0xAE, 0x36, 0x15, 0x22, 0x38,
30
   0xF4, 0xA7, 0x45, 0x4C, 0x81, 0xE9, 0x84, 0x97, 0x35, 0xCB, 0xCE, 0x3C, 0x71, 0x11, 0xC7, 0x89, 0x75, 0xFB, 0xDA,
31
   0xF8, 0x94, 0x59, 0x82, 0xC4, 0xFF, 0x49, 0x39, 0x67, 0xC0, 0xCF, 0xD7, 0xB8, 0x0F, 0x8E, 0x42, 0x23, 0x91, 0x6C,
32
   0xDB, 0xA4, 0x34, 0xF1, 0x48, 0xC2, 0x6F, 0x3D, 0x2D, 0x40, 0xBE, 0x3E, 0xBC, 0xC1, 0xAA, 0xBA, 0x4E, 0x55, 0x3B,
33
   0xDC, 0x68, 0x7F, 0x9C, 0xD8, 0x4A, 0x56, 0x77, 0xA0, 0xED, 0x46, 0xB5, 0x2B, 0x65, 0xFA, 0xE3, 0xB9, 0xB1, 0x9F,
34
   0x5E, 0xF9, 0xE6, 0xB2, 0x31, 0xEA, 0x6D, 0x5F, 0xE4, 0xF0, 0xCD, 0x88, 0x16, 0x3A, 0x58, 0xD4, 0x62, 0x29, 0x07,
35
   0x33, 0xE8, 0x1B, 0x05, 0x79, 0x90, 0x6A, 0x2A, 0x9A,
36
};
37

38
alignas(256) const uint8_t SEED_S1[256] = {
39
   0x38, 0xE8, 0x2D, 0xA6, 0xCF, 0xDE, 0xB3, 0xB8, 0xAF, 0x60, 0x55, 0xC7, 0x44, 0x6F, 0x6B, 0x5B, 0xC3, 0x62, 0x33,
40
   0xB5, 0x29, 0xA0, 0xE2, 0xA7, 0xD3, 0x91, 0x11, 0x06, 0x1C, 0xBC, 0x36, 0x4B, 0xEF, 0x88, 0x6C, 0xA8, 0x17, 0xC4,
41
   0x16, 0xF4, 0xC2, 0x45, 0xE1, 0xD6, 0x3F, 0x3D, 0x8E, 0x98, 0x28, 0x4E, 0xF6, 0x3E, 0xA5, 0xF9, 0x0D, 0xDF, 0xD8,
42
   0x2B, 0x66, 0x7A, 0x27, 0x2F, 0xF1, 0x72, 0x42, 0xD4, 0x41, 0xC0, 0x73, 0x67, 0xAC, 0x8B, 0xF7, 0xAD, 0x80, 0x1F,
43
   0xCA, 0x2C, 0xAA, 0x34, 0xD2, 0x0B, 0xEE, 0xE9, 0x5D, 0x94, 0x18, 0xF8, 0x57, 0xAE, 0x08, 0xC5, 0x13, 0xCD, 0x86,
44
   0xB9, 0xFF, 0x7D, 0xC1, 0x31, 0xF5, 0x8A, 0x6A, 0xB1, 0xD1, 0x20, 0xD7, 0x02, 0x22, 0x04, 0x68, 0x71, 0x07, 0xDB,
45
   0x9D, 0x99, 0x61, 0xBE, 0xE6, 0x59, 0xDD, 0x51, 0x90, 0xDC, 0x9A, 0xA3, 0xAB, 0xD0, 0x81, 0x0F, 0x47, 0x1A, 0xE3,
46
   0xEC, 0x8D, 0xBF, 0x96, 0x7B, 0x5C, 0xA2, 0xA1, 0x63, 0x23, 0x4D, 0xC8, 0x9E, 0x9C, 0x3A, 0x0C, 0x2E, 0xBA, 0x6E,
47
   0x9F, 0x5A, 0xF2, 0x92, 0xF3, 0x49, 0x78, 0xCC, 0x15, 0xFB, 0x70, 0x75, 0x7F, 0x35, 0x10, 0x03, 0x64, 0x6D, 0xC6,
48
   0x74, 0xD5, 0xB4, 0xEA, 0x09, 0x76, 0x19, 0xFE, 0x40, 0x12, 0xE0, 0xBD, 0x05, 0xFA, 0x01, 0xF0, 0x2A, 0x5E, 0xA9,
49
   0x56, 0x43, 0x85, 0x14, 0x89, 0x9B, 0xB0, 0xE5, 0x48, 0x79, 0x97, 0xFC, 0x1E, 0x82, 0x21, 0x8C, 0x1B, 0x5F, 0x77,
50
   0x54, 0xB2, 0x1D, 0x25, 0x4F, 0x00, 0x46, 0xED, 0x58, 0x52, 0xEB, 0x7E, 0xDA, 0xC9, 0xFD, 0x30, 0x95, 0x65, 0x3C,
51
   0xB6, 0xE4, 0xBB, 0x7C, 0x0E, 0x50, 0x39, 0x26, 0x32, 0x84, 0x69, 0x93, 0x37, 0xE7, 0x24, 0xA4, 0xCB, 0x53, 0x0A,
52
   0x87, 0xD9, 0x4C, 0x83, 0x8F, 0xCE, 0x3B, 0x4A, 0xB7,
53
};
54

55
/*
56
* SEED G Function
57
*/
58
BOTAN_FORCE_INLINE uint32_t SEED_G(uint32_t X) {
1,504✔
59
   const uint32_t M = 0x01010101;
1,504✔
60
   const uint32_t s0 = M * SEED_S0[get_byte<3>(X)];
248✔
61
   const uint32_t s1 = M * SEED_S1[get_byte<2>(X)];
1,504✔
62
   const uint32_t s2 = M * SEED_S0[get_byte<1>(X)];
1,504✔
63
   const uint32_t s3 = M * SEED_S1[get_byte<0>(X)];
1,504✔
64

65
   const uint32_t M0 = 0x3FCFF3FC;
1,504✔
66
   const uint32_t M1 = 0xFC3FCFF3;
1,504✔
67
   const uint32_t M2 = 0xF3FC3FCF;
1,504✔
68
   const uint32_t M3 = 0xCFF3FC3F;
1,504✔
69

70
   return (s0 & M0) ^ (s1 & M1) ^ (s2 & M2) ^ (s3 & M3);
1,504✔
71
}
72

73
}  // namespace
74

75
/*
76
* SEED Encryption
77
*/
78
void SEED::encrypt_n(const uint8_t in[], uint8_t out[], size_t blocks) const {
306✔
79
   assert_key_material_set();
306✔
80

81
#if defined(BOTAN_HAS_SEED_AVX512_GFNI)
82
   if(CPUID::has(CPUID::Feature::AVX512, CPUID::Feature::GFNI)) {
286✔
83
      return avx512_gfni_encrypt(in, out, blocks);
×
84
   }
85
#endif
86

87
#if defined(BOTAN_HAS_SEED_HWAES)
88
   if(CPUID::has(CPUID::Feature::HW_AES)) {
286✔
89
      return hwaes_encrypt(in, out, blocks);
271✔
90
   }
91
#endif
92

93
   prefetch_arrays(SEED_S0, SEED_S1);
15✔
94

95
   while(blocks >= 2) {
96✔
96
      uint32_t B00 = load_be<uint32_t>(in, 0);
66✔
97
      uint32_t B01 = load_be<uint32_t>(in, 1);
66✔
98
      uint32_t B02 = load_be<uint32_t>(in, 2);
66✔
99
      uint32_t B03 = load_be<uint32_t>(in, 3);
66✔
100
      uint32_t B10 = load_be<uint32_t>(in, 4);
66✔
101
      uint32_t B11 = load_be<uint32_t>(in, 5);
66✔
102
      uint32_t B12 = load_be<uint32_t>(in, 6);
66✔
103
      uint32_t B13 = load_be<uint32_t>(in, 7);
66✔
104

105
      for(size_t j = 0; j != 16; j += 2) {
594✔
106
         uint32_t T00 = B02 ^ m_K[2 * j];
528✔
107
         uint32_t T10 = B12 ^ m_K[2 * j];
528✔
108
         uint32_t T01 = SEED_G(B02 ^ B03 ^ m_K[2 * j + 1]);
528✔
109
         uint32_t T11 = SEED_G(B12 ^ B13 ^ m_K[2 * j + 1]);
528✔
110
         T00 = SEED_G(T01 + T00);
528✔
111
         T10 = SEED_G(T11 + T10);
528✔
112
         T01 = SEED_G(T01 + T00);
528✔
113
         T11 = SEED_G(T11 + T10);
528✔
114
         B01 ^= T01;
528✔
115
         B11 ^= T11;
528✔
116
         B00 ^= T00 + T01;
528✔
117
         B10 ^= T10 + T11;
528✔
118

119
         T00 = B00 ^ m_K[2 * j + 2];
528✔
120
         T10 = B10 ^ m_K[2 * j + 2];
528✔
121
         T01 = SEED_G(B00 ^ B01 ^ m_K[2 * j + 3]);
528✔
122
         T11 = SEED_G(B10 ^ B11 ^ m_K[2 * j + 3]);
528✔
123
         T10 = SEED_G(T11 + T10);
528✔
124
         T00 = SEED_G(T01 + T00);
528✔
125
         T01 = SEED_G(T01 + T00);
528✔
126
         T11 = SEED_G(T11 + T10);
528✔
127
         B03 ^= T01;
528✔
128
         B13 ^= T11;
528✔
129
         B02 ^= T00 + T01;
528✔
130
         B12 ^= T10 + T11;
528✔
131
      }
132

133
      store_be(out, B02, B03, B00, B01, B12, B13, B10, B11);
66✔
134

135
      in += 2 * BLOCK_SIZE;
66✔
136
      out += 2 * BLOCK_SIZE;
66✔
137

138
      blocks -= 2;
66✔
139
   }
140

141
   for(size_t i = 0; i != blocks; ++i) {
30✔
142
      uint32_t B0 = load_be<uint32_t>(in, 0);
15✔
143
      uint32_t B1 = load_be<uint32_t>(in, 1);
15✔
144
      uint32_t B2 = load_be<uint32_t>(in, 2);
15✔
145
      uint32_t B3 = load_be<uint32_t>(in, 3);
15✔
146

147
      for(size_t j = 0; j != 16; j += 2) {
135✔
148
         uint32_t T0 = B2 ^ m_K[2 * j];
120✔
149
         uint32_t T1 = SEED_G(B2 ^ B3 ^ m_K[2 * j + 1]);
120✔
150
         T0 = SEED_G(T1 + T0);
120✔
151
         T1 = SEED_G(T1 + T0);
120✔
152
         B1 ^= T1;
120✔
153
         B0 ^= T0 + T1;
120✔
154

155
         T0 = B0 ^ m_K[2 * j + 2];
120✔
156
         T1 = SEED_G(B0 ^ B1 ^ m_K[2 * j + 3]);
120✔
157
         T0 = SEED_G(T1 + T0);
120✔
158
         T1 = SEED_G(T1 + T0);
120✔
159
         B3 ^= T1;
120✔
160
         B2 ^= T0 + T1;
120✔
161
      }
162

163
      store_be(out, B2, B3, B0, B1);
15✔
164

165
      in += BLOCK_SIZE;
15✔
166
      out += BLOCK_SIZE;
15✔
167
   }
168
}
169

170
/*
171
* SEED Decryption
172
*/
173
void SEED::decrypt_n(const uint8_t in[], uint8_t out[], size_t blocks) const {
296✔
174
   assert_key_material_set();
296✔
175

176
#if defined(BOTAN_HAS_SEED_AVX512_GFNI)
177
   if(CPUID::has(CPUID::Feature::AVX512, CPUID::Feature::GFNI)) {
276✔
178
      return avx512_gfni_decrypt(in, out, blocks);
×
179
   }
180
#endif
181

182
#if defined(BOTAN_HAS_SEED_HWAES)
183
   if(CPUID::has(CPUID::Feature::HW_AES)) {
276✔
184
      return hwaes_decrypt(in, out, blocks);
266✔
185
   }
186
#endif
187

188
   prefetch_arrays(SEED_S0, SEED_S1);
10✔
189

190
   while(blocks >= 2) {
86✔
191
      uint32_t B00 = load_be<uint32_t>(in, 0);
66✔
192
      uint32_t B01 = load_be<uint32_t>(in, 1);
66✔
193
      uint32_t B02 = load_be<uint32_t>(in, 2);
66✔
194
      uint32_t B03 = load_be<uint32_t>(in, 3);
66✔
195
      uint32_t B10 = load_be<uint32_t>(in, 4);
66✔
196
      uint32_t B11 = load_be<uint32_t>(in, 5);
66✔
197
      uint32_t B12 = load_be<uint32_t>(in, 6);
66✔
198
      uint32_t B13 = load_be<uint32_t>(in, 7);
66✔
199

200
      for(size_t j = 0; j != 16; j += 2) {
594✔
201
         uint32_t T00 = B02 ^ m_K[30 - 2 * j];
528✔
202
         uint32_t T10 = B12 ^ m_K[30 - 2 * j];
528✔
203
         uint32_t T01 = SEED_G(B02 ^ B03 ^ m_K[31 - 2 * j]);
528✔
204
         uint32_t T11 = SEED_G(B12 ^ B13 ^ m_K[31 - 2 * j]);
528✔
205
         T00 = SEED_G(T01 + T00);
528✔
206
         T10 = SEED_G(T11 + T10);
528✔
207
         T01 = SEED_G(T01 + T00);
528✔
208
         T11 = SEED_G(T11 + T10);
528✔
209
         B01 ^= T01;
528✔
210
         B11 ^= T11;
528✔
211
         B00 ^= T00 + T01;
528✔
212
         B10 ^= T10 + T11;
528✔
213

214
         T00 = B00 ^ m_K[28 - 2 * j];
528✔
215
         T10 = B10 ^ m_K[28 - 2 * j];
528✔
216
         T01 = SEED_G(B00 ^ B01 ^ m_K[29 - 2 * j]);
528✔
217
         T11 = SEED_G(B10 ^ B11 ^ m_K[29 - 2 * j]);
528✔
218
         T00 = SEED_G(T01 + T00);
528✔
219
         T10 = SEED_G(T11 + T10);
528✔
220
         T01 = SEED_G(T01 + T00);
528✔
221
         T11 = SEED_G(T11 + T10);
528✔
222
         B03 ^= T01;
528✔
223
         B13 ^= T11;
528✔
224
         B02 ^= T00 + T01;
528✔
225
         B12 ^= T10 + T11;
528✔
226
      }
227

228
      store_be(out, B02, B03, B00, B01, B12, B13, B10, B11);
66✔
229

230
      in += 2 * BLOCK_SIZE;
66✔
231
      out += 2 * BLOCK_SIZE;
66✔
232
      blocks -= 2;
66✔
233
   }
234

235
   for(size_t i = 0; i != blocks; ++i) {
20✔
236
      uint32_t B0 = load_be<uint32_t>(in, 0);
10✔
237
      uint32_t B1 = load_be<uint32_t>(in, 1);
10✔
238
      uint32_t B2 = load_be<uint32_t>(in, 2);
10✔
239
      uint32_t B3 = load_be<uint32_t>(in, 3);
10✔
240

241
      for(size_t j = 0; j != 16; j += 2) {
90✔
242
         uint32_t T0 = B2 ^ m_K[30 - 2 * j];
80✔
243
         uint32_t T1 = SEED_G(B2 ^ B3 ^ m_K[31 - 2 * j]);
80✔
244
         T0 = SEED_G(T1 + T0);
80✔
245
         T1 = SEED_G(T1 + T0);
80✔
246
         B1 ^= T1;
80✔
247
         B0 ^= T0 + T1;
80✔
248

249
         T0 = B0 ^ m_K[28 - 2 * j];
80✔
250
         T1 = SEED_G(B0 ^ B1 ^ m_K[29 - 2 * j]);
80✔
251
         T0 = SEED_G(T1 + T0);
80✔
252
         T1 = SEED_G(T1 + T0);
80✔
253
         B3 ^= T1;
80✔
254
         B2 ^= T0 + T1;
80✔
255
      }
256

257
      store_be(out, B2, B3, B0, B1);
10✔
258

259
      in += BLOCK_SIZE;
10✔
260
      out += BLOCK_SIZE;
10✔
261
   }
262
}
263

264
bool SEED::has_keying_material() const {
642✔
265
   return !m_K.empty();
642✔
266
}
267

268
/*
269
* SEED Key Schedule
270
*/
271
void SEED::key_schedule(std::span<const uint8_t> key) {
31✔
272
   const uint32_t RC[16] = {0x9E3779B9,
31✔
273
                            0x3C6EF373,
274
                            0x78DDE6E6,
275
                            0xF1BBCDCC,
276
                            0xE3779B99,
277
                            0xC6EF3733,
278
                            0x8DDE6E67,
279
                            0x1BBCDCCF,
280
                            0x3779B99E,
281
                            0x6EF3733C,
282
                            0xDDE6E678,
283
                            0xBBCDCCF1,
284
                            0x779B99E3,
285
                            0xEF3733C6,
286
                            0xDE6E678D,
287
                            0xBCDCCF1B};
288

289
   secure_vector<uint32_t> WK(4);
31✔
290

291
   for(size_t i = 0; i != 4; ++i) {
155✔
292
      WK[i] = load_be<uint32_t>(key.data(), i);
124✔
293
   }
294

295
   m_K.resize(32);
31✔
296

297
   for(size_t i = 0; i != 16; i += 2) {
279✔
298
      m_K[2 * i] = SEED_G(WK[0] + WK[2] - RC[i]);
248✔
299
      m_K[2 * i + 1] = SEED_G(WK[1] - WK[3] + RC[i]) ^ m_K[2 * i];
248✔
300

301
      uint32_t T = (WK[0] & 0xFF) << 24;
248✔
302
      WK[0] = (WK[0] >> 8) | (get_byte<3>(WK[1]) << 24);
248✔
303
      WK[1] = (WK[1] >> 8) | T;
248✔
304

305
      m_K[2 * i + 2] = SEED_G(WK[0] + WK[2] - RC[i + 1]);
248✔
306
      m_K[2 * i + 3] = SEED_G(WK[1] - WK[3] + RC[i + 1]) ^ m_K[2 * i + 2];
248✔
307

308
      T = get_byte<0>(WK[3]);
248✔
309
      WK[3] = (WK[3] << 8) | get_byte<0>(WK[2]);
248✔
310
      WK[2] = (WK[2] << 8) | T;
248✔
311
   }
312
}
31✔
313

314
void SEED::clear() {
20✔
315
   zap(m_K);
20✔
316
}
20✔
317

318
size_t SEED::parallelism() const {
31✔
319
#if defined(BOTAN_HAS_SEED_AVX512_GFNI)
320
   if(CPUID::has(CPUID::Feature::AVX512, CPUID::Feature::GFNI)) {
31✔
321
      return 16;
322
   }
323
#endif
324

325
#if defined(BOTAN_HAS_SEED_HWAES)
326
   if(CPUID::has(CPUID::Feature::HW_AES)) {
31✔
327
      return 4;
16✔
328
   }
329
#endif
330

331
   return 1;
332
}
333

334
std::string SEED::provider() const {
10✔
335
#if defined(BOTAN_HAS_SEED_AVX512_GFNI)
336
   if(auto feat = CPUID::check(CPUID::Feature::AVX512, CPUID::Feature::GFNI)) {
10✔
337
      return *feat;
×
338
   }
×
339
#endif
340

341
#if defined(BOTAN_HAS_SEED_HWAES)
342
   if(auto feat = CPUID::check(CPUID::Feature::HW_AES)) {
10✔
343
      return *feat;
10✔
344
   }
5✔
345
#endif
346

347
   return "base";
5✔
348
}
349

350
}  // namespace Botan
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc