@li0ard/gost 0.0.1 → 0.1.3

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.
Files changed (55) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +47 -45
  3. package/gost3410/const.d.ts +47 -0
  4. package/gost3410/const.js +126 -0
  5. package/gost3410/conversion.d.ts +19 -0
  6. package/gost3410/conversion.js +35 -0
  7. package/gost3410/index.d.ts +29 -0
  8. package/gost3410/index.js +84 -0
  9. package/gost3410/vko.d.ts +38 -0
  10. package/gost3410/vko.js +47 -0
  11. package/gost341194/index.d.ts +23 -0
  12. package/gost341194/index.js +193 -0
  13. package/hmac.d.ts +15 -0
  14. package/hmac.js +22 -0
  15. package/index.d.ts +9 -0
  16. package/index.js +9 -0
  17. package/kdf.d.ts +7 -0
  18. package/kdf.js +59 -0
  19. package/kuznyechik/const.d.ts +4 -0
  20. package/kuznyechik/const.js +78 -0
  21. package/kuznyechik/index.d.ts +12 -0
  22. package/kuznyechik/index.js +207 -0
  23. package/magma/const.d.ts +62 -0
  24. package/magma/const.js +244 -0
  25. package/magma/index.d.ts +24 -0
  26. package/magma/index.js +86 -0
  27. package/modes/_keytransform.d.ts +5 -0
  28. package/modes/_keytransform.js +35 -0
  29. package/modes/cbc.d.ts +8 -0
  30. package/modes/cbc.js +42 -0
  31. package/modes/cfb.d.ts +8 -0
  32. package/modes/cfb.js +37 -0
  33. package/modes/ctr.d.ts +15 -0
  34. package/modes/ctr.js +62 -0
  35. package/modes/ecb.d.ts +7 -0
  36. package/modes/ecb.js +21 -0
  37. package/modes/index.d.ts +8 -0
  38. package/modes/index.js +8 -0
  39. package/modes/mac.d.ts +21 -0
  40. package/modes/mac.js +119 -0
  41. package/modes/mgm.d.ts +8 -0
  42. package/modes/mgm.js +90 -0
  43. package/modes/ofb.d.ts +8 -0
  44. package/modes/ofb.js +25 -0
  45. package/modes/wrap.d.ts +14 -0
  46. package/modes/wrap.js +57 -0
  47. package/package.json +48 -7
  48. package/streebog/const.d.ts +4 -0
  49. package/streebog/const.js +102 -0
  50. package/streebog/index.d.ts +66 -0
  51. package/streebog/index.js +295 -0
  52. package/types.d.ts +50 -0
  53. package/types.js +1 -0
  54. package/utils.d.ts +7 -0
  55. package/utils.js +47 -0
package/modes/ecb.js ADDED
@@ -0,0 +1,21 @@
1
+ /**
2
+ * **EN:** Electronic Codebook (ECB) mode
3
+ *
4
+ * **RU:** Режим простой замены
5
+ */
6
+ export const ecb = (cipher) => {
7
+ const encrypter = cipher.encrypt.bind(cipher);
8
+ const decrypter = cipher.decrypt.bind(cipher);
9
+ const core = (crypter, data) => {
10
+ if (data.length == 0 || data.length % cipher.blockSize !== 0)
11
+ throw new Error("Data not aligned");
12
+ const output = new Uint8Array(data.length);
13
+ for (let i = 0; i < data.length; i += cipher.blockSize)
14
+ output.set(crypter(data.subarray(i, i + cipher.blockSize)), i);
15
+ return output;
16
+ };
17
+ return {
18
+ encrypt: (plaintext) => core(encrypter, plaintext),
19
+ decrypt: (ciphertext) => core(decrypter, ciphertext),
20
+ };
21
+ };
@@ -0,0 +1,8 @@
1
+ export { cbc } from "./cbc.js";
2
+ export { cfb } from "./cfb.js";
3
+ export { ctr, cnt } from "./ctr.js";
4
+ export { ecb } from "./ecb.js";
5
+ export { mac, mac_legacy, omac_acpkm } from "./mac.js";
6
+ export { mgm } from "./mgm.js";
7
+ export { ofb } from "./ofb.js";
8
+ export { kexp15, kwp } from "./wrap.js";
package/modes/index.js ADDED
@@ -0,0 +1,8 @@
1
+ export { cbc } from "./cbc.js";
2
+ export { cfb } from "./cfb.js";
3
+ export { ctr, cnt } from "./ctr.js";
4
+ export { ecb } from "./ecb.js";
5
+ export { mac, mac_legacy, omac_acpkm } from "./mac.js";
6
+ export { mgm } from "./mgm.js";
7
+ export { ofb } from "./ofb.js";
8
+ export { kexp15, kwp } from "./wrap.js";
package/modes/mac.d.ts ADDED
@@ -0,0 +1,21 @@
1
+ import { type TArg } from "@noble/hashes/utils.js";
2
+ import type { Cipher, MACMode } from "../types.js";
3
+ import { Magma } from "../magma/index.js";
4
+ /**
5
+ * **EN:** Message Authentication Code (MAC) mode
6
+ *
7
+ * **RU:** Режим выработки имитовставки
8
+ */
9
+ export declare const mac: (cipher: Cipher) => MACMode;
10
+ /**
11
+ * **EN:** Message Authentication Code (MAC) mode (GOST 28147-89)
12
+ *
13
+ * **RU:** Режим выработки имитовставки (ГОСТ 28147-89)
14
+ */
15
+ export declare const mac_legacy: (cipher: Magma, iv?: TArg<Uint8Array>) => MACMode;
16
+ /**
17
+ * **EN:** Message Authentication Code with Advance Cryptographic Prolongation of Key Material (OMAC-ACPKM) mode
18
+ *
19
+ * **RU:** Режим выработки имитовставки с преобразованием ключа (ACPKM)
20
+ */
21
+ export declare const omac_acpkm: (cipher: Cipher) => MACMode;
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
+ };
@@ -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.0.1",
4
- "description": "OIDC trusted publishing setup package for @li0ard/gost",
5
- "keywords": [
6
- "oidc",
7
- "trusted-publishing",
8
- "setup"
9
- ]
3
+ "version": "0.1.3",
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,4 @@
1
+ import type { TArg } from "@noble/hashes/utils.js";
2
+ export declare const TAU: Uint8Array;
3
+ export declare const A: Uint32Array<ArrayBuffer>;
4
+ export declare const C: TArg<Uint8Array>[];
@@ -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 {};