|
| template<typename Builder > |
| field_t< Builder > | normalize_sparse_form (Builder *, field_t< Builder > &byte) |
| |
| template<typename Builder > |
| byte_pair< Builder > | apply_aes_sbox_map (Builder *, field_t< Builder > &input) |
| |
| template<typename Builder > |
| std::array< field_t< Builder >, 16 > | convert_into_sparse_bytes (Builder *ctx, const field_t< Builder > &block_data) |
| |
| template<typename Builder > |
| field_t< Builder > | convert_from_sparse_bytes (Builder *ctx, field_t< Builder > *sparse_bytes) |
| |
| template<typename Builder > |
| std::array< field_t< Builder >, EXTENDED_KEY_LENGTH > | expand_key (Builder *ctx, const field_t< Builder > &key) |
| | Expands a 128-bit AES key into the full key schedule (EXTENDED_KEY_LENGTH bytes / 11 round keys).
|
| |
| template<typename Builder > |
| void | shift_rows (byte_pair< Builder > *state) |
| | The SHIFTROW() operation as in FIPS 197, Section 5.1.2.
|
| |
| template<typename Builder > |
| void | mix_column_and_add_round_key (byte_pair< Builder > *column_pairs, field_t< Builder > *round_key, uint64_t round) |
| | Performs MixColumns on a single column and adds the round key (FIPS 197, Sections 5.1.3 & 5.1.4).
|
| |
| template<typename Builder > |
| void | mix_columns_and_add_round_key (byte_pair< Builder > *state_pairs, field_t< Builder > *round_key, uint64_t round) |
| |
| template<typename Builder > |
| void | sub_bytes (Builder *ctx, byte_pair< Builder > *state_pairs) |
| |
| template<typename Builder > |
| void | add_round_key (byte_pair< Builder > *sparse_state, field_t< Builder > *sparse_round_key, uint64_t round) |
| |
| template<typename Builder > |
| void | xor_with_iv (byte_pair< Builder > *state, field_t< Builder > *iv) |
| |
| template<typename Builder > |
| void | aes128_cipher (Builder *ctx, byte_pair< Builder > *state, field_t< Builder > *sparse_round_key) |
| |
| template<typename Builder > |
| std::vector< field_t< Builder > > | encrypt_buffer_cbc (const std::vector< field_t< Builder > > &input, const field_t< Builder > &iv, const field_t< Builder > &key) |
| |
| | INSTANTIATE_ENCRYPT_BUFFER_CBC (bb::UltraCircuitBuilder) |
| |
| | INSTANTIATE_ENCRYPT_BUFFER_CBC (bb::MegaCircuitBuilder) |
| |
| template<typename Builder > |
| std::vector< stdlib::field_t< Builder > > | encrypt_buffer_cbc (const std::vector< stdlib::field_t< Builder > > &input, const stdlib::field_t< Builder > &iv, const stdlib::field_t< Builder > &key) |
| |
Expands a 128-bit AES key into the full key schedule (EXTENDED_KEY_LENGTH bytes / 11 round keys).
Implements the AES-128 key expansion algorithm (FIPS 197, Section 5.2) in-circuit. The key schedule derives 11 round keys (each 16 bytes) from the original 128-bit key:
- Round key 0: The original key (used before round 1)
- Round keys 1-10: Derived keys for each encryption round
Algorithm per word i (where each word is 4 bytes):
- If i % 4 == 0: Apply RotWord (rotate left), SubWord (S-box), and XOR with Rcon[i/4]
- XOR with word[i-4] to produce word[i]
The function uses sparse form representation (base-9 digits) for efficient S-box lookups via plookup tables. Sparse form allows the S-box to be computed as a sequence of additions rather than bit manipulations.
Normalization: The add_counts array tracks how many additions have been accumulated in each sparse byte. When the count exceeds a threshold (3), or when the byte will be used as input to the S-box (indices where (j & 12) == 12), the value is normalized via a plookup to prevent overflow in the sparse representation.
- Template Parameters
-
- Parameters
-
| ctx | Pointer to the circuit builder context |
| key | The 128-bit encryption key packed into a field element (16 bytes, big-endian) |
- Returns
- std::array<field_t<Builder>, EXTENDED_KEY_LENGTH> The expanded key schedule as EXTENDED_KEY_LENGTH sparse-form bytes
- Note
- Round constants array is 0-indexed with a placeholder at index 0 (0x8d = 2^{-1} in GF(2^8)) so that round_constants[i] corresponds to Rcon[i] from FIPS 197.
Definition at line 107 of file aes128.cpp.
Performs MixColumns on a single column and adds the round key (FIPS 197, Sections 5.1.3 & 5.1.4).
MixColumns treats each column as a polynomial over GF(2^8) and multiplies it by a fixed matrix:
| r0 | | 2 3 1 1 | | s0 |
| r1 | = | 1 2 3 1 | × | s1 |
| r2 | | 1 1 2 3 | | s2 |
| r3 | | 3 1 1 2 | | s3 |
In GF(2^8), multiplication by 2 is the "xtime" operation, and multiplication by 3 is xtime(x) ⊕ x.
The byte_pair structure from the S-box lookup contains:
- `.first` = S(x) (the S-box output, i.e., "×1")
- `.second` = S(x) ⊕ xtime(S(x)) = 3·S(x) (precomputed "×3" value)
To get "×2": Since 3·x = 2·x ⊕ x, we have 2·x = 3·x ⊕ x = `.second` ⊕ `.first`.
In sparse form, ⊕ is represented by addition, so adding `.first` + `.second` and normalizing gives 2·x.
The formulas below use this identity. For example:
r0 = 2·s0 ⊕ 3·s1 ⊕ s2 ⊕ s3
= (s0 ⊕ 3·s0) ⊕ 3·s1 ⊕ s2 ⊕ s3 (since x ⊕ 3x = 2x in GF(2^8))
= s0.first + s0.second + s1.second + s2.first + s3.first
- Template Parameters
-
| Builder | The circuit builder type |
- Parameters
-
| column_pairs | Array of 4 byte_pairs representing one column of the state after SubBytes |
| round_key | The expanded key schedule (EXTENDED_KEY_LENGTH bytes in sparse form) |
| round | The current round number (1-10), used to index into round_key |
Definition at line 263 of file aes128.cpp.