cyberchef 9.52.1 → 9.53.0

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/CHANGELOG.md CHANGED
@@ -13,6 +13,9 @@ All major and minor version changes will be documented in this file. Details of
13
13
 
14
14
  ## Details
15
15
 
16
+ ### [9.53.0] - 2022-11-25
17
+ - Added 'AES Key Wrap' and 'AES Key Unwrap' operations [@mikecat] | [#1456]
18
+
16
19
  ### [9.52.0] - 2022-11-25
17
20
  - Added 'ChaCha' operation [@joostrijneveld] | [#1466]
18
21
 
@@ -333,6 +336,7 @@ All major and minor version changes will be documented in this file. Details of
333
336
 
334
337
 
335
338
 
339
+ [9.53.0]: https://github.com/gchq/CyberChef/releases/tag/v9.53.0
336
340
  [9.52.0]: https://github.com/gchq/CyberChef/releases/tag/v9.52.0
337
341
  [9.51.0]: https://github.com/gchq/CyberChef/releases/tag/v9.51.0
338
342
  [9.50.0]: https://github.com/gchq/CyberChef/releases/tag/v9.50.0
@@ -584,4 +588,5 @@ All major and minor version changes will be documented in this file. Details of
584
588
  [#1472]: https://github.com/gchq/CyberChef/pull/1472
585
589
  [#1457]: https://github.com/gchq/CyberChef/pull/1457
586
590
  [#1466]: https://github.com/gchq/CyberChef/pull/1466
591
+ [#1456]: https://github.com/gchq/CyberChef/pull/1456
587
592
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "cyberchef",
3
- "version": "9.52.1",
3
+ "version": "9.53.0",
4
4
  "description": "The Cyber Swiss Army Knife for encryption, encoding, compression and data analysis.",
5
5
  "author": "n1474335 <n1474335@gmail.com>",
6
6
  "homepage": "https://gchq.github.io/CyberChef",
@@ -125,6 +125,8 @@
125
125
  "JWT Decode",
126
126
  "Citrix CTX1 Encode",
127
127
  "Citrix CTX1 Decode",
128
+ "AES Key Wrap",
129
+ "AES Key Unwrap",
128
130
  "Pseudo-Random Number Generator",
129
131
  "Enigma",
130
132
  "Bombe",
@@ -348,6 +348,104 @@
348
348
  }
349
349
  ]
350
350
  },
351
+ "AES Key Unwrap": {
352
+ "module": "Ciphers",
353
+ "description": "Decryptor for a key wrapping algorithm defined in RFC3394, which is used to protect keys in untrusted storage or communications, using AES.<br><br>This algorithm uses an AES key (KEK: key-encryption key) and a 64-bit IV to decrypt 64-bit blocks.",
354
+ "infoURL": "https://wikipedia.org/wiki/Key_wrap",
355
+ "inputType": "string",
356
+ "outputType": "string",
357
+ "flowControl": false,
358
+ "manualBake": false,
359
+ "args": [
360
+ {
361
+ "name": "Key (KEK)",
362
+ "type": "toggleString",
363
+ "value": "",
364
+ "toggleValues": [
365
+ "Hex",
366
+ "UTF8",
367
+ "Latin1",
368
+ "Base64"
369
+ ]
370
+ },
371
+ {
372
+ "name": "IV",
373
+ "type": "toggleString",
374
+ "value": "a6a6a6a6a6a6a6a6",
375
+ "toggleValues": [
376
+ "Hex",
377
+ "UTF8",
378
+ "Latin1",
379
+ "Base64"
380
+ ]
381
+ },
382
+ {
383
+ "name": "Input",
384
+ "type": "option",
385
+ "value": [
386
+ "Hex",
387
+ "Raw"
388
+ ]
389
+ },
390
+ {
391
+ "name": "Output",
392
+ "type": "option",
393
+ "value": [
394
+ "Hex",
395
+ "Raw"
396
+ ]
397
+ }
398
+ ]
399
+ },
400
+ "AES Key Wrap": {
401
+ "module": "Ciphers",
402
+ "description": "A key wrapping algorithm defined in RFC3394, which is used to protect keys in untrusted storage or communications, using AES.<br><br>This algorithm uses an AES key (KEK: key-encryption key) and a 64-bit IV to encrypt 64-bit blocks.",
403
+ "infoURL": "https://wikipedia.org/wiki/Key_wrap",
404
+ "inputType": "string",
405
+ "outputType": "string",
406
+ "flowControl": false,
407
+ "manualBake": false,
408
+ "args": [
409
+ {
410
+ "name": "Key (KEK)",
411
+ "type": "toggleString",
412
+ "value": "",
413
+ "toggleValues": [
414
+ "Hex",
415
+ "UTF8",
416
+ "Latin1",
417
+ "Base64"
418
+ ]
419
+ },
420
+ {
421
+ "name": "IV",
422
+ "type": "toggleString",
423
+ "value": "a6a6a6a6a6a6a6a6",
424
+ "toggleValues": [
425
+ "Hex",
426
+ "UTF8",
427
+ "Latin1",
428
+ "Base64"
429
+ ]
430
+ },
431
+ {
432
+ "name": "Input",
433
+ "type": "option",
434
+ "value": [
435
+ "Hex",
436
+ "Raw"
437
+ ]
438
+ },
439
+ {
440
+ "name": "Output",
441
+ "type": "option",
442
+ "value": [
443
+ "Hex",
444
+ "Raw"
445
+ ]
446
+ }
447
+ ]
448
+ },
351
449
  "AND": {
352
450
  "module": "Default",
353
451
  "description": "AND the input with the given key.<br>e.g. <code>fe023da5</code>",
@@ -9,6 +9,8 @@ import A1Z26CipherDecode from "../../operations/A1Z26CipherDecode.mjs";
9
9
  import A1Z26CipherEncode from "../../operations/A1Z26CipherEncode.mjs";
10
10
  import AESDecrypt from "../../operations/AESDecrypt.mjs";
11
11
  import AESEncrypt from "../../operations/AESEncrypt.mjs";
12
+ import AESKeyUnwrap from "../../operations/AESKeyUnwrap.mjs";
13
+ import AESKeyWrap from "../../operations/AESKeyWrap.mjs";
12
14
  import AffineCipherDecode from "../../operations/AffineCipherDecode.mjs";
13
15
  import AffineCipherEncode from "../../operations/AffineCipherEncode.mjs";
14
16
  import AtbashCipher from "../../operations/AtbashCipher.mjs";
@@ -49,6 +51,8 @@ OpModules.Ciphers = {
49
51
  "A1Z26 Cipher Encode": A1Z26CipherEncode,
50
52
  "AES Decrypt": AESDecrypt,
51
53
  "AES Encrypt": AESEncrypt,
54
+ "AES Key Unwrap": AESKeyUnwrap,
55
+ "AES Key Wrap": AESKeyWrap,
52
56
  "Affine Cipher Decode": AffineCipherDecode,
53
57
  "Affine Cipher Encode": AffineCipherEncode,
54
58
  "Atbash Cipher": AtbashCipher,
@@ -0,0 +1,128 @@
1
+ /**
2
+ * @author mikecat
3
+ * @copyright Crown Copyright 2022
4
+ * @license Apache-2.0
5
+ */
6
+
7
+ import Operation from "../Operation.mjs";
8
+ import Utils from "../Utils.mjs";
9
+ import { toHexFast } from "../lib/Hex.mjs";
10
+ import forge from "node-forge";
11
+ import OperationError from "../errors/OperationError.mjs";
12
+
13
+ /**
14
+ * AES Key Unwrap operation
15
+ */
16
+ class AESKeyUnwrap extends Operation {
17
+
18
+ /**
19
+ * AESKeyUnwrap constructor
20
+ */
21
+ constructor() {
22
+ super();
23
+
24
+ this.name = "AES Key Unwrap";
25
+ this.module = "Ciphers";
26
+ this.description = "Decryptor for a key wrapping algorithm defined in RFC3394, which is used to protect keys in untrusted storage or communications, using AES.<br><br>This algorithm uses an AES key (KEK: key-encryption key) and a 64-bit IV to decrypt 64-bit blocks.";
27
+ this.infoURL = "https://wikipedia.org/wiki/Key_wrap";
28
+ this.inputType = "string";
29
+ this.outputType = "string";
30
+ this.args = [
31
+ {
32
+ "name": "Key (KEK)",
33
+ "type": "toggleString",
34
+ "value": "",
35
+ "toggleValues": ["Hex", "UTF8", "Latin1", "Base64"]
36
+ },
37
+ {
38
+ "name": "IV",
39
+ "type": "toggleString",
40
+ "value": "a6a6a6a6a6a6a6a6",
41
+ "toggleValues": ["Hex", "UTF8", "Latin1", "Base64"]
42
+ },
43
+ {
44
+ "name": "Input",
45
+ "type": "option",
46
+ "value": ["Hex", "Raw"]
47
+ },
48
+ {
49
+ "name": "Output",
50
+ "type": "option",
51
+ "value": ["Hex", "Raw"]
52
+ },
53
+ ];
54
+ }
55
+
56
+ /**
57
+ * @param {string} input
58
+ * @param {Object[]} args
59
+ * @returns {string}
60
+ */
61
+ run(input, args) {
62
+ const kek = Utils.convertToByteString(args[0].string, args[0].option),
63
+ iv = Utils.convertToByteString(args[1].string, args[1].option),
64
+ inputType = args[2],
65
+ outputType = args[3];
66
+
67
+ if (kek.length !== 16 && kek.length !== 24 && kek.length !== 32) {
68
+ throw new OperationError("KEK must be either 16, 24, or 32 bytes (currently " + kek.length + " bytes)");
69
+ }
70
+ if (iv.length !== 8) {
71
+ throw new OperationError("IV must be 8 bytes (currently " + iv.length + " bytes)");
72
+ }
73
+ const inputData = Utils.convertToByteString(input, inputType);
74
+ if (inputData.length % 8 !== 0 || inputData.length < 24) {
75
+ throw new OperationError("input must be 8n (n>=3) bytes (currently " + inputData.length + " bytes)");
76
+ }
77
+
78
+ const cipher = forge.cipher.createCipher("AES-ECB", kek);
79
+ cipher.start();
80
+ cipher.update(forge.util.createBuffer(""));
81
+ cipher.finish();
82
+ const paddingBlock = cipher.output.getBytes();
83
+
84
+ const decipher = forge.cipher.createDecipher("AES-ECB", kek);
85
+
86
+ let A = inputData.substring(0, 8);
87
+ const R = [];
88
+ for (let i = 8; i < inputData.length; i += 8) {
89
+ R.push(inputData.substring(i, i + 8));
90
+ }
91
+ let cntLower = R.length >>> 0;
92
+ let cntUpper = (R.length / ((1 << 30) * 4)) >>> 0;
93
+ cntUpper = cntUpper * 6 + ((cntLower * 6 / ((1 << 30) * 4)) >>> 0);
94
+ cntLower = cntLower * 6 >>> 0;
95
+ for (let j = 5; j >= 0; j--) {
96
+ for (let i = R.length - 1; i >= 0; i--) {
97
+ const aBuffer = Utils.strToArrayBuffer(A);
98
+ const aView = new DataView(aBuffer);
99
+ aView.setUint32(0, aView.getUint32(0) ^ cntUpper);
100
+ aView.setUint32(4, aView.getUint32(4) ^ cntLower);
101
+ A = Utils.arrayBufferToStr(aBuffer, false);
102
+ decipher.start();
103
+ decipher.update(forge.util.createBuffer(A + R[i] + paddingBlock));
104
+ decipher.finish();
105
+ const B = decipher.output.getBytes();
106
+ A = B.substring(0, 8);
107
+ R[i] = B.substring(8, 16);
108
+ cntLower--;
109
+ if (cntLower < 0) {
110
+ cntUpper--;
111
+ cntLower = 0xffffffff;
112
+ }
113
+ }
114
+ }
115
+ if (A !== iv) {
116
+ throw new OperationError("IV mismatch");
117
+ }
118
+ const P = R.join("");
119
+
120
+ if (outputType === "Hex") {
121
+ return toHexFast(Utils.strToArrayBuffer(P));
122
+ }
123
+ return P;
124
+ }
125
+
126
+ }
127
+
128
+ export default AESKeyUnwrap;
@@ -0,0 +1,115 @@
1
+ /**
2
+ * @author mikecat
3
+ * @copyright Crown Copyright 2022
4
+ * @license Apache-2.0
5
+ */
6
+
7
+ import Operation from "../Operation.mjs";
8
+ import Utils from "../Utils.mjs";
9
+ import { toHexFast } from "../lib/Hex.mjs";
10
+ import forge from "node-forge";
11
+ import OperationError from "../errors/OperationError.mjs";
12
+
13
+ /**
14
+ * AES Key Wrap operation
15
+ */
16
+ class AESKeyWrap extends Operation {
17
+
18
+ /**
19
+ * AESKeyWrap constructor
20
+ */
21
+ constructor() {
22
+ super();
23
+
24
+ this.name = "AES Key Wrap";
25
+ this.module = "Ciphers";
26
+ this.description = "A key wrapping algorithm defined in RFC3394, which is used to protect keys in untrusted storage or communications, using AES.<br><br>This algorithm uses an AES key (KEK: key-encryption key) and a 64-bit IV to encrypt 64-bit blocks.";
27
+ this.infoURL = "https://wikipedia.org/wiki/Key_wrap";
28
+ this.inputType = "string";
29
+ this.outputType = "string";
30
+ this.args = [
31
+ {
32
+ "name": "Key (KEK)",
33
+ "type": "toggleString",
34
+ "value": "",
35
+ "toggleValues": ["Hex", "UTF8", "Latin1", "Base64"]
36
+ },
37
+ {
38
+ "name": "IV",
39
+ "type": "toggleString",
40
+ "value": "a6a6a6a6a6a6a6a6",
41
+ "toggleValues": ["Hex", "UTF8", "Latin1", "Base64"]
42
+ },
43
+ {
44
+ "name": "Input",
45
+ "type": "option",
46
+ "value": ["Hex", "Raw"]
47
+ },
48
+ {
49
+ "name": "Output",
50
+ "type": "option",
51
+ "value": ["Hex", "Raw"]
52
+ },
53
+ ];
54
+ }
55
+
56
+ /**
57
+ * @param {string} input
58
+ * @param {Object[]} args
59
+ * @returns {string}
60
+ */
61
+ run(input, args) {
62
+ const kek = Utils.convertToByteString(args[0].string, args[0].option),
63
+ iv = Utils.convertToByteString(args[1].string, args[1].option),
64
+ inputType = args[2],
65
+ outputType = args[3];
66
+
67
+ if (kek.length !== 16 && kek.length !== 24 && kek.length !== 32) {
68
+ throw new OperationError("KEK must be either 16, 24, or 32 bytes (currently " + kek.length + " bytes)");
69
+ }
70
+ if (iv.length !== 8) {
71
+ throw new OperationError("IV must be 8 bytes (currently " + iv.length + " bytes)");
72
+ }
73
+ const inputData = Utils.convertToByteString(input, inputType);
74
+ if (inputData.length % 8 !== 0 || inputData.length < 16) {
75
+ throw new OperationError("input must be 8n (n>=2) bytes (currently " + inputData.length + " bytes)");
76
+ }
77
+
78
+ const cipher = forge.cipher.createCipher("AES-ECB", kek);
79
+
80
+ let A = iv;
81
+ const R = [];
82
+ for (let i = 0; i < inputData.length; i += 8) {
83
+ R.push(inputData.substring(i, i + 8));
84
+ }
85
+ let cntLower = 1, cntUpper = 0;
86
+ for (let j = 0; j < 6; j++) {
87
+ for (let i = 0; i < R.length; i++) {
88
+ cipher.start();
89
+ cipher.update(forge.util.createBuffer(A + R[i]));
90
+ cipher.finish();
91
+ const B = cipher.output.getBytes();
92
+ const msbBuffer = Utils.strToArrayBuffer(B.substring(0, 8));
93
+ const msbView = new DataView(msbBuffer);
94
+ msbView.setUint32(0, msbView.getUint32(0) ^ cntUpper);
95
+ msbView.setUint32(4, msbView.getUint32(4) ^ cntLower);
96
+ A = Utils.arrayBufferToStr(msbBuffer, false);
97
+ R[i] = B.substring(8, 16);
98
+ cntLower++;
99
+ if (cntLower > 0xffffffff) {
100
+ cntUpper++;
101
+ cntLower = 0;
102
+ }
103
+ }
104
+ }
105
+ const C = A + R.join("");
106
+
107
+ if (outputType === "Hex") {
108
+ return toHexFast(Utils.strToArrayBuffer(C));
109
+ }
110
+ return C;
111
+ }
112
+
113
+ }
114
+
115
+ export default AESKeyWrap;
@@ -10,6 +10,8 @@ import A1Z26CipherEncode from "./A1Z26CipherEncode.mjs";
10
10
  import ADD from "./ADD.mjs";
11
11
  import AESDecrypt from "./AESDecrypt.mjs";
12
12
  import AESEncrypt from "./AESEncrypt.mjs";
13
+ import AESKeyUnwrap from "./AESKeyUnwrap.mjs";
14
+ import AESKeyWrap from "./AESKeyWrap.mjs";
13
15
  import AND from "./AND.mjs";
14
16
  import AddLineNumbers from "./AddLineNumbers.mjs";
15
17
  import AddTextToImage from "./AddTextToImage.mjs";
@@ -404,6 +406,8 @@ export {
404
406
  ADD,
405
407
  AESDecrypt,
406
408
  AESEncrypt,
409
+ AESKeyUnwrap,
410
+ AESKeyWrap,
407
411
  AND,
408
412
  AddLineNumbers,
409
413
  AddTextToImage,
@@ -20,6 +20,8 @@ import {
20
20
  ADD as core_ADD,
21
21
  AESDecrypt as core_AESDecrypt,
22
22
  AESEncrypt as core_AESEncrypt,
23
+ AESKeyUnwrap as core_AESKeyUnwrap,
24
+ AESKeyWrap as core_AESKeyWrap,
23
25
  AND as core_AND,
24
26
  AddLineNumbers as core_AddLineNumbers,
25
27
  AddTextToImage as core_AddTextToImage,
@@ -414,6 +416,8 @@ function generateChef() {
414
416
  "ADD": _wrap(core_ADD),
415
417
  "AESDecrypt": _wrap(core_AESDecrypt),
416
418
  "AESEncrypt": _wrap(core_AESEncrypt),
419
+ "AESKeyUnwrap": _wrap(core_AESKeyUnwrap),
420
+ "AESKeyWrap": _wrap(core_AESKeyWrap),
417
421
  "AND": _wrap(core_AND),
418
422
  "addLineNumbers": _wrap(core_AddLineNumbers),
419
423
  "addTextToImage": _wrap(core_AddTextToImage),
@@ -816,6 +820,8 @@ const A1Z26CipherEncode = chef.A1Z26CipherEncode;
816
820
  const ADD = chef.ADD;
817
821
  const AESDecrypt = chef.AESDecrypt;
818
822
  const AESEncrypt = chef.AESEncrypt;
823
+ const AESKeyUnwrap = chef.AESKeyUnwrap;
824
+ const AESKeyWrap = chef.AESKeyWrap;
819
825
  const AND = chef.AND;
820
826
  const addLineNumbers = chef.addLineNumbers;
821
827
  const addTextToImage = chef.addTextToImage;
@@ -1212,6 +1218,8 @@ const operations = [
1212
1218
  ADD,
1213
1219
  AESDecrypt,
1214
1220
  AESEncrypt,
1221
+ AESKeyUnwrap,
1222
+ AESKeyWrap,
1215
1223
  AND,
1216
1224
  addLineNumbers,
1217
1225
  addTextToImage,
@@ -1612,6 +1620,8 @@ export {
1612
1620
  ADD,
1613
1621
  AESDecrypt,
1614
1622
  AESEncrypt,
1623
+ AESKeyUnwrap,
1624
+ AESKeyWrap,
1615
1625
  AND,
1616
1626
  addLineNumbers,
1617
1627
  addTextToImage,
@@ -128,6 +128,7 @@ import "./tests/NTLM.mjs";
128
128
  import "./tests/Shuffle.mjs";
129
129
  import "./tests/FletcherChecksum.mjs";
130
130
  import "./tests/CMAC.mjs";
131
+ import "./tests/AESKeyWrap.mjs";
131
132
 
132
133
  // Cannot test operations that use the File type yet
133
134
  // import "./tests/SplitColourChannels.mjs";
@@ -0,0 +1,324 @@
1
+ /**
2
+ * @author mikecat
3
+ * @copyright Crown Copyright 2022
4
+ * @license Apache-2.0
5
+ */
6
+ import TestRegister from "../../lib/TestRegister.mjs";
7
+
8
+ TestRegister.addTests([
9
+ {
10
+ "name": "AES Key Wrap: RFC Test Vector, 128-bit data, 128-bit KEK",
11
+ "input": "00112233445566778899aabbccddeeff",
12
+ "expectedOutput": "1fa68b0a8112b447aef34bd8fb5a7b829d3e862371d2cfe5",
13
+ "recipeConfig": [
14
+ {
15
+ "op": "AES Key Wrap",
16
+ "args": [
17
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
18
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
19
+ "Hex", "Hex"
20
+ ],
21
+ },
22
+ ],
23
+ },
24
+ {
25
+ "name": "AES Key Wrap: RFC Test Vector, 128-bit data, 192-bit KEK",
26
+ "input": "00112233445566778899aabbccddeeff",
27
+ "expectedOutput": "96778b25ae6ca435f92b5b97c050aed2468ab8a17ad84e5d",
28
+ "recipeConfig": [
29
+ {
30
+ "op": "AES Key Wrap",
31
+ "args": [
32
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f1011121314151617"},
33
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
34
+ "Hex", "Hex"
35
+ ],
36
+ },
37
+ ],
38
+ },
39
+ {
40
+ "name": "AES Key Wrap: RFC Test Vector, 128-bit data, 256-bit KEK",
41
+ "input": "00112233445566778899aabbccddeeff",
42
+ "expectedOutput": "64e8c3f9ce0f5ba263e9777905818a2a93c8191e7d6e8ae7",
43
+ "recipeConfig": [
44
+ {
45
+ "op": "AES Key Wrap",
46
+ "args": [
47
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f"},
48
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
49
+ "Hex", "Hex"
50
+ ],
51
+ },
52
+ ],
53
+ },
54
+ {
55
+ "name": "AES Key Wrap: RFC Test Vector, 192-bit data, 192-bit KEK",
56
+ "input": "00112233445566778899aabbccddeeff0001020304050607",
57
+ "expectedOutput": "031d33264e15d33268f24ec260743edce1c6c7ddee725a936ba814915c6762d2",
58
+ "recipeConfig": [
59
+ {
60
+ "op": "AES Key Wrap",
61
+ "args": [
62
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f1011121314151617"},
63
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
64
+ "Hex", "Hex"
65
+ ],
66
+ },
67
+ ],
68
+ },
69
+ {
70
+ "name": "AES Key Wrap: RFC Test Vector, 192-bit data, 256-bit KEK",
71
+ "input": "00112233445566778899aabbccddeeff0001020304050607",
72
+ "expectedOutput": "a8f9bc1612c68b3ff6e6f4fbe30e71e4769c8b80a32cb8958cd5d17d6b254da1",
73
+ "recipeConfig": [
74
+ {
75
+ "op": "AES Key Wrap",
76
+ "args": [
77
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f"},
78
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
79
+ "Hex", "Hex"
80
+ ],
81
+ },
82
+ ],
83
+ },
84
+ {
85
+ "name": "AES Key Wrap: RFC Test Vector, 256-bit data, 256-bit KEK",
86
+ "input": "00112233445566778899aabbccddeeff000102030405060708090a0b0c0d0e0f",
87
+ "expectedOutput": "28c9f404c4b810f4cbccb35cfb87f8263f5786e2d80ed326cbc7f0e71a99f43bfb988b9b7a02dd21",
88
+ "recipeConfig": [
89
+ {
90
+ "op": "AES Key Wrap",
91
+ "args": [
92
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f"},
93
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
94
+ "Hex", "Hex"
95
+ ],
96
+ },
97
+ ],
98
+ },
99
+ {
100
+ "name": "AES Key Unwrap: RFC Test Vector, 128-bit data, 128-bit KEK",
101
+ "input": "1fa68b0a8112b447aef34bd8fb5a7b829d3e862371d2cfe5",
102
+ "expectedOutput": "00112233445566778899aabbccddeeff",
103
+ "recipeConfig": [
104
+ {
105
+ "op": "AES Key Unwrap",
106
+ "args": [
107
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
108
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
109
+ "Hex", "Hex"
110
+ ],
111
+ },
112
+ ],
113
+ },
114
+ {
115
+ "name": "AES Key Unwrap: RFC Test Vector, 128-bit data, 192-bit KEK",
116
+ "input": "96778b25ae6ca435f92b5b97c050aed2468ab8a17ad84e5d",
117
+ "expectedOutput": "00112233445566778899aabbccddeeff",
118
+ "recipeConfig": [
119
+ {
120
+ "op": "AES Key Unwrap",
121
+ "args": [
122
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f1011121314151617"},
123
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
124
+ "Hex", "Hex"
125
+ ],
126
+ },
127
+ ],
128
+ },
129
+ {
130
+ "name": "AES Key Unwrap: RFC Test Vector, 128-bit data, 256-bit KEK",
131
+ "input": "64e8c3f9ce0f5ba263e9777905818a2a93c8191e7d6e8ae7",
132
+ "expectedOutput": "00112233445566778899aabbccddeeff",
133
+ "recipeConfig": [
134
+ {
135
+ "op": "AES Key Unwrap",
136
+ "args": [
137
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f"},
138
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
139
+ "Hex", "Hex"
140
+ ],
141
+ },
142
+ ],
143
+ },
144
+ {
145
+ "name": "AES Key Unwrap: RFC Test Vector, 192-bit data, 192-bit KEK",
146
+ "input": "031d33264e15d33268f24ec260743edce1c6c7ddee725a936ba814915c6762d2",
147
+ "expectedOutput": "00112233445566778899aabbccddeeff0001020304050607",
148
+ "recipeConfig": [
149
+ {
150
+ "op": "AES Key Unwrap",
151
+ "args": [
152
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f1011121314151617"},
153
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
154
+ "Hex", "Hex"
155
+ ],
156
+ },
157
+ ],
158
+ },
159
+ {
160
+ "name": "AES Key Unwrap: RFC Test Vector, 192-bit data, 256-bit KEK",
161
+ "input": "a8f9bc1612c68b3ff6e6f4fbe30e71e4769c8b80a32cb8958cd5d17d6b254da1",
162
+ "expectedOutput": "00112233445566778899aabbccddeeff0001020304050607",
163
+ "recipeConfig": [
164
+ {
165
+ "op": "AES Key Unwrap",
166
+ "args": [
167
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f"},
168
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
169
+ "Hex", "Hex"
170
+ ],
171
+ },
172
+ ],
173
+ },
174
+ {
175
+ "name": "AES Key Unwrap: RFC Test Vector, 256-bit data, 256-bit KEK",
176
+ "input": "28c9f404c4b810f4cbccb35cfb87f8263f5786e2d80ed326cbc7f0e71a99f43bfb988b9b7a02dd21",
177
+ "expectedOutput": "00112233445566778899aabbccddeeff000102030405060708090a0b0c0d0e0f",
178
+ "recipeConfig": [
179
+ {
180
+ "op": "AES Key Unwrap",
181
+ "args": [
182
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f101112131415161718191a1b1c1d1e1f"},
183
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
184
+ "Hex", "Hex"
185
+ ],
186
+ },
187
+ ],
188
+ },
189
+ {
190
+ "name": "AES Key Wrap: invalid KEK length",
191
+ "input": "00112233445566778899aabbccddeeff",
192
+ "expectedOutput": "KEK must be either 16, 24, or 32 bytes (currently 10 bytes)",
193
+ "recipeConfig": [
194
+ {
195
+ "op": "AES Key Wrap",
196
+ "args": [
197
+ {"option": "Hex", "string": "00010203040506070809"},
198
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
199
+ "Hex", "Hex"
200
+ ],
201
+ },
202
+ ],
203
+ },
204
+ {
205
+ "name": "AES Key Wrap: invalid IV length",
206
+ "input": "00112233445566778899aabbccddeeff",
207
+ "expectedOutput": "IV must be 8 bytes (currently 6 bytes)",
208
+ "recipeConfig": [
209
+ {
210
+ "op": "AES Key Wrap",
211
+ "args": [
212
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
213
+ {"option": "Hex", "string": "a6a6a6a6a6a6"},
214
+ "Hex", "Hex"
215
+ ],
216
+ },
217
+ ],
218
+ },
219
+ {
220
+ "name": "AES Key Wrap: input length not multiple of 8",
221
+ "input": "00112233445566778899aabbccddeeff0102",
222
+ "expectedOutput": "input must be 8n (n>=2) bytes (currently 18 bytes)",
223
+ "recipeConfig": [
224
+ {
225
+ "op": "AES Key Wrap",
226
+ "args": [
227
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
228
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
229
+ "Hex", "Hex"
230
+ ],
231
+ },
232
+ ],
233
+ },
234
+ {
235
+ "name": "AES Key Wrap: input too short",
236
+ "input": "0011223344556677",
237
+ "expectedOutput": "input must be 8n (n>=2) bytes (currently 8 bytes)",
238
+ "recipeConfig": [
239
+ {
240
+ "op": "AES Key Wrap",
241
+ "args": [
242
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
243
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
244
+ "Hex", "Hex"
245
+ ],
246
+ },
247
+ ],
248
+ },
249
+ {
250
+ "name": "AES Key Unwrap: invalid KEK length",
251
+ "input": "1fa68b0a8112b447aef34bd8fb5a7b829d3e862371d2cfe5",
252
+ "expectedOutput": "KEK must be either 16, 24, or 32 bytes (currently 10 bytes)",
253
+ "recipeConfig": [
254
+ {
255
+ "op": "AES Key Unwrap",
256
+ "args": [
257
+ {"option": "Hex", "string": "00010203040506070809"},
258
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
259
+ "Hex", "Hex"
260
+ ],
261
+ },
262
+ ],
263
+ },
264
+ {
265
+ "name": "AES Key Unwrap: invalid IV length",
266
+ "input": "1fa68b0a8112b447aef34bd8fb5a7b829d3e862371d2cfe5",
267
+ "expectedOutput": "IV must be 8 bytes (currently 6 bytes)",
268
+ "recipeConfig": [
269
+ {
270
+ "op": "AES Key Unwrap",
271
+ "args": [
272
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
273
+ {"option": "Hex", "string": "a6a6a6a6a6a6"},
274
+ "Hex", "Hex"
275
+ ],
276
+ },
277
+ ],
278
+ },
279
+ {
280
+ "name": "AES Key Unwrap: input length not multiple of 8",
281
+ "input": "1fa68b0a8112b447aef34bd8fb5a7b829d3e862371d2cfe5e621",
282
+ "expectedOutput": "input must be 8n (n>=3) bytes (currently 26 bytes)",
283
+ "recipeConfig": [
284
+ {
285
+ "op": "AES Key Unwrap",
286
+ "args": [
287
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
288
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
289
+ "Hex", "Hex"
290
+ ],
291
+ },
292
+ ],
293
+ },
294
+ {
295
+ "name": "AES Key Unwrap: input too short",
296
+ "input": "1fa68b0a8112b447aef34bd8fb5a7b82",
297
+ "expectedOutput": "input must be 8n (n>=3) bytes (currently 16 bytes)",
298
+ "recipeConfig": [
299
+ {
300
+ "op": "AES Key Unwrap",
301
+ "args": [
302
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
303
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
304
+ "Hex", "Hex"
305
+ ],
306
+ },
307
+ ],
308
+ },
309
+ {
310
+ "name": "AES Key Unwrap: corrupted input",
311
+ "input": "1fa68b0a8112b447aef34bd8fb5a7b829d3e862371d2cfe6",
312
+ "expectedOutput": "IV mismatch",
313
+ "recipeConfig": [
314
+ {
315
+ "op": "AES Key Unwrap",
316
+ "args": [
317
+ {"option": "Hex", "string": "000102030405060708090a0b0c0d0e0f"},
318
+ {"option": "Hex", "string": "a6a6a6a6a6a6a6a6"},
319
+ "Hex", "Hex"
320
+ ],
321
+ },
322
+ ],
323
+ },
324
+ ]);