Repository navigation
Conversation
|
We had agreed not to add more ciphers until we get through reviewing and locking in the overall architecture via the AES work. Closing this PR for now. |
482b254 to
caab3e9
Compare
83e1b74 to
8e28ccb
Compare
83e1b74 to
8e28ccb
Compare
|
The review round of PR #140 applied here, in
|
FindingsA. Memory Usage table undercounts (docs only). lib.rs:231-236 tabulates the
lib.rs:222-225 itself itemizes 64 + 32 + 32 B of working state, already more than the 96 B tabulated. Fix the |
|
Roy's two follow-ups from PR #140 applied here too, head
|
…arams types are exported Roy's B, C and E on PR #141. kl_kr and subkeys were pub methods on the pub CamelliaParams trait, reachable through any P: CamelliaParams, where AESParams carries only the constants and the Schedule type; they move to the sealed CamelliaParamsInternalTrait, which already existed with no members. The three params structs are exported from the crate root, as AES's are, so Camellia128Key<M> expands to a type a user can name and rustdoc links it. The Camellia-192 and -256 engine constructors list their error cases as the Camellia-128 one does, instead of pointing at ElectronicCodeBook::new; the three CRYPTREC vector arrays are static rather than const; the two index loops in the test reference engine iterate; and check_chain's explicit lifetime, which named no worker, is elided. Clippy on the crate is clean. Scoped mutants on schedule.rs: 117 tested, 114 caught, 2 unviable, 1 missed, the documented | / ^ equivalence in join. Assisted-by: Claude:claude-mythos-5-1
|
Roy's B, C and E applied in
Scoped mutants on |
The two that carry over from Roy's E on PR #141, the rest of B, C and E having no counterpart here: the key-schedule reference helper in the unit tests iterates the shift table instead of indexing it, and the two runtime asserts on ENCRYPTION_APPROVED, which clippy flags as constant and which key_tests and alg_name_tests both carried, are one compile-time pair in alg_name_tests. Clippy on the crate is clean; cargo test -p bouncycastle-tdes and the workspace all-targets build pass. Assisted-by: Claude:claude-mythos-5-1
…modules are public, the stack table is measured, and the doc nits PR #142's review, and the round PR #140 and #141 had before it. ARIAKey's three constructors carried as_cipher_key and a `_ =>` arm for MAC-mode keys, which lost their role when the AEAD, ECB and MAC pairs went; both go, and check_key_type stays ahead of the permutation's own check so that a key under a MAC mode refuses cipher material for its type and MAC material by the permutation, which mode_key_tests pins at both key lengths. The key docs name every mode that gives a key a role -- CTR at any nonce length, ECB<PKCS7> and ECB<NoPadding> among them -- rather than the four aliased ones. The mode and key modules are `pub`, as in bouncycastle-aes, so their docs render; the three params types are exported beside their trait, so the `ARIA*Key<M>` aliases name public types. The ModeNames comment says which modes RFC 5794 Appendix B gives an OID (CFB's parameters carry the segment size, so CFB8 is `id-aria*-cfb` with `k = 8`; GMAC has none). The Security Considerations heading takes the style guide's form and the anchor follows it. The Memory Usage section tabulates the measured stack per entry point and key length: bench_aria_mem_usage takes the AES bench's measure-closure shape for new and the six block entry points at each key length, and the figures are the deepest frame chain under each closure from the release build's frame-layout remarks and disassembly (closure, then encrypt_4blocks or expand, fo/fe, substitution_layer, ortho), which puts a one-block call at 416 B, not the "near 100 bytes" the Design section foregrounded for the working state alone; that sentence now points at the table. The three unit tests in hazmat/aria.rs that tested public behaviour only (the engine sizes, the algorithm names, the LANES constant) move to alg_name_tests; the Sec 2.2 decryption-order pin and the Appendix A.1 intermediate values stay. stream_mode_tests pins the CTR counter limit through an ARIA key under CTR<15>. Nits: the manifest comment, the sibling citations in bitslice.rs, the BlockPermutation attributions for methods that are on BlockPermutation, two clippy suggestions in the tests, and every doc or comment line past 100 columns. Assisted-by: Claude:claude-mythos-5-1
… and -d As for sm4 and camellia on PRs #140 and #141: aria*-cbc was CBC<NoPadding> with no --iv while aes*-cbc on this base is PKCS7 at any length with --iv/--iv-file, and the aria help pointed at aes128-cbc for an alignment rule it no longer has (PR #142 review). The three CBC commands are now CBC<PKCS7> over the same block-mode helpers; the nine stream commands take --iv/--iv-file through load_iv as the aes ones do; and all twelve take the direction as -d/--direction, which every other cipher command already does. The CLI tests pin encryption as well as decryption now that the IV can be supplied: aria*-cbc encrypt --iv reproduces the KISA CBC vectors followed by the PKCS7 block (computed from the permutation of the key's length), and aria*-cfb, -cfb8 and -ctr encrypt --iv reproduce the KISA stream vectors exactly, CTR under the twelve-byte zero nonce they imply. The alignment test becomes an any-length test plus a rejected unpadded ciphertext. Their module docs cite the files that exist. Assisted-by: Claude:claude-mythos-5-1
3c170c9 to
81cef74
Compare
The two that carry over from Roy's E on PR #141, the rest of B, C and E having no counterpart here: the key-schedule reference helper in the unit tests iterates the shift table instead of indexing it, and the two runtime asserts on ENCRYPTION_APPROVED, which clippy flags as constant and which key_tests and alg_name_tests both carried, are one compile-time pair in alg_name_tests. Clippy on the crate is clean; cargo test -p bouncycastle-tdes and the workspace all-targets build pass. Assisted-by: Claude:claude-mythos-5-1
fea89e9 to
71ec281
Compare
…arams types are exported Roy's B, C and E on PR #141. kl_kr and subkeys were pub methods on the pub CamelliaParams trait, reachable through any P: CamelliaParams, where AESParams carries only the constants and the Schedule type; they move to the sealed CamelliaParamsInternalTrait, which already existed with no members. The three params structs are exported from the crate root, as AES's are, so Camellia128Key<M> expands to a type a user can name and rustdoc links it. The Camellia-192 and -256 engine constructors list their error cases as the Camellia-128 one does, instead of pointing at ElectronicCodeBook::new; the three CRYPTREC vector arrays are static rather than const; the two index loops in the test reference engine iterate; and check_chain's explicit lifetime, which named no worker, is elided. Clippy on the crate is clean. Scoped mutants on schedule.rs: 117 tested, 114 caught, 2 unviable, 1 missed, the documented | / ^ equivalence in join. Assisted-by: Claude:claude-mythos-5-1
…modules are public, the stack table is measured, and the doc nits PR #142's review, and the round PR #140 and #141 had before it. ARIAKey's three constructors carried as_cipher_key and a `_ =>` arm for MAC-mode keys, which lost their role when the AEAD, ECB and MAC pairs went; both go, and check_key_type stays ahead of the permutation's own check so that a key under a MAC mode refuses cipher material for its type and MAC material by the permutation, which mode_key_tests pins at both key lengths. The key docs name every mode that gives a key a role -- CTR at any nonce length, ECB<PKCS7> and ECB<NoPadding> among them -- rather than the four aliased ones. The mode and key modules are `pub`, as in bouncycastle-aes, so their docs render; the three params types are exported beside their trait, so the `ARIA*Key<M>` aliases name public types. The ModeNames comment says which modes RFC 5794 Appendix B gives an OID (CFB's parameters carry the segment size, so CFB8 is `id-aria*-cfb` with `k = 8`; GMAC has none). The Security Considerations heading takes the style guide's form and the anchor follows it. The Memory Usage section tabulates the measured stack per entry point and key length: bench_aria_mem_usage takes the AES bench's measure-closure shape for new and the six block entry points at each key length, and the figures are the deepest frame chain under each closure from the release build's frame-layout remarks and disassembly (closure, then encrypt_4blocks or expand, fo/fe, substitution_layer, ortho), which puts a one-block call at 416 B, not the "near 100 bytes" the Design section foregrounded for the working state alone; that sentence now points at the table. The three unit tests in hazmat/aria.rs that tested public behaviour only (the engine sizes, the algorithm names, the LANES constant) move to alg_name_tests; the Sec 2.2 decryption-order pin and the Appendix A.1 intermediate values stay. stream_mode_tests pins the CTR counter limit through an ARIA key under CTR<15>. Nits: the manifest comment, the sibling citations in bitslice.rs, the BlockPermutation attributions for methods that are on BlockPermutation, two clippy suggestions in the tests, and every doc or comment line past 100 columns. Assisted-by: Claude:claude-mythos-5-1
…ECB and MAC pairs go CamelliaKey<P, M> carried the full AESKey role set: the AEAD and declared-AEAD pairs (GCM, CCM), the hazmat ECB pair (ECB<Blocks>) and the MAC pair (CMAC), none of which this crate aliases, checks against a published vector or exposes in the CLI. They were there for parity with AESKey only. The symmetric and block pairs remain; between them they cover CBC, CFB, CFB8 and CTR, the four modes the Camellia_* aliases name, and a key under any other mode has no role. mode_key_tests drops the ECB<Blocks> and GCM construction and framework runs. ModeNames keeps all nine names, since the mode types over the engine name themselves by them. Assisted-by: Claude:claude-mythos-5-1
Lifted onto this branch from feature/key-rework-memory (5607ba9), where AESKey and AESInternal gained the same: the engine compares the schedule through Secret's byte-wise equality, which inspects every byte so the time taken does not say where two differ, and a key is equal when its mode state is, bounded on the state rather than on Mode::KeyState. The key objects never hand the material back, so this is the only way two keys can be compared. mode_key_tests: equality follows the material for a clone, the same bytes and a single flipped bit. Assisted-by: Claude:claude-mythos-5-1
…tack table is measured, and the doc nits The same round as PR #140's review, applied here. CamelliaKey's three constructors carried as_cipher_key and a `_ =>` arm for MAC-mode keys, which lost their role in 922236e; both go, and with them check_key_type, since the permutation's own validation is the same check for every mode that has a role (a scoped `cargo mutants` on key.rs is 0 missed; the crate lists 577 mutants). The key docs name ECB<PKCS7> among the symmetric-pair modes. The Security Considerations heading takes the style guide's form and the anchor follows it. The Memory Usage section tabulates the measured stack per entry point and key length: bench_camellia_mem_usage takes the AES bench's measure-closure shape for new and the six block entry points at each key length, and the figures are the closure frames from the release build's frame-layout remarks plus the return address. The three unit tests in hazmat/camellia.rs that tested public behaviour only (the engine sizes, the algorithm names, the LANES constant) move to alg_name_tests or go; the Sec 2.3.3 subkey-swap pin stays. Nits: the manifest comment, the sm4 citation in bitslice.rs, the ElectronicCodeBook attributions for methods that are on BlockPermutation, "An Camellia", and every doc or comment line past 100 columns, including the two rustfmt could not fit. Assisted-by: Claude:claude-mythos-5-1
…file and -d As for sm4 on PR #140: camellia*-cbc was CBC<NoPadding> with no --iv while aes*-cbc on this base is PKCS7 at any length with --iv/--iv-file, and the camellia help pointed at aes128-cbc for an alignment rule it no longer has. The three CBC commands are now CBC<PKCS7> over the same block-mode helpers; the nine stream commands take --iv/--iv-file through load_iv as the aes ones do; and all twelve take the direction as -d/--direction, which every other cipher command already does. The CLI tests pin encryption as well as decryption now that the IV can be supplied: camellia*-cbc encrypt --iv reproduces the OpenSSL evpciph_camellia CBC chains followed by the PKCS7 block (computed from the permutation of the key's length), camellia*-cfb encrypt --iv reproduces the CFB chains exactly, and camellia128-cfb8 and -ctr under --iv are held to the library. The alignment test becomes an any-length test plus a rejected unpadded ciphertext. Their module docs cite the files that exist. Assisted-by: Claude:claude-mythos-5-1
…its over the engines Wycheproof carries camellia_ccm_test.json beside the camellia_cbc_pkcs5 file this crate already runs; the four-mode scope left it unrun. It runs now the way the AES CCM suite does, over the hazmat mode traits and the permutation directly, since the keys carry no AEAD role: 486 of the 552 cases are within SP 800-38C A.1's nonce and tag sets at the three key lengths (405 valid, 81 invalid) and the other 66 are counted as unsupported. All pass. The crate docs' provenance list names both Wycheproof files. Assisted-by: Claude:claude-mythos-5-1
The same undercount Roy found on PR #140's SM4 table: the figures were each entry point's `measure` closure frame alone, while the disassembly of the remark build shows the closure calling encrypt_4blocks (or the schedule's expand) out of line, which calls f, which calls ortho. Summing the chain with return addresses, on rustc 1.97 nightly x86-64: new 720 B for Camellia-128 and 1120 B for the other two, 496 B for the one-block calls, 512 B for the two-block calls and decrypt_4blocks, 528 B for encrypt_4blocks. The bench's method note says to sum the chain and lists each frame. Assisted-by: Claude:claude-mythos-5-1
…utation does As for SM4 on PR #140: 6327570 dropped the check against Mode::KEY_TYPE, leaving a key under a MAC mode declaring KEY_TYPE = MACKey while its constructor took cipher material and refused MAC material. The check is back on all three key lengths, as AESKey has it; mode_key_tests pins the constant, both materials and generate at 128 and 256 bits. Scoped mutants on key.rs: 28 tested, 5 caught, 23 unviable, none missed. Assisted-by: Claude:claude-mythos-5-1
…arams types are exported Roy's B, C and E on PR #141. kl_kr and subkeys were pub methods on the pub CamelliaParams trait, reachable through any P: CamelliaParams, where AESParams carries only the constants and the Schedule type; they move to the sealed CamelliaParamsInternalTrait, which already existed with no members. The three params structs are exported from the crate root, as AES's are, so Camellia128Key<M> expands to a type a user can name and rustdoc links it. The Camellia-192 and -256 engine constructors list their error cases as the Camellia-128 one does, instead of pointing at ElectronicCodeBook::new; the three CRYPTREC vector arrays are static rather than const; the two index loops in the test reference engine iterate; and check_chain's explicit lifetime, which named no worker, is elided. Clippy on the crate is clean. Scoped mutants on schedule.rs: 117 tested, 114 caught, 2 unviable, 1 missed, the documented | / ^ equivalence in join. Assisted-by: Claude:claude-mythos-5-1
…cs sit on the items, the Wycheproof CBC suite uses the shared loaders, and the CTR limit is pinned through a key Three of the aria review's findings hold for this crate too. The cbc, cfb, cfb8, ctr and key modules are private, so the docs each carried never rendered; they now sit on `Camellia_CBC_128`, `Camellia_CFB_128`, `Camellia_CFB8_128`, `Camellia_CTR_128` and `CamelliaKey`, the one path each has, and the module headers say so. The CAMELLIA-CBC-PKCS5 suite found its file through its own two candidate paths and skipped silently when neither resolved, accepted any error for an invalid case, and could not tell a zeroized output buffer from one never written; it is now the AES suite over the Camellia keys -- the shared `wycheproof_json` loader, the expected error read off the case's flags, a pre-filled output buffer that a failed decrypt must leave all zeros -- as `cbc_wycheproof.rs`, named as the suites it copies. And no test reached `Ctr`'s counter limit through a Camellia key: stream_mode_tests now does, under `CTR<15>`, where the 256th block is the last and the byte after it is refused. Assisted-by: Claude:claude-mythos-5-1
…rried over the rebase onto its release-based history This branch took feature/key-rework-memory by merge, and the merge commits carried the adaptations to what arrived. The rebase onto the branch's new history (key-rework-memory rebased onto release/0.1.3alpha, which carries feature/key-rework as one squash commit) dropped those merges; this commit restores the affected files to the branch's pre-rebase tip, so the tree is identical to it. Assisted-by: Claude:claude-mythos-5-1
…ey carries them -- 9accbde dropped them with the ARIA trim, and the Camellia-CCM and Camellia-CMAC Wycheproof suites now run through Camellia128Key<CCM<N, T>> and <CMAC> (486 and 306 cases; GCM has no published Camellia vector and is covered by the AEAD suite over the Gcm code the AES and ARIA suites pin); the constructor takes MAC material for a MAC mode, retagged for the permutation as AESKey does; Camellia_GCM_*, Camellia_CCM_*, Camellia_CMAC_* and Camellia_GMAC_* name the workers, with GMAC's nonce-bound pair inherent on the key; the mode-key suite adds the ECB<Blocks>, GCM and CCM_Packet keys and the MAC keys' round trips, and the docs say which modes a key now covers Assisted-by: Claude:claude-fable-5-1
…*-gcm and aes*-ccm commands over the Camellia keys (the CCM runner and its key table are shared with the AES file), with Wycheproof CCM known answers in both directions, GCM held to the library's own key, and tag-check and round-trip tests Assisted-by: Claude:claude-fable-5-1
Assisted-by: Claude:claude-fable-5-1
…andard or vector suite publishes one, so bc-java 1.87's GCMBlockCipher over CamelliaEngine supplies the ciphertext and tag at each key length (the RFC 3713 keys, a counting nonce, AAD and 45-byte message) and the empty-message tag, pinned through Camellia*Key<GCM> in both directions Assisted-by: Claude:claude-fable-5-1
…gh the binary in both directions at each key length Assisted-by: Claude:claude-fable-5-1
… testsuite/gcm-test.c carries them as "obtained from the authors": the AES-GCM specification's inputs under Camellia-128 and Camellia-256; the seven 12-byte-IV cases (1, 3, 4 and 13 to 16) run through Camellia128Key<GCM> and Camellia256Key<GCM> in both directions, the 8- and 60-byte-IV cases are outside GCM's fixed 96-bit nonce and said so; OpenSSL has no Camellia-GCM to check against Assisted-by: Claude:claude-fable-5-1
Assisted-by: Claude:claude-fable-5-1
…>> and its detached in-place one-shots rather than over the permutation; a weak-MAC-key test pins that as_cipher_key carries the MAC key's strength onto the retagged copy; the GMAC key is held to the GCM key over AAD alone at both key lengths, and the authors' empty GCM cases (1 and 13) run through Camellia*Key<GMAC> as its known answers; the CCM suite header no longer cites the AES crate's ACVP file (the same findings as PR #142's second round) Assisted-by: Claude:claude-fable-5-1
…rule -- key, IV, nonce and AAD files are raw bytes, or hex under the global --hex-input -- the GCM paragraphs say "the other Camellia modes", and the three camellia*-gcm commands carry the clippy allowance their AES twins have (as PR #142's second round) Assisted-by: Claude:claude-fable-5-1
…ver the rebase onto release/0.1.4alpha This branch took release/0.1.3alpha (029a17b, the squash merge of PR #190) by merge, and that merge commit carried the adaptations to what arrived. The rebase onto release/0.1.4alpha dropped the merge; this commit restores the affected files to the branch's pre-rebase tip, so the tree is identical to it apart from the 0.1.4 line's own version bump and notes file. Assisted-by: Claude:claude-fable-5-1
The two that carry over from Roy's E on PR #141, the rest of B, C and E having no counterpart here: the key-schedule reference helper in the unit tests iterates the shift table instead of indexing it, and the two runtime asserts on ENCRYPTION_APPROVED, which clippy flags as constant and which key_tests and alg_name_tests both carried, are one compile-time pair in alg_name_tests. Clippy on the crate is clean; cargo test -p bouncycastle-tdes and the workspace all-targets build pass. Assisted-by: Claude:claude-mythos-5-1
637b4d5 to
9b22094
Compare
…modules are public, the stack table is measured, and the doc nits PR #142's review, and the round PR #140 and #141 had before it. ARIAKey's three constructors carried as_cipher_key and a `_ =>` arm for MAC-mode keys, which lost their role when the AEAD, ECB and MAC pairs went; both go, and check_key_type stays ahead of the permutation's own check so that a key under a MAC mode refuses cipher material for its type and MAC material by the permutation, which mode_key_tests pins at both key lengths. The key docs name every mode that gives a key a role -- CTR at any nonce length, ECB<PKCS7> and ECB<NoPadding> among them -- rather than the four aliased ones. The mode and key modules are `pub`, as in bouncycastle-aes, so their docs render; the three params types are exported beside their trait, so the `ARIA*Key<M>` aliases name public types. The ModeNames comment says which modes RFC 5794 Appendix B gives an OID (CFB's parameters carry the segment size, so CFB8 is `id-aria*-cfb` with `k = 8`; GMAC has none). The Security Considerations heading takes the style guide's form and the anchor follows it. The Memory Usage section tabulates the measured stack per entry point and key length: bench_aria_mem_usage takes the AES bench's measure-closure shape for new and the six block entry points at each key length, and the figures are the deepest frame chain under each closure from the release build's frame-layout remarks and disassembly (closure, then encrypt_4blocks or expand, fo/fe, substitution_layer, ortho), which puts a one-block call at 416 B, not the "near 100 bytes" the Design section foregrounded for the working state alone; that sentence now points at the table. The three unit tests in hazmat/aria.rs that tested public behaviour only (the engine sizes, the algorithm names, the LANES constant) move to alg_name_tests; the Sec 2.2 decryption-order pin and the Appendix A.1 intermediate values stay. stream_mode_tests pins the CTR counter limit through an ARIA key under CTR<15>. Nits: the manifest comment, the sibling citations in bitslice.rs, the BlockPermutation attributions for methods that are on BlockPermutation, two clippy suggestions in the tests, and every doc or comment line past 100 columns. Assisted-by: Claude:claude-mythos-5-1
… and -d As for sm4 and camellia on PRs #140 and #141: aria*-cbc was CBC<NoPadding> with no --iv while aes*-cbc on this base is PKCS7 at any length with --iv/--iv-file, and the aria help pointed at aes128-cbc for an alignment rule it no longer has (PR #142 review). The three CBC commands are now CBC<PKCS7> over the same block-mode helpers; the nine stream commands take --iv/--iv-file through load_iv as the aes ones do; and all twelve take the direction as -d/--direction, which every other cipher command already does. The CLI tests pin encryption as well as decryption now that the IV can be supplied: aria*-cbc encrypt --iv reproduces the KISA CBC vectors followed by the PKCS7 block (computed from the permutation of the key's length), and aria*-cfb, -cfb8 and -ctr encrypt --iv reproduce the KISA stream vectors exactly, CTR under the twelve-byte zero nonce they imply. The alignment test becomes an any-length test plus a rejected unpadded ciphertext. Their module docs cite the files that exist. Assisted-by: Claude:claude-mythos-5-1
|
Rebased onto release/0.1.4alpha (ac20638: the 0.1.3 tree with the version bump and the new notes file) and retargeted there: feature/camellia is now 9b22094, replayed from 637b4d5 with the merge of 029a17b dropped and the tree restored to a reference merge, so it is identical to the old tip apart from the 0.1.4 setup. Workspace suite passes on the new tip. |
Summary
Adds
bouncycastle-camellia: a constant-time, table-free, low-memory Camellia block cipher (RFC 3713), ported from Bouncy Castle Java'sCamelliaEngine/CamelliaLightEngine, on the key objects of #172:Camellia128Key<M>,Camellia192Key<M>andCamellia256Key<M>over the enginesCamellia128Internaland friends.Rebased onto
feature/key-rework-memory(#172) on 2026-10-25 and ported to its key-object design; the base is now that branch. The review round of PR #140 is applied here in the last three commits: the keys' leftover MAC-key path is gone, the CLI matches the AES commands, the Memory Usage table is measured, the style and nit items are fixed, and the Wycheproof CAMELLIA-CCM suite runs through the mode traits.Update 2026-11-04: with the key settled as the source of the operator, the AEAD, ECB and MAC roles are back, as
AESKeycarries them (Camellia has GCM in RFC 6367, CCM in RFC 5528 and CMAC):Camellia*KeyunderGCM,CCM<N, T>,CCM_Packet<..>,ECB<Blocks>,CMAC<16>andGMAC<16>carry the matching pairs, with theCamellia_GCM_*,Camellia_CCM_*,Camellia_CMAC_*andCamellia_GMAC_*aliases and thecamellia{128,192,256}-{gcm,ccm}subcommands (the runners are the AES commands' over the Camellia keys). The Wycheproof CCM suite and the new CMAC suite (camellia_cmac_test.json, 306 cases) run through the keys; no standard or vector suite publishes a Camellia-GCM answer and OpenSSL has no Camellia-GCM at all, so GCM's known answers are the Camellia authors' own cases as carried in nettle'stestsuite/gcm-test.c(the AES-GCM specification's inputs under Camellia-128 and -256; the seven 12-byte-IV cases, ingcm_authors_tests.rs) and, for all three key lengths, Bouncy Castle Java's (bc-java 1.87'sGCMBlockCipheroverCamelliaEngine, the RFC 3713 keys, a counting nonce, AAD and 45-byte message, plus the empty-message tag), pinned at each key length throughCamellia*Key<GCM>ingcm_bc_java_tests.rsand through the binary in the CLI tests.Description
CamelliaKey<P, M>mirrorsAESKey: the key holds the mode's state, its workers borrow it, and which role pair a key carries is decided by its mode. The crate aliases CBC, CFB, CFB8 and CTR (Camellia_CBC_128<'k, Dir, Pad>,Camellia_CFB_128<'k, Dir>, ...); the keys carry the symmetric, block, ECB, AEAD and MAC role pairs, asAESKeydoes, so every one of the nine modes the engines name throughModeNameshas a key with a role. Keys and engines implementPartialEq/Eqin constant time over the expanded schedule, as on Key object rework: the traits lose their constructors, every mode gets a key, and workers borrow the key #172.camellia{128,192,256}-{cbc,cfb,cfb8,ctr,gcm,ccm}, through the key objects, with theaes*-*contract:camellia*-cbcisCBC<PKCS7>at any length, every command takes--iv/--iv-file(the IV or nonce is in band otherwise) and-d/--direction.Scope and Risk
New crate only; the shared changes it carries (the
bouncycastle-camelliaworkspace entry, the umbrella re-export, the memory bench) are additive. No behavioural change to AES or other existing ciphers.Validation
t_camellia.txtvectors; BC Java's ownCamelliaTestvectors, through the engines. OpenSSL CBC and CFB128 vectors, RFC 5528's nine CTR vectors (through a reference built from the SP 800-38A equations, which theCTRkeys are held to) and the CFB8 equations through the keys; Wycheproof CBC-PKCS5 (216 cases, 144 invalid) throughCamellia*Key<CBC<PKCS7>>, Wycheproofcamellia_ccm_test.json(486 of 552 cases dispatchable, those within SP 800-38C A.1's nonce and tag sets) throughCamellia*Key<CCM<N, T>>, andcamellia_cmac_test.json(306 cases) throughCamellia*Key<CMAC<16>>. The CLI tests pin two CCM cases and the three bc-java GCM answers through the binary in both directions, and cross-checkcamellia*-gcm's generated-nonce output against the library.TestFrameworkFromKeyMaterialfor every mode, and the block, symmetric and stream suites.cargo test --workspace: all passing;cargo test --workspace --all-targets --no-runbuilds the benches;cargo +nightly fmt --checkclean. The CLI integration tests pin the OpenSSL CBC and CFB vectors through the binary in both directions, encryption under--iv.cargo mutants -p bouncycastle-camelliaafter the review fixes: 577 mutants, 537 caught, 27 unviable, 13 missed (the same XOR/OR equivalences inortho::swap,p,fl,flinv, the S-box layer andjoinas before).AI Usage Statement
Assisted-by: Claude:claude-sonnet-5
Assisted-by: Claude:claude-mythos-5-1
🤖 Generated with Claude Code