update dependencies
This commit is contained in:
parent
7930d97270
commit
3a3a7e5a63
35 changed files with 1353 additions and 1134 deletions
|
|
@ -3,17 +3,17 @@ dots_indicator: 508f5883ac79bdbc10254092de3f28f571d261cd
|
|||
ed25519_edwards: 7353ba759ea9f4646cbf481c2ef949625c8ce4cf
|
||||
flutter_sharing_intent: aa1672f547d6579585fa27df0b28ffa2a2544aaa
|
||||
hand_signature: 1beedb164d093643365b0832277c377353c7464f
|
||||
hashlib: 983cdbd5ee2529b908876b57a7217c09c6bc148a
|
||||
hashlib: bc9c2f8dd7bbc72f47ccab0ce1111d40259c49bc
|
||||
hashlib_codecs: 2a966c37c3b9b1f5541ae88e99ab34acf3fc968b
|
||||
introduction_screen: 4a90e557630b28834479ed9c64a9d2d0185d8e48
|
||||
libsignal_protocol_dart: 618f0c0b49534245a640a31d204265440cbac9ee
|
||||
lottie: 4f1a5a52bdf1e1c1e12fa97c96174dcb05419e19
|
||||
mutex: 84ca903a3ac863735e3228c75a212133621f680f
|
||||
no_screenshot: 8e19a8d0e30bd1d5000425cabac7ef3e3da4d5ea
|
||||
no_screenshot: 57b4a072e9193b4fa1257a6f1acb13ef307625e7
|
||||
optional: 71c638891ce4f2aff35c7387727989f31f9d877d
|
||||
photo_view: a13ca2fc387a3fb1276126959e092c44d0029987
|
||||
pointycastle: bbd8569f68a7fccbdf0b92d0b44a9219c126c8dd
|
||||
qr: ff808bb3f354e6a7029ec953cbe0144a42021db6
|
||||
qr: 7b1e9665ca976f484e7975356cf26fc7a0ccf02e
|
||||
qr_flutter: d5e7206396105d643113618290bbcc755d05f492
|
||||
restart_app: 12339f63bf8e9631e619c4f9f6b4e013fa324715
|
||||
x25519: ecb1d357714537bba6e276ef45f093846d4beaee
|
||||
|
|
|
|||
|
|
@ -1,24 +1,38 @@
|
|||
// Copyright (c) 2024, Sudipto Chandra
|
||||
// Copyright (c) 2025, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
import 'dart:async';
|
||||
import 'dart:math' show Random;
|
||||
|
||||
import 'generator_js_legacy.dart'
|
||||
if (dart.library.js_interop) 'generator_js_interop.dart';
|
||||
|
||||
const int _mask32 = 0xFFFFFFFF;
|
||||
|
||||
int _seedCounter = Zone.current.hashCode;
|
||||
/// For Node.js environment + dart2js compiler
|
||||
class NodeRandom extends CryptoRandom implements Random {
|
||||
@override
|
||||
int nextInt(final int max) {
|
||||
if (max < 1 || max > _mask32 + 1) {
|
||||
throw RangeError.range(
|
||||
max, 1, _mask32 + 1, 'max', 'max must be <= (1 << 32)');
|
||||
}
|
||||
return cryptoRandomInt(max);
|
||||
}
|
||||
|
||||
@override
|
||||
double nextDouble() {
|
||||
final int first26Bits = nextInt(1 << 26);
|
||||
final int next27Bits = nextInt(1 << 27);
|
||||
final int random53Bits = (first26Bits << 27) + next27Bits; // JS int limit
|
||||
return random53Bits / (1 << 53);
|
||||
}
|
||||
|
||||
@override
|
||||
bool nextBool() => nextInt(2) == 1;
|
||||
}
|
||||
|
||||
/// Returns a secure random generator in JS runtime
|
||||
Random secureRandom() => Random($generateSeed());
|
||||
Random secureRandom() => NodeRandom();
|
||||
|
||||
/// Generates a random seed in JS runtime
|
||||
int $generateSeed() {
|
||||
int code = DateTime.now().millisecondsSinceEpoch;
|
||||
code -= _seedCounter++;
|
||||
if (code.bitLength & 1 == 1) {
|
||||
code *= ~code;
|
||||
}
|
||||
code ^= ~_seedCounter << 5;
|
||||
_seedCounter += code & 7;
|
||||
return code & _mask32;
|
||||
}
|
||||
/// Generates a random seed
|
||||
int $generateSeed() => secureRandom().nextInt(_mask32);
|
||||
|
|
|
|||
25
hashlib/lib/src/random/generator_js_interop.dart
Normal file
25
hashlib/lib/src/random/generator_js_interop.dart
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
// Copyright (c) 2025, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
import 'dart:js_interop';
|
||||
|
||||
@JS()
|
||||
@staticInterop
|
||||
class Crypto {}
|
||||
|
||||
extension on Crypto {
|
||||
external int randomInt(final int max);
|
||||
}
|
||||
|
||||
@JS('require')
|
||||
external Crypto require(final String id);
|
||||
|
||||
/// For Node.js environment + dart2js compiler
|
||||
abstract class CryptoRandom {
|
||||
Crypto? _crypto;
|
||||
|
||||
int cryptoRandomInt(final int max) {
|
||||
_crypto ??= require('crypto');
|
||||
return _crypto!.randomInt(max);
|
||||
}
|
||||
}
|
||||
29
hashlib/lib/src/random/generator_js_legacy.dart
Normal file
29
hashlib/lib/src/random/generator_js_legacy.dart
Normal file
|
|
@ -0,0 +1,29 @@
|
|||
// Copyright (c) 2025, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// Dart v2.19 compatible version
|
||||
// Works with dart2js in a Node.js runtime (where `require` exists).
|
||||
|
||||
// ignore_for_file: deprecated_member_use
|
||||
|
||||
import 'dart:js' as js;
|
||||
|
||||
js.JsObject _require(String id) {
|
||||
final r = js.context['require'];
|
||||
if (r == null) {
|
||||
throw StateError("`require` is not available.");
|
||||
}
|
||||
return (r as js.JsFunction).apply([id]) as js.JsObject;
|
||||
}
|
||||
|
||||
/// For Node.js environment + dart2js compiler
|
||||
abstract class CryptoRandom {
|
||||
js.JsObject? _crypto;
|
||||
js.JsFunction? _randomInt;
|
||||
|
||||
int cryptoRandomInt(final int max) {
|
||||
_crypto ??= _require('crypto');
|
||||
_randomInt ??= _crypto!['randomInt'] as js.JsFunction;
|
||||
return (_randomInt!.apply([max]) as num).toInt();
|
||||
}
|
||||
}
|
||||
|
|
@ -11,6 +11,4 @@ Random secureRandom() => Random.secure();
|
|||
|
||||
/// Generates a random seed
|
||||
@pragma('vm:prefer-inline')
|
||||
int $generateSeed() =>
|
||||
(DateTime.now().microsecondsSinceEpoch & _mask32) ^
|
||||
Random.secure().nextInt(_mask32);
|
||||
int $generateSeed() => Random.secure().nextInt(_mask32);
|
||||
|
|
|
|||
|
|
@ -11,8 +11,12 @@ import 'package:hashlib/src/algorithms/sm3.dart';
|
|||
import 'package:hashlib/src/algorithms/xxh64/xxh64.dart';
|
||||
import 'package:hashlib/src/core/hash_base.dart';
|
||||
|
||||
import 'generator_vm.dart' if (dart.library.js) 'generator_js.dart';
|
||||
export 'generator_vm.dart' if (dart.library.js) 'generator_js.dart';
|
||||
import 'generator_vm.dart'
|
||||
if (dart.library.html) 'generator_vm.dart'
|
||||
if (dart.library.js) 'generator_js.dart';
|
||||
export 'generator_vm.dart'
|
||||
if (dart.library.html) 'generator_vm.dart'
|
||||
if (dart.library.js) 'generator_js.dart';
|
||||
|
||||
const int _mask32 = 0xFFFFFFFF;
|
||||
|
||||
|
|
@ -34,13 +38,13 @@ enum RNG {
|
|||
case RNG.keccak:
|
||||
return _keccakGenerateor(seed);
|
||||
case RNG.sha256:
|
||||
return _hashGenerateor(SHA256Hash(), seed);
|
||||
return _hashGenerator(SHA256Hash(), seed);
|
||||
case RNG.md5:
|
||||
return _hashGenerateor(MD4Hash(), seed);
|
||||
return _hashGenerator(MD4Hash(), seed);
|
||||
case RNG.xxh64:
|
||||
return _hashGenerateor(XXHash64Sink(111), seed);
|
||||
return _hashGenerator(XXHash64Sink(111), seed);
|
||||
case RNG.sm3:
|
||||
return _hashGenerateor(SM3Hash(), seed);
|
||||
return _hashGenerator(SM3Hash(), seed);
|
||||
case RNG.system:
|
||||
return _systemGenerator(seed);
|
||||
case RNG.secure:
|
||||
|
|
@ -115,7 +119,7 @@ NextIntFunction _keccakGenerateor([int? seed]) {
|
|||
}
|
||||
|
||||
/// Returns a iterable of 32-bit integers generated from the [sink].
|
||||
NextIntFunction _hashGenerateor(
|
||||
NextIntFunction _hashGenerator(
|
||||
HashDigestSink sink, [
|
||||
int? seed,
|
||||
]) {
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
name: hashlib
|
||||
description: Secure hash functions, checksum generators, and key derivation algorithms optimized for Dart.
|
||||
homepage: https://github.com/bitanon/hashlib
|
||||
version: 2.2.0
|
||||
version: 2.3.0
|
||||
|
||||
environment:
|
||||
sdk: '>=2.19.0 <4.0.0'
|
||||
|
|
|
|||
134
hashlib/test/bcrypt/bcrypt_2a_test.dart
Normal file
134
hashlib/test/bcrypt/bcrypt_2a_test.dart
Normal file
|
|
@ -0,0 +1,134 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
import 'dart:convert';
|
||||
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('bcrypt version 2a', () {
|
||||
// http://cvsweb.openwall.com/cgi/cvsweb.cgi/Owl/packages/glibc/crypt_blowfish/wrapper.c?rev=HEAD
|
||||
test(r"$2a$06$DCq7YPn5Rq63x1Lad4cll.TV4S6ytwfsfvkgY8jIucDrjc8deX1s.", () {
|
||||
const password = r"";
|
||||
const encoded =
|
||||
r"$2a$06$DCq7YPn5Rq63x1Lad4cll.TV4S6ytwfsfvkgY8jIucDrjc8deX1s.";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
// https://stackoverflow.com/a/12761326/774398
|
||||
test(r"$2a$10$.TtQJ4Jr6isd4Hp.mVfZeuh6Gws4rOQ/vdBczhDx.19NFK0Y84Dle", () {
|
||||
const password = r"ππππππππ";
|
||||
const encoded =
|
||||
r"$2a$10$.TtQJ4Jr6isd4Hp.mVfZeuh6Gws4rOQ/vdBczhDx.19NFK0Y84Dle";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
// https://bitbucket.org/vadim/bcrypt.net/src/464c41416dc9/BCrypt.Net.Test/TestBCrypt.cs?fileviewer=file-view-default
|
||||
test(r"$2a$08$HqWuK6/Ng6sg9gQzbLrgb.Tl.ZHfXLhvt/SgVyWhQqgqcZ7ZuUtye", () {
|
||||
const password = r"";
|
||||
const encoded =
|
||||
r"$2a$08$HqWuK6/Ng6sg9gQzbLrgb.Tl.ZHfXLhvt/SgVyWhQqgqcZ7ZuUtye";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$06$m0CrhHm10qJ3lXRY.5zDGO3rS2KdeeWLuGmsfGlMfOxih58VYVfxe", () {
|
||||
const password = r"a";
|
||||
const encoded =
|
||||
r"$2a$06$m0CrhHm10qJ3lXRY.5zDGO3rS2KdeeWLuGmsfGlMfOxih58VYVfxe";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$06$If6bvum7DFjUnE9p2uDeDu0YHzrHM6tf.iqN8.yx.jNN1ILEf7h0i", () {
|
||||
const password = r"abc";
|
||||
const encoded =
|
||||
r"$2a$06$If6bvum7DFjUnE9p2uDeDu0YHzrHM6tf.iqN8.yx.jNN1ILEf7h0i";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$06$.rCVZVOThsIa97pEDOxvGuRRgzG64bvtJ0938xuqzv18d3ZpQhstC", () {
|
||||
const password = r"abcdefghijklmnopqrstuvwxyz";
|
||||
const encoded =
|
||||
r"$2a$06$.rCVZVOThsIa97pEDOxvGuRRgzG64bvtJ0938xuqzv18d3ZpQhstC";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$06$fPIsBO8qRqkjj273rfaOI.HtSV9jLDpTbZn782DC6/t7qT67P6FfO", () {
|
||||
const password = r"~!@#$%^&*() ~!@#$%^&*()PNBFRD";
|
||||
const encoded =
|
||||
r"$2a$06$fPIsBO8qRqkjj273rfaOI.HtSV9jLDpTbZn782DC6/t7qT67P6FfO";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
// https://github.com/pyca/bcrypt/blob/main/tests/test_bcrypt.py
|
||||
test(r"$2a$05$CCCCCCCCCCCCCCCCCCCCC.E5YPO9kmyuRGyh0XouQYb4YMJKvyOeW", () {
|
||||
var password = "U*U";
|
||||
var encoded =
|
||||
r"$2a$05$CCCCCCCCCCCCCCCCCCCCC.E5YPO9kmyuRGyh0XouQYb4YMJKvyOeW";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$CCCCCCCCCCCCCCCCCCCCC.VGOzA784oUp/Z0DY336zx7pLYAy0lwK", () {
|
||||
var password = "U*U*";
|
||||
var encoded =
|
||||
r"$2a$05$CCCCCCCCCCCCCCCCCCCCC.VGOzA784oUp/Z0DY336zx7pLYAy0lwK";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$XXXXXXXXXXXXXXXXXXXXXOAcXxm9kjPGEMsLznoKqmqw7tc8WCx4a", () {
|
||||
var password = "U*U*U";
|
||||
var encoded =
|
||||
r"$2a$05$XXXXXXXXXXXXXXXXXXXXXOAcXxm9kjPGEMsLznoKqmqw7tc8WCx4a";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$abcdefghijklmnopqrstuu5s2v8.iXieOjg/.AySBTTZIIVFJeBui", () {
|
||||
var password = "0123456789abcdefghijklmnopqrstuvwxyz"
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
|
||||
"chars after 72 are ignored";
|
||||
var encoded =
|
||||
r"$2a$05$abcdefghijklmnopqrstuu5s2v8.iXieOjg/.AySBTTZIIVFJeBui";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$/OK.fbVrR/bpIqNJ5ianF.swQOIzjOiJ9GHEPuhEkvqrUyvWhEMx6", () {
|
||||
var password = "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"chars after 72 are ignored as usual";
|
||||
var encoded =
|
||||
r"$2a$05$/OK.fbVrR/bpIqNJ5ianF.swQOIzjOiJ9GHEPuhEkvqrUyvWhEMx6";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$/OK.fbVrR/bpIqNJ5ianF.Sa7shbm4.OzKpvFnX1pQLmQW96oUlCq", () {
|
||||
var password = "\xa3";
|
||||
var encoded =
|
||||
r"$2a$05$/OK.fbVrR/bpIqNJ5ianF.Sa7shbm4.OzKpvFnX1pQLmQW96oUlCq";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$04$tecY.9ylRInW/rAAzXCXPOOlyYeCNzmNTzPDNSIFztFMKbvs/s5XG", () {
|
||||
var password =
|
||||
"g7\r\x01\xf3\xd4\xd0\xa9JB^\x18\x007P\xb2N\xc7\x1c\xee\x87&\x83C"
|
||||
"\x8b\xe8\x18\xc5>\x86\x14/\xd6\xcc\x1cJ\xde\xd7ix\xeb\xdeO\xef"
|
||||
"\xe1i\xac\xcb\x03\x96v1' \xd6@.m\xa5!\xa0\xef\xc0(";
|
||||
var encoded =
|
||||
r"$2a$04$tecY.9ylRInW/rAAzXCXPOOlyYeCNzmNTzPDNSIFztFMKbvs/s5XG";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
});
|
||||
}
|
||||
186
hashlib/test/bcrypt/bcrypt_2b_test.dart
Normal file
186
hashlib/test/bcrypt/bcrypt_2b_test.dart
Normal file
|
|
@ -0,0 +1,186 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
import 'dart:convert';
|
||||
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
// https://github.com/pyca/bcrypt/blob/main/tests/test_bcrypt.py
|
||||
group('bcrypt version 2b', () {
|
||||
test(r"$2b$04$cVWp4XaNU8a4v1uMRum2SO026BWLIoQMD/TXg5uZV.0P.uO8m3YEm", () {
|
||||
var password = "Kk4DQuMMfZL9o";
|
||||
var encoded =
|
||||
r"$2b$04$cVWp4XaNU8a4v1uMRum2SO026BWLIoQMD/TXg5uZV.0P.uO8m3YEm";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$pQ7gRO7e6wx/936oXhNjrOUNOHL1D0h1N2IDbJZYs.1ppzSof6SPy", () {
|
||||
var password = "9IeRXmnGxMYbs";
|
||||
var encoded =
|
||||
r"$2b$04$pQ7gRO7e6wx/936oXhNjrOUNOHL1D0h1N2IDbJZYs.1ppzSof6SPy";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$SQe9knOzepOVKoYXo9xTteNYr6MBwVz4tpriJVe3PNgYufGIsgKcW", () {
|
||||
var password = "xVQVbwa1S0M8r";
|
||||
var encoded =
|
||||
r"$2b$04$SQe9knOzepOVKoYXo9xTteNYr6MBwVz4tpriJVe3PNgYufGIsgKcW";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$eH8zX.q5Q.j2hO1NkVYJQOM6KxntS/ow3.YzVmFrE4t//CoF4fvne", () {
|
||||
var password = "Zfgr26LWd22Za";
|
||||
var encoded =
|
||||
r"$2b$04$eH8zX.q5Q.j2hO1NkVYJQOM6KxntS/ow3.YzVmFrE4t//CoF4fvne";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$ahiTdwRXpUG2JLRcIznxc.s1.ydaPGD372bsGs8NqyYjLY1inG5n2", () {
|
||||
var password = "Tg4daC27epFBE";
|
||||
var encoded =
|
||||
r"$2b$04$ahiTdwRXpUG2JLRcIznxc.s1.ydaPGD372bsGs8NqyYjLY1inG5n2";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$nQn78dV0hGHf5wUBe0zOFu8n07ZbWWOKoGasZKRspZxtt.vBRNMIy", () {
|
||||
var password = "xhQPMmwh5ALzW";
|
||||
var encoded =
|
||||
r"$2b$04$nQn78dV0hGHf5wUBe0zOFu8n07ZbWWOKoGasZKRspZxtt.vBRNMIy";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$cvXudZ5ugTg95W.rOjMITuM1jC0piCl3zF5cmGhzCibHZrNHkmckG", () {
|
||||
var password = "59je8h5Gj71tg";
|
||||
var encoded =
|
||||
r"$2b$04$cvXudZ5ugTg95W.rOjMITuM1jC0piCl3zF5cmGhzCibHZrNHkmckG";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$YYjtiq4Uh88yUsExO0RNTuEJ.tZlsONac16A8OcLHleWFjVawfGvO", () {
|
||||
var password = "wT4fHJa2N9WSW";
|
||||
var encoded =
|
||||
r"$2b$04$YYjtiq4Uh88yUsExO0RNTuEJ.tZlsONac16A8OcLHleWFjVawfGvO";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$WLTjgY/pZSyqX/fbMbJzf.qxCeTMQOzgL.CimRjMHtMxd/VGKojMu", () {
|
||||
var password = "uSgFRnQdOgm4S";
|
||||
var encoded =
|
||||
r"$2b$04$WLTjgY/pZSyqX/fbMbJzf.qxCeTMQOzgL.CimRjMHtMxd/VGKojMu";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$2moPs/x/wnCfeQ5pCheMcuSJQ/KYjOZG780UjA/SiR.KsYWNrC7SG", () {
|
||||
var password = "tEPtJZXur16Vg";
|
||||
var encoded =
|
||||
r"$2b$04$2moPs/x/wnCfeQ5pCheMcuSJQ/KYjOZG780UjA/SiR.KsYWNrC7SG";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$HrEYC/AQ2HS77G78cQDZQ.r44WGcruKw03KHlnp71yVQEwpsi3xl2", () {
|
||||
var password = "vvho8C6nlVf9K";
|
||||
var encoded =
|
||||
r"$2b$04$HrEYC/AQ2HS77G78cQDZQ.r44WGcruKw03KHlnp71yVQEwpsi3xl2";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$vVYgSTfB8KVbmhbZE/k3R.ux9A0lJUM4CZwCkHI9fifke2.rTF7MG", () {
|
||||
var password = "5auCCY9by0Ruf";
|
||||
var encoded =
|
||||
r"$2b$04$vVYgSTfB8KVbmhbZE/k3R.ux9A0lJUM4CZwCkHI9fifke2.rTF7MG";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$JfoNrR8.doieoI8..F.C1OQgwE3uTeuardy6lw0AjALUzOARoyf2m", () {
|
||||
var password = "GtTkR6qn2QOZW";
|
||||
var encoded =
|
||||
r"$2b$04$JfoNrR8.doieoI8..F.C1OQgwE3uTeuardy6lw0AjALUzOARoyf2m";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$HP3I0PUs7KBEzMBNFw7o3O7f/uxaZU7aaDot1quHMgB2yrwBXsgyy", () {
|
||||
var password = "zKo8vdFSnjX0f";
|
||||
var encoded =
|
||||
r"$2b$04$HP3I0PUs7KBEzMBNFw7o3O7f/uxaZU7aaDot1quHMgB2yrwBXsgyy";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$xnFVhJsTzsFBTeP3PpgbMeMREb6rdKV9faW54Sx.yg9plf4jY8qT6", () {
|
||||
var password = "I9VfYlacJiwiK";
|
||||
var encoded =
|
||||
r"$2b$04$xnFVhJsTzsFBTeP3PpgbMeMREb6rdKV9faW54Sx.yg9plf4jY8qT6";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$WQp9.igoLqVr6Qk70mz6xuRxE0RttVXXdukpR9N54x17ecad34ZF6", () {
|
||||
var password = "VFPO7YXnHQbQO";
|
||||
var encoded =
|
||||
r"$2b$04$WQp9.igoLqVr6Qk70mz6xuRxE0RttVXXdukpR9N54x17ecad34ZF6";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$xgZtlonpAHSU/njOCdKztOPuPFzCNVpB4LGicO4/OGgHv.uKHkwsS", () {
|
||||
var password = "VDx5BdxfxstYk";
|
||||
var encoded =
|
||||
r"$2b$04$xgZtlonpAHSU/njOCdKztOPuPFzCNVpB4LGicO4/OGgHv.uKHkwsS";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$2Siw3Nv3Q/gTOIPetAyPr.GNj3aO0lb1E5E9UumYGKjP9BYqlNWJe", () {
|
||||
var password = "dEe6XfVGrrfSH";
|
||||
var encoded =
|
||||
r"$2b$04$2Siw3Nv3Q/gTOIPetAyPr.GNj3aO0lb1E5E9UumYGKjP9BYqlNWJe";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$7/Qj7Kd8BcSahPO4khB8me4ssDJCW3r4OGYqPF87jxtrSyPj5cS5m", () {
|
||||
var password = "cTT0EAFdwJiLn";
|
||||
var encoded =
|
||||
r"$2b$04$7/Qj7Kd8BcSahPO4khB8me4ssDJCW3r4OGYqPF87jxtrSyPj5cS5m";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$VvlCUKbTMjaxaYJ.k5juoecpG/7IzcH1AkmqKi.lIZMVIOLClWAk.", () {
|
||||
var password = "J8eHUDuxBB520";
|
||||
var encoded =
|
||||
r"$2b$04$VvlCUKbTMjaxaYJ.k5juoecpG/7IzcH1AkmqKi.lIZMVIOLClWAk.";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$10$keO.ZZs22YtygVF6BLfhGOI/JjshJYPp8DZsUtym6mJV2Eha2Hdd.", () {
|
||||
var password = [
|
||||
125, 62, 179, 254, 241, 139, 160, 230, 40, 162, 76, 122, 113, 195, //
|
||||
80, 127, 204, 200, 98, 123, 249, 20, 246, 246, 96, 129, 71, 53, 236,
|
||||
29, 135, 16, 191, 167, 225, 125, 73, 55, 32, 150, 223, 99, 242, 191,
|
||||
179, 86, 104, 223, 77, 136, 113, 247, 255, 27, 130, 126, 122, 19, 221,
|
||||
233, 132, 0, 221, 52
|
||||
];
|
||||
var encoded =
|
||||
r"$2b$10$keO.ZZs22YtygVF6BLfhGOI/JjshJYPp8DZsUtym6mJV2Eha2Hdd.";
|
||||
var output = bcrypt(password, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
});
|
||||
}
|
||||
24
hashlib/test/bcrypt/bcrypt_2y_test.dart
Normal file
24
hashlib/test/bcrypt/bcrypt_2y_test.dart
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('bcrypt version 2y', () {
|
||||
test(r"$2y$05$/OK.fbVrR/bpIqNJ5ianF.Sa7shbm4.OzKpvFnX1pQLmQW96oUlCq", () {
|
||||
var password = "\xa3";
|
||||
var encoded =
|
||||
r"$2y$05$/OK.fbVrR/bpIqNJ5ianF.Sa7shbm4.OzKpvFnX1pQLmQW96oUlCq";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2y$05$/OK.fbVrR/bpIqNJ5ianF.CE5elHaaO4EbggVDjb8P19RukzXSM3e", () {
|
||||
var password = "\xff\xff\xa3";
|
||||
var encoded =
|
||||
r"$2y$05$/OK.fbVrR/bpIqNJ5ianF.CE5elHaaO4EbggVDjb8P19RukzXSM3e";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
});
|
||||
}
|
||||
221
hashlib/test/bcrypt/bcrypt_basic_test.dart
Normal file
221
hashlib/test/bcrypt/bcrypt_basic_test.dart
Normal file
|
|
@ -0,0 +1,221 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
import 'dart:convert';
|
||||
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('bcrypt functionality', () {
|
||||
test("name", () {
|
||||
expect(Bcrypt(cost: 10).name, r'Bcrypt/2b');
|
||||
expect(Bcrypt(cost: 10, version: BcryptVersion.$2a).name, r'Bcrypt/2a');
|
||||
expect(Bcrypt(cost: 10, version: BcryptVersion.$2x).name, r'Bcrypt/2x');
|
||||
expect(Bcrypt(cost: 10, version: BcryptVersion.$2y).name, r'Bcrypt/2y');
|
||||
expect(Bcrypt(cost: 10, version: BcryptVersion.$2b).name, r'Bcrypt/2b');
|
||||
});
|
||||
|
||||
// http://openwall.info/wiki/john/sample-hashes
|
||||
test("bcrypt", () {
|
||||
const password = r"password";
|
||||
const salt = r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO";
|
||||
const encoded =
|
||||
r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe";
|
||||
var output = bcrypt(utf8.encode(password), salt);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test("bcryptVerify", () {
|
||||
const password = r"password";
|
||||
const encoded =
|
||||
r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe";
|
||||
expect(bcryptVerify(encoded, password.codeUnits), true);
|
||||
});
|
||||
|
||||
test("bcryptSalt", () {
|
||||
final salt = bcryptSalt(nb: 5, version: BcryptVersion.$2a);
|
||||
expect(salt.length, 29);
|
||||
expect(salt, startsWith(r"$2a$05$"));
|
||||
});
|
||||
|
||||
test("bcryptSalt with security", () {
|
||||
final salt = bcryptSalt(security: BcryptSecurity.strong);
|
||||
expect(salt.length, 29);
|
||||
expect(salt, startsWith(r"$2b$15$"));
|
||||
});
|
||||
|
||||
test("bcryptSalt with security overrides", () {
|
||||
final salt = bcryptSalt(security: BcryptSecurity.strong, nb: 10);
|
||||
expect(salt.length, 29);
|
||||
expect(salt, startsWith(r"$2b$10$"));
|
||||
});
|
||||
|
||||
test("bcryptDigest", () {
|
||||
var password = "password".codeUnits;
|
||||
var salt = fromBase64(
|
||||
"bvIG6Nmid91Mu9RcmmWZfO",
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
var result = fromBase64(
|
||||
'5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe',
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
const encoded =
|
||||
r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe";
|
||||
final output = bcryptDigest(
|
||||
password,
|
||||
nb: 5,
|
||||
salt: salt,
|
||||
version: BcryptVersion.$2a,
|
||||
);
|
||||
expect(output.bytes, equals(result));
|
||||
expect(output.encoded(), equals(encoded));
|
||||
expect(output.toString(), equals(encoded));
|
||||
});
|
||||
test("bcryptDigest with security", () {
|
||||
var password = "password".codeUnits;
|
||||
var salt = fromBase64(
|
||||
"bvIG6Nmid91Mu9RcmmWZfO",
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
var result = fromBase64(
|
||||
'5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe',
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
final output = bcryptDigest(
|
||||
password,
|
||||
salt: salt,
|
||||
version: BcryptVersion.$2a,
|
||||
security: BcryptSecurity.little,
|
||||
);
|
||||
expect(output.bytes, equals(result));
|
||||
});
|
||||
test("Bcrypt instance with security", () {
|
||||
var password = "password".codeUnits;
|
||||
var salt = fromBase64(
|
||||
"bvIG6Nmid91Mu9RcmmWZfO",
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
var result = fromBase64(
|
||||
'5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe',
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
final output = Bcrypt.fromSecurity(
|
||||
BcryptSecurity.little,
|
||||
salt: salt,
|
||||
version: BcryptVersion.$2a,
|
||||
).convert(password);
|
||||
expect(output.bytes, equals(result));
|
||||
});
|
||||
test("The cost must be at least 0", () {
|
||||
BcryptContext(cost: 0);
|
||||
expect(() => BcryptContext(cost: -10), throwsArgumentError);
|
||||
expect(() => BcryptContext(cost: -1), throwsArgumentError);
|
||||
});
|
||||
test("The cost must be at most 31", () {
|
||||
BcryptContext(cost: 31);
|
||||
expect(() => BcryptContext(cost: 32), throwsArgumentError);
|
||||
expect(() => BcryptContext(cost: 100), throwsArgumentError);
|
||||
});
|
||||
test("The salt must be exactly 16-bytes", () {
|
||||
BcryptContext(cost: 4, salt: List.filled(16, 0));
|
||||
expect(
|
||||
() => BcryptContext(cost: 4, salt: []),
|
||||
throwsArgumentError,
|
||||
);
|
||||
expect(
|
||||
() => BcryptContext(cost: 4, salt: List.filled(15, 0)),
|
||||
throwsArgumentError,
|
||||
);
|
||||
expect(
|
||||
() => BcryptContext(cost: 4, salt: List.filled(17, 0)),
|
||||
throwsArgumentError,
|
||||
);
|
||||
});
|
||||
test("Bcrypt from encoded", () {
|
||||
Bcrypt.fromEncoded(fromCrypt(r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO"));
|
||||
});
|
||||
test("Bcrypt from encoded with invalid version", () {
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2c$05$bvIG6Nmid91Mu9RcmmWZfO")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid version',
|
||||
),
|
||||
),
|
||||
);
|
||||
});
|
||||
test("Bcrypt from encoded with invalid cost", () {
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2x$bvIG6Nmid91Mu9RcmmWZfO")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid cost',
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2y$32$bvIG6Nmid91Mu9RcmmWZfO")),
|
||||
throwsA(
|
||||
isA<ArgumentError>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'The cost must be at most 31',
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2y$-1$bvIG6Nmid91Mu9RcmmWZfO")),
|
||||
throwsA(
|
||||
isA<ArgumentError>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'The cost must be at least 0',
|
||||
),
|
||||
),
|
||||
);
|
||||
});
|
||||
test("Bcrypt from encoded with invalid salt", () {
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2b$05$bvIG6Nmid91Mu9RcmmWZf")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid hash',
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2b$05$bvIG6Nmid91Mu9RcmmWZf0")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid length',
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(
|
||||
r"$2b$05$DCq7YPn5Rq63x1Lad4cll.TV4S6ytwfsfvkgY8jIucDrjc8deX1")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid hash',
|
||||
),
|
||||
),
|
||||
);
|
||||
Bcrypt.fromEncoded(fromCrypt(
|
||||
r"$2a$06$DCq7YPn5Rq63x1Lad4cll.TV4S6ytwfsfvkgY8jIucDrjc8deX1s1",
|
||||
));
|
||||
});
|
||||
});
|
||||
}
|
||||
110
hashlib/test/bcrypt/bcrypt_cost_test.dart
Normal file
110
hashlib/test/bcrypt/bcrypt_cost_test.dart
Normal file
|
|
@ -0,0 +1,110 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
import 'dart:convert';
|
||||
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('bcrypt big cost', () {
|
||||
test(r"$2a$10$k1wbIrmNyFAPwPVPSVa/zecw2BCEnBwVS2GbrmgzxFUOqW9dk4TCW", () {
|
||||
const password = r"";
|
||||
const encoded =
|
||||
r"$2a$10$k1wbIrmNyFAPwPVPSVa/zecw2BCEnBwVS2GbrmgzxFUOqW9dk4TCW";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$k42ZFHFWqBp3vWli.nIn8uYyIkbvYRvodzbfbK18SSsY.CsIQPlxO", () {
|
||||
const password = r"";
|
||||
const encoded =
|
||||
r"$2a$12$k42ZFHFWqBp3vWli.nIn8uYyIkbvYRvodzbfbK18SSsY.CsIQPlxO";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$08$cfcvVd2aQ8CMvoMpP2EBfeodLEkkFJ9umNEfPD18.hUF62qqlC/V.", () {
|
||||
const password = r"a";
|
||||
const encoded =
|
||||
r"$2a$08$cfcvVd2aQ8CMvoMpP2EBfeodLEkkFJ9umNEfPD18.hUF62qqlC/V.";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$10$k87L/MF28Q673VKh8/cPi.SUl7MU/rWuSiIDDFayrKk/1tBsSQu4u", () {
|
||||
const password = r"a";
|
||||
const encoded =
|
||||
r"$2a$10$k87L/MF28Q673VKh8/cPi.SUl7MU/rWuSiIDDFayrKk/1tBsSQu4u";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$8NJH3LsPrANStV6XtBakCez0cKHXVxmvxIlcz785vxAIZrihHZpeS", () {
|
||||
const password = r"a";
|
||||
const encoded =
|
||||
r"$2a$12$8NJH3LsPrANStV6XtBakCez0cKHXVxmvxIlcz785vxAIZrihHZpeS";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$08$Ro0CUfOqk6cXEKf3dyaM7OhSCvnwM9s4wIX9JeLapehKK5YdLxKcm", () {
|
||||
const password = r"abc";
|
||||
const encoded =
|
||||
r"$2a$08$Ro0CUfOqk6cXEKf3dyaM7OhSCvnwM9s4wIX9JeLapehKK5YdLxKcm";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$10$WvvTPHKwdBJ3uk0Z37EMR.hLA2W6N9AEBhEgrAOljy2Ae5MtaSIUi", () {
|
||||
const password = r"abc";
|
||||
const encoded =
|
||||
r"$2a$10$WvvTPHKwdBJ3uk0Z37EMR.hLA2W6N9AEBhEgrAOljy2Ae5MtaSIUi";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$EXRkfkdmXn2gzds2SSitu.MW9.gAVqa9eLS1//RYtYCmB1eLHg.9q", () {
|
||||
const password = r"abc";
|
||||
const encoded =
|
||||
r"$2a$12$EXRkfkdmXn2gzds2SSitu.MW9.gAVqa9eLS1//RYtYCmB1eLHg.9q";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$08$aTsUwsyowQuzRrDqFflhgekJ8d9/7Z3GV3UcgvzQW3J5zMyrTvlz.", () {
|
||||
const password = r"abcdefghijklmnopqrstuvwxyz";
|
||||
const encoded =
|
||||
r"$2a$08$aTsUwsyowQuzRrDqFflhgekJ8d9/7Z3GV3UcgvzQW3J5zMyrTvlz.";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$10$fVH8e28OQRj9tqiDXs1e1uxpsjN0c7II7YPKXua2NAKYvM6iQk7dq", () {
|
||||
const password = r"abcdefghijklmnopqrstuvwxyz";
|
||||
const encoded =
|
||||
r"$2a$10$fVH8e28OQRj9tqiDXs1e1uxpsjN0c7II7YPKXua2NAKYvM6iQk7dq";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$D4G5f18o7aMMfwasBL7GpuQWuP3pkrZrOAnqP.bmezbMng.QwJ/pG", () {
|
||||
const password = r"abcdefghijklmnopqrstuvwxyz";
|
||||
const encoded =
|
||||
r"$2a$12$D4G5f18o7aMMfwasBL7GpuQWuP3pkrZrOAnqP.bmezbMng.QwJ/pG";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$08$Eq2r4G/76Wv39MzSX262huzPz612MZiYHVUJe/OcOql2jo4.9UxTW", () {
|
||||
const password = r"~!@#$%^&*() ~!@#$%^&*()PNBFRD";
|
||||
const encoded =
|
||||
r"$2a$08$Eq2r4G/76Wv39MzSX262huzPz612MZiYHVUJe/OcOql2jo4.9UxTW";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$10$LgfYWkbzEvQ4JakH7rOvHe0y8pHKF9OaFgwUZ2q7W2FFZmZzJYlfS", () {
|
||||
const password = r"~!@#$%^&*() ~!@#$%^&*()PNBFRD";
|
||||
const encoded =
|
||||
r"$2a$10$LgfYWkbzEvQ4JakH7rOvHe0y8pHKF9OaFgwUZ2q7W2FFZmZzJYlfS";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$WApznUOJfkEGSmYRfnkrPOr466oFDCaj4b6HY3EXGvfxm43seyhgC", () {
|
||||
const password = r"~!@#$%^&*() ~!@#$%^&*()PNBFRD";
|
||||
const encoded =
|
||||
r"$2a$12$WApznUOJfkEGSmYRfnkrPOr466oFDCaj4b6HY3EXGvfxm43seyhgC";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
}, skip: true);
|
||||
}
|
||||
|
|
@ -1,643 +0,0 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
import 'dart:convert';
|
||||
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('bcrypt test', () {
|
||||
group('functionality test', () {
|
||||
test("name", () {
|
||||
expect(Bcrypt(cost: 10).name, r'Bcrypt/2b');
|
||||
expect(Bcrypt(cost: 10, version: BcryptVersion.$2a).name, r'Bcrypt/2a');
|
||||
expect(Bcrypt(cost: 10, version: BcryptVersion.$2x).name, r'Bcrypt/2x');
|
||||
expect(Bcrypt(cost: 10, version: BcryptVersion.$2y).name, r'Bcrypt/2y');
|
||||
expect(Bcrypt(cost: 10, version: BcryptVersion.$2b).name, r'Bcrypt/2b');
|
||||
});
|
||||
|
||||
// http://openwall.info/wiki/john/sample-hashes
|
||||
test("bcrypt", () {
|
||||
const password = r"password";
|
||||
const salt = r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO";
|
||||
const encoded =
|
||||
r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe";
|
||||
var output = bcrypt(utf8.encode(password), salt);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test("bcryptVerify", () {
|
||||
const password = r"password";
|
||||
const encoded =
|
||||
r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe";
|
||||
expect(bcryptVerify(encoded, password.codeUnits), true);
|
||||
});
|
||||
|
||||
test("bcryptSalt", () {
|
||||
final salt = bcryptSalt(nb: 5, version: BcryptVersion.$2a);
|
||||
expect(salt.length, 29);
|
||||
expect(salt, startsWith(r"$2a$05$"));
|
||||
});
|
||||
|
||||
test("bcryptSalt with security", () {
|
||||
final salt = bcryptSalt(security: BcryptSecurity.strong);
|
||||
expect(salt.length, 29);
|
||||
expect(salt, startsWith(r"$2b$15$"));
|
||||
});
|
||||
|
||||
test("bcryptSalt with security overrides", () {
|
||||
final salt = bcryptSalt(security: BcryptSecurity.strong, nb: 10);
|
||||
expect(salt.length, 29);
|
||||
expect(salt, startsWith(r"$2b$10$"));
|
||||
});
|
||||
|
||||
test("bcryptDigest", () {
|
||||
var password = "password".codeUnits;
|
||||
var salt = fromBase64(
|
||||
"bvIG6Nmid91Mu9RcmmWZfO",
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
var result = fromBase64(
|
||||
'5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe',
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
const encoded =
|
||||
r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe";
|
||||
final output = bcryptDigest(
|
||||
password,
|
||||
nb: 5,
|
||||
salt: salt,
|
||||
version: BcryptVersion.$2a,
|
||||
);
|
||||
expect(output.bytes, equals(result));
|
||||
expect(output.encoded(), equals(encoded));
|
||||
expect(output.toString(), equals(encoded));
|
||||
});
|
||||
test("bcryptDigest with security", () {
|
||||
var password = "password".codeUnits;
|
||||
var salt = fromBase64(
|
||||
"bvIG6Nmid91Mu9RcmmWZfO",
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
var result = fromBase64(
|
||||
'5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe',
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
final output = bcryptDigest(
|
||||
password,
|
||||
salt: salt,
|
||||
version: BcryptVersion.$2a,
|
||||
security: BcryptSecurity.little,
|
||||
);
|
||||
expect(output.bytes, equals(result));
|
||||
});
|
||||
test("Bcrypt instance with security", () {
|
||||
var password = "password".codeUnits;
|
||||
var salt = fromBase64(
|
||||
"bvIG6Nmid91Mu9RcmmWZfO",
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
var result = fromBase64(
|
||||
'5HJIMCT8riNW0hEp8f6/FuA2/mHZFpe',
|
||||
codec: Base64Codec.bcrypt,
|
||||
);
|
||||
final output = Bcrypt.fromSecurity(
|
||||
BcryptSecurity.little,
|
||||
salt: salt,
|
||||
version: BcryptVersion.$2a,
|
||||
).convert(password);
|
||||
expect(output.bytes, equals(result));
|
||||
});
|
||||
test("The cost must be at least 0", () {
|
||||
BcryptContext(cost: 0);
|
||||
expect(() => BcryptContext(cost: -10), throwsArgumentError);
|
||||
expect(() => BcryptContext(cost: -1), throwsArgumentError);
|
||||
});
|
||||
test("The cost must be at most 31", () {
|
||||
BcryptContext(cost: 31);
|
||||
expect(() => BcryptContext(cost: 32), throwsArgumentError);
|
||||
expect(() => BcryptContext(cost: 100), throwsArgumentError);
|
||||
});
|
||||
test("The salt must be exactly 16-bytes", () {
|
||||
BcryptContext(cost: 4, salt: List.filled(16, 0));
|
||||
expect(
|
||||
() => BcryptContext(cost: 4, salt: []),
|
||||
throwsArgumentError,
|
||||
);
|
||||
expect(
|
||||
() => BcryptContext(cost: 4, salt: List.filled(15, 0)),
|
||||
throwsArgumentError,
|
||||
);
|
||||
expect(
|
||||
() => BcryptContext(cost: 4, salt: List.filled(17, 0)),
|
||||
throwsArgumentError,
|
||||
);
|
||||
});
|
||||
test("Bcrypt from encoded", () {
|
||||
Bcrypt.fromEncoded(fromCrypt(r"$2a$05$bvIG6Nmid91Mu9RcmmWZfO"));
|
||||
});
|
||||
test("Bcrypt from encoded with invalid version", () {
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2c$05$bvIG6Nmid91Mu9RcmmWZfO")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid version',
|
||||
),
|
||||
),
|
||||
);
|
||||
});
|
||||
test("Bcrypt from encoded with invalid cost", () {
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2x$bvIG6Nmid91Mu9RcmmWZfO")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid cost',
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2y$32$bvIG6Nmid91Mu9RcmmWZfO")),
|
||||
throwsA(
|
||||
isA<ArgumentError>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'The cost must be at most 31',
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2y$-1$bvIG6Nmid91Mu9RcmmWZfO")),
|
||||
throwsA(
|
||||
isA<ArgumentError>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'The cost must be at least 0',
|
||||
),
|
||||
),
|
||||
);
|
||||
});
|
||||
test("Bcrypt from encoded with invalid salt", () {
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2b$05$bvIG6Nmid91Mu9RcmmWZf")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid hash',
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(r"$2b$05$bvIG6Nmid91Mu9RcmmWZf0")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid length',
|
||||
),
|
||||
),
|
||||
);
|
||||
expect(
|
||||
() => Bcrypt.fromEncoded(fromCrypt(
|
||||
r"$2b$05$DCq7YPn5Rq63x1Lad4cll.TV4S6ytwfsfvkgY8jIucDrjc8deX1")),
|
||||
throwsA(
|
||||
isA<FormatException>().having(
|
||||
(e) => e.message,
|
||||
'message',
|
||||
'Invalid hash',
|
||||
),
|
||||
),
|
||||
);
|
||||
Bcrypt.fromEncoded(fromCrypt(
|
||||
r"$2a$06$DCq7YPn5Rq63x1Lad4cll.TV4S6ytwfsfvkgY8jIucDrjc8deX1s1",
|
||||
));
|
||||
});
|
||||
});
|
||||
|
||||
group('version 2a', () {
|
||||
// http://cvsweb.openwall.com/cgi/cvsweb.cgi/Owl/packages/glibc/crypt_blowfish/wrapper.c?rev=HEAD
|
||||
test(r"$2a$06$DCq7YPn5Rq63x1Lad4cll.TV4S6ytwfsfvkgY8jIucDrjc8deX1s.", () {
|
||||
const password = r"";
|
||||
const encoded =
|
||||
r"$2a$06$DCq7YPn5Rq63x1Lad4cll.TV4S6ytwfsfvkgY8jIucDrjc8deX1s.";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
// https://stackoverflow.com/a/12761326/774398
|
||||
test(r"$2a$10$.TtQJ4Jr6isd4Hp.mVfZeuh6Gws4rOQ/vdBczhDx.19NFK0Y84Dle", () {
|
||||
const password = r"ππππππππ";
|
||||
const encoded =
|
||||
r"$2a$10$.TtQJ4Jr6isd4Hp.mVfZeuh6Gws4rOQ/vdBczhDx.19NFK0Y84Dle";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
// https://bitbucket.org/vadim/bcrypt.net/src/464c41416dc9/BCrypt.Net.Test/TestBCrypt.cs?fileviewer=file-view-default
|
||||
test(r"$2a$08$HqWuK6/Ng6sg9gQzbLrgb.Tl.ZHfXLhvt/SgVyWhQqgqcZ7ZuUtye", () {
|
||||
const password = r"";
|
||||
const encoded =
|
||||
r"$2a$08$HqWuK6/Ng6sg9gQzbLrgb.Tl.ZHfXLhvt/SgVyWhQqgqcZ7ZuUtye";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$06$m0CrhHm10qJ3lXRY.5zDGO3rS2KdeeWLuGmsfGlMfOxih58VYVfxe", () {
|
||||
const password = r"a";
|
||||
const encoded =
|
||||
r"$2a$06$m0CrhHm10qJ3lXRY.5zDGO3rS2KdeeWLuGmsfGlMfOxih58VYVfxe";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$06$If6bvum7DFjUnE9p2uDeDu0YHzrHM6tf.iqN8.yx.jNN1ILEf7h0i", () {
|
||||
const password = r"abc";
|
||||
const encoded =
|
||||
r"$2a$06$If6bvum7DFjUnE9p2uDeDu0YHzrHM6tf.iqN8.yx.jNN1ILEf7h0i";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$06$.rCVZVOThsIa97pEDOxvGuRRgzG64bvtJ0938xuqzv18d3ZpQhstC", () {
|
||||
const password = r"abcdefghijklmnopqrstuvwxyz";
|
||||
const encoded =
|
||||
r"$2a$06$.rCVZVOThsIa97pEDOxvGuRRgzG64bvtJ0938xuqzv18d3ZpQhstC";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$06$fPIsBO8qRqkjj273rfaOI.HtSV9jLDpTbZn782DC6/t7qT67P6FfO", () {
|
||||
const password = r"~!@#$%^&*() ~!@#$%^&*()PNBFRD";
|
||||
const encoded =
|
||||
r"$2a$06$fPIsBO8qRqkjj273rfaOI.HtSV9jLDpTbZn782DC6/t7qT67P6FfO";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
// https://github.com/pyca/bcrypt/blob/main/tests/test_bcrypt.py
|
||||
test(r"$2a$05$CCCCCCCCCCCCCCCCCCCCC.E5YPO9kmyuRGyh0XouQYb4YMJKvyOeW", () {
|
||||
var password = "U*U";
|
||||
var encoded =
|
||||
r"$2a$05$CCCCCCCCCCCCCCCCCCCCC.E5YPO9kmyuRGyh0XouQYb4YMJKvyOeW";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$CCCCCCCCCCCCCCCCCCCCC.VGOzA784oUp/Z0DY336zx7pLYAy0lwK", () {
|
||||
var password = "U*U*";
|
||||
var encoded =
|
||||
r"$2a$05$CCCCCCCCCCCCCCCCCCCCC.VGOzA784oUp/Z0DY336zx7pLYAy0lwK";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$XXXXXXXXXXXXXXXXXXXXXOAcXxm9kjPGEMsLznoKqmqw7tc8WCx4a", () {
|
||||
var password = "U*U*U";
|
||||
var encoded =
|
||||
r"$2a$05$XXXXXXXXXXXXXXXXXXXXXOAcXxm9kjPGEMsLznoKqmqw7tc8WCx4a";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$abcdefghijklmnopqrstuu5s2v8.iXieOjg/.AySBTTZIIVFJeBui", () {
|
||||
var password = "0123456789abcdefghijklmnopqrstuvwxyz"
|
||||
"ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
|
||||
"chars after 72 are ignored";
|
||||
var encoded =
|
||||
r"$2a$05$abcdefghijklmnopqrstuu5s2v8.iXieOjg/.AySBTTZIIVFJeBui";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$/OK.fbVrR/bpIqNJ5ianF.swQOIzjOiJ9GHEPuhEkvqrUyvWhEMx6", () {
|
||||
var password = "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
|
||||
"chars after 72 are ignored as usual";
|
||||
var encoded =
|
||||
r"$2a$05$/OK.fbVrR/bpIqNJ5ianF.swQOIzjOiJ9GHEPuhEkvqrUyvWhEMx6";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$05$/OK.fbVrR/bpIqNJ5ianF.Sa7shbm4.OzKpvFnX1pQLmQW96oUlCq", () {
|
||||
var password = "\xa3";
|
||||
var encoded =
|
||||
r"$2a$05$/OK.fbVrR/bpIqNJ5ianF.Sa7shbm4.OzKpvFnX1pQLmQW96oUlCq";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2a$04$tecY.9ylRInW/rAAzXCXPOOlyYeCNzmNTzPDNSIFztFMKbvs/s5XG", () {
|
||||
var password =
|
||||
"g7\r\x01\xf3\xd4\xd0\xa9JB^\x18\x007P\xb2N\xc7\x1c\xee\x87&\x83C"
|
||||
"\x8b\xe8\x18\xc5>\x86\x14/\xd6\xcc\x1cJ\xde\xd7ix\xeb\xdeO\xef"
|
||||
"\xe1i\xac\xcb\x03\x96v1' \xd6@.m\xa5!\xa0\xef\xc0(";
|
||||
var encoded =
|
||||
r"$2a$04$tecY.9ylRInW/rAAzXCXPOOlyYeCNzmNTzPDNSIFztFMKbvs/s5XG";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
});
|
||||
|
||||
group('version 2y', () {
|
||||
test(r"$2y$05$/OK.fbVrR/bpIqNJ5ianF.Sa7shbm4.OzKpvFnX1pQLmQW96oUlCq", () {
|
||||
var password = "\xa3";
|
||||
var encoded =
|
||||
r"$2y$05$/OK.fbVrR/bpIqNJ5ianF.Sa7shbm4.OzKpvFnX1pQLmQW96oUlCq";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2y$05$/OK.fbVrR/bpIqNJ5ianF.CE5elHaaO4EbggVDjb8P19RukzXSM3e", () {
|
||||
var password = "\xff\xff\xa3";
|
||||
var encoded =
|
||||
r"$2y$05$/OK.fbVrR/bpIqNJ5ianF.CE5elHaaO4EbggVDjb8P19RukzXSM3e";
|
||||
var output = bcrypt(password.codeUnits, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
});
|
||||
|
||||
// https://github.com/pyca/bcrypt/blob/main/tests/test_bcrypt.py
|
||||
group('version 2b', () {
|
||||
test(r"$2b$04$cVWp4XaNU8a4v1uMRum2SO026BWLIoQMD/TXg5uZV.0P.uO8m3YEm", () {
|
||||
var password = "Kk4DQuMMfZL9o";
|
||||
var encoded =
|
||||
r"$2b$04$cVWp4XaNU8a4v1uMRum2SO026BWLIoQMD/TXg5uZV.0P.uO8m3YEm";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$pQ7gRO7e6wx/936oXhNjrOUNOHL1D0h1N2IDbJZYs.1ppzSof6SPy", () {
|
||||
var password = "9IeRXmnGxMYbs";
|
||||
var encoded =
|
||||
r"$2b$04$pQ7gRO7e6wx/936oXhNjrOUNOHL1D0h1N2IDbJZYs.1ppzSof6SPy";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$SQe9knOzepOVKoYXo9xTteNYr6MBwVz4tpriJVe3PNgYufGIsgKcW", () {
|
||||
var password = "xVQVbwa1S0M8r";
|
||||
var encoded =
|
||||
r"$2b$04$SQe9knOzepOVKoYXo9xTteNYr6MBwVz4tpriJVe3PNgYufGIsgKcW";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$eH8zX.q5Q.j2hO1NkVYJQOM6KxntS/ow3.YzVmFrE4t//CoF4fvne", () {
|
||||
var password = "Zfgr26LWd22Za";
|
||||
var encoded =
|
||||
r"$2b$04$eH8zX.q5Q.j2hO1NkVYJQOM6KxntS/ow3.YzVmFrE4t//CoF4fvne";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$ahiTdwRXpUG2JLRcIznxc.s1.ydaPGD372bsGs8NqyYjLY1inG5n2", () {
|
||||
var password = "Tg4daC27epFBE";
|
||||
var encoded =
|
||||
r"$2b$04$ahiTdwRXpUG2JLRcIznxc.s1.ydaPGD372bsGs8NqyYjLY1inG5n2";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$nQn78dV0hGHf5wUBe0zOFu8n07ZbWWOKoGasZKRspZxtt.vBRNMIy", () {
|
||||
var password = "xhQPMmwh5ALzW";
|
||||
var encoded =
|
||||
r"$2b$04$nQn78dV0hGHf5wUBe0zOFu8n07ZbWWOKoGasZKRspZxtt.vBRNMIy";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$cvXudZ5ugTg95W.rOjMITuM1jC0piCl3zF5cmGhzCibHZrNHkmckG", () {
|
||||
var password = "59je8h5Gj71tg";
|
||||
var encoded =
|
||||
r"$2b$04$cvXudZ5ugTg95W.rOjMITuM1jC0piCl3zF5cmGhzCibHZrNHkmckG";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$YYjtiq4Uh88yUsExO0RNTuEJ.tZlsONac16A8OcLHleWFjVawfGvO", () {
|
||||
var password = "wT4fHJa2N9WSW";
|
||||
var encoded =
|
||||
r"$2b$04$YYjtiq4Uh88yUsExO0RNTuEJ.tZlsONac16A8OcLHleWFjVawfGvO";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$WLTjgY/pZSyqX/fbMbJzf.qxCeTMQOzgL.CimRjMHtMxd/VGKojMu", () {
|
||||
var password = "uSgFRnQdOgm4S";
|
||||
var encoded =
|
||||
r"$2b$04$WLTjgY/pZSyqX/fbMbJzf.qxCeTMQOzgL.CimRjMHtMxd/VGKojMu";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$2moPs/x/wnCfeQ5pCheMcuSJQ/KYjOZG780UjA/SiR.KsYWNrC7SG", () {
|
||||
var password = "tEPtJZXur16Vg";
|
||||
var encoded =
|
||||
r"$2b$04$2moPs/x/wnCfeQ5pCheMcuSJQ/KYjOZG780UjA/SiR.KsYWNrC7SG";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$HrEYC/AQ2HS77G78cQDZQ.r44WGcruKw03KHlnp71yVQEwpsi3xl2", () {
|
||||
var password = "vvho8C6nlVf9K";
|
||||
var encoded =
|
||||
r"$2b$04$HrEYC/AQ2HS77G78cQDZQ.r44WGcruKw03KHlnp71yVQEwpsi3xl2";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$vVYgSTfB8KVbmhbZE/k3R.ux9A0lJUM4CZwCkHI9fifke2.rTF7MG", () {
|
||||
var password = "5auCCY9by0Ruf";
|
||||
var encoded =
|
||||
r"$2b$04$vVYgSTfB8KVbmhbZE/k3R.ux9A0lJUM4CZwCkHI9fifke2.rTF7MG";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$JfoNrR8.doieoI8..F.C1OQgwE3uTeuardy6lw0AjALUzOARoyf2m", () {
|
||||
var password = "GtTkR6qn2QOZW";
|
||||
var encoded =
|
||||
r"$2b$04$JfoNrR8.doieoI8..F.C1OQgwE3uTeuardy6lw0AjALUzOARoyf2m";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$HP3I0PUs7KBEzMBNFw7o3O7f/uxaZU7aaDot1quHMgB2yrwBXsgyy", () {
|
||||
var password = "zKo8vdFSnjX0f";
|
||||
var encoded =
|
||||
r"$2b$04$HP3I0PUs7KBEzMBNFw7o3O7f/uxaZU7aaDot1quHMgB2yrwBXsgyy";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$xnFVhJsTzsFBTeP3PpgbMeMREb6rdKV9faW54Sx.yg9plf4jY8qT6", () {
|
||||
var password = "I9VfYlacJiwiK";
|
||||
var encoded =
|
||||
r"$2b$04$xnFVhJsTzsFBTeP3PpgbMeMREb6rdKV9faW54Sx.yg9plf4jY8qT6";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$WQp9.igoLqVr6Qk70mz6xuRxE0RttVXXdukpR9N54x17ecad34ZF6", () {
|
||||
var password = "VFPO7YXnHQbQO";
|
||||
var encoded =
|
||||
r"$2b$04$WQp9.igoLqVr6Qk70mz6xuRxE0RttVXXdukpR9N54x17ecad34ZF6";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$xgZtlonpAHSU/njOCdKztOPuPFzCNVpB4LGicO4/OGgHv.uKHkwsS", () {
|
||||
var password = "VDx5BdxfxstYk";
|
||||
var encoded =
|
||||
r"$2b$04$xgZtlonpAHSU/njOCdKztOPuPFzCNVpB4LGicO4/OGgHv.uKHkwsS";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$2Siw3Nv3Q/gTOIPetAyPr.GNj3aO0lb1E5E9UumYGKjP9BYqlNWJe", () {
|
||||
var password = "dEe6XfVGrrfSH";
|
||||
var encoded =
|
||||
r"$2b$04$2Siw3Nv3Q/gTOIPetAyPr.GNj3aO0lb1E5E9UumYGKjP9BYqlNWJe";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$7/Qj7Kd8BcSahPO4khB8me4ssDJCW3r4OGYqPF87jxtrSyPj5cS5m", () {
|
||||
var password = "cTT0EAFdwJiLn";
|
||||
var encoded =
|
||||
r"$2b$04$7/Qj7Kd8BcSahPO4khB8me4ssDJCW3r4OGYqPF87jxtrSyPj5cS5m";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$04$VvlCUKbTMjaxaYJ.k5juoecpG/7IzcH1AkmqKi.lIZMVIOLClWAk.", () {
|
||||
var password = "J8eHUDuxBB520";
|
||||
var encoded =
|
||||
r"$2b$04$VvlCUKbTMjaxaYJ.k5juoecpG/7IzcH1AkmqKi.lIZMVIOLClWAk.";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
|
||||
test(r"$2b$10$keO.ZZs22YtygVF6BLfhGOI/JjshJYPp8DZsUtym6mJV2Eha2Hdd.", () {
|
||||
var password = [
|
||||
125, 62, 179, 254, 241, 139, 160, 230, 40, 162, 76, 122, 113, 195, //
|
||||
80, 127, 204, 200, 98, 123, 249, 20, 246, 246, 96, 129, 71, 53, 236,
|
||||
29, 135, 16, 191, 167, 225, 125, 73, 55, 32, 150, 223, 99, 242, 191,
|
||||
179, 86, 104, 223, 77, 136, 113, 247, 255, 27, 130, 126, 122, 19, 221,
|
||||
233, 132, 0, 221, 52
|
||||
];
|
||||
var encoded =
|
||||
r"$2b$10$keO.ZZs22YtygVF6BLfhGOI/JjshJYPp8DZsUtym6mJV2Eha2Hdd.";
|
||||
var output = bcrypt(password, encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
});
|
||||
|
||||
group('big cost', () {
|
||||
test(r"$2a$10$k1wbIrmNyFAPwPVPSVa/zecw2BCEnBwVS2GbrmgzxFUOqW9dk4TCW", () {
|
||||
const password = r"";
|
||||
const encoded =
|
||||
r"$2a$10$k1wbIrmNyFAPwPVPSVa/zecw2BCEnBwVS2GbrmgzxFUOqW9dk4TCW";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$k42ZFHFWqBp3vWli.nIn8uYyIkbvYRvodzbfbK18SSsY.CsIQPlxO", () {
|
||||
const password = r"";
|
||||
const encoded =
|
||||
r"$2a$12$k42ZFHFWqBp3vWli.nIn8uYyIkbvYRvodzbfbK18SSsY.CsIQPlxO";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$08$cfcvVd2aQ8CMvoMpP2EBfeodLEkkFJ9umNEfPD18.hUF62qqlC/V.", () {
|
||||
const password = r"a";
|
||||
const encoded =
|
||||
r"$2a$08$cfcvVd2aQ8CMvoMpP2EBfeodLEkkFJ9umNEfPD18.hUF62qqlC/V.";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$10$k87L/MF28Q673VKh8/cPi.SUl7MU/rWuSiIDDFayrKk/1tBsSQu4u", () {
|
||||
const password = r"a";
|
||||
const encoded =
|
||||
r"$2a$10$k87L/MF28Q673VKh8/cPi.SUl7MU/rWuSiIDDFayrKk/1tBsSQu4u";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$8NJH3LsPrANStV6XtBakCez0cKHXVxmvxIlcz785vxAIZrihHZpeS", () {
|
||||
const password = r"a";
|
||||
const encoded =
|
||||
r"$2a$12$8NJH3LsPrANStV6XtBakCez0cKHXVxmvxIlcz785vxAIZrihHZpeS";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$08$Ro0CUfOqk6cXEKf3dyaM7OhSCvnwM9s4wIX9JeLapehKK5YdLxKcm", () {
|
||||
const password = r"abc";
|
||||
const encoded =
|
||||
r"$2a$08$Ro0CUfOqk6cXEKf3dyaM7OhSCvnwM9s4wIX9JeLapehKK5YdLxKcm";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$10$WvvTPHKwdBJ3uk0Z37EMR.hLA2W6N9AEBhEgrAOljy2Ae5MtaSIUi", () {
|
||||
const password = r"abc";
|
||||
const encoded =
|
||||
r"$2a$10$WvvTPHKwdBJ3uk0Z37EMR.hLA2W6N9AEBhEgrAOljy2Ae5MtaSIUi";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$EXRkfkdmXn2gzds2SSitu.MW9.gAVqa9eLS1//RYtYCmB1eLHg.9q", () {
|
||||
const password = r"abc";
|
||||
const encoded =
|
||||
r"$2a$12$EXRkfkdmXn2gzds2SSitu.MW9.gAVqa9eLS1//RYtYCmB1eLHg.9q";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$08$aTsUwsyowQuzRrDqFflhgekJ8d9/7Z3GV3UcgvzQW3J5zMyrTvlz.", () {
|
||||
const password = r"abcdefghijklmnopqrstuvwxyz";
|
||||
const encoded =
|
||||
r"$2a$08$aTsUwsyowQuzRrDqFflhgekJ8d9/7Z3GV3UcgvzQW3J5zMyrTvlz.";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$10$fVH8e28OQRj9tqiDXs1e1uxpsjN0c7II7YPKXua2NAKYvM6iQk7dq", () {
|
||||
const password = r"abcdefghijklmnopqrstuvwxyz";
|
||||
const encoded =
|
||||
r"$2a$10$fVH8e28OQRj9tqiDXs1e1uxpsjN0c7II7YPKXua2NAKYvM6iQk7dq";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$D4G5f18o7aMMfwasBL7GpuQWuP3pkrZrOAnqP.bmezbMng.QwJ/pG", () {
|
||||
const password = r"abcdefghijklmnopqrstuvwxyz";
|
||||
const encoded =
|
||||
r"$2a$12$D4G5f18o7aMMfwasBL7GpuQWuP3pkrZrOAnqP.bmezbMng.QwJ/pG";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$08$Eq2r4G/76Wv39MzSX262huzPz612MZiYHVUJe/OcOql2jo4.9UxTW", () {
|
||||
const password = r"~!@#$%^&*() ~!@#$%^&*()PNBFRD";
|
||||
const encoded =
|
||||
r"$2a$08$Eq2r4G/76Wv39MzSX262huzPz612MZiYHVUJe/OcOql2jo4.9UxTW";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$10$LgfYWkbzEvQ4JakH7rOvHe0y8pHKF9OaFgwUZ2q7W2FFZmZzJYlfS", () {
|
||||
const password = r"~!@#$%^&*() ~!@#$%^&*()PNBFRD";
|
||||
const encoded =
|
||||
r"$2a$10$LgfYWkbzEvQ4JakH7rOvHe0y8pHKF9OaFgwUZ2q7W2FFZmZzJYlfS";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
test(r"$2a$12$WApznUOJfkEGSmYRfnkrPOr466oFDCaj4b6HY3EXGvfxm43seyhgC", () {
|
||||
const password = r"~!@#$%^&*() ~!@#$%^&*()PNBFRD";
|
||||
const encoded =
|
||||
r"$2a$12$WApznUOJfkEGSmYRfnkrPOr466oFDCaj4b6HY3EXGvfxm43seyhgC";
|
||||
var output = bcrypt(utf8.encode(password), encoded);
|
||||
expect(output, equals(encoded));
|
||||
});
|
||||
}, skip: true);
|
||||
});
|
||||
}
|
||||
109
hashlib/test/compare/compare_blake2b512_test.dart
Normal file
109
hashlib/test/compare/compare_blake2b512_test.dart
Normal file
|
|
@ -0,0 +1,109 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:pointycastle/digests/blake2b.dart' as pc_blake2b;
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('blake2b512 comparison', () {
|
||||
test('with pointycastle', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = blake2b512.convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(digestSize: 64).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with key', () {
|
||||
final key = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = blake2b512.mac.by(key).convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(digestSize: 64, key: key).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with salt', () {
|
||||
final salt = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = Blake2b(64, salt: salt).convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(digestSize: 64, salt: salt).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with personalization', () {
|
||||
final personalization = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = Blake2b(
|
||||
64,
|
||||
aad: personalization,
|
||||
).convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(
|
||||
digestSize: 64,
|
||||
personalization: personalization,
|
||||
).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with salt and personalization', () {
|
||||
final salt = randomBytes(16);
|
||||
final personalization = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = Blake2b(
|
||||
64,
|
||||
salt: salt,
|
||||
aad: personalization,
|
||||
).convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(
|
||||
digestSize: 64,
|
||||
salt: salt,
|
||||
personalization: personalization,
|
||||
).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with key, salt and personalization', () {
|
||||
final key = randomBytes(16);
|
||||
final salt = randomBytes(16);
|
||||
final aad = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = Blake2b(64).mac.by(key, salt: salt, aad: aad).hex(data);
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(
|
||||
digestSize: 64,
|
||||
key: key,
|
||||
salt: salt,
|
||||
personalization: aad,
|
||||
).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
55
hashlib/test/compare/compare_hmac_test.dart
Normal file
55
hashlib/test/compare/compare_hmac_test.dart
Normal file
|
|
@ -0,0 +1,55 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'package:crypto/crypto.dart' as crypto;
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('HMAC comparison', () {
|
||||
test('with crypto for MD5', () {
|
||||
var key = "key";
|
||||
var msg = "The quick brown fox jumps over the lazy dog";
|
||||
var expected = "80070713463e7749b90c2dc24911e275";
|
||||
var actual = toHex(
|
||||
md5.hmac.byString(key).convert(msg.codeUnits).bytes,
|
||||
);
|
||||
var actual2 = toHex(
|
||||
crypto.Hmac(crypto.md5, key.codeUnits).convert(msg.codeUnits).bytes,
|
||||
);
|
||||
expect(actual2, expected, reason: "Key: $key | Message: $msg");
|
||||
expect(actual, expected, reason: "Key: $key | Message: $msg");
|
||||
});
|
||||
|
||||
test('with crypto', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final key = randomBytes(i & 0x7F);
|
||||
expect(
|
||||
toHex(sha1.hmac.by(key).convert(data).bytes),
|
||||
toHex(crypto.Hmac(crypto.sha1, key).convert(data).bytes),
|
||||
reason: 'Key: "${String.fromCharCodes(key)}" [${key.length}]\n'
|
||||
'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
final key = randomBytes(i & 0x7F);
|
||||
expect(
|
||||
toHex(sha384.hmac.by(key).convert(data).bytes),
|
||||
toHex(crypto.Hmac(crypto.sha384, key).convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
}
|
||||
45
hashlib/test/compare/compare_keccak_test.dart
Normal file
45
hashlib/test/compare/compare_keccak_test.dart
Normal file
|
|
@ -0,0 +1,45 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'dart:typed_data';
|
||||
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:pointycastle/digests/keccak.dart' as pc_keccak;
|
||||
import 'package:pointycastle/digests/sha3.dart' as pc_sha3;
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('Keccak comparison', () {
|
||||
test('with keccak256', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
var pc = pc_keccak.KeccakDigest(256);
|
||||
var other = pc.process(Uint8List.fromList(data));
|
||||
expect(
|
||||
keccak256.convert(data).hex(),
|
||||
toHex(other),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('with sha3', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
var pc = pc_sha3.SHA3Digest(256);
|
||||
var other = pc.process(Uint8List.fromList(data));
|
||||
expect(
|
||||
sha3_256.convert(data).hex(),
|
||||
toHex(other),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
36
hashlib/test/compare/compare_md4_test.dart
Normal file
36
hashlib/test/compare/compare_md4_test.dart
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:pointycastle/digests/md4.dart' as pc_md4;
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('MD4 comparison', () {
|
||||
test('with pointy-castle', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(md4.convert(data).bytes),
|
||||
toHex(pc_md4.MD4Digest().process(data)),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('for a file sync', () {
|
||||
var file = File('LICENSE');
|
||||
var hash = pc_md4.MD4Digest().process(file.readAsBytesSync());
|
||||
var hash2 = md4.fileSync(file);
|
||||
expect(hash2.hex(), toHex(hash));
|
||||
}, tags: 'vm-only');
|
||||
});
|
||||
}
|
||||
54
hashlib/test/compare/compare_md5_test.dart
Normal file
54
hashlib/test/compare/compare_md5_test.dart
Normal file
|
|
@ -0,0 +1,54 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:crypto/crypto.dart' as crypto;
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('MD5 comparison', () {
|
||||
test('for a file async', () async {
|
||||
var file = File('LICENSE');
|
||||
var hash = await crypto.md5.bind(file.openRead()).first;
|
||||
var hash2 = await md5.file(file);
|
||||
expect(hash2.hex(), toHex(hash.bytes));
|
||||
}, tags: 'vm-only');
|
||||
|
||||
test('for a file sync', () async {
|
||||
var file = File('LICENSE');
|
||||
var hash = await crypto.md5.bind(file.openRead()).first;
|
||||
var hash2 = md5.fileSync(file);
|
||||
expect(hash2.hex(), toHex(hash.bytes));
|
||||
}, tags: 'vm-only');
|
||||
|
||||
test('with crypto', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(md5.convert(data).bytes),
|
||||
toHex(crypto.md5.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(md5.convert(data).bytes),
|
||||
toHex(crypto.md5.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
}
|
||||
62
hashlib/test/compare/compare_sha224_test.dart
Normal file
62
hashlib/test/compare/compare_sha224_test.dart
Normal file
|
|
@ -0,0 +1,62 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'package:crypto/crypto.dart' as crypto;
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('SHA-224 comparison', () {
|
||||
test('against known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha224.convert(data).bytes),
|
||||
toHex(crypto.sha224.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha224.convert(data).bytes),
|
||||
toHex(crypto.sha224.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
|
||||
group('SHA-256 comparison', () {
|
||||
test('against known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha256.convert(data).bytes),
|
||||
toHex(crypto.sha256.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha256.convert(data).bytes),
|
||||
toHex(crypto.sha256.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
38
hashlib/test/compare/compare_sha384_test.dart
Normal file
38
hashlib/test/compare/compare_sha384_test.dart
Normal file
|
|
@ -0,0 +1,38 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'package:crypto/crypto.dart' as crypto;
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('SHA-384 comparison', () {
|
||||
test('against known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha384.convert(data).bytes),
|
||||
toHex(crypto.sha384.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha384.convert(data).bytes),
|
||||
toHex(crypto.sha384.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
}
|
||||
38
hashlib/test/compare/compare_sha512_224_test.dart
Normal file
38
hashlib/test/compare/compare_sha512_224_test.dart
Normal file
|
|
@ -0,0 +1,38 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'package:crypto/crypto.dart' as crypto;
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('SHA-512/224 comparison', () {
|
||||
test('with known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512t224.convert(data).bytes),
|
||||
toHex(crypto.sha512224.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512t224.convert(data).bytes),
|
||||
toHex(crypto.sha512224.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
}
|
||||
38
hashlib/test/compare/compare_sha512_256_test.dart
Normal file
38
hashlib/test/compare/compare_sha512_256_test.dart
Normal file
|
|
@ -0,0 +1,38 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'package:crypto/crypto.dart' as crypto;
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('SHA-512/256 comparison', () {
|
||||
test('with known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512t256.convert(data).bytes),
|
||||
toHex(crypto.sha512256.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512t256.convert(data).bytes),
|
||||
toHex(crypto.sha512256.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
}
|
||||
38
hashlib/test/compare/compare_sha512_test.dart
Normal file
38
hashlib/test/compare/compare_sha512_test.dart
Normal file
|
|
@ -0,0 +1,38 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'package:crypto/crypto.dart' as crypto;
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('SHA-512 comparison', () {
|
||||
test('with known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512.convert(data).bytes),
|
||||
toHex(crypto.sha512.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512.convert(data).bytes),
|
||||
toHex(crypto.sha512.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
}
|
||||
36
hashlib/test/compare/compare_sm3_test.dart
Normal file
36
hashlib/test/compare/compare_sm3_test.dart
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:pointycastle/digests/sm3.dart' as pc_sm3;
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('SM3 comparison', () {
|
||||
test('with pointy-castle', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
sm3.convert(data).hex(),
|
||||
toHex(pc_sm3.SM3Digest().process(data)),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('for a file sync', () {
|
||||
var file = File('LICENSE');
|
||||
var hash = pc_sm3.SM3Digest().process(file.readAsBytesSync());
|
||||
var hash2 = sm3.fileSync(file);
|
||||
expect(hash2.hex(), toHex(hash));
|
||||
}, tags: 'vm-only');
|
||||
});
|
||||
}
|
||||
|
|
@ -1,432 +0,0 @@
|
|||
// Copyright (c) 2023, Sudipto Chandra
|
||||
// All rights reserved. Check LICENSE file for details.
|
||||
|
||||
// ignore_for_file: library_annotations
|
||||
|
||||
@Tags(['vm-only'])
|
||||
|
||||
import 'dart:io';
|
||||
import 'dart:typed_data';
|
||||
|
||||
import 'package:crypto/crypto.dart' as crypto;
|
||||
import 'package:hashlib/codecs.dart';
|
||||
import 'package:hashlib/hashlib.dart';
|
||||
import 'package:hashlib/random.dart';
|
||||
import 'package:pointycastle/digests/blake2b.dart' as pc_blake2b;
|
||||
import 'package:pointycastle/digests/keccak.dart' as pc_keccak;
|
||||
import 'package:pointycastle/digests/md4.dart' as pc_md4;
|
||||
import 'package:pointycastle/digests/sha3.dart' as pc_sha3;
|
||||
import 'package:pointycastle/digests/sm3.dart' as pc_sm3;
|
||||
import 'package:test/test.dart';
|
||||
|
||||
void main() {
|
||||
group('blake2b512 comparison', () {
|
||||
test('with pointycastle', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = blake2b512.convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(digestSize: 64).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with key', () {
|
||||
final key = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = blake2b512.mac.by(key).convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(digestSize: 64, key: key).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with salt', () {
|
||||
final salt = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = Blake2b(64, salt: salt).convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(digestSize: 64, salt: salt).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with personalization', () {
|
||||
final personalization = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = Blake2b(
|
||||
64,
|
||||
aad: personalization,
|
||||
).convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(
|
||||
digestSize: 64,
|
||||
personalization: personalization,
|
||||
).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with salt and personalization', () {
|
||||
final salt = randomBytes(16);
|
||||
final personalization = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = Blake2b(
|
||||
64,
|
||||
salt: salt,
|
||||
aad: personalization,
|
||||
).convert(data).hex();
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(
|
||||
digestSize: 64,
|
||||
salt: salt,
|
||||
personalization: personalization,
|
||||
).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
|
||||
test('with pointycastle with key, salt and personalization', () {
|
||||
final key = randomBytes(16);
|
||||
final salt = randomBytes(16);
|
||||
final aad = randomBytes(16);
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final out1 = Blake2b(64).mac.by(key, salt: salt, aad: aad).hex(data);
|
||||
final out2 = toHex(
|
||||
pc_blake2b.Blake2bDigest(
|
||||
digestSize: 64,
|
||||
key: key,
|
||||
salt: salt,
|
||||
personalization: aad,
|
||||
).process(data),
|
||||
);
|
||||
expect(out1, equals(out2), reason: 'size: $i');
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
group('HMAC comparison', () {
|
||||
test('with crypto for MD5', () {
|
||||
var key = "key";
|
||||
var msg = "The quick brown fox jumps over the lazy dog";
|
||||
var expected = "80070713463e7749b90c2dc24911e275";
|
||||
var actual = toHex(
|
||||
md5.hmac.byString(key).convert(msg.codeUnits).bytes,
|
||||
);
|
||||
var actual2 = toHex(
|
||||
crypto.Hmac(crypto.md5, key.codeUnits).convert(msg.codeUnits).bytes,
|
||||
);
|
||||
expect(actual2, expected, reason: "Key: $key | Message: $msg");
|
||||
expect(actual, expected, reason: "Key: $key | Message: $msg");
|
||||
});
|
||||
|
||||
test('with crypto', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
final key = randomBytes(i & 0x7F);
|
||||
expect(
|
||||
toHex(sha1.hmac.by(key).convert(data).bytes),
|
||||
toHex(crypto.Hmac(crypto.sha1, key).convert(data).bytes),
|
||||
reason: 'Key: "${String.fromCharCodes(key)}" [${key.length}]\n'
|
||||
'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
final key = randomBytes(i & 0x7F);
|
||||
expect(
|
||||
toHex(sha384.hmac.by(key).convert(data).bytes),
|
||||
toHex(crypto.Hmac(crypto.sha384, key).convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
|
||||
group('Keccak comparison', () {
|
||||
test('with keccak256', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
var pc = pc_keccak.KeccakDigest(256);
|
||||
var other = pc.process(Uint8List.fromList(data));
|
||||
expect(
|
||||
keccak256.convert(data).hex(),
|
||||
toHex(other),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('with sha3', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
var pc = pc_sha3.SHA3Digest(256);
|
||||
var other = pc.process(Uint8List.fromList(data));
|
||||
expect(
|
||||
sha3_256.convert(data).hex(),
|
||||
toHex(other),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
group('MD5 comparison', () {
|
||||
test('for a file async', () async {
|
||||
var file = File('LICENSE');
|
||||
var hash = await crypto.md5.bind(file.openRead()).first;
|
||||
var hash2 = await md5.file(file);
|
||||
expect(hash2.hex(), toHex(hash.bytes));
|
||||
}, tags: 'vm-only');
|
||||
|
||||
test('for a file sync', () async {
|
||||
var file = File('LICENSE');
|
||||
var hash = await crypto.md5.bind(file.openRead()).first;
|
||||
var hash2 = md5.fileSync(file);
|
||||
expect(hash2.hex(), toHex(hash.bytes));
|
||||
}, tags: 'vm-only');
|
||||
|
||||
test('with crypto', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(md5.convert(data).bytes),
|
||||
toHex(crypto.md5.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(md5.convert(data).bytes),
|
||||
toHex(crypto.md5.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
|
||||
group('MD4 comparison', () {
|
||||
test('with pointy-castle', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(md4.convert(data).bytes),
|
||||
toHex(pc_md4.MD4Digest().process(data)),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('for a file sync', () {
|
||||
var file = File('LICENSE');
|
||||
var hash = pc_md4.MD4Digest().process(file.readAsBytesSync());
|
||||
var hash2 = md4.fileSync(file);
|
||||
expect(hash2.hex(), toHex(hash));
|
||||
}, tags: 'vm-only');
|
||||
});
|
||||
|
||||
group('SM3 comparison', () {
|
||||
test('with pointy-castle', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
sm3.convert(data).hex(),
|
||||
toHex(pc_sm3.SM3Digest().process(data)),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('for a file sync', () {
|
||||
var file = File('LICENSE');
|
||||
var hash = pc_sm3.SM3Digest().process(file.readAsBytesSync());
|
||||
var hash2 = sm3.fileSync(file);
|
||||
expect(hash2.hex(), toHex(hash));
|
||||
}, tags: 'vm-only');
|
||||
});
|
||||
|
||||
group('SHA1 comparison', () {
|
||||
test('against known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha1.convert(data).bytes),
|
||||
toHex(crypto.sha1.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha1.convert(data).bytes),
|
||||
toHex(crypto.sha1.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
|
||||
group('SHA-224 comparison', () {
|
||||
test('against known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha224.convert(data).bytes),
|
||||
toHex(crypto.sha224.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha224.convert(data).bytes),
|
||||
toHex(crypto.sha224.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
|
||||
group('SHA-256 comparison', () {
|
||||
test('against known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha256.convert(data).bytes),
|
||||
toHex(crypto.sha256.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha256.convert(data).bytes),
|
||||
toHex(crypto.sha256.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
group('SHA-384 comparison', () {
|
||||
test('against known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha384.convert(data).bytes),
|
||||
toHex(crypto.sha384.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha384.convert(data).bytes),
|
||||
toHex(crypto.sha384.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
|
||||
group('SHA-512/224 comparison', () {
|
||||
test('with known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512t224.convert(data).bytes),
|
||||
toHex(crypto.sha512224.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512t224.convert(data).bytes),
|
||||
toHex(crypto.sha512224.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
|
||||
group('SHA-512/256 comparison', () {
|
||||
test('with known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512t256.convert(data).bytes),
|
||||
toHex(crypto.sha512256.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512t256.convert(data).bytes),
|
||||
toHex(crypto.sha512256.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
|
||||
group('SHA-512 comparison', () {
|
||||
test('with known implementations', () {
|
||||
for (int i = 0; i < 100; ++i) {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512.convert(data).bytes),
|
||||
toHex(crypto.sha512.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
test('run in parallel', () async {
|
||||
await Future.wait(List.generate(10, (i) => i).map((i) async {
|
||||
final data = randomBytes(i);
|
||||
expect(
|
||||
toHex(sha512.convert(data).bytes),
|
||||
toHex(crypto.sha512.convert(data).bytes),
|
||||
reason: 'Message: "${String.fromCharCodes(data)}" [${data.length}]',
|
||||
);
|
||||
}));
|
||||
});
|
||||
});
|
||||
}
|
||||
|
|
@ -146,7 +146,7 @@ void main() {
|
|||
'f4fd0a0cb3bf9c9dc04e3f177936249ac87d619ed41b6b05d2d6dfe95d32153338b'
|
||||
'c03c4b68fd46e13c9c0e7f7946ee6856cf068f1702e2fbd98';
|
||||
expect(hash.hex(), matcher);
|
||||
});
|
||||
}, skip: true);
|
||||
|
||||
test("with security", () {
|
||||
var hash = scrypt(
|
||||
|
|
|
|||
|
|
@ -28,8 +28,8 @@ final tests = {
|
|||
"e0afca6342847c80827fdc511f0004e53239d3c2f82f67ddd8185bef",
|
||||
List.filled(511, "a").join():
|
||||
"6eb1c24577241c0871ec3ab020786f59cecb2edb6acef2d483051d6a",
|
||||
List.filled(1000000, "a").join():
|
||||
"20794655980c91d8bbb4c1ea97618a4bf03f42581948b2ee4ee7ad67",
|
||||
// List.filled(1000000, "a").join():
|
||||
// "20794655980c91d8bbb4c1ea97618a4bf03f42581948b2ee4ee7ad67",
|
||||
};
|
||||
|
||||
void main() {
|
||||
|
|
|
|||
|
|
@ -28,8 +28,8 @@ final tests = {
|
|||
"02425c0f5b0dabf3d2b9115f3f7723a02ad8bcfb1534a0d231614fd42b8188f6",
|
||||
List.filled(511, "a").join():
|
||||
"058fc5084b6355a06099bfef3de8e360344046dc5a47026de47470b9aabb5bfd",
|
||||
List.filled(1000000, "a").join():
|
||||
"cdc76e5c9914fb9281a1c7e284d73e67f1809a48a497200e046d39ccc7112cd0",
|
||||
// List.filled(1000000, "a").join():
|
||||
// "cdc76e5c9914fb9281a1c7e284d73e67f1809a48a497200e046d39ccc7112cd0",
|
||||
};
|
||||
|
||||
void main() {
|
||||
|
|
|
|||
|
|
@ -34,9 +34,9 @@ final tests = {
|
|||
List.filled(511, "a").join():
|
||||
"db100a1eed3842c61d73064b62543cd4531dafa8bfecf6f27d"
|
||||
"cfdebbaf60ea14563ea1b486e4f6b9a14fcb0dac05c5f2",
|
||||
List.filled(1000000, "a").join():
|
||||
"9d0e1809716474cb086e834e310a4a1ced149e9c00f2485279"
|
||||
"72cec5704c2a5b07b8b3dc38ecc4ebae97ddd87f3d8985",
|
||||
// List.filled(1000000, "a").join():
|
||||
// "9d0e1809716474cb086e834e310a4a1ced149e9c00f2485279"
|
||||
// "72cec5704c2a5b07b8b3dc38ecc4ebae97ddd87f3d8985",
|
||||
};
|
||||
|
||||
void main() {
|
||||
|
|
|
|||
|
|
@ -16,6 +16,8 @@ final tests = {
|
|||
"944cd2847fb54558d4775db0485a50003111c8e5daa63fe722c6aa37",
|
||||
"The quick brown fox jumps over the lazy cog":
|
||||
"2b9d6565a7e40f780ba8ab7c8dcf41e3ed3b77997f4c55aa987eede5",
|
||||
List.filled(112, "a").join():
|
||||
"79b41fef2a0439d2705724a67615f7bcbcd2bf5664a7774b80818eb6",
|
||||
List.filled(512, "a").join():
|
||||
"057bab73fa47ac3e597a34d02c1e285e2d5d8a2e90c9079f549b4af6",
|
||||
List.filled(128, "a").join():
|
||||
|
|
@ -24,10 +26,8 @@ final tests = {
|
|||
"502ec9656e1e0b96f9a2699c04cec265edc690b729c45037c6b37a00",
|
||||
List.filled(511, "a").join():
|
||||
"bd0452a57045c857de05b1c1d94fb49624b00ceaf0ec4c0d4d656a89",
|
||||
List.filled(1000000, "a").join():
|
||||
"37ab331d76f0d36de422bd0edeb22a28accd487b7a8453ae965dd287",
|
||||
List.filled(112, "a").join():
|
||||
"79b41fef2a0439d2705724a67615f7bcbcd2bf5664a7774b80818eb6",
|
||||
// List.filled(1000000, "a").join():
|
||||
// "37ab331d76f0d36de422bd0edeb22a28accd487b7a8453ae965dd287",
|
||||
};
|
||||
|
||||
void main() {
|
||||
|
|
|
|||
|
|
@ -16,6 +16,8 @@ final tests = {
|
|||
"dd9d67b371519c339ed8dbd25af90e976a1eeefd4ad3d889005e532fc5bef04d",
|
||||
"The quick brown fox jumps over the lazy cog":
|
||||
"cc8d255a7f2f38fd50388fd1f65ea7910835c5c1e73da46fba01ea50d5dd76fb",
|
||||
List.filled(112, "a").join():
|
||||
"9216b5303edb66504570bee90e48ea5beaa5e9fe9f760bbd3e0460559fc005f6",
|
||||
List.filled(512, "a").join():
|
||||
"092b65b92e80ccf4c66683684fb02da4567160534abede190e9b2edef6156839",
|
||||
List.filled(128, "a").join():
|
||||
|
|
@ -24,10 +26,8 @@ final tests = {
|
|||
"a59cf33e5ad3e70d4962adbb833d021eafa48f85dd9788f84fca4cf762c5f1c7",
|
||||
List.filled(511, "a").join():
|
||||
"7e627ccc0719192627fcf9f3987d3da9a61f261a09580371e1ea4622b8ccfcc8",
|
||||
List.filled(1000000, "a").join():
|
||||
"9a59a052930187a97038cae692f30708aa6491923ef5194394dc68d56c74fb21",
|
||||
List.filled(112, "a").join():
|
||||
"9216b5303edb66504570bee90e48ea5beaa5e9fe9f760bbd3e0460559fc005f6",
|
||||
// List.filled(1000000, "a").join():
|
||||
// "9a59a052930187a97038cae692f30708aa6491923ef5194394dc68d56c74fb21",
|
||||
};
|
||||
|
||||
void main() {
|
||||
|
|
|
|||
|
|
@ -22,6 +22,9 @@ final tests = {
|
|||
"The quick brown fox jumps over the lazy cog":
|
||||
"3eeee1d0e11733ef152a6c29503b3ae20c4f1f3cda4cb26f1bc1a41f91c7fe4a"
|
||||
"b3bd86494049e201c4bd5155f31ecb7a3c8606843c4cc8dfcab7da11c8ae5045",
|
||||
List.filled(112, "a").join():
|
||||
"c01d080efd492776a1c43bd23dd99d0a2e626d481e16782e75d54c2503b5dc32"
|
||||
"bd05f0f1ba33e568b88fd2d970929b719ecbb152f58f130a407c8830604b70ca",
|
||||
List.filled(512, "a").join():
|
||||
"0210d27bcbe05c2156627c5f136ade1338ab98e06a4591a00b0bcaa61662a593"
|
||||
"1d0b3bd41a67b5c140627923f5f6307669eb508d8db38b2a8cd41aebd783394b",
|
||||
|
|
@ -34,12 +37,9 @@ final tests = {
|
|||
List.filled(511, "a").join():
|
||||
"fe32a1f497ce532d041889133436c7086ea40410af5728a6b958aa4a169de44e"
|
||||
"3884311461188be5f65e79b9a53d010d8347ac20118e4e05df787a17ba71204b",
|
||||
List.filled(1000000, "a").join():
|
||||
"e718483d0ce769644e2e42c7bc15b4638e1f98b13b2044285632a803afa973eb"
|
||||
"de0ff244877ea60a4cb0432ce577c31beb009c5c2c49aa2e4eadb217ad8cc09b",
|
||||
List.filled(112, "a").join():
|
||||
"c01d080efd492776a1c43bd23dd99d0a2e626d481e16782e75d54c2503b5dc32"
|
||||
"bd05f0f1ba33e568b88fd2d970929b719ecbb152f58f130a407c8830604b70ca",
|
||||
// List.filled(1000000, "a").join():
|
||||
// "e718483d0ce769644e2e42c7bc15b4638e1f98b13b2044285632a803afa973eb"
|
||||
// "de0ff244877ea60a4cb0432ce577c31beb009c5c2c49aa2e4eadb217ad8cc09b",
|
||||
};
|
||||
|
||||
void main() {
|
||||
|
|
|
|||
|
|
@ -34,8 +34,8 @@ final tests = {
|
|||
"97baef04b5211a439b17eb067ad904e52b12058d7510669ad29b63b9d4609479",
|
||||
List.filled(511, "a").join():
|
||||
"5f4141700026fec7880a6d1d5f34dcc9253dea2df32928f71bc93860d675b38c",
|
||||
List.filled(1000000, "a").join():
|
||||
"c8aaf89429554029e231941a2acc0ad61ff2a5acd8fadd25847a3a732b3b02c3",
|
||||
// List.filled(1000000, "a").join():
|
||||
// "c8aaf89429554029e231941a2acc0ad61ff2a5acd8fadd25847a3a732b3b02c3",
|
||||
};
|
||||
|
||||
void main() {
|
||||
|
|
|
|||
|
|
@ -2,14 +2,14 @@ group 'com.flutterplaza.no_screenshot'
|
|||
version '1.0-SNAPSHOT'
|
||||
|
||||
buildscript {
|
||||
ext.kotlin_version = '1.6.10'
|
||||
ext.kotlin_version = '2.1.0'
|
||||
repositories {
|
||||
google()
|
||||
mavenCentral()
|
||||
}
|
||||
|
||||
dependencies {
|
||||
classpath 'com.android.tools.build:gradle:7.1.3'
|
||||
classpath 'com.android.tools.build:gradle:8.6.0'
|
||||
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
|
||||
}
|
||||
}
|
||||
|
|
@ -26,7 +26,7 @@ apply plugin: 'kotlin-android'
|
|||
|
||||
android {
|
||||
namespace "com.flutterplaza.no_screenshot"
|
||||
compileSdkVersion 31
|
||||
compileSdk 36
|
||||
|
||||
compileOptions {
|
||||
sourceCompatibility JavaVersion.VERSION_1_8
|
||||
|
|
|
|||
|
|
@ -1,8 +1,8 @@
|
|||
name: no_screenshot
|
||||
description: Flutter plugin to enable, disable, toggle or stream screenshot activities in your application.
|
||||
version: 0.3.2-beta.3
|
||||
version: 0.3.2
|
||||
homepage: https://flutterplaza.com
|
||||
repository: https://github.com/FlutterPlaza/no_screenshot/releases/tag/v0.3.2-beta.3
|
||||
repository: https://github.com/FlutterPlaza/no_screenshot/releases/tag/v0.3.2
|
||||
|
||||
environment:
|
||||
sdk: '>=3.0.0 <4.0.0'
|
||||
|
|
@ -16,7 +16,7 @@ dependencies:
|
|||
dev_dependencies:
|
||||
flutter_test:
|
||||
sdk: flutter
|
||||
flutter_lints: ^4.0.0
|
||||
flutter_lints: ">=4.0.0 <6.0.0"
|
||||
flutter_driver:
|
||||
sdk: flutter
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue