@li0ard/gost 0.0.1 → 0.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/gost3410/const.d.ts +47 -0
- package/gost3410/const.js +126 -0
- package/gost3410/conversion.d.ts +19 -0
- package/gost3410/conversion.js +35 -0
- package/gost3410/index.d.ts +29 -0
- package/gost3410/index.js +84 -0
- package/gost3410/vko.d.ts +38 -0
- package/gost3410/vko.js +47 -0
- package/gost341194/index.d.ts +23 -0
- package/gost341194/index.js +193 -0
- package/hmac.d.ts +15 -0
- package/hmac.js +22 -0
- package/index.d.ts +9 -0
- package/index.js +9 -0
- package/kdf.d.ts +7 -0
- package/kdf.js +59 -0
- package/kuznyechik/const.d.ts +4 -0
- package/kuznyechik/const.js +78 -0
- package/kuznyechik/index.d.ts +12 -0
- package/kuznyechik/index.js +207 -0
- package/magma/const.d.ts +62 -0
- package/magma/const.js +244 -0
- package/magma/index.d.ts +24 -0
- package/magma/index.js +86 -0
- package/modes/_keytransform.d.ts +5 -0
- package/modes/_keytransform.js +35 -0
- package/modes/cbc.d.ts +8 -0
- package/modes/cbc.js +42 -0
- package/modes/cfb.d.ts +8 -0
- package/modes/cfb.js +37 -0
- package/modes/ctr.d.ts +15 -0
- package/modes/ctr.js +62 -0
- package/modes/ecb.d.ts +7 -0
- package/modes/ecb.js +21 -0
- package/modes/index.d.ts +8 -0
- package/modes/index.js +8 -0
- package/modes/mac.d.ts +21 -0
- package/modes/mac.js +119 -0
- package/modes/mgm.d.ts +8 -0
- package/modes/mgm.js +90 -0
- package/modes/ofb.d.ts +8 -0
- package/modes/ofb.js +25 -0
- package/modes/wrap.d.ts +14 -0
- package/modes/wrap.js +57 -0
- package/package.json +48 -7
- package/streebog/const.d.ts +4 -0
- package/streebog/const.js +102 -0
- package/streebog/index.d.ts +66 -0
- package/streebog/index.js +295 -0
- package/types.d.ts +50 -0
- package/types.js +1 -0
- package/utils.d.ts +7 -0
- package/utils.js +47 -0
- package/README.md +0 -45
package/modes/mac.js
ADDED
|
@@ -0,0 +1,119 @@
|
|
|
1
|
+
import {} from "@noble/hashes/utils.js";
|
|
2
|
+
import { pad1, pad3, xorBytes } from "../utils.js";
|
|
3
|
+
import { bytesToNumberBE, numberToVarBytesBE } from "@noble/curves/utils.js";
|
|
4
|
+
import { magmaKeySequences, Magma } from "../magma/index.js";
|
|
5
|
+
import { acpkm_master } from "./_keytransform.js";
|
|
6
|
+
const Rb64 = 0b11011;
|
|
7
|
+
const Rb128 = 0b10000111;
|
|
8
|
+
/**
|
|
9
|
+
* **EN:** Message Authentication Code (MAC) mode
|
|
10
|
+
*
|
|
11
|
+
* **RU:** Режим выработки имитовставки
|
|
12
|
+
*/
|
|
13
|
+
export const mac = (cipher) => {
|
|
14
|
+
const encrypter = cipher.encrypt.bind(cipher);
|
|
15
|
+
const macShift = (data, xorLsb = 0) => numberToVarBytesBE((bytesToNumberBE(data) * BigInt(2)) ^ BigInt(xorLsb)).slice(-cipher.blockSize);
|
|
16
|
+
const macKs = () => {
|
|
17
|
+
const Rb = cipher.blockSize === 16 ? Rb128 : Rb64;
|
|
18
|
+
const l = encrypter(new Uint8Array(cipher.blockSize));
|
|
19
|
+
let k1;
|
|
20
|
+
if ((l[0] & 0x80) !== 0)
|
|
21
|
+
k1 = macShift(l, Rb);
|
|
22
|
+
else
|
|
23
|
+
k1 = macShift(l);
|
|
24
|
+
let k2;
|
|
25
|
+
if ((k1[0] & 0x80) !== 0)
|
|
26
|
+
k2 = macShift(k1, Rb);
|
|
27
|
+
else
|
|
28
|
+
k2 = macShift(k1);
|
|
29
|
+
return [k1, k2];
|
|
30
|
+
};
|
|
31
|
+
return {
|
|
32
|
+
compute: (msg) => {
|
|
33
|
+
const [k1, k2] = macKs();
|
|
34
|
+
let tailOffset;
|
|
35
|
+
if (msg.length % cipher.blockSize === 0)
|
|
36
|
+
tailOffset = msg.length - cipher.blockSize;
|
|
37
|
+
else
|
|
38
|
+
tailOffset = msg.length - (msg.length % cipher.blockSize);
|
|
39
|
+
let prev = new Uint8Array(cipher.blockSize);
|
|
40
|
+
for (let i = 0; i < tailOffset; i += cipher.blockSize)
|
|
41
|
+
prev = encrypter(xorBytes(msg.subarray(i, i + cipher.blockSize), prev));
|
|
42
|
+
const tail = msg.subarray(tailOffset);
|
|
43
|
+
const xorWithPrev = xorBytes(pad3(tail, cipher.blockSize), prev);
|
|
44
|
+
return encrypter(xorBytes(xorWithPrev, (tail.length === cipher.blockSize ? k1 : k2)));
|
|
45
|
+
}
|
|
46
|
+
};
|
|
47
|
+
};
|
|
48
|
+
/**
|
|
49
|
+
* **EN:** Message Authentication Code (MAC) mode (GOST 28147-89)
|
|
50
|
+
*
|
|
51
|
+
* **RU:** Режим выработки имитовставки (ГОСТ 28147-89)
|
|
52
|
+
*/
|
|
53
|
+
export const mac_legacy = (cipher, iv = new Uint8Array(cipher.blockSize)) => {
|
|
54
|
+
const split = (data) => [
|
|
55
|
+
(data[0] | data[1] << 8 | data[2] << 16 | data[3] << 24) >>> 0,
|
|
56
|
+
(data[4] | data[5] << 8 | data[6] << 16 | data[7] << 24) >>> 0
|
|
57
|
+
];
|
|
58
|
+
const join = (ns) => new Uint8Array([
|
|
59
|
+
(ns[1] >> 0) & 0xFF, (ns[1] >> 8) & 0xFF, (ns[1] >> 16) & 0xFF, (ns[1] >> 24) & 0xFF,
|
|
60
|
+
(ns[0] >> 0) & 0xFF, (ns[0] >> 8) & 0xFF, (ns[0] >> 16) & 0xFF, (ns[0] >> 24) & 0xFF
|
|
61
|
+
]);
|
|
62
|
+
return {
|
|
63
|
+
compute: (msg) => {
|
|
64
|
+
const paddedData = pad1(msg, cipher.blockSize);
|
|
65
|
+
let prev = split(iv).reverse();
|
|
66
|
+
for (let i = 0; i < paddedData.length; i += cipher.blockSize)
|
|
67
|
+
prev = split(Magma.reverseChunks(cipher.proceedBlock(Magma.reverseChunks(xorBytes(paddedData.subarray(i, i + cipher.blockSize), join(prev))), magmaKeySequences.MAC)));
|
|
68
|
+
return join(prev);
|
|
69
|
+
}
|
|
70
|
+
};
|
|
71
|
+
};
|
|
72
|
+
/**
|
|
73
|
+
* **EN:** Message Authentication Code with Advance Cryptographic Prolongation of Key Material (OMAC-ACPKM) mode
|
|
74
|
+
*
|
|
75
|
+
* **RU:** Режим выработки имитовставки с преобразованием ключа (ACPKM)
|
|
76
|
+
*/
|
|
77
|
+
export const omac_acpkm = (cipher) => {
|
|
78
|
+
const sectionSize = cipher.blockSize * 2;
|
|
79
|
+
return {
|
|
80
|
+
compute: (msg) => {
|
|
81
|
+
let encrypter = cipher.encrypt.bind(cipher);
|
|
82
|
+
let tail_offset = 0;
|
|
83
|
+
if (msg.length % cipher.blockSize == 0)
|
|
84
|
+
tail_offset = msg.length - cipher.blockSize;
|
|
85
|
+
else
|
|
86
|
+
tail_offset = msg.length - (msg.length % cipher.blockSize);
|
|
87
|
+
let prev = new Uint8Array(cipher.blockSize).fill(0);
|
|
88
|
+
let sections = msg.length;
|
|
89
|
+
if (msg.length % sectionSize != 0)
|
|
90
|
+
sections += 1;
|
|
91
|
+
let keymats = acpkm_master(cipher, (32 + cipher.blockSize) * sections);
|
|
92
|
+
let k1 = new Uint8Array(sectionSize);
|
|
93
|
+
for (let i = 0; i < tail_offset; i += cipher.blockSize) {
|
|
94
|
+
if (i % sectionSize == 0) {
|
|
95
|
+
let keymat = keymats.slice(0, 32 + cipher.blockSize);
|
|
96
|
+
keymats = keymats.slice(32 + cipher.blockSize);
|
|
97
|
+
let key = keymat.slice(0, 32);
|
|
98
|
+
k1 = keymat.slice(32);
|
|
99
|
+
// @ts-ignore
|
|
100
|
+
let cipher2 = new cipher.constructor(key);
|
|
101
|
+
encrypter = cipher2.encrypt.bind(cipher2);
|
|
102
|
+
}
|
|
103
|
+
prev = encrypter(xorBytes(msg.slice(i, i + cipher.blockSize), prev));
|
|
104
|
+
}
|
|
105
|
+
const tail = msg.slice(tail_offset);
|
|
106
|
+
if (tail.length == cipher.blockSize) {
|
|
107
|
+
let key = keymats.slice(0, 32);
|
|
108
|
+
k1 = keymats.slice(32);
|
|
109
|
+
// @ts-ignore
|
|
110
|
+
let cipher2 = new cipher.constructor(key);
|
|
111
|
+
encrypter = cipher2.encrypt.bind(cipher2);
|
|
112
|
+
}
|
|
113
|
+
let k2 = numberToVarBytesBE(bytesToNumberBE(k1) << 1n);
|
|
114
|
+
if ((k1.slice()[0] & 0x80) != 0)
|
|
115
|
+
k2 = xorBytes(k2, numberToVarBytesBE(cipher.blockSize == 16 ? Rb128 : Rb64));
|
|
116
|
+
return encrypter(xorBytes(xorBytes(pad3(tail, cipher.blockSize), prev), (tail.length == cipher.blockSize) ? k1 : k2));
|
|
117
|
+
}
|
|
118
|
+
};
|
|
119
|
+
};
|
package/modes/mgm.d.ts
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { type TArg } from "@noble/hashes/utils.js";
|
|
2
|
+
import type { AEADMode, Cipher } from "../types.js";
|
|
3
|
+
/**
|
|
4
|
+
* **EN:** Multilinear Galois (MGM) mode (AEAD)
|
|
5
|
+
*
|
|
6
|
+
* **RU:** Режим шифрования с имитозащитой и ассоциированными данными (AEAD)
|
|
7
|
+
*/
|
|
8
|
+
export declare const mgm: (cipher: Cipher, nonce: TArg<Uint8Array>, tagSize?: number) => AEADMode;
|
package/modes/mgm.js
ADDED
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
import { concatBytes } from "@noble/hashes/utils.js";
|
|
2
|
+
import { bytesToNumberBE, equalBytes, numberToBytesBE } from "@noble/curves/utils.js";
|
|
3
|
+
import { pad1, xorBytes } from "../utils.js";
|
|
4
|
+
/**
|
|
5
|
+
* **EN:** Multilinear Galois (MGM) mode (AEAD)
|
|
6
|
+
*
|
|
7
|
+
* **RU:** Режим шифрования с имитозащитой и ассоциированными данными (AEAD)
|
|
8
|
+
*/
|
|
9
|
+
export const mgm = (cipher, nonce, tagSize = cipher.blockSize) => {
|
|
10
|
+
const halfbs = cipher.blockSize / 2;
|
|
11
|
+
const _incr = (data) => numberToBytesBE(bytesToNumberBE(data) + 1n, halfbs);
|
|
12
|
+
const incr_r = (data) => concatBytes(data.subarray(0, halfbs), _incr(data.subarray(halfbs)));
|
|
13
|
+
const incr_l = (data) => concatBytes(_incr(data.subarray(0, halfbs)), data.subarray(halfbs));
|
|
14
|
+
if (tagSize < 4 || tagSize > cipher.blockSize)
|
|
15
|
+
throw new Error("Invalid tagSize");
|
|
16
|
+
const encrypter = cipher.encrypt.bind(cipher);
|
|
17
|
+
const maxSize = (1n << BigInt(cipher.blockSize * 4)) - 1n;
|
|
18
|
+
const r = (cipher.blockSize == 8 ? 0x1B : 0x87);
|
|
19
|
+
const validateSizes = (plaintext, additional) => {
|
|
20
|
+
if (plaintext.length == 0 && additional.length == 0)
|
|
21
|
+
throw new Error("At least one of plaintext or additional_data required");
|
|
22
|
+
if ((plaintext.length + additional.length) > maxSize)
|
|
23
|
+
throw new Error("plaintext+additional_data are too big");
|
|
24
|
+
};
|
|
25
|
+
const mul = (a, b) => {
|
|
26
|
+
let x = bytesToNumberBE(a);
|
|
27
|
+
let y = bytesToNumberBE(b);
|
|
28
|
+
let z = 0n;
|
|
29
|
+
const max_bit = 1n << (BigInt(cipher.blockSize) * 8n - 1n);
|
|
30
|
+
while (y > 0n) {
|
|
31
|
+
if ((y & 1n) == 1n)
|
|
32
|
+
z ^= x;
|
|
33
|
+
if ((x & max_bit) > 0n)
|
|
34
|
+
x = ((x ^ max_bit) << 1n) ^ BigInt(r);
|
|
35
|
+
else
|
|
36
|
+
x <<= 1n;
|
|
37
|
+
y >>= 1n;
|
|
38
|
+
}
|
|
39
|
+
return numberToBytesBE(z, cipher.blockSize);
|
|
40
|
+
};
|
|
41
|
+
const crypt = (icn, data) => {
|
|
42
|
+
icn[0] &= 0x7F;
|
|
43
|
+
let enc = encrypter(icn);
|
|
44
|
+
const res = [];
|
|
45
|
+
while (data.length > 0) {
|
|
46
|
+
res.push(xorBytes(encrypter(enc), data));
|
|
47
|
+
enc = incr_r(enc);
|
|
48
|
+
data = data.slice(cipher.blockSize);
|
|
49
|
+
}
|
|
50
|
+
return concatBytes(...res);
|
|
51
|
+
};
|
|
52
|
+
const auth = (icn, text, ad) => {
|
|
53
|
+
icn[0] |= 0x80;
|
|
54
|
+
let enc = encrypter(icn);
|
|
55
|
+
let _sum = new Uint8Array(cipher.blockSize);
|
|
56
|
+
const ad_len = ad.length;
|
|
57
|
+
const text_len = text.length;
|
|
58
|
+
while (ad.length > 0) {
|
|
59
|
+
_sum = xorBytes(_sum, mul(encrypter(enc), pad1(ad.slice(0, cipher.blockSize), cipher.blockSize)));
|
|
60
|
+
enc = incr_l(enc);
|
|
61
|
+
ad = ad.slice(cipher.blockSize);
|
|
62
|
+
}
|
|
63
|
+
while (text.length > 0) {
|
|
64
|
+
_sum = xorBytes(_sum, mul(encrypter(enc), pad1(text.slice(0, cipher.blockSize), cipher.blockSize)));
|
|
65
|
+
enc = incr_l(enc);
|
|
66
|
+
text = text.slice(cipher.blockSize);
|
|
67
|
+
}
|
|
68
|
+
_sum = xorBytes(_sum, mul(encrypter(enc), concatBytes(numberToBytesBE(ad_len * 8, halfbs), numberToBytesBE(text_len * 8, halfbs))));
|
|
69
|
+
return encrypter(_sum).slice(0, tagSize);
|
|
70
|
+
};
|
|
71
|
+
return {
|
|
72
|
+
seal: (plaintext, aad = new Uint8Array()) => {
|
|
73
|
+
validateSizes(plaintext, aad);
|
|
74
|
+
const icn = nonce.slice();
|
|
75
|
+
const ciphertext = crypt(icn, plaintext);
|
|
76
|
+
const tag = auth(icn, ciphertext, aad);
|
|
77
|
+
return concatBytes(ciphertext, tag);
|
|
78
|
+
},
|
|
79
|
+
open: (ciphertext, aad = new Uint8Array()) => {
|
|
80
|
+
validateSizes(ciphertext, aad);
|
|
81
|
+
const icn = nonce.slice();
|
|
82
|
+
const ct = ciphertext.slice(0, (ciphertext.length - tagSize));
|
|
83
|
+
const tag_expected = ciphertext.subarray((ciphertext.length - tagSize));
|
|
84
|
+
const tag = auth(icn, ct, aad);
|
|
85
|
+
if (!equalBytes(tag_expected, tag))
|
|
86
|
+
throw new Error("Invalid authentication tag");
|
|
87
|
+
return crypt(icn, ct);
|
|
88
|
+
}
|
|
89
|
+
};
|
|
90
|
+
};
|
package/modes/ofb.d.ts
ADDED
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
import { type TArg } from "@noble/hashes/utils.js";
|
|
2
|
+
import type { Cipher, StreamMode } from "../types.js";
|
|
3
|
+
/**
|
|
4
|
+
* **EN:** Output Feedback (OFB) mode
|
|
5
|
+
*
|
|
6
|
+
* **RU:** Режим гаммирования с обратной связью по выходу
|
|
7
|
+
*/
|
|
8
|
+
export declare const ofb: (cipher: Cipher, iv: TArg<Uint8Array>) => StreamMode;
|
package/modes/ofb.js
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { concatBytes } from "@noble/hashes/utils.js";
|
|
2
|
+
import { xorBytes, getPadLength } from "../utils.js";
|
|
3
|
+
/**
|
|
4
|
+
* **EN:** Output Feedback (OFB) mode
|
|
5
|
+
*
|
|
6
|
+
* **RU:** Режим гаммирования с обратной связью по выходу
|
|
7
|
+
*/
|
|
8
|
+
export const ofb = (cipher, iv) => {
|
|
9
|
+
if (iv.length == 0 || iv.length % cipher.blockSize !== 0)
|
|
10
|
+
throw new Error("Invalid IV size");
|
|
11
|
+
const encrypter = cipher.encrypt.bind(cipher);
|
|
12
|
+
return {
|
|
13
|
+
crypt: (msg) => {
|
|
14
|
+
let r = [];
|
|
15
|
+
for (let i = 0; i < iv.length; i += cipher.blockSize)
|
|
16
|
+
r.push(iv.slice(i, i + cipher.blockSize));
|
|
17
|
+
const result = [];
|
|
18
|
+
for (let i = 0; i < (msg.length + getPadLength(msg.length, cipher.blockSize)); i += cipher.blockSize) {
|
|
19
|
+
r = r.slice(1).concat(encrypter(r[0]));
|
|
20
|
+
result.push(xorBytes(r[r.length - 1], msg.subarray(i, i + cipher.blockSize)));
|
|
21
|
+
}
|
|
22
|
+
return concatBytes(...result);
|
|
23
|
+
}
|
|
24
|
+
};
|
|
25
|
+
};
|
package/modes/wrap.d.ts
ADDED
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { type TArg } from "@noble/hashes/utils.js";
|
|
2
|
+
import type { Cipher, WrapMode, WrapModeMagma } from "../types.js";
|
|
3
|
+
/**
|
|
4
|
+
* **EN:** KExp15/KImp15 key wrapping
|
|
5
|
+
*
|
|
6
|
+
* **RU:** Режим обёртки ключей шифрования KExp15/KImp15
|
|
7
|
+
*/
|
|
8
|
+
export declare const kexp15: (cipherEnc: Cipher, cipherMac: Cipher, iv: TArg<Uint8Array>) => WrapMode;
|
|
9
|
+
/**
|
|
10
|
+
* **EN:** GOST 28147-89 key wrapping
|
|
11
|
+
*
|
|
12
|
+
* **RU:** Режим обёртки ключей шифрования согласно ГОСТ 28147-89
|
|
13
|
+
*/
|
|
14
|
+
export declare const kwp: (kek: TArg<Uint8Array>, isCryptoPro?: boolean, sbox?: TArg<Uint8Array>[]) => WrapModeMagma;
|
package/modes/wrap.js
ADDED
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
import { concatBytes } from "@noble/hashes/utils.js";
|
|
2
|
+
import { mac as _mac, mac_legacy } from "./mac.js";
|
|
3
|
+
import { ctr } from "./ctr.js";
|
|
4
|
+
import { equalBytes } from "@noble/curves/utils.js";
|
|
5
|
+
import { ID_GOST_28147_89_CRYPTO_PRO_A_PARAM_SET } from "../magma/const";
|
|
6
|
+
import { Magma } from "../magma/index.js";
|
|
7
|
+
import { ecb } from "./ecb.js";
|
|
8
|
+
import { cp_kek_diversify } from "./_keytransform.js";
|
|
9
|
+
/**
|
|
10
|
+
* **EN:** KExp15/KImp15 key wrapping
|
|
11
|
+
*
|
|
12
|
+
* **RU:** Режим обёртки ключей шифрования KExp15/KImp15
|
|
13
|
+
*/
|
|
14
|
+
export const kexp15 = (cipherEnc, cipherMac, iv) => {
|
|
15
|
+
if (iv.length != (cipherEnc.blockSize / 2) || iv.length != (cipherMac.blockSize / 2))
|
|
16
|
+
throw new Error("Invalid IV size");
|
|
17
|
+
return {
|
|
18
|
+
wrap: (msg) => {
|
|
19
|
+
const mac = _mac(cipherMac).compute(concatBytes(iv, msg));
|
|
20
|
+
return ctr(cipherEnc, iv).crypt(concatBytes(msg, mac));
|
|
21
|
+
},
|
|
22
|
+
unwrap: (msg) => {
|
|
23
|
+
const key_and_key_mac = ctr(cipherEnc, iv).crypt(msg);
|
|
24
|
+
const key = key_and_key_mac.slice(0, -cipherEnc.blockSize), key_mac = key_and_key_mac.slice(-cipherEnc.blockSize);
|
|
25
|
+
const mac = _mac(cipherMac).compute(concatBytes(iv, key));
|
|
26
|
+
if (!equalBytes(key_mac, mac))
|
|
27
|
+
throw new Error("Invalid key MAC");
|
|
28
|
+
return key;
|
|
29
|
+
}
|
|
30
|
+
};
|
|
31
|
+
};
|
|
32
|
+
/**
|
|
33
|
+
* **EN:** GOST 28147-89 key wrapping
|
|
34
|
+
*
|
|
35
|
+
* **RU:** Режим обёртки ключей шифрования согласно ГОСТ 28147-89
|
|
36
|
+
*/
|
|
37
|
+
export const kwp = (kek, isCryptoPro = false, sbox = ID_GOST_28147_89_CRYPTO_PRO_A_PARAM_SET) => {
|
|
38
|
+
return {
|
|
39
|
+
wrap: (ukm, cek) => {
|
|
40
|
+
const cipher = new Magma(isCryptoPro ? cp_kek_diversify(kek, ukm, sbox) : kek, sbox, true);
|
|
41
|
+
const cek_mac = mac_legacy(cipher, ukm).compute(cek).subarray(0, 4);
|
|
42
|
+
const cek_enc = ecb(cipher).encrypt(cek);
|
|
43
|
+
return concatBytes(ukm, cek_enc, cek_mac);
|
|
44
|
+
},
|
|
45
|
+
unwrap: (wrapped) => {
|
|
46
|
+
if (wrapped.length !== 44 && wrapped.length !== 76)
|
|
47
|
+
throw new Error("Invalid data length");
|
|
48
|
+
const [ukm, cek_enc, cek_mac] = [wrapped.slice(0, 8), wrapped.slice(8, wrapped.length - 4), wrapped.slice(-4)];
|
|
49
|
+
const cipher = new Magma(isCryptoPro ? cp_kek_diversify(kek, ukm, sbox) : kek, sbox, true);
|
|
50
|
+
const cek = ecb(cipher).decrypt(cek_enc);
|
|
51
|
+
const mac_computed = mac_legacy(cipher, ukm).compute(cek).subarray(0, 4);
|
|
52
|
+
if (!equalBytes(cek_mac, mac_computed))
|
|
53
|
+
throw new Error("Invalid MAC");
|
|
54
|
+
return cek;
|
|
55
|
+
}
|
|
56
|
+
};
|
|
57
|
+
};
|
package/package.json
CHANGED
|
@@ -1,10 +1,51 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@li0ard/gost",
|
|
3
|
-
"version": "0.
|
|
4
|
-
"
|
|
5
|
-
"
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
"
|
|
9
|
-
|
|
3
|
+
"version": "0.1.2",
|
|
4
|
+
"main": "index.js",
|
|
5
|
+
"types": "index.d.ts",
|
|
6
|
+
"type": "module",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": "./index.js",
|
|
9
|
+
"./gost3410.js": "./gost3410/index.js",
|
|
10
|
+
"./gost341194.js": "./gost341194/index.js",
|
|
11
|
+
"./kuznyechik.js": "./kuznyechik/index.js",
|
|
12
|
+
"./magma.js": "./kuznyechik/magma.js",
|
|
13
|
+
"./modes.js": "./modes/index.js",
|
|
14
|
+
"./streebog.js": "./streebog/index.js",
|
|
15
|
+
"./hmac.js": "./hmac.js",
|
|
16
|
+
"./kdf.js": "./kdf.js",
|
|
17
|
+
"./types.js": "./types.js"
|
|
18
|
+
},
|
|
19
|
+
"author": "li0ard",
|
|
20
|
+
"repository": {
|
|
21
|
+
"type": "git",
|
|
22
|
+
"url": "git+https://github.com/li0ard/gost.git"
|
|
23
|
+
},
|
|
24
|
+
"bugs": {
|
|
25
|
+
"url": "https://github.com/li0ard/gost/issues"
|
|
26
|
+
},
|
|
27
|
+
"homepage": "https://github.com/li0ard/gost#readme",
|
|
28
|
+
"funding": "https://li0ard.rest/donate",
|
|
29
|
+
"description": "GOST cryptography algorithms in pure TypeScript",
|
|
30
|
+
"license": "MIT",
|
|
31
|
+
"scripts": {
|
|
32
|
+
"build": "rm -rf dist/ && tsc --project tsconfig.build.json",
|
|
33
|
+
"docs": "typedoc --options .config/typedoc/config.cjs"
|
|
34
|
+
},
|
|
35
|
+
"devDependencies": {
|
|
36
|
+
"@types/bun": "latest",
|
|
37
|
+
"typedoc": "^0.28.19"
|
|
38
|
+
},
|
|
39
|
+
"peerDependencies": {
|
|
40
|
+
"typescript": "^5"
|
|
41
|
+
},
|
|
42
|
+
"dependencies": {
|
|
43
|
+
"@noble/curves": "^2.2.0",
|
|
44
|
+
"@noble/hashes": "^2.2.0"
|
|
45
|
+
},
|
|
46
|
+
"files": ["**/*.js", "**/*.d.ts"],
|
|
47
|
+
"publishConfig": {
|
|
48
|
+
"access": "public"
|
|
49
|
+
},
|
|
50
|
+
"keywords": ["gost", "crypto", "magma", "kuznyechik", "streebog", "gost341194", "tc26"]
|
|
10
51
|
}
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
export const TAU = new Uint8Array([
|
|
2
|
+
0x00, 0x08, 0x10, 0x18, 0x20, 0x28, 0x30, 0x38,
|
|
3
|
+
0x01, 0x09, 0x11, 0x19, 0x21, 0x29, 0x31, 0x39,
|
|
4
|
+
0x02, 0x0a, 0x12, 0x1a, 0x22, 0x2a, 0x32, 0x3a,
|
|
5
|
+
0x03, 0x0b, 0x13, 0x1b, 0x23, 0x2b, 0x33, 0x3b,
|
|
6
|
+
0x04, 0x0c, 0x14, 0x1c, 0x24, 0x2c, 0x34, 0x3c,
|
|
7
|
+
0x05, 0x0d, 0x15, 0x1d, 0x25, 0x2d, 0x35, 0x3d,
|
|
8
|
+
0x06, 0x0e, 0x16, 0x1e, 0x26, 0x2e, 0x36, 0x3e,
|
|
9
|
+
0x07, 0x0f, 0x17, 0x1f, 0x27, 0x2f, 0x37, 0x3f,
|
|
10
|
+
]);
|
|
11
|
+
export const A = new Uint32Array([
|
|
12
|
+
0x8e20faa7, 0x2ba0b470, 0x47107ddd, 0x9b505a38, 0xad08b0e0, 0xc3282d1c, 0xd8045870, 0xef14980e,
|
|
13
|
+
0x6c022c38, 0xf90a4c07, 0x3601161c, 0xf205268d, 0x1b8e0b0e, 0x798c13c8, 0x83478b07, 0xb2468764,
|
|
14
|
+
0xa011d380, 0x818e8f40, 0x5086e740, 0xce47c920, 0x2843fd20, 0x67adea10, 0x14aff010, 0xbdd87508,
|
|
15
|
+
0x0ad97808, 0xd06cb404, 0x05e23c04, 0x68365a02, 0x8c711e02, 0x341b2d01, 0x46b60f01, 0x1a83988e,
|
|
16
|
+
0x90dab52a, 0x387ae76f, 0x486dd415, 0x1c3dfdb9, 0x24b86a84, 0x0e90f0d2, 0x125c3542, 0x07487869,
|
|
17
|
+
0x092e9421, 0x8d243cba, 0x8a174a9e, 0xc8121e5d, 0x4585254f, 0x64090fa0, 0xaccc9ca9, 0x328a8950,
|
|
18
|
+
0x9d4df05d, 0x5f661451, 0xc0a878a0, 0xa1330aa6, 0x60543c50, 0xde970553, 0x302a1e28, 0x6fc58ca7,
|
|
19
|
+
0x18150f14, 0xb9ec46dd, 0x0c84890a, 0xd27623e0, 0x0642ca05, 0x693b9f70, 0x0321658c, 0xba93c138,
|
|
20
|
+
0x86275df0, 0x9ce8aaa8, 0x439da078, 0x4e745554, 0xafc0503c, 0x273aa42a, 0xd960281e, 0x9d1d5215,
|
|
21
|
+
0xe230140f, 0xc0802984, 0x71180a89, 0x60409a42, 0xb60c05ca, 0x30204d21, 0x5b068c65, 0x1810a89e,
|
|
22
|
+
0x456c3488, 0x7a3805b9, 0xac361a44, 0x3d1c8cd2, 0x561b0d22, 0x900e4669, 0x2b838811, 0x480723ba,
|
|
23
|
+
0x9bcf4486, 0x248d9f5d, 0xc3e92243, 0x12c8c1a0, 0xeffa11af, 0x0964ee50, 0xf97d86d9, 0x8a327728,
|
|
24
|
+
0xe4fa2054, 0xa80b329c, 0x727d102a, 0x548b194e, 0x39b00815, 0x2acb8227, 0x92580484, 0x15eb419d,
|
|
25
|
+
0x492c0242, 0x84fbaec0, 0xaa160121, 0x42f35760, 0x550b8e9e, 0x21f7a530, 0xa48b474f, 0x9ef5dc18,
|
|
26
|
+
0x70a6a56e, 0x2440598e, 0x3853dc37, 0x1220a247, 0x1ca76e95, 0x091051ad, 0x0edd37c4, 0x8a08a6d8,
|
|
27
|
+
0x07e09562, 0x4504536c, 0x8d70c431, 0xac02a736, 0xc8386296, 0x5601dd1b, 0x641c314b, 0x2b8ee083,
|
|
28
|
+
]);
|
|
29
|
+
export const C = [
|
|
30
|
+
new Uint8Array([
|
|
31
|
+
0xb1, 0x08, 0x5b, 0xda, 0x1e, 0xca, 0xda, 0xe9, 0xeb, 0xcb, 0x2f, 0x81, 0xc0, 0x65, 0x7c, 0x1f,
|
|
32
|
+
0x2f, 0x6a, 0x76, 0x43, 0x2e, 0x45, 0xd0, 0x16, 0x71, 0x4e, 0xb8, 0x8d, 0x75, 0x85, 0xc4, 0xfc,
|
|
33
|
+
0x4b, 0x7c, 0xe0, 0x91, 0x92, 0x67, 0x69, 0x01, 0xa2, 0x42, 0x2a, 0x08, 0xa4, 0x60, 0xd3, 0x15,
|
|
34
|
+
0x05, 0x76, 0x74, 0x36, 0xcc, 0x74, 0x4d, 0x23, 0xdd, 0x80, 0x65, 0x59, 0xf2, 0xa6, 0x45, 0x07,
|
|
35
|
+
]),
|
|
36
|
+
new Uint8Array([
|
|
37
|
+
0x6f, 0xa3, 0xb5, 0x8a, 0xa9, 0x9d, 0x2f, 0x1a, 0x4f, 0xe3, 0x9d, 0x46, 0x0f, 0x70, 0xb5, 0xd7,
|
|
38
|
+
0xf3, 0xfe, 0xea, 0x72, 0x0a, 0x23, 0x2b, 0x98, 0x61, 0xd5, 0x5e, 0x0f, 0x16, 0xb5, 0x01, 0x31,
|
|
39
|
+
0x9a, 0xb5, 0x17, 0x6b, 0x12, 0xd6, 0x99, 0x58, 0x5c, 0xb5, 0x61, 0xc2, 0xdb, 0x0a, 0xa7, 0xca,
|
|
40
|
+
0x55, 0xdd, 0xa2, 0x1b, 0xd7, 0xcb, 0xcd, 0x56, 0xe6, 0x79, 0x04, 0x70, 0x21, 0xb1, 0x9b, 0xb7,
|
|
41
|
+
]),
|
|
42
|
+
new Uint8Array([
|
|
43
|
+
0xf5, 0x74, 0xdc, 0xac, 0x2b, 0xce, 0x2f, 0xc7, 0x0a, 0x39, 0xfc, 0x28, 0x6a, 0x3d, 0x84, 0x35,
|
|
44
|
+
0x06, 0xf1, 0x5e, 0x5f, 0x52, 0x9c, 0x1f, 0x8b, 0xf2, 0xea, 0x75, 0x14, 0xb1, 0x29, 0x7b, 0x7b,
|
|
45
|
+
0xd3, 0xe2, 0x0f, 0xe4, 0x90, 0x35, 0x9e, 0xb1, 0xc1, 0xc9, 0x3a, 0x37, 0x60, 0x62, 0xdb, 0x09,
|
|
46
|
+
0xc2, 0xb6, 0xf4, 0x43, 0x86, 0x7a, 0xdb, 0x31, 0x99, 0x1e, 0x96, 0xf5, 0x0a, 0xba, 0x0a, 0xb2,
|
|
47
|
+
]),
|
|
48
|
+
new Uint8Array([
|
|
49
|
+
0xef, 0x1f, 0xdf, 0xb3, 0xe8, 0x15, 0x66, 0xd2, 0xf9, 0x48, 0xe1, 0xa0, 0x5d, 0x71, 0xe4, 0xdd,
|
|
50
|
+
0x48, 0x8e, 0x85, 0x7e, 0x33, 0x5c, 0x3c, 0x7d, 0x9d, 0x72, 0x1c, 0xad, 0x68, 0x5e, 0x35, 0x3f,
|
|
51
|
+
0xa9, 0xd7, 0x2c, 0x82, 0xed, 0x03, 0xd6, 0x75, 0xd8, 0xb7, 0x13, 0x33, 0x93, 0x52, 0x03, 0xbe,
|
|
52
|
+
0x34, 0x53, 0xea, 0xa1, 0x93, 0xe8, 0x37, 0xf1, 0x22, 0x0c, 0xbe, 0xbc, 0x84, 0xe3, 0xd1, 0x2e,
|
|
53
|
+
]),
|
|
54
|
+
new Uint8Array([
|
|
55
|
+
0x4b, 0xea, 0x6b, 0xac, 0xad, 0x47, 0x47, 0x99, 0x9a, 0x3f, 0x41, 0x0c, 0x6c, 0xa9, 0x23, 0x63,
|
|
56
|
+
0x7f, 0x15, 0x1c, 0x1f, 0x16, 0x86, 0x10, 0x4a, 0x35, 0x9e, 0x35, 0xd7, 0x80, 0x0f, 0xff, 0xbd,
|
|
57
|
+
0xbf, 0xcd, 0x17, 0x47, 0x25, 0x3a, 0xf5, 0xa3, 0xdf, 0xff, 0x00, 0xb7, 0x23, 0x27, 0x1a, 0x16,
|
|
58
|
+
0x7a, 0x56, 0xa2, 0x7e, 0xa9, 0xea, 0x63, 0xf5, 0x60, 0x17, 0x58, 0xfd, 0x7c, 0x6c, 0xfe, 0x57,
|
|
59
|
+
]),
|
|
60
|
+
new Uint8Array([
|
|
61
|
+
0xae, 0x4f, 0xae, 0xae, 0x1d, 0x3a, 0xd3, 0xd9, 0x6f, 0xa4, 0xc3, 0x3b, 0x7a, 0x30, 0x39, 0xc0,
|
|
62
|
+
0x2d, 0x66, 0xc4, 0xf9, 0x51, 0x42, 0xa4, 0x6c, 0x18, 0x7f, 0x9a, 0xb4, 0x9a, 0xf0, 0x8e, 0xc6,
|
|
63
|
+
0xcf, 0xfa, 0xa6, 0xb7, 0x1c, 0x9a, 0xb7, 0xb4, 0x0a, 0xf2, 0x1f, 0x66, 0xc2, 0xbe, 0xc6, 0xb6,
|
|
64
|
+
0xbf, 0x71, 0xc5, 0x72, 0x36, 0x90, 0x4f, 0x35, 0xfa, 0x68, 0x40, 0x7a, 0x46, 0x64, 0x7d, 0x6e,
|
|
65
|
+
]),
|
|
66
|
+
new Uint8Array([
|
|
67
|
+
0xf4, 0xc7, 0x0e, 0x16, 0xee, 0xaa, 0xc5, 0xec, 0x51, 0xac, 0x86, 0xfe, 0xbf, 0x24, 0x09, 0x54,
|
|
68
|
+
0x39, 0x9e, 0xc6, 0xc7, 0xe6, 0xbf, 0x87, 0xc9, 0xd3, 0x47, 0x3e, 0x33, 0x19, 0x7a, 0x93, 0xc9,
|
|
69
|
+
0x09, 0x92, 0xab, 0xc5, 0x2d, 0x82, 0x2c, 0x37, 0x06, 0x47, 0x69, 0x83, 0x28, 0x4a, 0x05, 0x04,
|
|
70
|
+
0x35, 0x17, 0x45, 0x4c, 0xa2, 0x3c, 0x4a, 0xf3, 0x88, 0x86, 0x56, 0x4d, 0x3a, 0x14, 0xd4, 0x93,
|
|
71
|
+
]),
|
|
72
|
+
new Uint8Array([
|
|
73
|
+
0x9b, 0x1f, 0x5b, 0x42, 0x4d, 0x93, 0xc9, 0xa7, 0x03, 0xe7, 0xaa, 0x02, 0x0c, 0x6e, 0x41, 0x41,
|
|
74
|
+
0x4e, 0xb7, 0xf8, 0x71, 0x9c, 0x36, 0xde, 0x1e, 0x89, 0xb4, 0x44, 0x3b, 0x4d, 0xdb, 0xc4, 0x9a,
|
|
75
|
+
0xf4, 0x89, 0x2b, 0xcb, 0x92, 0x9b, 0x06, 0x90, 0x69, 0xd1, 0x8d, 0x2b, 0xd1, 0xa5, 0xc4, 0x2f,
|
|
76
|
+
0x36, 0xac, 0xc2, 0x35, 0x59, 0x51, 0xa8, 0xd9, 0xa4, 0x7f, 0x0d, 0xd4, 0xbf, 0x02, 0xe7, 0x1e,
|
|
77
|
+
]),
|
|
78
|
+
new Uint8Array([
|
|
79
|
+
0x37, 0x8f, 0x5a, 0x54, 0x16, 0x31, 0x22, 0x9b, 0x94, 0x4c, 0x9a, 0xd8, 0xec, 0x16, 0x5f, 0xde,
|
|
80
|
+
0x3a, 0x7d, 0x3a, 0x1b, 0x25, 0x89, 0x42, 0x24, 0x3c, 0xd9, 0x55, 0xb7, 0xe0, 0x0d, 0x09, 0x84,
|
|
81
|
+
0x80, 0x0a, 0x44, 0x0b, 0xdb, 0xb2, 0xce, 0xb1, 0x7b, 0x2b, 0x8a, 0x9a, 0xa6, 0x07, 0x9c, 0x54,
|
|
82
|
+
0x0e, 0x38, 0xdc, 0x92, 0xcb, 0x1f, 0x2a, 0x60, 0x72, 0x61, 0x44, 0x51, 0x83, 0x23, 0x5a, 0xdb,
|
|
83
|
+
]),
|
|
84
|
+
new Uint8Array([
|
|
85
|
+
0xab, 0xbe, 0xde, 0xa6, 0x80, 0x05, 0x6f, 0x52, 0x38, 0x2a, 0xe5, 0x48, 0xb2, 0xe4, 0xf3, 0xf3,
|
|
86
|
+
0x89, 0x41, 0xe7, 0x1c, 0xff, 0x8a, 0x78, 0xdb, 0x1f, 0xff, 0xe1, 0x8a, 0x1b, 0x33, 0x61, 0x03,
|
|
87
|
+
0x9f, 0xe7, 0x67, 0x02, 0xaf, 0x69, 0x33, 0x4b, 0x7a, 0x1e, 0x6c, 0x30, 0x3b, 0x76, 0x52, 0xf4,
|
|
88
|
+
0x36, 0x98, 0xfa, 0xd1, 0x15, 0x3b, 0xb6, 0xc3, 0x74, 0xb4, 0xc7, 0xfb, 0x98, 0x45, 0x9c, 0xed,
|
|
89
|
+
]),
|
|
90
|
+
new Uint8Array([
|
|
91
|
+
0x7b, 0xcd, 0x9e, 0xd0, 0xef, 0xc8, 0x89, 0xfb, 0x30, 0x02, 0xc6, 0xcd, 0x63, 0x5a, 0xfe, 0x94,
|
|
92
|
+
0xd8, 0xfa, 0x6b, 0xbb, 0xeb, 0xab, 0x07, 0x61, 0x20, 0x01, 0x80, 0x21, 0x14, 0x84, 0x66, 0x79,
|
|
93
|
+
0x8a, 0x1d, 0x71, 0xef, 0xea, 0x48, 0xb9, 0xca, 0xef, 0xba, 0xcd, 0x1d, 0x7d, 0x47, 0x6e, 0x98,
|
|
94
|
+
0xde, 0xa2, 0x59, 0x4a, 0xc0, 0x6f, 0xd8, 0x5d, 0x6b, 0xca, 0xa4, 0xcd, 0x81, 0xf3, 0x2d, 0x1b,
|
|
95
|
+
]),
|
|
96
|
+
new Uint8Array([
|
|
97
|
+
0x37, 0x8e, 0xe7, 0x67, 0xf1, 0x16, 0x31, 0xba, 0xd2, 0x13, 0x80, 0xb0, 0x04, 0x49, 0xb1, 0x7a,
|
|
98
|
+
0xcd, 0xa4, 0x3c, 0x32, 0xbc, 0xdf, 0x1d, 0x77, 0xf8, 0x20, 0x12, 0xd4, 0x30, 0x21, 0x9f, 0x9b,
|
|
99
|
+
0x5d, 0x80, 0xef, 0x9d, 0x18, 0x91, 0xcc, 0x86, 0xe7, 0x1d, 0xa4, 0xaa, 0x88, 0xe1, 0x28, 0x52,
|
|
100
|
+
0xfa, 0xf4, 0x17, 0xd5, 0xd9, 0xb2, 0x1b, 0x99, 0x48, 0xbc, 0x92, 0x4a, 0xf1, 0x1b, 0xd7, 0x20,
|
|
101
|
+
])
|
|
102
|
+
];
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
import { type Hash, type TArg, type TRet } from "@noble/hashes/utils.js";
|
|
2
|
+
/** Streebog (GOST R 34.11-2012) hash function */
|
|
3
|
+
declare abstract class Streebog<T extends Streebog<T>> implements Hash<Streebog<T>> {
|
|
4
|
+
private is512;
|
|
5
|
+
readonly blockLen = 64;
|
|
6
|
+
readonly outputLen: number;
|
|
7
|
+
readonly canXOF = false;
|
|
8
|
+
protected buffer: Uint8Array;
|
|
9
|
+
abstract _cloneInto(to?: T): T;
|
|
10
|
+
abstract clone(): T;
|
|
11
|
+
/** Streebog (GOST R 34.11-2012) hash function */
|
|
12
|
+
constructor(is512: boolean);
|
|
13
|
+
destroy(): void;
|
|
14
|
+
update(data: TArg<Uint8Array>): this;
|
|
15
|
+
digest(): TRet<Uint8Array>;
|
|
16
|
+
digestInto(buf: TArg<Uint8Array>): void;
|
|
17
|
+
}
|
|
18
|
+
/** Streebog-256 (GOST R 34.11-2012) hash function */
|
|
19
|
+
export declare class Streebog256 extends Streebog<Streebog256> {
|
|
20
|
+
/** Streebog-256 (GOST R 34.11-2012) hash function */
|
|
21
|
+
constructor();
|
|
22
|
+
/** Create hash instance */
|
|
23
|
+
static create(): Streebog256;
|
|
24
|
+
clone(): Streebog256;
|
|
25
|
+
_cloneInto(to?: Streebog256): Streebog256;
|
|
26
|
+
}
|
|
27
|
+
/** Streebog-512 (GOST R 34.11-2012) hash function */
|
|
28
|
+
export declare class Streebog512 extends Streebog<Streebog512> {
|
|
29
|
+
/** Streebog-512 (GOST R 34.11-2012) hash function */
|
|
30
|
+
constructor();
|
|
31
|
+
/** Create hash instance */
|
|
32
|
+
static create(): Streebog512;
|
|
33
|
+
clone(): Streebog512;
|
|
34
|
+
_cloneInto(to?: Streebog512): Streebog512;
|
|
35
|
+
}
|
|
36
|
+
/** Streebog-256 (GOST R 34.11-2012) hash function */
|
|
37
|
+
export declare const streebog256: {
|
|
38
|
+
outputLen: number;
|
|
39
|
+
blockLen: number;
|
|
40
|
+
canXOF: boolean;
|
|
41
|
+
} & import("@noble/hashes/utils.js").HashInfo & {
|
|
42
|
+
(msg: TArg<Uint8Array>): TRet<Uint8Array>;
|
|
43
|
+
create(): Streebog256;
|
|
44
|
+
} & ((msg: TArg<TArg<Uint8Array<ArrayBufferLike>>>) => Uint8Array<ArrayBufferLike> & Uint8Array<ArrayBuffer>) & {
|
|
45
|
+
outputLen: number;
|
|
46
|
+
blockLen: number;
|
|
47
|
+
canXOF: boolean;
|
|
48
|
+
oid?: TRet<Uint8Array> | undefined;
|
|
49
|
+
create: () => Streebog256;
|
|
50
|
+
};
|
|
51
|
+
/** Streebog-512 (GOST R 34.11-2012) hash function */
|
|
52
|
+
export declare const streebog512: {
|
|
53
|
+
outputLen: number;
|
|
54
|
+
blockLen: number;
|
|
55
|
+
canXOF: boolean;
|
|
56
|
+
} & import("@noble/hashes/utils.js").HashInfo & {
|
|
57
|
+
(msg: TArg<Uint8Array>): TRet<Uint8Array>;
|
|
58
|
+
create(): Streebog512;
|
|
59
|
+
} & ((msg: TArg<TArg<Uint8Array<ArrayBufferLike>>>) => Uint8Array<ArrayBufferLike> & Uint8Array<ArrayBuffer>) & {
|
|
60
|
+
outputLen: number;
|
|
61
|
+
blockLen: number;
|
|
62
|
+
canXOF: boolean;
|
|
63
|
+
oid?: TRet<Uint8Array> | undefined;
|
|
64
|
+
create: () => Streebog512;
|
|
65
|
+
};
|
|
66
|
+
export {};
|