diff options
| author | cirakg <cirakg@cirakg.xyz> | 2026-10-18 23:44:18 +0200 |
|---|---|---|
| committer | cirakg <cirakg@cirakg.xyz> | 2026-10-18 23:44:18 +0200 |
| commit | 93aa7e3aa291f3328cf34a5a2f86172f41d0affd (patch) | |
| tree | ac44438e7340fde609ad6458e31e122612cf35d1 /test/BenchTest.mc | |
| parent | 5646ae7f40dc53c9ebed0b3b6e907cc85fcd5993 (diff) | |
test: add cross-checked crypto/OTP vectors, unit tests and stricter screenshots
- gen_vectors.py: RFC/FIPS/NIST vectors recomputed with Python's stdlib
(openssl for AES) before use, plus seeded cases around SHA padding
boundaries, 2038 and 2100; generates test/data/Vectors.mc.
- 31 Monkey C tests (hashes, HMAC, PBKDF2, HKDF, AES, sealed records incl.
every-byte tamper detection, Base32 errors, 100 OTP and 12 Steam
vectors, clock, jobs) and a benchmark; pass on all four test devices.
- Screenshot tolerance 0.01 %: one changed character no longer passes.
- Golden images updated for version 0.2.0.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Diffstat (limited to 'test/BenchTest.mc')
| -rw-r--r-- | test/BenchTest.mc | 70 |
1 files changed, 70 insertions, 0 deletions
diff --git a/test/BenchTest.mc b/test/BenchTest.mc new file mode 100644 index 0000000..7e1f612 --- /dev/null +++ b/test/BenchTest.mc @@ -0,0 +1,70 @@ +// Author: cirakg & claude ai +// Summary: Benchmarks of the crypto and OTP primitives; logs BENCH lines for docs/PERFORMANCE.md, never fails. +// +// Simulator timings run on the PC's CPU, so they only compare primitives with +// each other (for example how much SHA-512 costs against native SHA-1). +// Watch timings come from the on-watch benchmark in M4. + +import Toybox.Lang; +import Toybox.System; +import Toybox.Test; + +(:test) +module Bench { + // Run fn `times` times and log the average in microseconds. + function measure(logger as Test.Logger, name as String, times as Number, fn as Method() as Void) as Void { + var start = System.getTimer(); + for (var i = 0; i < times; i++) { + fn.invoke(); + } + var elapsed = System.getTimer() - start; + logger.debug("BENCH " + name + " us_per_call=" + (elapsed * 1000 / times)); + } + + class Cases { + var secret20 as ByteArray = new [20]b; + var secret64 as ByteArray = new [64]b; + var keys as SealedBox.Keys = new SealedBox.Keys(new [32]b); + var box as ByteArray = []b; + + function initialize() { + box = SealedBox.seal(keys, []b, new [20]b); + } + + function totpSha1() as Void { + Otp.totp(Hashes.SHA1, secret20, 1700000000l, 30, 6); + } + + function totpSha256() as Void { + Otp.totp(Hashes.SHA256, secret20, 1700000000l, 30, 6); + } + + function totpSha512() as Void { + Otp.totp(Hashes.SHA512, secret64, 1700000000l, 30, 6); + } + + function pbkdf2Thousand() as Void { + Kdf.pbkdf2([1, 2, 3, 4, 5, 6]b, new [16]b, 1000, 32); + } + + function sealOpen() as Void { + SealedBox.open(keys, []b, SealedBox.seal(keys, []b, new [20]b)); + } + + function selfTest() as Void { + SelfTest.run(); + } + } +} + +(:test) +function benchmarkPrimitives(logger as Test.Logger) as Boolean { + var c = new Bench.Cases(); + Bench.measure(logger, "totp_sha1", 20, c.method(:totpSha1)); + Bench.measure(logger, "totp_sha256", 20, c.method(:totpSha256)); + Bench.measure(logger, "totp_sha512", 20, c.method(:totpSha512)); + Bench.measure(logger, "pbkdf2_1000_iterations", 3, c.method(:pbkdf2Thousand)); + Bench.measure(logger, "sealedbox_seal_open", 20, c.method(:sealOpen)); + Bench.measure(logger, "self_test", 3, c.method(:selfTest)); + return true; +} |
