mirror of
https://github.com/gchq/CyberChef
synced 2025-12-05 23:53:27 +00:00
Compare commits
242 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
f367c1f78b | ||
|
|
13d87d397d | ||
|
|
ed2c886359 | ||
|
|
6337e84708 | ||
|
|
f600571c6d | ||
|
|
5d4c7244e1 | ||
|
|
b6bdcaa71f | ||
|
|
c8eab5d218 | ||
|
|
8ab56a29ac | ||
|
|
973b5f3f5c | ||
|
|
076a1f97c2 | ||
|
|
d96ef37d81 | ||
|
|
56f8302402 | ||
|
|
97e6a7cbd8 | ||
|
|
d89d79116c | ||
|
|
367d79e820 | ||
|
|
283d7f2159 | ||
|
|
dacb3ef6c3 | ||
|
|
22454ae842 | ||
|
|
79b9b63982 | ||
|
|
2f68bf30a4 | ||
|
|
50f078cc45 | ||
|
|
47a410d6ab | ||
|
|
31cbf8cccc | ||
|
|
88bd321e3e | ||
|
|
b4a586c0b9 | ||
|
|
63593f1b6c | ||
|
|
dcff8971e8 | ||
|
|
3f7059a235 | ||
|
|
71c743ff5a | ||
|
|
15fbe5a459 | ||
|
|
cd47394709 | ||
|
|
6f4ee8b7b6 | ||
|
|
8c5d05b611 | ||
|
|
3bdcf4d851 | ||
|
|
1d1c69ca51 | ||
|
|
c4c679021d | ||
|
|
c16d13e2c9 | ||
|
|
97613eb3c7 | ||
|
|
a946d04a72 | ||
|
|
cc35ec82eb | ||
|
|
d6604e0008 | ||
|
|
b9e63efc37 | ||
|
|
b458707921 | ||
|
|
6ec52c6cd2 | ||
|
|
79d7a5dd87 | ||
|
|
1653d0212a | ||
|
|
c378bcb00b | ||
|
|
215e7a5f5d | ||
|
|
6b686681d5 | ||
|
|
20ea050728 | ||
|
|
4b6132a2d7 | ||
|
|
4cf80e3ebb | ||
|
|
045747f543 | ||
|
|
b10c5e3256 | ||
|
|
69df2e4183 | ||
|
|
12ebd35c4d | ||
|
|
30c5f76cf0 | ||
|
|
3a979b6cda | ||
|
|
863bdffa84 | ||
|
|
42b956e402 | ||
|
|
4acf7b4e4f | ||
|
|
42e881326f | ||
|
|
3c4893d7c7 | ||
|
|
027aca4ab2 | ||
|
|
2d471f551f | ||
|
|
5c598b69b0 | ||
|
|
037300de79 | ||
|
|
6990dcae89 | ||
|
|
6e81d6dfcd | ||
|
|
cea30465d8 | ||
|
|
b301d16cb2 | ||
|
|
19c002fcdd | ||
|
|
ab3a73fe58 | ||
|
|
91fc2c28dc | ||
|
|
ca47ba3c7c | ||
|
|
e1b456c01c | ||
|
|
5eb7e00eac | ||
|
|
8bcf68c8a1 | ||
|
|
520eaedd9a | ||
|
|
4c5e664ce0 | ||
|
|
53c500eb1b | ||
|
|
253346a201 | ||
|
|
c5d82a76ab | ||
|
|
18a9dfffc7 | ||
|
|
38838e4dca | ||
|
|
5c151d727b | ||
|
|
2d5b157c91 | ||
|
|
10d3d27a33 | ||
|
|
1614442bd7 | ||
|
|
a3c5b1e107 | ||
|
|
3f0af9cdea | ||
|
|
f4de4de8c1 | ||
|
|
69033a7343 | ||
|
|
5a22106731 | ||
|
|
5155d0ed56 | ||
|
|
9be674103f | ||
|
|
ba24e12454 | ||
|
|
b76aa16143 | ||
|
|
8f7bb3a7c9 | ||
|
|
be2b466376 | ||
|
|
f957925aac | ||
|
|
1bf8d63d1a | ||
|
|
8875144307 | ||
|
|
d5c01f387a | ||
|
|
32709cd60f | ||
|
|
aaf0a91975 | ||
|
|
6cc6230b91 | ||
|
|
dd630f20f8 | ||
|
|
0c6efd95fa | ||
|
|
a276378887 | ||
|
|
98d861a639 | ||
|
|
3b3c27072f | ||
|
|
3089c39369 | ||
|
|
0cbb17f7ce | ||
|
|
54793f2b78 | ||
|
|
f1ffe19ec8 | ||
|
|
e638fb69b5 | ||
|
|
718a94b5e0 | ||
|
|
3079059ce3 | ||
|
|
d6c6981bc0 | ||
|
|
8aeb7b60a7 | ||
|
|
9197ac6510 | ||
|
|
b67ad3073c | ||
|
|
4a4f37f888 | ||
|
|
c55331f220 | ||
|
|
757ec98554 | ||
|
|
14309f2069 | ||
|
|
e6b89d571e | ||
|
|
d957198fd6 | ||
|
|
903bd22999 | ||
|
|
04ee2fb3e4 | ||
|
|
ac2466a304 | ||
|
|
ab4c9ef0d6 | ||
|
|
a69063de9b | ||
|
|
62b76777c0 | ||
|
|
32a91bda0a | ||
|
|
a15af602e0 | ||
|
|
ec9dfd2918 | ||
|
|
016086ef4e | ||
|
|
2e5ea968ee | ||
|
|
5dde1c1c04 | ||
|
|
be14d56eae | ||
|
|
100b097ace | ||
|
|
3833c5f9fe | ||
|
|
3470dd9f3b | ||
|
|
c5e8649284 | ||
|
|
a95f43aa4d | ||
|
|
0420aa8edb | ||
|
|
806b43dfec | ||
|
|
98f4fe4c2b | ||
|
|
0d63b3cbae | ||
|
|
7061c05f77 | ||
|
|
9b9a182f9f | ||
|
|
2d9e7fcc6d | ||
|
|
56946a66aa | ||
|
|
c9242e32fe | ||
|
|
22e8883934 | ||
|
|
552a18d89a | ||
|
|
6b725e9114 | ||
|
|
415beaa0b0 | ||
|
|
e9fe227ed7 | ||
|
|
c1be109592 | ||
|
|
88e603bbf1 | ||
|
|
c7b2095bb4 | ||
|
|
7396117d89 | ||
|
|
fd96bf345b | ||
|
|
2820660264 | ||
|
|
86145dbf67 | ||
|
|
135b17186e | ||
|
|
ce494339ef | ||
|
|
dd5af7eb10 | ||
|
|
3abe99078e | ||
|
|
edbd540c68 | ||
|
|
06d9302d96 | ||
|
|
032b4bed7f | ||
|
|
8559f5c8ea | ||
|
|
91133172d5 | ||
|
|
001f3f30cd | ||
|
|
a1b1059ad1 | ||
|
|
69a0122fea | ||
|
|
3d505b4248 | ||
|
|
70d4e3394c | ||
|
|
3905c01a0d | ||
|
|
2a49af1ec3 | ||
|
|
3d4f54e8bc | ||
|
|
61f2f2d2e3 | ||
|
|
00058bd5c7 | ||
|
|
383fe50fc9 | ||
|
|
e4fdadc573 | ||
|
|
032f8808ef | ||
|
|
10cf0d13c2 | ||
|
|
6c9fea97ef | ||
|
|
4c2d612bdd | ||
|
|
8e9fece77d | ||
|
|
c818370123 | ||
|
|
bf2643802a | ||
|
|
1ad079fbd4 | ||
|
|
2d9e8773f5 | ||
|
|
5aa13f2428 | ||
|
|
38f5fcde86 | ||
|
|
f99ab87ca1 | ||
|
|
d3d230a76d | ||
|
|
e7c6a05e9f | ||
|
|
17ec5c2683 | ||
|
|
8d1839b9e2 | ||
|
|
23213a4ac5 | ||
|
|
e81c81351d | ||
|
|
36e16d9925 | ||
|
|
84eaaf4819 | ||
|
|
757096d97a | ||
|
|
2393eac218 | ||
|
|
745d21d1bc | ||
|
|
cb34518a89 | ||
|
|
821dd9c48c | ||
|
|
740f3924df | ||
|
|
f052ed9b00 | ||
|
|
2507362741 | ||
|
|
481a4266b0 | ||
|
|
92d9abf43a | ||
|
|
5bcdd99870 | ||
|
|
e11bb38625 | ||
|
|
affe057cab | ||
|
|
c1b2fc9400 | ||
|
|
782e0f3475 | ||
|
|
6be7ac89d4 | ||
|
|
ad2424cfdd | ||
|
|
b9703e2bb6 | ||
|
|
198b67104f | ||
|
|
8dab0eac58 | ||
|
|
8b78383732 | ||
|
|
f1c31ea966 | ||
|
|
1a1fad7433 | ||
|
|
ab248a0209 | ||
|
|
6155dbb6e9 | ||
|
|
0c06e64051 | ||
|
|
ed84614389 | ||
|
|
67bd2605c0 | ||
|
|
83c145c2ac | ||
|
|
53bf52c989 | ||
|
|
77a0238406 | ||
|
|
c7f13ff67f |
19
.babelrc
19
.babelrc
@@ -1,19 +0,0 @@
|
||||
{
|
||||
"presets": [
|
||||
["env", {
|
||||
"targets": {
|
||||
"chrome": 40,
|
||||
"firefox": 35,
|
||||
"edge": 14,
|
||||
"node": "6.5"
|
||||
},
|
||||
"modules": false,
|
||||
"useBuiltIns": true
|
||||
}]
|
||||
],
|
||||
"plugins": [
|
||||
["babel-plugin-transform-builtin-extend", {
|
||||
"globals": ["Error"]
|
||||
}]
|
||||
]
|
||||
}
|
||||
@@ -36,7 +36,7 @@ deploy:
|
||||
skip_cleanup: true
|
||||
email: "n1474335@gmail.com"
|
||||
api_key:
|
||||
secure: "Z3FK6bm4RfQEIRXZ1lBNzQkVIoHpivThr9U+XBHmsBgIfdrK/XUnzs/slugo+NIz8nPiGmMx4gxyJonBCLHDGb1ysky2aEWTl26c0teaF4DeQEjWC1ZaGzv8MV1/GkUamnr1qouXjyUhyEAp33rd8ccN9Rq3QNYB/qLDcA9/FCme7JCW6sCd4zWO0LGEYMJEMc2FzAUkqhqsI05hegGhSDgKXRn5PmLARek4yHD+Hx7pstaTeQIy0WoGJjdzoB3iJIMmo/hWZGzZafktUOh223c5qzx4zMpDRNmMngBUw6R94nKd4KvplYRgB87Y3L/aiVU4CF+axwLmK8RPaC1wbJnlHf06zxHPdiFmsY/zKPpNel+nOnxzRrF5l2KMU4TU6gug3s9Jnzp9T5UMfhp0jW3YkxHGeuOPOeE1i0lTUWUGWrPHLQquAhLfkr2zxaU4ETk/y85hq9W4LAy0ENEDVXX2jP7FnI4Z1fdpmljpmVNJR+outPg6t+Coqgvil7v7XpMtDm8lKQanVYuxwmkb/ncOWFRWuM2j5zIEg3CHnFDcJ9bYrfKRg0b0tb/2BWD14pQnV76goVwzJQYVzdPc8TKIYJw2BZ1Nh9c0iruQVebe/6l1FX9fDCkz8VMmltni61/LxZrf8y0NT1YaU1raeNY2dH5UWvEa9p72FPMI6Eg="
|
||||
secure: "UnDQL3Kh+GK2toL0TK3FObO0ujVssU3Eg4BBuYdjwLB81GhiGE5/DTh7THdZPOpbLo6wQeOwfZDuMeKC1OU+0Uf4NsdYFu1aq6xMO20qBQ4qUfgsyiK4Qgywj9gk0p1+OFZdGAZ/j1CNRAaF71XQIY6iV84c+SO4WoizXYrNT0Jh4sr2DA4/97G2xmJtPi0qOzYrJ09R56ZUozmqeik5G0pMRIuJRbpjS/7bZXV+N7WV0ombZc9RkUaetbabEVOLQ+Xx5YAIVq+VuEeMe9VBSnxY/FfCLmy1wJsjGzpLCyBI9nbrG4nw8Wgc2m8NfK9rcpIvBTGner9r2j60NVDkZ8kLZPrqXhq6AZMwa+oz6K5UQCqRo2RRQzSGwXxg67HY5Tcq+oNmjd+DqpPg4LZ3eGlluyP5XfG+hpSr9Ya4d8q8SrUWLxkoLHI6ZKMtoKFbTCSSQPiluW5hsZxjz3yDkkjsJw64M/EM8UyJrgaXqDklQu+7rBGKLfsK6os7RDiqjBWpQ7gwpo8HvY0O8yqEAabPz+QGkanpjcCOZCXFbSkzWxYy37RMAPu88iINVZVlZE4l+WJenCpZY95ueyy0mG9cyMSzVRPyX6A+/n4H6VMFPFjpGDLTD588ACEjY1lmHfS/eXwXJcgqPPD2gW0XdRdUheU/ssqlfCfGWQMTDXs="
|
||||
on:
|
||||
tags: true
|
||||
branch: master
|
||||
|
||||
140
CHANGELOG.md
140
CHANGELOG.md
@@ -1,36 +1,140 @@
|
||||
# Changelog
|
||||
All notable changes to this project will be documented in this file.
|
||||
All major and minor version changes will be documented in this file. Details of patch-level version changes can be found in [commit messages](https://github.com/gchq/CyberChef/commits/master).
|
||||
|
||||
|
||||
### [8.15.0] - 2018-12-18
|
||||
- 'Text Encoding Brute Force' operation added [@Cynser] | [#439]
|
||||
|
||||
### [8.14.0] - 2018-12-18
|
||||
- 'To Base62' and 'From Base62' operations added [@tcode2k16] | [#443]
|
||||
|
||||
### [8.13.0] - 2018-12-15
|
||||
- 'A1Z26 Cipher Encode' and 'A1Z26 Cipher Decode' operations added [@jarmovanlenthe] | [#441]
|
||||
|
||||
### [8.12.0] - 2018-11-21
|
||||
- 'Citrix CTX1 Encode' and 'Citrix CTX1 Decode' operations added [@bwhitn] | [#428]
|
||||
|
||||
### [8.11.0] - 2018-11-13
|
||||
- 'CSV to JSON' and 'JSON to CSV' operations added [@n1474335] | [#277]
|
||||
|
||||
### [8.10.0] - 2018-11-07
|
||||
- 'Remove Diacritics' operation added [@klaxon1] | [#387]
|
||||
|
||||
### [8.9.0] - 2018-11-07
|
||||
- 'Defang URL' operation added [@arnydo] | [#394]
|
||||
|
||||
### [8.8.0] - 2018-10-10
|
||||
- 'Parse TLV' operation added [@GCHQ77703] | [#351]
|
||||
|
||||
### [8.7.0] - 2018-08-31
|
||||
- 'JWT Sign', 'JWT Verify' and 'JWT Decode' operations added [@GCHQ77703] | [#348]
|
||||
|
||||
### [8.6.0] - 2018-08-29
|
||||
- 'To Geohash' and 'From Geohash' operations added [@GCHQ77703] | [#344]
|
||||
|
||||
### [8.5.0] - 2018-08-23
|
||||
- 'To Braille' and 'From Braille' operations added [@n1474335] | [#255]
|
||||
|
||||
### [8.4.0] - 2018-08-23
|
||||
- 'To Base85' and 'From Base85' operations added [@PenguinGeorge] | [#340]
|
||||
|
||||
### [8.3.0] - 2018-08-21
|
||||
- 'To MessagePack' and 'From MessagePack' operations added [@artemisbot] | [#338]
|
||||
|
||||
### [8.2.0] - 2018-08-21
|
||||
- Information links added to most operations, accessible in the description popover [@PenguinGeorge] | [#298]
|
||||
|
||||
### [8.1.0] - 2018-08-19
|
||||
- 'Dechunk HTTP response' operation added [@sevzero] | [#311]
|
||||
|
||||
## [8.0.0] - 2018-08-05
|
||||
- Codebase rewritten using [ES modules](https://hacks.mozilla.org/2018/03/es-modules-a-cartoon-deep-dive/) and [classes](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes) #284
|
||||
- Operation architecture restructured to make adding new operations a lot simpler #284
|
||||
- A script has been added to aid in the creation of new operations by running `npm run newop` @n1474335 #284
|
||||
- 'Magic' operation added - [automated detection of encoded data](https://github.com/gchq/CyberChef/wiki/Automatic-detection-of-encoded-data-using-CyberChef-Magic) @n1474335 #239
|
||||
- UI updated to use [Bootstrap Material Design](https://fezvrasta.github.io/bootstrap-material-design/) @n1474335 #248
|
||||
- `JSON`, `File` and `List<File>` Dish types added @n1474335 #284
|
||||
- `OperationError` type added for better handling of errors thrown by operations @d98762625 #296
|
||||
- A `present()` method has been added, allowing operations to pass machine-friendly data to subsequent operations whilst presenting human-friendly data to the user @n1474335 #284
|
||||
- Set operations added @d98762625 #281
|
||||
- 'To Table' operation added @JustAnotherMark #294
|
||||
- 'Haversine distance' operation added @Dachande663 #325
|
||||
- Started keeping a changelog @n1474335
|
||||
- Codebase rewritten using [ES modules](https://hacks.mozilla.org/2018/03/es-modules-a-cartoon-deep-dive/) and [classes](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes) [@n1474335] [@d98762625] [@artemisbot] [@picapi] | [#284]
|
||||
- Operation architecture restructured to make adding new operations a lot simpler [@n1474335] | [#284]
|
||||
- A script has been added to aid in the creation of new operations by running `npm run newop` [@n1474335] | [#284]
|
||||
- 'Magic' operation added - [automated detection of encoded data](https://github.com/gchq/CyberChef/wiki/Automatic-detection-of-encoded-data-using-CyberChef-Magic) [@n1474335] | [#239]
|
||||
- UI updated to use [Bootstrap Material Design](https://fezvrasta.github.io/bootstrap-material-design/) [@n1474335] | [#248]
|
||||
- `JSON`, `File` and `List<File>` Dish types added [@n1474335] | [#284]
|
||||
- `OperationError` type added for better handling of errors thrown by operations [@d98762625] | [#296]
|
||||
- A `present()` method has been added, allowing operations to pass machine-friendly data to subsequent operations whilst presenting human-friendly data to the user [@n1474335] | [#284]
|
||||
- Set operations added [@d98762625] | [#281]
|
||||
- 'To Table' operation added [@JustAnotherMark] | [#294]
|
||||
- 'Haversine distance' operation added [@Dachande663] | [#325]
|
||||
- Started keeping a changelog [@n1474335]
|
||||
|
||||
## [7.0.0] - 2017-12-28
|
||||
- Added support for loading, processing and downloading files up to 500MB @n1474335 #224
|
||||
- Added support for loading, processing and downloading files up to 500MB [@n1474335] | [#224]
|
||||
|
||||
## [6.0.0] - 2017-09-19
|
||||
- Added threading support, moving all recipe processing into a [Web Worker](https://developer.mozilla.org/en-US/docs/Web/API/Web_Workers_API/Using_web_workers) to increase performance and allow long-running operations to be cancelled @n1474335 #173
|
||||
- Created modules so that operations relying on large libraries can be downloaded separately as required, reducing the initial loading time for the app @n1474335 #173
|
||||
- Threading support added. All recipe processing moved into a [Web Worker](https://developer.mozilla.org/en-US/docs/Web/API/Web_Workers_API/Using_web_workers) to increase performance and to allow long-running operations to be cancelled [@n1474335] | [#173]
|
||||
- Module system created so that operations relying on large libraries can be downloaded separately as required, reducing the initial loading time for the app [@n1474335] | [#173]
|
||||
|
||||
## [5.0.0] - 2017-03-30
|
||||
- Configured Webpack build process, Babel transpilation and ES6 imports and exports @n1474335 #95
|
||||
- Webpack build process configured with Babel transpilation and ES6 imports and exports [@n1474335] | [#95]
|
||||
|
||||
## [4.0.0] - 2016-11-28
|
||||
- Initial open source commit @n1474335
|
||||
- Initial open source commit [@n1474335] | [b1d73a72](https://github.com/gchq/CyberChef/commit/b1d73a725dc7ab9fb7eb789296efd2b7e4b08306)
|
||||
|
||||
|
||||
|
||||
[8.15.0]: https://github.com/gchq/CyberChef/releases/tag/v8.15.0
|
||||
[8.14.0]: https://github.com/gchq/CyberChef/releases/tag/v8.14.0
|
||||
[8.13.0]: https://github.com/gchq/CyberChef/releases/tag/v8.13.0
|
||||
[8.12.0]: https://github.com/gchq/CyberChef/releases/tag/v8.12.0
|
||||
[8.11.0]: https://github.com/gchq/CyberChef/releases/tag/v8.11.0
|
||||
[8.10.0]: https://github.com/gchq/CyberChef/releases/tag/v8.10.0
|
||||
[8.9.0]: https://github.com/gchq/CyberChef/releases/tag/v8.9.0
|
||||
[8.8.0]: https://github.com/gchq/CyberChef/releases/tag/v8.8.0
|
||||
[8.7.0]: https://github.com/gchq/CyberChef/releases/tag/v8.7.0
|
||||
[8.6.0]: https://github.com/gchq/CyberChef/releases/tag/v8.6.0
|
||||
[8.5.0]: https://github.com/gchq/CyberChef/releases/tag/v8.5.0
|
||||
[8.4.0]: https://github.com/gchq/CyberChef/releases/tag/v8.4.0
|
||||
[8.3.0]: https://github.com/gchq/CyberChef/releases/tag/v8.3.0
|
||||
[8.2.0]: https://github.com/gchq/CyberChef/releases/tag/v8.2.0
|
||||
[8.1.0]: https://github.com/gchq/CyberChef/releases/tag/v8.1.0
|
||||
[8.0.0]: https://github.com/gchq/CyberChef/releases/tag/v8.0.0
|
||||
[7.0.0]: https://github.com/gchq/CyberChef/releases/tag/v7.0.0
|
||||
[6.0.0]: https://github.com/gchq/CyberChef/releases/tag/v6.0.0
|
||||
[5.0.0]: https://github.com/gchq/CyberChef/releases/tag/v5.0.0
|
||||
[4.0.0]: https://github.com/gchq/CyberChef/commit/b1d73a725dc7ab9fb7eb789296efd2b7e4b08306
|
||||
|
||||
[@n1474335]: https://github.com/n1474335
|
||||
[@d98762625]: https://github.com/d98762625
|
||||
[@GCHQ77703]: https://github.com/GCHQ77703
|
||||
[@artemisbot]: https://github.com/artemisbot
|
||||
[@picapi]: https://github.com/picapi
|
||||
[@Dachande663]: https://github.com/Dachande663
|
||||
[@JustAnotherMark]: https://github.com/JustAnotherMark
|
||||
[@sevzero]: https://github.com/sevzero
|
||||
[@PenguinGeorge]: https://github.com/PenguinGeorge
|
||||
[@arnydo]: https://github.com/arnydo
|
||||
[@klaxon1]: https://github.com/klaxon1
|
||||
[@bwhitn]: https://github.com/bwhitn
|
||||
[@jarmovanlenthe]: https://github.com/jarmovanlenthe
|
||||
[@tcode2k16]: https://github.com/tcode2k16
|
||||
[@Cynser]: https://github.com/Cynser
|
||||
|
||||
[#95]: https://github.com/gchq/CyberChef/pull/299
|
||||
[#173]: https://github.com/gchq/CyberChef/pull/173
|
||||
[#224]: https://github.com/gchq/CyberChef/pull/224
|
||||
[#239]: https://github.com/gchq/CyberChef/pull/239
|
||||
[#248]: https://github.com/gchq/CyberChef/pull/248
|
||||
[#255]: https://github.com/gchq/CyberChef/issues/255
|
||||
[#277]: https://github.com/gchq/CyberChef/issues/277
|
||||
[#281]: https://github.com/gchq/CyberChef/pull/281
|
||||
[#284]: https://github.com/gchq/CyberChef/pull/284
|
||||
[#294]: https://github.com/gchq/CyberChef/pull/294
|
||||
[#296]: https://github.com/gchq/CyberChef/pull/296
|
||||
[#298]: https://github.com/gchq/CyberChef/pull/298
|
||||
[#311]: https://github.com/gchq/CyberChef/pull/311
|
||||
[#325]: https://github.com/gchq/CyberChef/pull/325
|
||||
[#338]: https://github.com/gchq/CyberChef/pull/338
|
||||
[#340]: https://github.com/gchq/CyberChef/pull/340
|
||||
[#344]: https://github.com/gchq/CyberChef/pull/344
|
||||
[#348]: https://github.com/gchq/CyberChef/pull/348
|
||||
[#351]: https://github.com/gchq/CyberChef/pull/351
|
||||
[#387]: https://github.com/gchq/CyberChef/pull/387
|
||||
[#394]: https://github.com/gchq/CyberChef/pull/394
|
||||
[#428]: https://github.com/gchq/CyberChef/pull/428
|
||||
[#439]: https://github.com/gchq/CyberChef/pull/439
|
||||
[#441]: https://github.com/gchq/CyberChef/pull/441
|
||||
[#443]: https://github.com/gchq/CyberChef/pull/443
|
||||
|
||||
18
Gruntfile.js
18
Gruntfile.js
@@ -22,7 +22,7 @@ module.exports = function (grunt) {
|
||||
// Tasks
|
||||
grunt.registerTask("dev",
|
||||
"A persistent task which creates a development build whenever source files are modified.",
|
||||
["clean:dev", "exec:generateConfig", "concurrent:dev"]);
|
||||
["clean:dev", "clean:config", "exec:generateConfig", "concurrent:dev"]);
|
||||
|
||||
grunt.registerTask("node",
|
||||
"Compiles CyberChef into a single NodeJS module.",
|
||||
@@ -38,7 +38,7 @@ module.exports = function (grunt) {
|
||||
|
||||
grunt.registerTask("prod",
|
||||
"Creates a production-ready build. Use the --msg flag to add a compile message.",
|
||||
["eslint", "clean:prod", "exec:generateConfig", "webpack:web", "inline", "chmod"]);
|
||||
["eslint", "clean:prod", "clean:config", "exec:generateConfig", "webpack:web", "inline", "chmod"]);
|
||||
|
||||
grunt.registerTask("default",
|
||||
"Lints the code base",
|
||||
@@ -143,7 +143,7 @@ module.exports = function (grunt) {
|
||||
options: {
|
||||
configFile: "./.eslintrc.json"
|
||||
},
|
||||
configs: ["Gruntfile.js"],
|
||||
configs: ["*.js"],
|
||||
core: ["src/core/**/*.{js,mjs}", "!src/core/vendor/**/*", "!src/core/operations/legacy/**/*"],
|
||||
web: ["src/web/**/*.{js,mjs}"],
|
||||
node: ["src/node/**/*.{js,mjs}"],
|
||||
@@ -280,7 +280,11 @@ module.exports = function (grunt) {
|
||||
chunks: false,
|
||||
modules: false,
|
||||
entrypoints: false,
|
||||
warningsFilter: [/source-map/, /dependency is an expression/],
|
||||
warningsFilter: [
|
||||
/source-map/,
|
||||
/dependency is an expression/,
|
||||
/export 'default'/
|
||||
],
|
||||
}
|
||||
},
|
||||
start: {
|
||||
@@ -382,13 +386,13 @@ module.exports = function (grunt) {
|
||||
"mkdir -p src/core/config/modules",
|
||||
"echo 'export default {};\n' > src/core/config/modules/OpModules.mjs",
|
||||
"echo '[]\n' > src/core/config/OperationConfig.json",
|
||||
"node --experimental-modules src/core/config/scripts/generateOpsIndex.mjs",
|
||||
"node --experimental-modules src/core/config/scripts/generateConfig.mjs",
|
||||
"node --experimental-modules --no-warnings --no-deprecation src/core/config/scripts/generateOpsIndex.mjs",
|
||||
"node --experimental-modules --no-warnings --no-deprecation src/core/config/scripts/generateConfig.mjs",
|
||||
"echo '--- Config scripts finished. ---\n'"
|
||||
].join(";")
|
||||
},
|
||||
tests: {
|
||||
command: "node --experimental-modules test/index.mjs"
|
||||
command: "node --experimental-modules --no-warnings --no-deprecation test/index.mjs"
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
@@ -88,9 +88,8 @@ Contributing a new operation to CyberChef is super easy! There is a quickstart s
|
||||
|
||||
An installation walkthrough, how-to guides for adding new operations and themes, descriptions of the repository structure, available data types and coding conventions can all be found in the project [wiki pages](https://github.com/gchq/CyberChef/wiki).
|
||||
|
||||
- Sign the [GCHQ Contributor Licence Agreement](https://github.com/gchq/Gaffer/wiki/GCHQ-OSS-Contributor-License-Agreement-V1.0)
|
||||
- Push your changes to your fork.
|
||||
- Submit a pull request.
|
||||
- Submit a pull request. If you are doing this for the first time, you will be prompted to sign the [GCHQ Contributor Licence Agreement](https://cla-assistant.io/gchq/CyberChef) via the CLA assistant on the pull request. This will also ask whether you are happy for GCHQ to contact you about a token of thanks for your contribution, or about job opportunities at GCHQ.
|
||||
|
||||
|
||||
## Licencing
|
||||
|
||||
23
babel.config.js
Normal file
23
babel.config.js
Normal file
@@ -0,0 +1,23 @@
|
||||
module.exports = function(api) {
|
||||
api.cache.forever();
|
||||
|
||||
return {
|
||||
"presets": [
|
||||
["@babel/preset-env", {
|
||||
"targets": {
|
||||
"chrome": 40,
|
||||
"firefox": 35,
|
||||
"edge": 14,
|
||||
"node": "6.5"
|
||||
},
|
||||
"modules": false,
|
||||
"useBuiltIns": "entry"
|
||||
}]
|
||||
],
|
||||
"plugins": [
|
||||
["babel-plugin-transform-builtin-extend", {
|
||||
"globals": ["Error"]
|
||||
}]
|
||||
]
|
||||
};
|
||||
};
|
||||
5846
package-lock.json
generated
5846
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
75
package.json
75
package.json
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "cyberchef",
|
||||
"version": "8.0.1",
|
||||
"version": "8.15.1",
|
||||
"description": "The Cyber Swiss Army Knife for encryption, encoding, compression and data analysis.",
|
||||
"author": "n1474335 <n1474335@gmail.com>",
|
||||
"homepage": "https://gchq.github.io/CyberChef",
|
||||
@@ -30,45 +30,44 @@
|
||||
"main": "build/node/CyberChef.js",
|
||||
"bugs": "https://github.com/gchq/CyberChef/issues",
|
||||
"devDependencies": {
|
||||
"autoprefixer": "^9.1.0",
|
||||
"babel-core": "^6.26.3",
|
||||
"babel-loader": "^7.1.5",
|
||||
"babel-preset-env": "^1.7.0",
|
||||
"@babel/core": "^7.1.5",
|
||||
"@babel/preset-env": "^7.1.5",
|
||||
"autoprefixer": "^9.3.1",
|
||||
"babel-loader": "^8.0.4",
|
||||
"bootstrap": "^4.1.3",
|
||||
"colors": "^1.3.1",
|
||||
"css-loader": "^1.0.0",
|
||||
"eslint": "^5.3.0",
|
||||
"colors": "^1.3.2",
|
||||
"css-loader": "^1.0.1",
|
||||
"eslint": "^5.8.0",
|
||||
"exports-loader": "^0.7.0",
|
||||
"extract-text-webpack-plugin": "^4.0.0-alpha0",
|
||||
"file-loader": "^1.1.11",
|
||||
"file-loader": "^2.0.0",
|
||||
"grunt": "^1.0.3",
|
||||
"grunt-accessibility": "~6.0.0",
|
||||
"grunt-chmod": "~1.1.1",
|
||||
"grunt-concurrent": "^2.3.1",
|
||||
"grunt-contrib-clean": "~1.1.0",
|
||||
"grunt-contrib-clean": "~2.0.0",
|
||||
"grunt-contrib-copy": "~1.0.0",
|
||||
"grunt-contrib-watch": "^1.1.0",
|
||||
"grunt-eslint": "^21.0.0",
|
||||
"grunt-exec": "~3.0.0",
|
||||
"grunt-jsdoc": "^2.2.1",
|
||||
"grunt-webpack": "^3.1.2",
|
||||
"grunt-jsdoc": "^2.3.0",
|
||||
"grunt-webpack": "^3.1.3",
|
||||
"html-webpack-plugin": "^3.2.0",
|
||||
"imports-loader": "^0.8.0",
|
||||
"ink-docstrap": "^1.3.2",
|
||||
"js-to-mjs": "^0.2.0",
|
||||
"jsdoc-babel": "^0.4.0",
|
||||
"node-sass": "^4.9.2",
|
||||
"postcss-css-variables": "^0.9.0",
|
||||
"postcss-import": "^12.0.0",
|
||||
"postcss-loader": "^2.1.6",
|
||||
"jsdoc-babel": "^0.5.0",
|
||||
"node-sass": "^4.10.0",
|
||||
"postcss-css-variables": "^0.11.0",
|
||||
"postcss-import": "^12.0.1",
|
||||
"postcss-loader": "^3.0.0",
|
||||
"prompt": "^1.0.0",
|
||||
"sass-loader": "^7.1.0",
|
||||
"sitemap": "^1.13.0",
|
||||
"style-loader": "^0.21.0",
|
||||
"url-loader": "^1.0.1",
|
||||
"sitemap": "^2.1.0",
|
||||
"style-loader": "^0.23.1",
|
||||
"url-loader": "^1.1.2",
|
||||
"web-resource-inliner": "^4.2.1",
|
||||
"webpack": "^4.16.4",
|
||||
"webpack-dev-server": "^3.1.5",
|
||||
"webpack": "^4.25.1",
|
||||
"webpack-dev-server": "^3.1.10",
|
||||
"webpack-node-externals": "^1.7.2",
|
||||
"worker-loader": "^2.0.0"
|
||||
},
|
||||
@@ -77,46 +76,49 @@
|
||||
"babel-plugin-transform-builtin-extend": "1.1.2",
|
||||
"babel-polyfill": "^6.26.0",
|
||||
"bcryptjs": "^2.4.3",
|
||||
"bignumber.js": "^7.2.1",
|
||||
"bignumber.js": "^8.0.1",
|
||||
"bootstrap-colorpicker": "^2.5.3",
|
||||
"bootstrap-material-design": "^4.1.1",
|
||||
"bson": "^3.0.2",
|
||||
"chi-squared": "^1.1.0",
|
||||
"crypto-api": "^0.8.0",
|
||||
"crypto-api": "^0.8.3",
|
||||
"crypto-js": "^3.1.9-1",
|
||||
"ctph.js": "0.0.5",
|
||||
"diff": "^3.5.0",
|
||||
"es6-promisify": "^6.0.0",
|
||||
"es6-promisify": "^6.0.1",
|
||||
"escodegen": "^1.11.0",
|
||||
"esmangle": "^1.0.1",
|
||||
"esprima": "^4.0.1",
|
||||
"exif-parser": "^0.1.12",
|
||||
"file-saver": "^1.3.8",
|
||||
"highlight.js": "^9.12.0",
|
||||
"file-saver": "^2.0.0-rc.4",
|
||||
"highlight.js": "^9.13.1",
|
||||
"jquery": "^3.3.1",
|
||||
"js-crc": "^0.2.0",
|
||||
"js-sha3": "^0.7.0",
|
||||
"js-sha3": "^0.8.0",
|
||||
"jsbn": "^1.1.0",
|
||||
"jsesc": "^2.5.1",
|
||||
"jsonpath": "^1.0.0",
|
||||
"jsonwebtoken": "^8.3.0",
|
||||
"jsrsasign": "8.0.12",
|
||||
"kbpgp": "^2.0.77",
|
||||
"lodash": "^4.17.10",
|
||||
"kbpgp": "^2.0.82",
|
||||
"lodash": "^4.17.11",
|
||||
"loglevel": "^1.6.1",
|
||||
"loglevel-message-prefix": "^3.0.0",
|
||||
"moment": "^2.22.2",
|
||||
"moment-timezone": "^0.5.21",
|
||||
"node-forge": "^0.7.5",
|
||||
"moment-timezone": "^0.5.23",
|
||||
"ngeohash": "^0.6.0",
|
||||
"node-forge": "^0.7.6",
|
||||
"node-md6": "^0.1.0",
|
||||
"notepack.io": "^2.1.3",
|
||||
"nwmatcher": "^1.4.4",
|
||||
"otp": "^0.1.3",
|
||||
"popper.js": "^1.14.4",
|
||||
"scryptsy": "^2.0.0",
|
||||
"snackbarjs": "^1.1.0",
|
||||
"sortablejs": "^1.7.0",
|
||||
"split.js": "^1.3.5",
|
||||
"split.js": "^1.5.9",
|
||||
"ssdeep.js": "0.0.2",
|
||||
"ua-parser-js": "^0.7.18",
|
||||
"ua-parser-js": "^0.7.19",
|
||||
"utf8": "^3.0.0",
|
||||
"vkbeautify": "^0.99.3",
|
||||
"xmldom": "^0.1.27",
|
||||
@@ -130,7 +132,6 @@
|
||||
"test": "grunt test",
|
||||
"docs": "grunt docs",
|
||||
"lint": "grunt lint",
|
||||
"newop": "node --experimental-modules src/core/config/scripts/newOperation.mjs",
|
||||
"postinstall": "[ -f node_modules/crypto-api/src/crypto-api.mjs ] || npx j2m node_modules/crypto-api/src/crypto-api.js"
|
||||
"newop": "node --experimental-modules src/core/config/scripts/newOperation.mjs"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -169,7 +169,7 @@ class Dish {
|
||||
this.value = this.value instanceof BigNumber ? Utils.strToByteArray(this.value.toFixed()) : [];
|
||||
break;
|
||||
case Dish.JSON:
|
||||
this.value = this.value ? Utils.strToByteArray(JSON.stringify(this.value)) : [];
|
||||
this.value = this.value ? Utils.strToByteArray(JSON.stringify(this.value, null, 4)) : [];
|
||||
break;
|
||||
case Dish.FILE:
|
||||
this.value = await Utils.readFile(this.value);
|
||||
|
||||
@@ -29,6 +29,7 @@ class Operation {
|
||||
this.name = "";
|
||||
this.module = "";
|
||||
this.description = "";
|
||||
this.infoURL = null;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -8,6 +8,8 @@ import utf8 from "utf8";
|
||||
import moment from "moment-timezone";
|
||||
import {fromBase64} from "./lib/Base64";
|
||||
import {fromHex} from "./lib/Hex";
|
||||
import {fromDecimal} from "./lib/Decimal";
|
||||
import {fromBinary} from "./lib/Binary";
|
||||
|
||||
|
||||
/**
|
||||
@@ -297,7 +299,7 @@ class Utils {
|
||||
* Accepts hex, Base64, UTF8 and Latin1 strings.
|
||||
*
|
||||
* @param {string} str
|
||||
* @param {string} type - One of "Hex", "Base64", "UTF8" or "Latin1"
|
||||
* @param {string} type - One of "Binary", "Hex", "Decimal", "Base64", "UTF8" or "Latin1"
|
||||
* @returns {byteArray}
|
||||
*
|
||||
* @example
|
||||
@@ -312,8 +314,12 @@ class Utils {
|
||||
*/
|
||||
static convertToByteArray(str, type) {
|
||||
switch (type.toLowerCase()) {
|
||||
case "binary":
|
||||
return fromBinary(str);
|
||||
case "hex":
|
||||
return fromHex(str);
|
||||
case "decimal":
|
||||
return fromDecimal(str);
|
||||
case "base64":
|
||||
return fromBase64(str, null, "byteArray");
|
||||
case "utf8":
|
||||
@@ -330,7 +336,7 @@ class Utils {
|
||||
* Accepts hex, Base64, UTF8 and Latin1 strings.
|
||||
*
|
||||
* @param {string} str
|
||||
* @param {string} type - One of "Hex", "Base64", "UTF8" or "Latin1"
|
||||
* @param {string} type - One of "Binary", "Hex", "Decimal", "Base64", "UTF8" or "Latin1"
|
||||
* @returns {string}
|
||||
*
|
||||
* @example
|
||||
@@ -345,8 +351,12 @@ class Utils {
|
||||
*/
|
||||
static convertToByteString(str, type) {
|
||||
switch (type.toLowerCase()) {
|
||||
case "binary":
|
||||
return Utils.byteArrayToChars(fromBinary(str));
|
||||
case "hex":
|
||||
return Utils.byteArrayToChars(fromHex(str));
|
||||
case "decimal":
|
||||
return Utils.byteArrayToChars(fromDecimal(str));
|
||||
case "base64":
|
||||
return Utils.byteArrayToChars(fromBase64(str, null, "byteArray"));
|
||||
case "utf8":
|
||||
@@ -550,8 +560,6 @@ class Utils {
|
||||
if (renderNext) {
|
||||
cell += b;
|
||||
renderNext = false;
|
||||
} else if (b === "\\") {
|
||||
renderNext = true;
|
||||
} else if (b === "\"" && !inString) {
|
||||
inString = true;
|
||||
} else if (b === "\"" && inString) {
|
||||
@@ -565,6 +573,10 @@ class Utils {
|
||||
cell = "";
|
||||
lines.push(line);
|
||||
line = [];
|
||||
// Skip next byte if it is also a line delim (e.g. \r\n)
|
||||
if (lineDelims.indexOf(next) >= 0 && next !== b) {
|
||||
i++;
|
||||
}
|
||||
} else {
|
||||
cell += b;
|
||||
}
|
||||
@@ -769,7 +781,7 @@ class Utils {
|
||||
args = m[2]
|
||||
.replace(/"/g, '\\"') // Escape double quotes
|
||||
.replace(/(^|,|{|:)'/g, '$1"') // Replace opening ' with "
|
||||
.replace(/([^\\])'(,|:|}|$)/g, '$1"$2') // Replace closing ' with "
|
||||
.replace(/([^\\]|[^\\]\\\\)'(,|:|}|$)/g, '$1"$2') // Replace closing ' with "
|
||||
.replace(/\\'/g, "'"); // Unescape single quotes
|
||||
args = "[" + args + "]";
|
||||
|
||||
|
||||
@@ -25,6 +25,10 @@
|
||||
"From Base32",
|
||||
"To Base58",
|
||||
"From Base58",
|
||||
"To Base62",
|
||||
"From Base62",
|
||||
"To Base85",
|
||||
"From Base85",
|
||||
"To Base",
|
||||
"From Base",
|
||||
"To BCD",
|
||||
@@ -47,7 +51,15 @@
|
||||
"Change IP format",
|
||||
"Encode text",
|
||||
"Decode text",
|
||||
"Swap endianness"
|
||||
"Text Encoding Brute Force",
|
||||
"Swap endianness",
|
||||
"To MessagePack",
|
||||
"From MessagePack",
|
||||
"To Braille",
|
||||
"From Braille",
|
||||
"Parse TLV",
|
||||
"CSV to JSON",
|
||||
"JSON to CSV"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -77,12 +89,19 @@
|
||||
"Bifid Cipher Decode",
|
||||
"Affine Cipher Encode",
|
||||
"Affine Cipher Decode",
|
||||
"A1Z26 Cipher Encode",
|
||||
"A1Z26 Cipher Decode",
|
||||
"Atbash Cipher",
|
||||
"Substitute",
|
||||
"Derive PBKDF2 key",
|
||||
"Derive EVP key",
|
||||
"Bcrypt",
|
||||
"Scrypt",
|
||||
"JWT Sign",
|
||||
"JWT Verify",
|
||||
"JWT Decode",
|
||||
"Citrix CTX1 Encode",
|
||||
"Citrix CTX1 Decode",
|
||||
"Pseudo-Random Number Generator"
|
||||
]
|
||||
},
|
||||
@@ -137,6 +156,7 @@
|
||||
"ops": [
|
||||
"HTTP request",
|
||||
"Strip HTTP headers",
|
||||
"Dechunk HTTP response",
|
||||
"Parse User Agent",
|
||||
"Parse IP range",
|
||||
"Parse IPv6 address",
|
||||
@@ -148,7 +168,8 @@
|
||||
"Change IP format",
|
||||
"Group IP addresses",
|
||||
"Encode NetBIOS Name",
|
||||
"Decode NetBIOS Name"
|
||||
"Decode NetBIOS Name",
|
||||
"Defang URL"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -156,6 +177,7 @@
|
||||
"ops": [
|
||||
"Encode text",
|
||||
"Decode text",
|
||||
"Remove Diacritics",
|
||||
"Unescape Unicode Characters"
|
||||
]
|
||||
},
|
||||
@@ -282,7 +304,9 @@
|
||||
"Adler-32 Checksum",
|
||||
"CRC-16 Checksum",
|
||||
"CRC-32 Checksum",
|
||||
"TCP/IP Checksum"
|
||||
"TCP/IP Checksum",
|
||||
"To Geohash",
|
||||
"From Geohash"
|
||||
]
|
||||
},
|
||||
{
|
||||
@@ -312,7 +336,9 @@
|
||||
"To Camel case",
|
||||
"To Kebab case",
|
||||
"BSON serialise",
|
||||
"BSON deserialise"
|
||||
"BSON deserialise",
|
||||
"To MessagePack",
|
||||
"From MessagePack"
|
||||
]
|
||||
},
|
||||
{
|
||||
|
||||
@@ -35,12 +35,13 @@ for (const opObj in Ops) {
|
||||
const op = new Ops[opObj]();
|
||||
|
||||
operationConfig[op.name] = {
|
||||
module: op.module,
|
||||
module: op.module,
|
||||
description: op.description,
|
||||
inputType: op.inputType,
|
||||
outputType: op.presentType,
|
||||
infoURL: op.infoURL,
|
||||
inputType: op.inputType,
|
||||
outputType: op.presentType,
|
||||
flowControl: op.flowControl,
|
||||
args: op.args
|
||||
args: op.args
|
||||
};
|
||||
|
||||
if (op.hasOwnProperty("patterns")) {
|
||||
|
||||
@@ -53,6 +53,12 @@ If your operation does not rely on a library, just leave this blank and it will
|
||||
prompt: "Description",
|
||||
type: "string"
|
||||
},
|
||||
infoURL: {
|
||||
description: "An optional URL for an external site can be added to give more information about the operation. Wikipedia links are often suitable. If linking to Wikipedia, use an international link (e.g. https://wikipedia.org/...) rather than a localised link (e.g. https://en.wikipedia.org/...).",
|
||||
example: "https://wikipedia.org/wiki/Percent-encoding",
|
||||
prompt: "Information URL",
|
||||
type: "string",
|
||||
},
|
||||
inputType: {
|
||||
description: `The input type defines how the input data will be presented to your operation. Check the project wiki for a full description of each type. The options are: ${ioTypes.join(", ")}.`,
|
||||
example: "string",
|
||||
@@ -141,6 +147,7 @@ class ${moduleName} extends Operation {
|
||||
this.name = "${result.opName}";
|
||||
this.module = "${result.module}";
|
||||
this.description = "${(new EscapeString).run(result.description, ["Special chars", "Double"])}";
|
||||
this.infoURL = "${result.infoURL}";
|
||||
this.inputType = "${result.inputType}";
|
||||
this.outputType = "${result.outputType}";
|
||||
this.args = [
|
||||
|
||||
@@ -81,6 +81,7 @@ export function fromBase64(data, alphabet="A-Za-z0-9+/=", returnType="string", r
|
||||
return returnType === "string" ? "" : [];
|
||||
}
|
||||
|
||||
alphabet = alphabet || "A-Za-z0-9+/=";
|
||||
alphabet = Utils.expandAlphRange(alphabet).join("");
|
||||
|
||||
const output = [];
|
||||
@@ -125,14 +126,14 @@ export function fromBase64(data, alphabet="A-Za-z0-9+/=", returnType="string", r
|
||||
* Base64 alphabets.
|
||||
*/
|
||||
export const ALPHABET_OPTIONS = [
|
||||
{name: "Standard: A-Za-z0-9+/=", value: "A-Za-z0-9+/="},
|
||||
{name: "URL safe: A-Za-z0-9-_", value: "A-Za-z0-9-_"},
|
||||
{name: "Standard (RFC 4648): A-Za-z0-9+/=", value: "A-Za-z0-9+/="},
|
||||
{name: "URL safe (RFC 4648 \u00A75): A-Za-z0-9-_", value: "A-Za-z0-9-_"},
|
||||
{name: "Filename safe: A-Za-z0-9+-=", value: "A-Za-z0-9+\\-="},
|
||||
{name: "itoa64: ./0-9A-Za-z=", value: "./0-9A-Za-z="},
|
||||
{name: "XML: A-Za-z0-9_.", value: "A-Za-z0-9_."},
|
||||
{name: "y64: A-Za-z0-9._-", value: "A-Za-z0-9._-"},
|
||||
{name: "z64: 0-9a-zA-Z+/=", value: "0-9a-zA-Z+/="},
|
||||
{name: "Radix-64: 0-9A-Za-z+/=", value: "0-9A-Za-z+/="},
|
||||
{name: "Radix-64 (RFC 4880): 0-9A-Za-z+/=", value: "0-9A-Za-z+/="},
|
||||
{name: "Uuencoding: [space]-_", value: " -_"},
|
||||
{name: "Xxencoding: +-0-9A-Za-z", value: "+\\-0-9A-Za-z"},
|
||||
{name: "BinHex: !-,-0-689@A-NP-VX-Z[`a-fh-mp-r", value: "!-,-0-689@A-NP-VX-Z[`a-fh-mp-r"},
|
||||
|
||||
45
src/core/lib/Base85.mjs
Normal file
45
src/core/lib/Base85.mjs
Normal file
@@ -0,0 +1,45 @@
|
||||
/**
|
||||
* Base85 resources.
|
||||
*
|
||||
* @author PenguinGeorge [george@penguingeorge.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
/**
|
||||
* Base85 alphabet options.
|
||||
*/
|
||||
export const ALPHABET_OPTIONS = [
|
||||
{
|
||||
name: "Standard",
|
||||
value: "!-u",
|
||||
},
|
||||
{
|
||||
name: "Z85 (ZeroMQ)",
|
||||
value: "0-9a-zA-Z.\\-:+=^!/*?&<>()[]{}@%$#",
|
||||
},
|
||||
{
|
||||
name: "IPv6",
|
||||
value: "0-9A-Za-z!#$%&()*+\\-;<=>?@^_`{|~}",
|
||||
}
|
||||
];
|
||||
|
||||
|
||||
/**
|
||||
* Returns the name of the alphabet, when given the alphabet.
|
||||
*
|
||||
* @param {string} alphabet
|
||||
* @returns {string}
|
||||
*/
|
||||
export function alphabetName(alphabet) {
|
||||
alphabet = alphabet.replace("'", "'");
|
||||
alphabet = alphabet.replace("\"", """);
|
||||
alphabet = alphabet.replace("\\", "\");
|
||||
let name;
|
||||
|
||||
ALPHABET_OPTIONS.forEach(function(a) {
|
||||
if (escape(alphabet) === escape(a.value)) name = a.name;
|
||||
});
|
||||
|
||||
return name;
|
||||
}
|
||||
70
src/core/lib/Binary.mjs
Normal file
70
src/core/lib/Binary.mjs
Normal file
@@ -0,0 +1,70 @@
|
||||
/**
|
||||
* Binary functions.
|
||||
*
|
||||
* @author n1474335 [n1474335@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Utils from "../Utils";
|
||||
|
||||
|
||||
/**
|
||||
* Convert a byte array into a binary string.
|
||||
*
|
||||
* @param {Uint8Array|byteArray} data
|
||||
* @param {string} [delim="Space"]
|
||||
* @param {number} [padding=8]
|
||||
* @returns {string}
|
||||
*
|
||||
* @example
|
||||
* // returns "00010000 00100000 00110000"
|
||||
* toBinary([10,20,30]);
|
||||
*
|
||||
* // returns "00010000 00100000 00110000"
|
||||
* toBinary([10,20,30], ":");
|
||||
*/
|
||||
export function toBinary(data, delim="Space", padding=8) {
|
||||
if (!data) return "";
|
||||
|
||||
delim = Utils.charRep(delim);
|
||||
let output = "";
|
||||
|
||||
for (let i = 0; i < data.length; i++) {
|
||||
output += data[i].toString(2).padStart(padding, "0") + delim;
|
||||
}
|
||||
|
||||
if (delim.length) {
|
||||
return output.slice(0, -delim.length);
|
||||
} else {
|
||||
return output;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Convert a binary string into a byte array.
|
||||
*
|
||||
* @param {string} data
|
||||
* @param {string} [delim]
|
||||
* @param {number} [byteLen=8]
|
||||
* @returns {byteArray}
|
||||
*
|
||||
* @example
|
||||
* // returns [10,20,30]
|
||||
* fromBinary("00010000 00100000 00110000");
|
||||
*
|
||||
* // returns [10,20,30]
|
||||
* fromBinary("00010000:00100000:00110000", "Colon");
|
||||
*/
|
||||
export function fromBinary(data, delim="Space", byteLen=8) {
|
||||
const delimRegex = Utils.regexRep(delim);
|
||||
data = data.replace(delimRegex, "");
|
||||
|
||||
const output = [];
|
||||
for (let i = 0; i < data.length; i += byteLen) {
|
||||
output.push(parseInt(data.substr(i, byteLen), 2));
|
||||
}
|
||||
return output;
|
||||
}
|
||||
|
||||
@@ -25,6 +25,7 @@ export function bitOp (input, key, func, nullPreserving, scheme) {
|
||||
|
||||
for (let i = 0; i < input.length; i++) {
|
||||
k = key[i % key.length];
|
||||
if (scheme === "Cascade") k = input[i + 1] || 0;
|
||||
o = input[i];
|
||||
x = nullPreserving && (o === 0 || o === k) ? o : func(o, k);
|
||||
result.push(x);
|
||||
@@ -115,3 +116,9 @@ export function sub(operand, key) {
|
||||
const result = operand - key;
|
||||
return (result < 0) ? 256 + result : result;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Delimiter options for bitwise operations
|
||||
*/
|
||||
export const BITWISE_OP_DELIMS = ["Hex", "Decimal", "Binary", "Base64", "UTF8", "Latin1"];
|
||||
|
||||
15
src/core/lib/Braille.mjs
Normal file
15
src/core/lib/Braille.mjs
Normal file
@@ -0,0 +1,15 @@
|
||||
/**
|
||||
* Braille resources.
|
||||
*
|
||||
* @author n1474335 [n1474335@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
/**
|
||||
* Braille lookup table.
|
||||
*/
|
||||
export const BRAILLE_LOOKUP = {
|
||||
ascii: " A1B'K2L@CIF/MSP\"E3H9O6R^DJG>NTQ,*5<-U8V.%[$+X!&;:4\\0Z7(_?W]#Y)=",
|
||||
dot6: "⠀⠁⠂⠃⠄⠅⠆⠇⠈⠉⠊⠋⠌⠍⠎⠏⠐⠑⠒⠓⠔⠕⠖⠗⠘⠙⠚⠛⠜⠝⠞⠟⠠⠡⠢⠣⠤⠥⠦⠧⠨⠩⠪⠫⠬⠭⠮⠯⠰⠱⠲⠳⠴⠵⠶⠷⠸⠹⠺⠻⠼⠽⠾⠿"
|
||||
};
|
||||
37
src/core/lib/Decimal.mjs
Normal file
37
src/core/lib/Decimal.mjs
Normal file
@@ -0,0 +1,37 @@
|
||||
/**
|
||||
* Decimal functions.
|
||||
*
|
||||
* @author n1474335 [n1474335@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Utils from "../Utils";
|
||||
|
||||
|
||||
/**
|
||||
* Convert a string of decimal values into a byte array.
|
||||
*
|
||||
* @param {string} data
|
||||
* @param {string} [delim]
|
||||
* @returns {byteArray}
|
||||
*
|
||||
* @example
|
||||
* // returns [10,20,30]
|
||||
* fromDecimal("10 20 30");
|
||||
*
|
||||
* // returns [10,20,30]
|
||||
* fromDecimal("10:20:30", "Colon");
|
||||
*/
|
||||
export function fromDecimal(data, delim="Auto") {
|
||||
delim = Utils.charRep(delim);
|
||||
const output = [];
|
||||
let byteStr = data.split(delim);
|
||||
if (byteStr[byteStr.length-1] === "")
|
||||
byteStr = byteStr.slice(0, byteStr.length-1);
|
||||
|
||||
for (let i = 0; i < byteStr.length; i++) {
|
||||
output[i] = parseInt(byteStr[i], 10);
|
||||
}
|
||||
return output;
|
||||
}
|
||||
@@ -39,3 +39,21 @@ export function search (input, searchRegex, removeRegex, includeTotal) {
|
||||
|
||||
return output;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* URL regular expression
|
||||
*/
|
||||
const protocol = "[A-Z]+://",
|
||||
hostname = "[-\\w]+(?:\\.\\w[-\\w]*)+",
|
||||
port = ":\\d+",
|
||||
path = "/[^.!,?\"<>\\[\\]{}\\s\\x7F-\\xFF]*" +
|
||||
"(?:[.!,?]+[^.!,?\"<>\\[\\]{}\\s\\x7F-\\xFF]+)*";
|
||||
|
||||
export const URL_REGEX = new RegExp(protocol + hostname + "(?:" + port + ")?(?:" + path + ")?", "ig");
|
||||
|
||||
|
||||
/**
|
||||
* Domain name regular expression
|
||||
*/
|
||||
export const DOMAIN_REGEX = /\b((?=[a-z0-9-]{1,63}\.)(xn--)?[a-z0-9]+(-[a-z0-9]+)*\.)+[a-z]{2,63}\b/ig;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Byte representation functions.
|
||||
* Hexadecimal functions.
|
||||
*
|
||||
* @author n1474335 [n1474335@gmail.com]
|
||||
* @copyright Crown Copyright 2016
|
||||
@@ -83,8 +83,7 @@ export function toHexFast(data) {
|
||||
* // returns [10,20,30]
|
||||
* fromHex("0a:14:1e", "Colon");
|
||||
*/
|
||||
export function fromHex(data, delim, byteLen=2) {
|
||||
delim = delim || "Auto";
|
||||
export function fromHex(data, delim="Auto", byteLen=2) {
|
||||
if (delim !== "None") {
|
||||
const delimRegex = delim === "Auto" ? /[^a-f\d]/gi : Utils.regexRep(delim);
|
||||
data = data.replace(delimRegex, "");
|
||||
|
||||
@@ -3,6 +3,7 @@
|
||||
*
|
||||
* @author picapi
|
||||
* @author n1474335 [n1474335@gmail.com]
|
||||
* @author Klaxon [klaxon@veyr.com]
|
||||
* @copyright Crown Copyright 2016
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
@@ -109,8 +110,8 @@ export function ipv6CidrRange(cidr, includeNetworkInfo) {
|
||||
* @returns {string}
|
||||
*/
|
||||
export function ipv4HyphenatedRange(range, includeNetworkInfo, enumerateAddresses, allowLargeList) {
|
||||
const ip1 = strToIpv4(range[1]),
|
||||
ip2 = strToIpv4(range[2]);
|
||||
const ip1 = strToIpv4(range[0].split("-")[0].trim()),
|
||||
ip2 = strToIpv4(range[0].split("-")[1].trim());
|
||||
|
||||
let output = "";
|
||||
|
||||
@@ -162,8 +163,8 @@ Total addresses in range: ${(((ip2 - ip1) >>> 0) + 1)}
|
||||
* @returns {string}
|
||||
*/
|
||||
export function ipv6HyphenatedRange(range, includeNetworkInfo) {
|
||||
const ip1 = strToIpv6(range[1]),
|
||||
ip2 = strToIpv6(range[14]),
|
||||
const ip1 = strToIpv6(range[0].split("-")[0].trim()),
|
||||
ip2 = strToIpv6(range[0].split("-")[1].trim()),
|
||||
total = new Array(128).fill();
|
||||
|
||||
let output = "",
|
||||
@@ -188,6 +189,93 @@ export function ipv6HyphenatedRange(range, includeNetworkInfo) {
|
||||
return output;
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses a list of IPv4 addresses separated by a new line (\n) and displays information
|
||||
* about it.
|
||||
*
|
||||
* @param {RegExp} list
|
||||
* @param {boolean} includeNetworkInfo
|
||||
* @param {boolean} enumerateAddresses
|
||||
* @param {boolean} allowLargeList
|
||||
* @returns {string}
|
||||
*/
|
||||
export function ipv4ListedRange(match, includeNetworkInfo, enumerateAddresses, allowLargeList) {
|
||||
|
||||
let ipv4List = match[0].split("\n");
|
||||
ipv4List = ipv4List.filter(Boolean);
|
||||
|
||||
const ipv4CidrList = ipv4List.filter(function(a) {
|
||||
return a.includes("/");
|
||||
});
|
||||
for (let i = 0; i < ipv4CidrList.length; i++) {
|
||||
const network = strToIpv4(ipv4CidrList[i].split("/")[0]);
|
||||
const cidrRange = parseInt(ipv4CidrList[i].split("/")[1], 10);
|
||||
if (cidrRange < 0 || cidrRange > 31) {
|
||||
return "IPv4 CIDR must be less than 32";
|
||||
}
|
||||
const mask = ~(0xFFFFFFFF >>> cidrRange),
|
||||
cidrIp1 = network & mask,
|
||||
cidrIp2 = cidrIp1 | ~mask;
|
||||
ipv4List.splice(ipv4List.indexOf(ipv4CidrList[i]), 1);
|
||||
ipv4List.push(ipv4ToStr(cidrIp1), ipv4ToStr(cidrIp2));
|
||||
}
|
||||
|
||||
ipv4List = ipv4List.sort(ipv4Compare);
|
||||
const ip1 = ipv4List[0];
|
||||
const ip2 = ipv4List[ipv4List.length - 1];
|
||||
const range = [ip1 + " - " + ip2];
|
||||
return ipv4HyphenatedRange(range, includeNetworkInfo, enumerateAddresses, allowLargeList);
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses a list of IPv6 addresses separated by a new line (\n) and displays information
|
||||
* about it.
|
||||
*
|
||||
* @param {RegExp} list
|
||||
* @param {boolean} includeNetworkInfo
|
||||
* @returns {string}
|
||||
*/
|
||||
export function ipv6ListedRange(match, includeNetworkInfo) {
|
||||
|
||||
let ipv6List = match[0].split("\n");
|
||||
ipv6List = ipv6List.filter(function(str) {
|
||||
return str.trim();
|
||||
});
|
||||
for (let i =0; i < ipv6List.length; i++){
|
||||
ipv6List[i] = ipv6List[i].trim();
|
||||
}
|
||||
const ipv6CidrList = ipv6List.filter(function(a) {
|
||||
return a.includes("/");
|
||||
});
|
||||
|
||||
for (let i = 0; i < ipv6CidrList.length; i++) {
|
||||
|
||||
const network = strToIpv6(ipv6CidrList[i].split("/")[0]);
|
||||
const cidrRange = parseInt(ipv6CidrList[i].split("/")[1], 10);
|
||||
|
||||
if (cidrRange < 0 || cidrRange > 127) {
|
||||
return "IPv6 CIDR must be less than 128";
|
||||
}
|
||||
|
||||
const cidrIp1 = new Array(8),
|
||||
cidrIp2 = new Array(8);
|
||||
|
||||
const mask = genIpv6Mask(cidrRange);
|
||||
|
||||
for (let j = 0; j < 8; j++) {
|
||||
cidrIp1[j] = network[j] & mask[j];
|
||||
cidrIp2[j] = cidrIp1[j] | (~mask[j] & 0x0000FFFF);
|
||||
}
|
||||
ipv6List.splice(ipv6List.indexOf(ipv6CidrList[i]), 1);
|
||||
ipv6List.push(ipv6ToStr(cidrIp1), ipv6ToStr(cidrIp2));
|
||||
}
|
||||
ipv6List = ipv6List.sort(ipv6Compare);
|
||||
const ip1 = ipv6List[0];
|
||||
const ip2 = ipv6List[ipv6List.length - 1];
|
||||
const range = [ip1 + " - " + ip2];
|
||||
return ipv6HyphenatedRange(range, includeNetworkInfo);
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts an IPv4 address from string format to numerical format.
|
||||
*
|
||||
@@ -391,6 +479,37 @@ export function genIpv6Mask(cidr) {
|
||||
return mask;
|
||||
}
|
||||
|
||||
/**
|
||||
* Comparison operation for sorting of IPv4 addresses.
|
||||
*
|
||||
* @param {string} a
|
||||
* @param {string} b
|
||||
* @returns {number}
|
||||
*/
|
||||
export function ipv4Compare(a, b) {
|
||||
return strToIpv4(a) - strToIpv4(b);
|
||||
}
|
||||
|
||||
/**
|
||||
* Comparison operation for sorting of IPv6 addresses.
|
||||
*
|
||||
* @param {string} a
|
||||
* @param {string} b
|
||||
* @returns {number}
|
||||
*/
|
||||
export function ipv6Compare(a, b) {
|
||||
|
||||
const a_ = strToIpv6(a),
|
||||
b_ = strToIpv6(b);
|
||||
|
||||
for (let i = 0; i < a_.length; i++){
|
||||
if (a_[i] !== b_[i]){
|
||||
return a_[i] - b_[i];
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
const _LARGE_RANGE_ERROR = "The specified range contains more than 65,536 addresses. Running this query could crash your browser. If you want to run it, select the \"Allow large queries\" option. You are advised to turn off \"Auto Bake\" whilst editing large ranges.";
|
||||
|
||||
/**
|
||||
|
||||
@@ -265,9 +265,10 @@ class Magic {
|
||||
* performance)
|
||||
* @param {Object[]} [recipeConfig=[]] - The recipe configuration up to this point
|
||||
* @param {boolean} [useful=false] - Whether the current recipe should be scored highly
|
||||
* @param {string} [crib=null] - The regex crib provided by the user, for filtering the operation output
|
||||
* @returns {Object[]} - A sorted list of the recipes most likely to result in correct decoding
|
||||
*/
|
||||
async speculativeExecution(depth=0, extLang=false, intensive=false, recipeConfig=[], useful=false) {
|
||||
async speculativeExecution(depth=0, extLang=false, intensive=false, recipeConfig=[], useful=false, crib=null) {
|
||||
if (depth < 0) return [];
|
||||
|
||||
// Find any operations that can be run on this data
|
||||
@@ -284,9 +285,9 @@ class Magic {
|
||||
isUTF8: this.isUTF8(),
|
||||
entropy: this.calcEntropy(),
|
||||
matchingOps: matchingOps,
|
||||
useful: useful
|
||||
useful: useful,
|
||||
matchesCrib: crib && crib.test(this.inputStr)
|
||||
});
|
||||
|
||||
const prevOp = recipeConfig[recipeConfig.length - 1];
|
||||
|
||||
// Execute each of the matching operations, then recursively call the speculativeExecution()
|
||||
@@ -305,7 +306,7 @@ class Magic {
|
||||
|
||||
const magic = new Magic(output, this.opPatterns),
|
||||
speculativeResults = await magic.speculativeExecution(
|
||||
depth-1, extLang, intensive, [...recipeConfig, opConfig], op.useful);
|
||||
depth-1, extLang, intensive, [...recipeConfig, opConfig], op.useful, crib);
|
||||
|
||||
results = results.concat(speculativeResults);
|
||||
}));
|
||||
@@ -317,7 +318,7 @@ class Magic {
|
||||
await Promise.all(bfEncodings.map(async enc => {
|
||||
const magic = new Magic(enc.data, this.opPatterns),
|
||||
bfResults = await magic.speculativeExecution(
|
||||
depth-1, extLang, false, [...recipeConfig, enc.conf]);
|
||||
depth-1, extLang, false, [...recipeConfig, enc.conf], false, crib);
|
||||
|
||||
results = results.concat(bfResults);
|
||||
}));
|
||||
|
||||
78
src/core/lib/TLVParser.mjs
Normal file
78
src/core/lib/TLVParser.mjs
Normal file
@@ -0,0 +1,78 @@
|
||||
/**
|
||||
* Parser for Type-length-value data.
|
||||
*
|
||||
* @author gchq77703 []
|
||||
* @author n1474335 [n1474335@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
const defaults = {
|
||||
location: 0,
|
||||
bytesInLength: 1,
|
||||
basicEncodingRules: false
|
||||
};
|
||||
|
||||
/**
|
||||
* TLVParser library
|
||||
*/
|
||||
export default class TLVParser {
|
||||
|
||||
/**
|
||||
* TLVParser constructor
|
||||
*
|
||||
* @param {byteArray} input
|
||||
* @param {Object} options
|
||||
*/
|
||||
constructor(input, options) {
|
||||
this.input = input;
|
||||
Object.assign(this, defaults, options);
|
||||
}
|
||||
|
||||
/**
|
||||
* @returns {number}
|
||||
*/
|
||||
getLength() {
|
||||
if (this.basicEncodingRules) {
|
||||
const bit = this.input[this.location];
|
||||
if (bit & 0x80) {
|
||||
this.bytesInLength = bit & ~0x80;
|
||||
} else {
|
||||
this.location++;
|
||||
return bit & ~0x80;
|
||||
}
|
||||
}
|
||||
|
||||
let length = 0;
|
||||
|
||||
for (let i = 0; i < this.bytesInLength; i++) {
|
||||
length += this.input[this.location] * Math.pow(Math.pow(2, 8), i);
|
||||
this.location++;
|
||||
}
|
||||
|
||||
return length;
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {number} length
|
||||
* @returns {number[]}
|
||||
*/
|
||||
getValue(length) {
|
||||
const value = [];
|
||||
|
||||
for (let i = 0; i < length; i++) {
|
||||
if (this.location > this.input.length) return value;
|
||||
value.push(this.input[this.location]);
|
||||
this.location++;
|
||||
}
|
||||
|
||||
return value;
|
||||
}
|
||||
|
||||
/**
|
||||
* @returns {boolean}
|
||||
*/
|
||||
atEnd() {
|
||||
return this.input.length <= this.location;
|
||||
}
|
||||
}
|
||||
63
src/core/operations/A1Z26CipherDecode.mjs
Normal file
63
src/core/operations/A1Z26CipherDecode.mjs
Normal file
@@ -0,0 +1,63 @@
|
||||
/**
|
||||
* @author Jarmo van Lenthe [github.com/jarmovanlenthe]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import Utils from "../Utils";
|
||||
import {DELIM_OPTIONS} from "../lib/Delim";
|
||||
import OperationError from "../errors/OperationError";
|
||||
|
||||
/**
|
||||
* A1Z26 Cipher Decode operation
|
||||
*/
|
||||
class A1Z26CipherDecode extends Operation {
|
||||
|
||||
/**
|
||||
* A1Z26CipherDecode constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "A1Z26 Cipher Decode";
|
||||
this.module = "Ciphers";
|
||||
this.description = "Converts alphabet order numbers into their corresponding alphabet character.<br><br>e.g. <code>1</code> becomes <code>a</code> and <code>2</code> becomes <code>b</code>.";
|
||||
this.infoURL = "";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
{
|
||||
name: "Delimiter",
|
||||
type: "option",
|
||||
value: DELIM_OPTIONS
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} input
|
||||
* @param {Object[]} args
|
||||
* @returns {string}
|
||||
*/
|
||||
run(input, args) {
|
||||
const delim = Utils.charRep(args[0] || "Space");
|
||||
|
||||
if (input.length === 0) {
|
||||
return [];
|
||||
}
|
||||
|
||||
const bites = input.split(delim);
|
||||
let latin1 = "";
|
||||
for (let i = 0; i < bites.length; i++) {
|
||||
if (bites[i] < 1 || bites[i] > 26) {
|
||||
throw new OperationError("Error: all numbers must be between 1 and 26.");
|
||||
}
|
||||
latin1 += Utils.chr(parseInt(bites[i], 10) + 96);
|
||||
}
|
||||
return latin1;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default A1Z26CipherDecode;
|
||||
61
src/core/operations/A1Z26CipherEncode.mjs
Normal file
61
src/core/operations/A1Z26CipherEncode.mjs
Normal file
@@ -0,0 +1,61 @@
|
||||
/**
|
||||
* @author Jarmo van Lenthe [github.com/jarmovanlenthe]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import Utils from "../Utils";
|
||||
import {DELIM_OPTIONS} from "../lib/Delim";
|
||||
|
||||
/**
|
||||
* A1Z26 Cipher Encode operation
|
||||
*/
|
||||
class A1Z26CipherEncode extends Operation {
|
||||
|
||||
/**
|
||||
* A1Z26CipherEncode constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "A1Z26 Cipher Encode";
|
||||
this.module = "Ciphers";
|
||||
this.description = "Converts alphabet characters into their corresponding alphabet order number.<br><br>e.g. <code>a</code> becomes <code>1</code> and <code>b</code> becomes <code>2</code>.<br><br>Non-alphabet characters are dropped.";
|
||||
this.infoURL = "";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
{
|
||||
name: "Delimiter",
|
||||
type: "option",
|
||||
value: DELIM_OPTIONS
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} input
|
||||
* @param {Object[]} args
|
||||
* @returns {string}
|
||||
*/
|
||||
run(input, args) {
|
||||
const delim = Utils.charRep(args[0] || "Space");
|
||||
let output = "";
|
||||
|
||||
const sanitizedinput = input.toLowerCase(),
|
||||
charcode = Utils.strToCharcode(sanitizedinput);
|
||||
|
||||
for (let i = 0; i < charcode.length; i++) {
|
||||
const ordinal = charcode[i] - 96;
|
||||
|
||||
if (ordinal > 0 && ordinal <= 26) {
|
||||
output += ordinal.toString(10) + delim;
|
||||
}
|
||||
}
|
||||
return output.slice(0, -delim.length);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default A1Z26CipherEncode;
|
||||
@@ -6,7 +6,7 @@
|
||||
|
||||
import Operation from "../Operation";
|
||||
import Utils from "../Utils";
|
||||
import { bitOp, add } from "../lib/BitwiseOp";
|
||||
import { bitOp, add, BITWISE_OP_DELIMS } from "../lib/BitwiseOp";
|
||||
|
||||
/**
|
||||
* ADD operation
|
||||
@@ -22,6 +22,7 @@ class ADD extends Operation {
|
||||
this.name = "ADD";
|
||||
this.module = "Default";
|
||||
this.description = "ADD the input with the given key (e.g. <code>fe023da5</code>), MOD 255";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bitwise_operation#Bitwise_operators";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
@@ -29,7 +30,7 @@ class ADD extends Operation {
|
||||
"name": "Key",
|
||||
"type": "toggleString",
|
||||
"value": "",
|
||||
"toggleValues": ["Hex", "Base64", "UTF8", "Latin1"]
|
||||
"toggleValues": BITWISE_OP_DELIMS
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
@@ -23,6 +23,7 @@ class AESDecrypt extends Operation {
|
||||
this.name = "AES Decrypt";
|
||||
this.module = "Ciphers";
|
||||
this.description = "Advanced Encryption Standard (AES) is a U.S. Federal Information Processing Standard (FIPS). It was selected after a 5-year process where 15 competing designs were evaluated.<br><br><b>Key:</b> The following algorithms will be used based on the size of the key:<ul><li>16 bytes = AES-128</li><li>24 bytes = AES-192</li><li>32 bytes = AES-256</li></ul><br><br><b>IV:</b> The Initialization Vector should be 16 bytes long. If not entered, it will default to 16 null bytes.<br><br><b>Padding:</b> In CBC and ECB mode, PKCS#7 padding will be used.<br><br><b>GCM Tag:</b> This field is ignored unless 'GCM' mode is used.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Advanced_Encryption_Standard";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -23,6 +23,7 @@ class AESEncrypt extends Operation {
|
||||
this.name = "AES Encrypt";
|
||||
this.module = "Ciphers";
|
||||
this.description = "Advanced Encryption Standard (AES) is a U.S. Federal Information Processing Standard (FIPS). It was selected after a 5-year process where 15 competing designs were evaluated.<br><br><b>Key:</b> The following algorithms will be used based on the size of the key:<ul><li>16 bytes = AES-128</li><li>24 bytes = AES-192</li><li>32 bytes = AES-256</li></ul>You can generate a password-based key using one of the KDF operations.<br><br><b>IV:</b> The Initialization Vector should be 16 bytes long. If not entered, it will default to 16 null bytes.<br><br><b>Padding:</b> In CBC and ECB mode, PKCS#7 padding will be used.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Advanced_Encryption_Standard";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -6,7 +6,7 @@
|
||||
|
||||
import Operation from "../Operation";
|
||||
import Utils from "../Utils";
|
||||
import { bitOp, and } from "../lib/BitwiseOp";
|
||||
import { bitOp, and, BITWISE_OP_DELIMS } from "../lib/BitwiseOp";
|
||||
|
||||
/**
|
||||
* AND operation
|
||||
@@ -22,6 +22,7 @@ class AND extends Operation {
|
||||
this.name = "AND";
|
||||
this.module = "Default";
|
||||
this.description = "AND the input with the given key.<br>e.g. <code>fe023da5</code>";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bitwise_operation#AND";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
@@ -29,7 +30,7 @@ class AND extends Operation {
|
||||
"name": "Key",
|
||||
"type": "toggleString",
|
||||
"value": "",
|
||||
"toggleValues": ["Hex", "Base64", "UTF8", "Latin1"]
|
||||
"toggleValues": BITWISE_OP_DELIMS
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
@@ -21,6 +21,7 @@ class Adler32Checksum extends Operation {
|
||||
this.name = "Adler-32 Checksum";
|
||||
this.module = "Hashing";
|
||||
this.description = "Adler-32 is a checksum algorithm which was invented by Mark Adler in 1995, and is a modification of the Fletcher checksum. Compared to a cyclic redundancy check of the same length, it trades reliability for speed (preferring the latter).<br><br>Adler-32 is more reliable than Fletcher-16, and slightly less reliable than Fletcher-32.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Adler-32";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -22,6 +22,7 @@ class AffineCipherDecode extends Operation {
|
||||
this.name = "Affine Cipher Decode";
|
||||
this.module = "Ciphers";
|
||||
this.description = "The Affine cipher is a type of monoalphabetic substitution cipher. To decrypt, each letter in an alphabet is mapped to its numeric equivalent, decrypted by a mathematical function, and converted back to a letter.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Affine_cipher";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -21,6 +21,7 @@ class AffineCipherEncode extends Operation {
|
||||
this.name = "Affine Cipher Encode";
|
||||
this.module = "Ciphers";
|
||||
this.description = "The Affine cipher is a type of monoalphabetic substitution cipher, wherein each letter in an alphabet is mapped to its numeric equivalent, encrypted using simple mathematical function, <code>(ax + b) % 26</code>, and converted back to a letter.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Affine_cipher";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -21,6 +21,7 @@ class AnalyseHash extends Operation {
|
||||
this.name = "Analyse hash";
|
||||
this.module = "Hashing";
|
||||
this.description = "Tries to determine information about a given hash and suggests which algorithm may have been used to generate it based on its length.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Comparison_of_cryptographic_hash_functions";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -21,6 +21,7 @@ class AtbashCipher extends Operation {
|
||||
this.name = "Atbash Cipher";
|
||||
this.module = "Ciphers";
|
||||
this.description = "Atbash is a mono-alphabetic substitution cipher originally used to encode the Hebrew alphabet. It has been modified here for use with the Latin alphabet.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Atbash";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -22,6 +22,7 @@ class BSONDeserialise extends Operation {
|
||||
this.name = "BSON deserialise";
|
||||
this.module = "BSON";
|
||||
this.description = "BSON is a computer data interchange format used mainly as a data storage and network transfer format in the MongoDB database. It is a binary form for representing simple data structures, associative arrays (called objects or documents in MongoDB), and various data types of specific interest to MongoDB. The name 'BSON' is based on the term JSON and stands for 'Binary JSON'.<br><br>Input data should be in a raw bytes format.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/BSON";
|
||||
this.inputType = "ArrayBuffer";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -22,6 +22,7 @@ class BSONSerialise extends Operation {
|
||||
this.name = "BSON serialise";
|
||||
this.module = "BSON";
|
||||
this.description = "BSON is a computer data interchange format used mainly as a data storage and network transfer format in the MongoDB database. It is a binary form for representing simple data structures, associative arrays (called objects or documents in MongoDB), and various data types of specific interest to MongoDB. The name 'BSON' is based on the term JSON and stands for 'Binary JSON'.<br><br>Input data should be valid JSON.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/BSON";
|
||||
this.inputType = "string";
|
||||
this.outputType = "ArrayBuffer";
|
||||
this.args = [];
|
||||
|
||||
@@ -21,6 +21,7 @@ class Bcrypt extends Operation {
|
||||
this.name = "Bcrypt";
|
||||
this.module = "Hashing";
|
||||
this.description = "bcrypt is a password hashing function designed by Niels Provos and David Mazi\xe8res, based on the Blowfish cipher, and presented at USENIX in 1999. Besides incorporating a salt to protect against rainbow table attacks, bcrypt is an adaptive function: over time, the iteration count (rounds) can be increased to make it slower, so it remains resistant to brute-force search attacks even with increasing computation power.<br><br>Enter the password in the input to generate its hash.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bcrypt";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -21,6 +21,7 @@ class BcryptCompare extends Operation {
|
||||
this.name = "Bcrypt compare";
|
||||
this.module = "Hashing";
|
||||
this.description = "Tests whether the input matches the given bcrypt hash. To test multiple possible passwords, use the 'Fork' operation.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bcrypt";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -22,6 +22,7 @@ class BcryptParse extends Operation {
|
||||
this.name = "Bcrypt parse";
|
||||
this.module = "Hashing";
|
||||
this.description = "Parses a bcrypt hash to determine the number of rounds used, the salt, and the password hash.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bcrypt";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -22,6 +22,7 @@ class BifidCipherDecode extends Operation {
|
||||
this.name = "Bifid Cipher Decode";
|
||||
this.module = "Ciphers";
|
||||
this.description = "The Bifid cipher is a cipher which uses a Polybius square in conjunction with transposition, which can be fairly difficult to decipher without knowing the alphabet keyword.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bifid_cipher";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -22,6 +22,7 @@ class BifidCipherEncode extends Operation {
|
||||
this.name = "Bifid Cipher Encode";
|
||||
this.module = "Ciphers";
|
||||
this.description = "The Bifid cipher is a cipher which uses a Polybius square in conjunction with transposition, which can be fairly difficult to decipher without knowing the alphabet keyword.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bifid_cipher";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -20,6 +20,7 @@ class BitShiftLeft extends Operation {
|
||||
this.name = "Bit shift left";
|
||||
this.module = "Default";
|
||||
this.description = "Shifts the bits in each byte towards the left by the specified amount.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bitwise_operation#Bit_shifts";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
|
||||
@@ -20,6 +20,7 @@ class BitShiftRight extends Operation {
|
||||
this.name = "Bit shift right";
|
||||
this.module = "Default";
|
||||
this.description = "Shifts the bits in each byte towards the right by the specified amount.<br><br><i>Logical shifts</i> replace the leftmost bits with zeros.<br><i>Arithmetic shifts</i> preserve the most significant bit (MSB) of the original byte keeping the sign the same (positive or negative).";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bitwise_operation#Bit_shifts";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
|
||||
@@ -38,6 +38,7 @@ class BlowfishDecrypt extends Operation {
|
||||
this.name = "Blowfish Decrypt";
|
||||
this.module = "Ciphers";
|
||||
this.description = "Blowfish is a symmetric-key block cipher designed in 1993 by Bruce Schneier and included in a large number of cipher suites and encryption products. AES now receives more attention.<br><br><b>IV:</b> The Initialization Vector should be 8 bytes long. If not entered, it will default to 8 null bytes.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Blowfish_(cipher)";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -39,6 +39,7 @@ class BlowfishEncrypt extends Operation {
|
||||
this.name = "Blowfish Encrypt";
|
||||
this.module = "Ciphers";
|
||||
this.description = "Blowfish is a symmetric-key block cipher designed in 1993 by Bruce Schneier and included in a large number of cipher suites and encryption products. AES now receives more attention.<br><br><b>IV:</b> The Initialization Vector should be 8 bytes long. If not entered, it will default to 8 null bytes.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Blowfish_(cipher)";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import bzip2 from "../vendor/bzip2.js";
|
||||
import bzip2 from "../vendor/bzip2";
|
||||
import OperationError from "../errors/OperationError";
|
||||
|
||||
/**
|
||||
@@ -22,6 +22,7 @@ class Bzip2Decompress extends Operation {
|
||||
this.name = "Bzip2 Decompress";
|
||||
this.module = "Compression";
|
||||
this.description = "Decompresses data using the Bzip2 algorithm.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Bzip2";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -21,6 +21,7 @@ class CRC16Checksum extends Operation {
|
||||
this.name = "CRC-16 Checksum";
|
||||
this.module = "Hashing";
|
||||
this.description = "A cyclic redundancy check (CRC) is an error-detecting code commonly used in digital networks and storage devices to detect accidental changes to raw data.<br><br>The CRC was invented by W. Wesley Peterson in 1961.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Cyclic_redundancy_check";
|
||||
this.inputType = "ArrayBuffer";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -21,6 +21,7 @@ class CRC32Checksum extends Operation {
|
||||
this.name = "CRC-32 Checksum";
|
||||
this.module = "Hashing";
|
||||
this.description = "A cyclic redundancy check (CRC) is an error-detecting code commonly used in digital networks and storage devices to detect accidental changes to raw data.<br><br>The CRC was invented by W. Wesley Peterson in 1961; the 32-bit CRC function of Ethernet and many other standards is the work of several researchers and was published in 1975.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Cyclic_redundancy_check";
|
||||
this.inputType = "ArrayBuffer";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -23,6 +23,7 @@ class CSSSelector extends Operation {
|
||||
this.name = "CSS selector";
|
||||
this.module = "Code";
|
||||
this.description = "Extract information from an HTML document with a CSS selector";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Cascading_Style_Sheets#Selector";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
80
src/core/operations/CSVToJSON.mjs
Normal file
80
src/core/operations/CSVToJSON.mjs
Normal file
@@ -0,0 +1,80 @@
|
||||
/**
|
||||
* @author n1474335 [n1474335@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import OperationError from "../errors/OperationError";
|
||||
import Utils from "../Utils";
|
||||
|
||||
/**
|
||||
* CSV to JSON operation
|
||||
*/
|
||||
class CSVToJSON extends Operation {
|
||||
|
||||
/**
|
||||
* CSVToJSON constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "CSV to JSON";
|
||||
this.module = "Default";
|
||||
this.description = "Converts a CSV file to JSON format.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Comma-separated_values";
|
||||
this.inputType = "string";
|
||||
this.outputType = "JSON";
|
||||
this.args = [
|
||||
{
|
||||
name: "Cell delimiters",
|
||||
type: "binaryShortString",
|
||||
value: ","
|
||||
},
|
||||
{
|
||||
name: "Row delimiters",
|
||||
type: "binaryShortString",
|
||||
value: "\\r\\n"
|
||||
},
|
||||
{
|
||||
name: "Format",
|
||||
type: "option",
|
||||
value: ["Array of dictionaries", "Array of arrays"]
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} input
|
||||
* @param {Object[]} args
|
||||
* @returns {JSON}
|
||||
*/
|
||||
run(input, args) {
|
||||
const [cellDelims, rowDelims, format] = args;
|
||||
let json, header;
|
||||
|
||||
try {
|
||||
json = Utils.parseCSV(input, cellDelims.split(""), rowDelims.split(""));
|
||||
} catch (err) {
|
||||
throw new OperationError("Unable to parse CSV: " + err);
|
||||
}
|
||||
|
||||
switch (format) {
|
||||
case "Array of dictionaries":
|
||||
header = json[0];
|
||||
return json.slice(1).map(row => {
|
||||
const obj = {};
|
||||
header.forEach((h, i) => {
|
||||
obj[h] = row[i];
|
||||
});
|
||||
return obj;
|
||||
});
|
||||
case "Array of arrays":
|
||||
default:
|
||||
return json;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default CSVToJSON;
|
||||
@@ -21,6 +21,7 @@ class CTPH extends Operation {
|
||||
this.name = "CTPH";
|
||||
this.module = "Hashing";
|
||||
this.description = "Context Triggered Piecewise Hashing, also called Fuzzy Hashing, can match inputs that have homologies. Such inputs have sequences of identical bytes in the same order, although bytes in between these sequences may be different in both content and length.<br><br>CTPH was originally based on the work of Dr. Andrew Tridgell and a spam email detector called SpamSum. This method was adapted by Jesse Kornblum and published at the DFRWS conference in 2006 in a paper 'Identifying Almost Identical Files Using Context Triggered Piecewise Hashing'.";
|
||||
this.infoURL = "https://forensicswiki.org/wiki/Context_Triggered_Piecewise_Hashing";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -21,6 +21,7 @@ class CartesianProduct extends Operation {
|
||||
this.name = "Cartesian Product";
|
||||
this.module = "Default";
|
||||
this.description = "Calculates the cartesian product of multiple sets of data, returning all possible combinations.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Cartesian_product";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -21,7 +21,7 @@ class ChangeIPFormat extends Operation {
|
||||
super();
|
||||
|
||||
this.name = "Change IP format";
|
||||
this.module = "JSBN";
|
||||
this.module = "Default";
|
||||
this.description = "Convert an IP address from one format to another, e.g. <code>172.20.23.54</code> to <code>ac141736</code>";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
@@ -29,12 +29,12 @@ class ChangeIPFormat extends Operation {
|
||||
{
|
||||
"name": "Input format",
|
||||
"type": "option",
|
||||
"value": ["Hex", "Raw"]
|
||||
"value": ["Dotted Decimal", "Decimal", "Hex"]
|
||||
},
|
||||
{
|
||||
"name": "Output format",
|
||||
"type": "option",
|
||||
"value": ["Hex", "Raw"]
|
||||
"value": ["Dotted Decimal", "Decimal", "Hex"]
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
@@ -20,6 +20,7 @@ class ChiSquare extends Operation {
|
||||
this.name = "Chi Square";
|
||||
this.module = "Default";
|
||||
this.description = "Calculates the Chi Square distribution of values.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Chi-squared_distribution";
|
||||
this.inputType = "ArrayBuffer";
|
||||
this.outputType = "number";
|
||||
this.args = [];
|
||||
|
||||
58
src/core/operations/CitrixCTX1Decode.mjs
Normal file
58
src/core/operations/CitrixCTX1Decode.mjs
Normal file
@@ -0,0 +1,58 @@
|
||||
/**
|
||||
* @author bwhitn [brian.m.whitney@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import OperationError from "../errors/OperationError";
|
||||
import cptable from "../vendor/js-codepage/cptable.js";
|
||||
|
||||
/**
|
||||
* Citrix CTX1 Decode operation
|
||||
*/
|
||||
class CitrixCTX1Decode extends Operation {
|
||||
|
||||
/**
|
||||
* CitrixCTX1Decode constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "Citrix CTX1 Decode";
|
||||
this.module = "Encodings";
|
||||
this.description = "Decodes strings in a Citrix CTX1 password format to plaintext.";
|
||||
this.infoURL = "https://www.reddit.com/r/AskNetsec/comments/1s3r6y/citrix_ctx1_hash_decoding/";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {byteArray} input
|
||||
* @param {Object[]} args
|
||||
* @returns {string}
|
||||
*/
|
||||
run(input, args) {
|
||||
if (input.length % 4 !== 0) {
|
||||
throw new OperationError("Incorrect hash length");
|
||||
}
|
||||
const revinput = input.reverse();
|
||||
const result = [];
|
||||
let temp = 0;
|
||||
for (let i = 0; i < revinput.length; i += 2) {
|
||||
if (i + 2 >= revinput.length) {
|
||||
temp = 0;
|
||||
} else {
|
||||
temp = ((revinput[i + 2] - 0x41) & 0xf) ^ (((revinput[i + 3]- 0x41) << 4) & 0xf0);
|
||||
}
|
||||
temp = (((revinput[i] - 0x41) & 0xf) ^ (((revinput[i + 1] - 0x41) << 4) & 0xf0)) ^ 0xa5 ^ temp;
|
||||
result.push(temp);
|
||||
}
|
||||
// Decodes a utf-16le string
|
||||
return cptable.utils.decode(1200, result.reverse());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default CitrixCTX1Decode;
|
||||
50
src/core/operations/CitrixCTX1Encode.mjs
Normal file
50
src/core/operations/CitrixCTX1Encode.mjs
Normal file
@@ -0,0 +1,50 @@
|
||||
/**
|
||||
* @author bwhitn [brian.m.whitney@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import cptable from "../vendor/js-codepage/cptable.js";
|
||||
|
||||
/**
|
||||
* Citrix CTX1 Encode operation
|
||||
*/
|
||||
class CitrixCTX1Encode extends Operation {
|
||||
|
||||
/**
|
||||
* CitrixCTX1Encode constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "Citrix CTX1 Encode";
|
||||
this.module = "Encodings";
|
||||
this.description = "Encodes strings to Citrix CTX1 password format.";
|
||||
this.infoURL = "https://www.reddit.com/r/AskNetsec/comments/1s3r6y/citrix_ctx1_hash_decoding/";
|
||||
this.inputType = "string";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} input
|
||||
* @param {Object[]} args
|
||||
* @returns {byteArray}
|
||||
*/
|
||||
run(input, args) {
|
||||
const utf16pass = Array.from(cptable.utils.encode(1200, input));
|
||||
const result = [];
|
||||
let temp = 0;
|
||||
for (let i = 0; i < utf16pass.length; i++) {
|
||||
temp = utf16pass[i] ^ 0xa5 ^ temp;
|
||||
result.push(((temp >>> 4) & 0xf) + 0x41);
|
||||
result.push((temp & 0xf) + 0x41);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default CitrixCTX1Encode;
|
||||
@@ -24,6 +24,7 @@ class CompareCTPHHashes extends Operation {
|
||||
this.name = "Compare CTPH hashes";
|
||||
this.module = "Hashing";
|
||||
this.description = "Compares two Context Triggered Piecewise Hashing (CTPH) fuzzy hashes to determine the similarity between them on a scale of 0 to 100.";
|
||||
this.infoURL = "https://forensicswiki.org/wiki/Context_Triggered_Piecewise_Hashing";
|
||||
this.inputType = "string";
|
||||
this.outputType = "Number";
|
||||
this.args = [
|
||||
|
||||
@@ -24,6 +24,7 @@ class CompareSSDEEPHashes extends Operation {
|
||||
this.name = "Compare SSDEEP hashes";
|
||||
this.module = "Hashing";
|
||||
this.description = "Compares two SSDEEP fuzzy hashes to determine the similarity between them on a scale of 0 to 100.";
|
||||
this.infoURL = "https://forensicswiki.org/wiki/Ssdeep";
|
||||
this.inputType = "string";
|
||||
this.outputType = "Number";
|
||||
this.args = [
|
||||
|
||||
@@ -20,6 +20,7 @@ class ConvertArea extends Operation {
|
||||
this.name = "Convert area";
|
||||
this.module = "Default";
|
||||
this.description = "Converts a unit of area to another format.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Orders_of_magnitude_(area)";
|
||||
this.inputType = "BigNumber";
|
||||
this.outputType = "BigNumber";
|
||||
this.args = [
|
||||
|
||||
@@ -20,6 +20,7 @@ class ConvertDataUnits extends Operation {
|
||||
this.name = "Convert data units";
|
||||
this.module = "Default";
|
||||
this.description = "Converts a unit of data to another format.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Orders_of_magnitude_(data)";
|
||||
this.inputType = "BigNumber";
|
||||
this.outputType = "BigNumber";
|
||||
this.args = [
|
||||
|
||||
@@ -20,6 +20,7 @@ class ConvertDistance extends Operation {
|
||||
this.name = "Convert distance";
|
||||
this.module = "Default";
|
||||
this.description = "Converts a unit of distance to another format.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Orders_of_magnitude_(length)";
|
||||
this.inputType = "BigNumber";
|
||||
this.outputType = "BigNumber";
|
||||
this.args = [
|
||||
|
||||
@@ -20,6 +20,7 @@ class ConvertMass extends Operation {
|
||||
this.name = "Convert mass";
|
||||
this.module = "Default";
|
||||
this.description = "Converts a unit of mass to another format.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Orders_of_magnitude_(mass)";
|
||||
this.inputType = "BigNumber";
|
||||
this.outputType = "BigNumber";
|
||||
this.args = [
|
||||
|
||||
@@ -20,6 +20,7 @@ class ConvertSpeed extends Operation {
|
||||
this.name = "Convert speed";
|
||||
this.module = "Default";
|
||||
this.description = "Converts a unit of speed to another format.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Orders_of_magnitude_(speed)";
|
||||
this.inputType = "BigNumber";
|
||||
this.outputType = "BigNumber";
|
||||
this.args = [
|
||||
|
||||
@@ -23,6 +23,7 @@ class DESDecrypt extends Operation {
|
||||
this.name = "DES Decrypt";
|
||||
this.module = "Ciphers";
|
||||
this.description = "DES is a previously dominant algorithm for encryption, and was published as an official U.S. Federal Information Processing Standard (FIPS). It is now considered to be insecure due to its small key size.<br><br><b>Key:</b> DES uses a key length of 8 bytes (64 bits).<br>Triple DES uses a key length of 24 bytes (192 bits).<br><br><b>IV:</b> The Initialization Vector should be 8 bytes long. If not entered, it will default to 8 null bytes.<br><br><b>Padding:</b> In CBC and ECB mode, PKCS#7 padding will be used.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Data_Encryption_Standard";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -23,6 +23,7 @@ class DESEncrypt extends Operation {
|
||||
this.name = "DES Encrypt";
|
||||
this.module = "Ciphers";
|
||||
this.description = "DES is a previously dominant algorithm for encryption, and was published as an official U.S. Federal Information Processing Standard (FIPS). It is now considered to be insecure due to its small key size.<br><br><b>Key:</b> DES uses a key length of 8 bytes (64 bits).<br>Triple DES uses a key length of 24 bytes (192 bits).<br><br>You can generate a password-based key using one of the KDF operations.<br><br><b>IV:</b> The Initialization Vector should be 8 bytes long. If not entered, it will default to 8 null bytes.<br><br><b>Padding:</b> In CBC and ECB mode, PKCS#7 padding will be used.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Data_Encryption_Standard";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
51
src/core/operations/DechunkHTTPResponse.mjs
Normal file
51
src/core/operations/DechunkHTTPResponse.mjs
Normal file
@@ -0,0 +1,51 @@
|
||||
/**
|
||||
* @author sevzero [sevzero@protonmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
|
||||
/**
|
||||
* Dechunk HTTP response operation
|
||||
*/
|
||||
class DechunkHTTPResponse extends Operation {
|
||||
|
||||
/**
|
||||
* DechunkHTTPResponse constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "Dechunk HTTP response";
|
||||
this.module = "Default";
|
||||
this.description = "Parses an HTTP response transferred using Transfer-Encoding: Chunked";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Chunked_transfer_encoding";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} input
|
||||
* @param {Object[]} args
|
||||
* @returns {string}
|
||||
*/
|
||||
run(input, args) {
|
||||
const chunks = [];
|
||||
let chunkSizeEnd = input.indexOf("\n") + 1;
|
||||
const lineEndings = input.charAt(chunkSizeEnd - 2) === "\r" ? "\r\n" : "\n";
|
||||
const lineEndingsLength = lineEndings.length;
|
||||
let chunkSize = parseInt(input.slice(0, chunkSizeEnd), 16);
|
||||
while (!isNaN(chunkSize)) {
|
||||
chunks.push(input.slice(chunkSizeEnd, chunkSize + chunkSizeEnd));
|
||||
input = input.slice(chunkSizeEnd + chunkSize + lineEndingsLength);
|
||||
chunkSizeEnd = input.indexOf(lineEndings) + lineEndingsLength;
|
||||
chunkSize = parseInt(input.slice(0, chunkSizeEnd), 16);
|
||||
}
|
||||
return chunks.join("") + input;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default DechunkHTTPResponse;
|
||||
@@ -20,6 +20,7 @@ class DecodeNetBIOSName extends Operation {
|
||||
this.name = "Decode NetBIOS Name";
|
||||
this.module = "Default";
|
||||
this.description = "NetBIOS names as seen across the client interface to NetBIOS are exactly 16 bytes long. Within the NetBIOS-over-TCP protocols, a longer representation is used.<br><br>There are two levels of encoding. The first level maps a NetBIOS name into a domain system name. The second level maps the domain system name into the 'compressed' representation required for interaction with the domain name system.<br><br>This operation decodes the first level of encoding. See RFC 1001 for full details.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/NetBIOS";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
|
||||
@@ -29,6 +29,7 @@ class DecodeText extends Operation {
|
||||
Object.keys(IO_FORMAT).map(e => `<li>${e}</li>`).join("\n"),
|
||||
"</ul>",
|
||||
].join("\n");
|
||||
this.infoURL = "https://wikipedia.org/wiki/Character_encoding";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
102
src/core/operations/DefangURL.mjs
Normal file
102
src/core/operations/DefangURL.mjs
Normal file
@@ -0,0 +1,102 @@
|
||||
/**
|
||||
* @author arnydo [arnydo@protonmail.com]
|
||||
* @author n1474335 [n1474335@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import {URL_REGEX, DOMAIN_REGEX} from "../lib/Extract";
|
||||
|
||||
/**
|
||||
* DefangURL operation
|
||||
*/
|
||||
class DefangURL extends Operation {
|
||||
|
||||
/**
|
||||
* DefangURL constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "Defang URL";
|
||||
this.module = "Default";
|
||||
this.description = "Takes a Universal Resource Locator (URL) and 'Defangs' it; meaning the URL becomes invalid, neutralising the risk of accidentally clicking on a malicious link.<br><br>This is often used when dealing with malicious links or IOCs.<br><br>Works well when combined with the 'Extract URLs' operation.";
|
||||
this.infoURL = "https://isc.sans.edu/forums/diary/Defang+all+the+things/22744/";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
{
|
||||
name: "Escape dots",
|
||||
type: "boolean",
|
||||
value: true
|
||||
},
|
||||
{
|
||||
name: "Escape http",
|
||||
type: "boolean",
|
||||
value: true
|
||||
},
|
||||
{
|
||||
name: "Escape ://",
|
||||
type: "boolean",
|
||||
value: true
|
||||
},
|
||||
{
|
||||
name: "Process",
|
||||
type: "option",
|
||||
value: ["Valid domains and full URLs", "Only full URLs", "Everything"]
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} input
|
||||
* @param {Object[]} args
|
||||
* @returns {string}
|
||||
*/
|
||||
run(input, args) {
|
||||
const [dots, http, slashes, process] = args;
|
||||
|
||||
switch (process) {
|
||||
case "Valid domains and full URLs":
|
||||
input = input.replace(URL_REGEX, x => {
|
||||
return defangURL(x, dots, http, slashes);
|
||||
});
|
||||
input = input.replace(DOMAIN_REGEX, x => {
|
||||
return defangURL(x, dots, http, slashes);
|
||||
});
|
||||
break;
|
||||
case "Only full URLs":
|
||||
input = input.replace(URL_REGEX, x => {
|
||||
return defangURL(x, dots, http, slashes);
|
||||
});
|
||||
break;
|
||||
case "Everything":
|
||||
input = defangURL(input, dots, http, slashes);
|
||||
break;
|
||||
}
|
||||
|
||||
return input;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Defangs a given URL
|
||||
*
|
||||
* @param {string} url
|
||||
* @param {boolean} dots
|
||||
* @param {boolean} http
|
||||
* @param {boolean} slashes
|
||||
* @returns {string}
|
||||
*/
|
||||
function defangURL(url, dots, http, slashes) {
|
||||
if (dots) url = url.replace(/\./g, "[.]");
|
||||
if (http) url = url.replace(/http/gi, "hxxp");
|
||||
if (slashes) url = url.replace(/:\/\//g, "[://]");
|
||||
|
||||
return url;
|
||||
}
|
||||
|
||||
export default DefangURL;
|
||||
@@ -21,7 +21,8 @@ class DeriveEVPKey extends Operation {
|
||||
|
||||
this.name = "Derive EVP key";
|
||||
this.module = "Ciphers";
|
||||
this.description = "EVP is a password-based key derivation function (PBKDF) used extensively in OpenSSL. In many applications of cryptography, user security is ultimately dependent on a password, and because a password usually can't be used directly as a cryptographic key, some processing is required.<br><br>A salt provides a large set of keys for any given password, and an iteration count increases the cost of producing keys from a password, thereby also increasing the difficulty of attack.<br><br>If you leave the salt argument empty, a random salt will be generated.";
|
||||
this.description = "This operation performs a password-based key derivation function (PBKDF) used extensively in OpenSSL. In many applications of cryptography, user security is ultimately dependent on a password, and because a password usually can't be used directly as a cryptographic key, some processing is required.<br><br>A salt provides a large set of keys for any given password, and an iteration count increases the cost of producing keys from a password, thereby also increasing the difficulty of attack.<br><br>If you leave the salt argument empty, a random salt will be generated.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Key_derivation_function";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -22,6 +22,7 @@ class DerivePBKDF2Key extends Operation {
|
||||
this.name = "Derive PBKDF2 key";
|
||||
this.module = "Ciphers";
|
||||
this.description = "PBKDF2 is a password-based key derivation function. It is part of RSA Laboratories' Public-Key Cryptography Standards (PKCS) series, specifically PKCS #5 v2.0, also published as Internet Engineering Task Force's RFC 2898.<br><br>In many applications of cryptography, user security is ultimately dependent on a password, and because a password usually can't be used directly as a cryptographic key, some processing is required.<br><br>A salt provides a large set of keys for any given password, and an iteration count increases the cost of producing keys from a password, thereby also increasing the difficulty of attack.<br><br>If you leave the salt argument empty, a random salt will be generated.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/PBKDF2";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -21,6 +21,7 @@ class DetectFileType extends Operation {
|
||||
this.name = "Detect File Type";
|
||||
this.module = "Default";
|
||||
this.description = "Attempts to guess the MIME (Multipurpose Internet Mail Extensions) type of the data based on 'magic bytes'.<br><br>Currently supports the following file types: 7z, amr, avi, bmp, bz2, class, cr2, crx, dex, dmg, doc, elf, eot, epub, exe, flac, flv, gif, gz, ico, iso, jpg, jxr, m4a, m4v, mid, mkv, mov, mp3, mp4, mpg, ogg, otf, pdf, png, ppt, ps, psd, rar, rtf, sqlite, swf, tar, tar.z, tif, ttf, utf8, vmdk, wav, webm, webp, wmv, woff, woff2, xls, xz, zip.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/List_of_file_signatures";
|
||||
this.inputType = "ArrayBuffer";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -23,6 +23,7 @@ class Diff extends Operation {
|
||||
this.name = "Diff";
|
||||
this.module = "Diff";
|
||||
this.description = "Compares two inputs (separated by the specified delimiter) and highlights the differences between them.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/File_comparison";
|
||||
this.inputType = "string";
|
||||
this.outputType = "html";
|
||||
this.args = [
|
||||
|
||||
@@ -22,6 +22,7 @@ class DisassembleX86 extends Operation {
|
||||
this.name = "Disassemble x86";
|
||||
this.module = "Shellcode";
|
||||
this.description = "Disassembly is the process of translating machine language into assembly language.<br><br>This operation supports 64-bit, 32-bit and 16-bit code written for Intel or AMD x86 processors. It is particularly useful for reverse engineering shellcode.<br><br>Input should be in hexadecimal.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/X86";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -5,7 +5,6 @@
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import OperationError from "../errors/OperationError";
|
||||
|
||||
/**
|
||||
* Drop bytes operation
|
||||
@@ -20,7 +19,7 @@ class DropBytes extends Operation {
|
||||
|
||||
this.name = "Drop bytes";
|
||||
this.module = "Default";
|
||||
this.description = "Cuts a slice of the specified number of bytes out of the data.";
|
||||
this.description = "Cuts a slice of the specified number of bytes out of the data. Negative values are allowed.";
|
||||
this.inputType = "ArrayBuffer";
|
||||
this.outputType = "ArrayBuffer";
|
||||
this.args = [
|
||||
@@ -50,14 +49,25 @@ class DropBytes extends Operation {
|
||||
* @throws {OperationError} if invalid input
|
||||
*/
|
||||
run(input, args) {
|
||||
const start = args[0],
|
||||
length = args[1],
|
||||
applyToEachLine = args[2];
|
||||
|
||||
if (start < 0 || length < 0)
|
||||
throw new OperationError("Error: Invalid value");
|
||||
let start = args[0],
|
||||
length = args[1];
|
||||
const applyToEachLine = args[2];
|
||||
|
||||
if (!applyToEachLine) {
|
||||
if (start < 0) { // Take from the end
|
||||
start = input.byteLength + start;
|
||||
}
|
||||
|
||||
if (length < 0) { // Flip start point
|
||||
start = start + length;
|
||||
if (start < 0) {
|
||||
start = input.byteLength + start;
|
||||
length = start - length;
|
||||
} else {
|
||||
length = -length;
|
||||
}
|
||||
}
|
||||
|
||||
const left = input.slice(0, start),
|
||||
right = input.slice(start + length, input.byteLength);
|
||||
const result = new Uint8Array(left.byteLength + right.byteLength);
|
||||
@@ -82,10 +92,28 @@ class DropBytes extends Operation {
|
||||
}
|
||||
lines.push(line);
|
||||
|
||||
let output = [];
|
||||
let output = [],
|
||||
s = start,
|
||||
l = length;
|
||||
for (i = 0; i < lines.length; i++) {
|
||||
output = output.concat(lines[i].slice(0, start).concat(lines[i].slice(start+length, lines[i].length)));
|
||||
if (s < 0) { // Take from the end
|
||||
s = lines[i].length + s;
|
||||
}
|
||||
|
||||
if (l < 0) { // Flip start point
|
||||
s = s + l;
|
||||
if (s < 0) {
|
||||
s = lines[i].length + s;
|
||||
l = s - l;
|
||||
} else {
|
||||
l = -l;
|
||||
}
|
||||
}
|
||||
|
||||
output = output.concat(lines[i].slice(0, s).concat(lines[i].slice(s+l, lines[i].length)));
|
||||
output.push(0x0a);
|
||||
s = start;
|
||||
l = length;
|
||||
}
|
||||
return new Uint8Array(output.slice(0, output.length-1)).buffer;
|
||||
}
|
||||
|
||||
@@ -20,6 +20,7 @@ class EncodeNetBIOSName extends Operation {
|
||||
this.name = "Encode NetBIOS Name";
|
||||
this.module = "Default";
|
||||
this.description = "NetBIOS names as seen across the client interface to NetBIOS are exactly 16 bytes long. Within the NetBIOS-over-TCP protocols, a longer representation is used.<br><br>There are two levels of encoding. The first level maps a NetBIOS name into a domain system name. The second level maps the domain system name into the 'compressed' representation required for interaction with the domain name system.<br><br>This operation carries out the first level of encoding. See RFC 1001 for full details.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/NetBIOS";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
|
||||
@@ -29,6 +29,7 @@ class EncodeText extends Operation {
|
||||
Object.keys(IO_FORMAT).map(e => `<li>${e}</li>`).join("\n"),
|
||||
"</ul>",
|
||||
].join("\n");
|
||||
this.infoURL = "https://wikipedia.org/wiki/Character_encoding";
|
||||
this.inputType = "string";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
|
||||
@@ -21,6 +21,7 @@ class Entropy extends Operation {
|
||||
this.name = "Entropy";
|
||||
this.module = "Default";
|
||||
this.description = "Shannon Entropy, in the context of information theory, is a measure of the rate at which information is produced by a source of data. It can be used, in a broad sense, to detect whether data is likely to be structured or unstructured. 8 is the maximum, representing highly unstructured, 'random' data. English language text usually falls somewhere between 3.5 and 5. Properly encrypted or compressed data should have an entropy of over 7.5.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Entropy_(information_theory)";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "number";
|
||||
this.presentType = "html";
|
||||
|
||||
@@ -22,6 +22,7 @@ class EscapeString extends Operation {
|
||||
this.name = "Escape string";
|
||||
this.module = "Default";
|
||||
this.description = "Escapes special characters in a string so that they do not cause conflicts. For example, <code>Don't stop me now</code> becomes <code>Don\\'t stop me now</code>.<br><br>Supports the following escape sequences:<ul><li><code>\\n</code> (Line feed/newline)</li><li><code>\\r</code> (Carriage return)</li><li><code>\\t</code> (Horizontal tab)</li><li><code>\\b</code> (Backspace)</li><li><code>\\f</code> (Form feed)</li><li><code>\\xnn</code> (Hex, where n is 0-f)</li><li><code>\\\\</code> (Backslash)</li><li><code>\\'</code> (Single quote)</li><li><code>\\"</code> (Double quote)</li><li><code>\\unnnn</code> (Unicode character)</li><li><code>\\u{nnnnnn}</code> (Unicode code point)</li></ul>";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Escape_sequence";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import { search } from "../lib/Extract";
|
||||
import { search, DOMAIN_REGEX } from "../lib/Extract";
|
||||
|
||||
/**
|
||||
* Extract domains operation
|
||||
@@ -38,10 +38,8 @@ class ExtractDomains extends Operation {
|
||||
* @returns {string}
|
||||
*/
|
||||
run(input, args) {
|
||||
const displayTotal = args[0],
|
||||
regex = /\b((?=[a-z0-9-]{1,63}\.)(xn--)?[a-z0-9]+(-[a-z0-9]+)*\.)+[a-z]{2,63}\b/ig;
|
||||
|
||||
return search(input, regex, null, displayTotal);
|
||||
const displayTotal = args[0];
|
||||
return search(input, DOMAIN_REGEX, null, displayTotal);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -28,6 +28,7 @@ class ExtractEXIF extends Operation {
|
||||
"<br><br>",
|
||||
"EXIF data from photos usually contains information about the image file itself as well as the device used to create it.",
|
||||
].join("\n");
|
||||
this.infoURL = "https://wikipedia.org/wiki/Exif";
|
||||
this.inputType = "ArrayBuffer";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -39,8 +39,8 @@ class ExtractEmailAddresses extends Operation {
|
||||
*/
|
||||
run(input, args) {
|
||||
const displayTotal = args[0],
|
||||
regex = /\b\w[-.\w]*@[-\w]+(?:\.[-\w]+)*\.[A-Z]{2,4}\b/ig;
|
||||
|
||||
// email regex from: https://www.regextester.com/98066
|
||||
regex = /(?:[\u00A0-\uD7FF\uE000-\uFFFF-a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[\u00A0-\uD7FF\uE000-\uFFFF-a-z0-9!#$%&'*+/=?^_`{|}~-]+)*|"(?:[\x01-\x08\x0b\x0c\x0e-\x1f\x21\x23-\x5b\x5d-\x7f]|\\[\x01-\x09\x0b\x0c\x0e-\x7f])*")@(?:(?:[\u00A0-\uD7FF\uE000-\uFFFF-a-z0-9](?:[\u00A0-\uD7FF\uE000-\uFFFF-a-z0-9-]*[\u00A0-\uD7FF\uE000-\uFFFF-a-z0-9])?\.)+[\u00A0-\uD7FF\uE000-\uFFFF-a-z0-9](?:[\u00A0-\uD7FF\uE000-\uFFFF-a-z0-9-]*[\u00A0-\uD7FF\uE000-\uFFFF-a-z0-9])?|\[(?:(?:(2(5[0-5]|[0-4][0-9])|1[0-9][0-9]|[1-9]?[0-9]))\.){3}(?:(2(5[0-5]|[0-4][0-9])|1[0-9][0-9]|[1-9]?[0-9])|[a-z0-9-]*[a-z0-9]:(?:[\x01-\x08\x0b\x0c\x0e-\x1f\x21-\x5a\x53-\x7f]|\\[\x01-\x09\x0b\x0c\x0e-\x7f])+)\])/ig;
|
||||
return search(input, regex, null, displayTotal);
|
||||
}
|
||||
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import { search } from "../lib/Extract";
|
||||
import { search, URL_REGEX } from "../lib/Extract";
|
||||
|
||||
/**
|
||||
* Extract URLs operation
|
||||
@@ -38,16 +38,8 @@ class ExtractURLs extends Operation {
|
||||
* @returns {string}
|
||||
*/
|
||||
run(input, args) {
|
||||
const displayTotal = args[0],
|
||||
protocol = "[A-Z]+://",
|
||||
hostname = "[-\\w]+(?:\\.\\w[-\\w]*)+",
|
||||
port = ":\\d+";
|
||||
let path = "/[^.!,?\"<>\\[\\]{}\\s\\x7F-\\xFF]*";
|
||||
|
||||
path += "(?:[.!,?]+[^.!,?\"<>\\[\\]{}\\s\\x7F-\\xFF]+)*";
|
||||
const regex = new RegExp(protocol + hostname + "(?:" + port +
|
||||
")?(?:" + path + ")?", "ig");
|
||||
return search(input, regex, null, displayTotal);
|
||||
const displayTotal = args[0];
|
||||
return search(input, URL_REGEX, null, displayTotal);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -8,6 +8,7 @@ import Operation from "../Operation";
|
||||
import Utils from "../Utils";
|
||||
import {INPUT_DELIM_OPTIONS} from "../lib/Delim";
|
||||
import OperationError from "../errors/OperationError";
|
||||
import XRegExp from "xregexp";
|
||||
|
||||
/**
|
||||
* Filter operation
|
||||
@@ -21,7 +22,7 @@ class Filter extends Operation {
|
||||
super();
|
||||
|
||||
this.name = "Filter";
|
||||
this.module = "Default";
|
||||
this.module = "Regex";
|
||||
this.description = "Splits up the input using the specified delimiter and then filters each branch based on a regular expression.";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
@@ -55,7 +56,7 @@ class Filter extends Operation {
|
||||
let regex;
|
||||
|
||||
try {
|
||||
regex = new RegExp(args[1]);
|
||||
regex = new XRegExp(args[1]);
|
||||
} catch (err) {
|
||||
throw new OperationError(`Invalid regex. Details: ${err.message}`);
|
||||
}
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
|
||||
import Operation from "../Operation";
|
||||
import Utils from "../Utils";
|
||||
import XRegExp from "xregexp";
|
||||
|
||||
/**
|
||||
* Find / Replace operation
|
||||
@@ -21,6 +22,7 @@ class FindReplace extends Operation {
|
||||
this.name = "Find / Replace";
|
||||
this.module = "Regex";
|
||||
this.description = "Replaces all occurrences of the first string with the second.<br><br>Includes support for regular expressions (regex), simple strings and extended strings (which support \\n, \\r, \\t, \\b, \\f and escaped hex bytes using \\x notation, e.g. \\x00 for a null byte).";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Regular_expression";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
@@ -49,6 +51,11 @@ class FindReplace extends Operation {
|
||||
"name": "Multiline matching",
|
||||
"type": "boolean",
|
||||
"value": true
|
||||
},
|
||||
{
|
||||
"name": "Dot matches all",
|
||||
"type": "boolean",
|
||||
"value": false
|
||||
}
|
||||
];
|
||||
}
|
||||
@@ -59,16 +66,17 @@ class FindReplace extends Operation {
|
||||
* @returns {string}
|
||||
*/
|
||||
run(input, args) {
|
||||
const [{option: type}, replace, g, i, m] = args;
|
||||
const [{option: type}, replace, g, i, m, s] = args;
|
||||
let find = args[0].string,
|
||||
modifiers = "";
|
||||
|
||||
if (g) modifiers += "g";
|
||||
if (i) modifiers += "i";
|
||||
if (m) modifiers += "m";
|
||||
if (s) modifiers += "s";
|
||||
|
||||
if (type === "Regex") {
|
||||
find = new RegExp(find, modifiers);
|
||||
find = new XRegExp(find, modifiers);
|
||||
return input.replace(find, replace);
|
||||
}
|
||||
|
||||
@@ -76,7 +84,7 @@ class FindReplace extends Operation {
|
||||
find = Utils.parseEscapedChars(find);
|
||||
}
|
||||
|
||||
find = new RegExp(Utils.escapeRegex(find), modifiers);
|
||||
find = new XRegExp(Utils.escapeRegex(find), modifiers);
|
||||
|
||||
return input.replace(find, replace);
|
||||
}
|
||||
|
||||
@@ -21,6 +21,7 @@ class Fletcher16Checksum extends Operation {
|
||||
this.name = "Fletcher-16 Checksum";
|
||||
this.module = "Hashing";
|
||||
this.description = "The Fletcher checksum is an algorithm for computing a position-dependent checksum devised by John Gould Fletcher at Lawrence Livermore Labs in the late 1970s.<br><br>The objective of the Fletcher checksum was to provide error-detection properties approaching those of a cyclic redundancy check but with the lower computational effort associated with summation techniques.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Fletcher%27s_checksum#Fletcher-16";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -21,6 +21,7 @@ class Fletcher32Checksum extends Operation {
|
||||
this.name = "Fletcher-32 Checksum";
|
||||
this.module = "Hashing";
|
||||
this.description = "The Fletcher checksum is an algorithm for computing a position-dependent checksum devised by John Gould Fletcher at Lawrence Livermore Labs in the late 1970s.<br><br>The objective of the Fletcher checksum was to provide error-detection properties approaching those of a cyclic redundancy check but with the lower computational effort associated with summation techniques.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Fletcher%27s_checksum#Fletcher-32";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -21,6 +21,7 @@ class Fletcher64Checksum extends Operation {
|
||||
this.name = "Fletcher-64 Checksum";
|
||||
this.module = "Hashing";
|
||||
this.description = "The Fletcher checksum is an algorithm for computing a position-dependent checksum devised by John Gould Fletcher at Lawrence Livermore Labs in the late 1970s.<br><br>The objective of the Fletcher checksum was to provide error-detection properties approaching those of a cyclic redundancy check but with the lower computational effort associated with summation techniques.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Fletcher%27s_checksum#Fletcher-64";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -21,6 +21,7 @@ class Fletcher8Checksum extends Operation {
|
||||
this.name = "Fletcher-8 Checksum";
|
||||
this.module = "Hashing";
|
||||
this.description = "The Fletcher checksum is an algorithm for computing a position-dependent checksum devised by John Gould Fletcher at Lawrence Livermore Labs in the late 1970s.<br><br>The objective of the Fletcher checksum was to provide error-detection properties approaching those of a cyclic redundancy check but with the lower computational effort associated with summation techniques.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Fletcher%27s_checksum";
|
||||
this.inputType = "byteArray";
|
||||
this.outputType = "string";
|
||||
this.args = [];
|
||||
|
||||
@@ -20,6 +20,7 @@ class FormatMACAddresses extends Operation {
|
||||
this.name = "Format MAC addresses";
|
||||
this.module = "Default";
|
||||
this.description = "Displays given MAC addresses in multiple different formats.<br><br>Expects addresses in a list separated by newlines, spaces or commas.<br><br>WARNING: There are no validity checks.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/MAC_address#Notational_conventions";
|
||||
this.inputType = "string";
|
||||
this.outputType = "string";
|
||||
this.args = [
|
||||
|
||||
@@ -22,6 +22,7 @@ class FrequencyDistribution extends Operation {
|
||||
this.name = "Frequency distribution";
|
||||
this.module = "Default";
|
||||
this.description = "Displays the distribution of bytes in the data as a graph.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Frequency_distribution";
|
||||
this.inputType = "ArrayBuffer";
|
||||
this.outputType = "json";
|
||||
this.presentType = "html";
|
||||
|
||||
@@ -24,6 +24,7 @@ class FromBCD extends Operation {
|
||||
this.name = "From BCD";
|
||||
this.module = "Default";
|
||||
this.description = "Binary-Coded Decimal (BCD) is a class of binary encodings of decimal numbers where each decimal digit is represented by a fixed number of bits, usually four or eight. Special bit patterns are sometimes used for a sign.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Binary-coded_decimal";
|
||||
this.inputType = "string";
|
||||
this.outputType = "BigNumber";
|
||||
this.args = [
|
||||
|
||||
@@ -22,6 +22,7 @@ class FromBase extends Operation {
|
||||
this.name = "From Base";
|
||||
this.module = "Default";
|
||||
this.description = "Converts a number to decimal from a given numerical base.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Radix";
|
||||
this.inputType = "string";
|
||||
this.outputType = "BigNumber";
|
||||
this.args = [
|
||||
|
||||
@@ -21,6 +21,7 @@ class FromBase32 extends Operation {
|
||||
this.name = "From Base32";
|
||||
this.module = "Default";
|
||||
this.description = "Base32 is a notation for encoding arbitrary byte data using a restricted set of symbols that can be conveniently used by humans and processed by computers. It uses a smaller set of characters than Base64, usually the uppercase alphabet and the numbers 2 to 7.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Base32";
|
||||
this.inputType = "string";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
|
||||
@@ -23,6 +23,7 @@ class FromBase58 extends Operation {
|
||||
this.name = "From Base58";
|
||||
this.module = "Default";
|
||||
this.description = "Base58 (similar to Base64) is a notation for encoding arbitrary byte data. It differs from Base64 by removing easily misread characters (i.e. l, I, 0 and O) to improve human readability.<br><br>This operation decodes data from an ASCII string (with an alphabet of your choosing, presets included) back into its raw form.<br><br>e.g. <code>StV1DL6CwTryKyV</code> becomes <code>hello world</code><br><br>Base58 is commonly used in cryptocurrencies (Bitcoin, Ripple, etc).";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Base58";
|
||||
this.inputType = "string";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
@@ -70,6 +71,11 @@ class FromBase58 extends Operation {
|
||||
|
||||
if (input.length === 0) return [];
|
||||
|
||||
let zeroPrefix = 0;
|
||||
for (let i = 0; i < input.length && input[i] === alphabet[0]; i++) {
|
||||
zeroPrefix++;
|
||||
}
|
||||
|
||||
[].forEach.call(input, function(c, charIndex) {
|
||||
const index = alphabet.indexOf(c);
|
||||
|
||||
@@ -97,6 +103,10 @@ class FromBase58 extends Operation {
|
||||
}
|
||||
});
|
||||
|
||||
while (zeroPrefix--) {
|
||||
result.push(0);
|
||||
}
|
||||
|
||||
return result.reverse();
|
||||
}
|
||||
|
||||
|
||||
58
src/core/operations/FromBase62.mjs
Normal file
58
src/core/operations/FromBase62.mjs
Normal file
@@ -0,0 +1,58 @@
|
||||
/**
|
||||
* @author tcode2k16 [tcode2k16@gmail.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import BigNumber from "bignumber.js";
|
||||
import Utils from "../Utils";
|
||||
|
||||
|
||||
/**
|
||||
* From Base62 operation
|
||||
*/
|
||||
class FromBase62 extends Operation {
|
||||
|
||||
/**
|
||||
* FromBase62 constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "From Base62";
|
||||
this.module = "Default";
|
||||
this.description = "Base62 is a notation for encoding arbitrary byte data using a restricted set of symbols that can be conveniently used by humans and processed by computers. The high number base results in shorter strings than with the decimal or hexadecimal system.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/List_of_numeral_systems";
|
||||
this.inputType = "string";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
{
|
||||
name: "Alphabet",
|
||||
type: "string",
|
||||
value: "0-9A-Za-z"
|
||||
}
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} input
|
||||
* @param {Object[]} args
|
||||
* @returns {byteArray}
|
||||
*/
|
||||
run(input, args) {
|
||||
if (input.length < 1) return [];
|
||||
const ALPHABET = Utils.expandAlphRange(args[0]).join("");
|
||||
const BN = BigNumber.clone({ ALPHABET });
|
||||
|
||||
const re = new RegExp("[^" + ALPHABET.replace(/[[\]\\\-^$]/g, "\\$&") + "]", "g");
|
||||
input = input.replace(re, "");
|
||||
|
||||
const number = new BN(input, 62);
|
||||
|
||||
return Utils.convertToByteArray(number.toString(16), "Hex");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default FromBase62;
|
||||
@@ -21,6 +21,7 @@ class FromBase64 extends Operation {
|
||||
this.name = "From Base64";
|
||||
this.module = "Default";
|
||||
this.description = "Base64 is a notation for encoding arbitrary byte data using a restricted set of symbols that can be conveniently used by humans and processed by computers.<br><br>This operation decodes data from an ASCII Base64 string back into its raw format.<br><br>e.g. <code>aGVsbG8=</code> becomes <code>hello</code>";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Base64";
|
||||
this.inputType = "string";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
@@ -37,44 +38,44 @@ class FromBase64 extends Operation {
|
||||
];
|
||||
this.patterns = [
|
||||
{
|
||||
match: "^(?:[A-Z\\d+/]{4})+(?:[A-Z\\d+/]{2}==|[A-Z\\d+/]{3}=)?$",
|
||||
match: "^\\s*(?:[A-Z\\d+/]{4})+(?:[A-Z\\d+/]{2}==|[A-Z\\d+/]{3}=)?\\s*$",
|
||||
flags: "i",
|
||||
args: ["A-Za-z0-9+/=", false]
|
||||
args: ["A-Za-z0-9+/=", true]
|
||||
},
|
||||
{
|
||||
match: "^[A-Z\\d\\-_]{20,}$",
|
||||
match: "^\\s*[A-Z\\d\\-_]{20,}\\s*$",
|
||||
flags: "i",
|
||||
args: ["A-Za-z0-9-_", false]
|
||||
args: ["A-Za-z0-9-_", true]
|
||||
},
|
||||
{
|
||||
match: "^(?:[A-Z\\d+\\-]{4}){5,}(?:[A-Z\\d+\\-]{2}==|[A-Z\\d+\\-]{3}=)?$",
|
||||
match: "^\\s*(?:[A-Z\\d+\\-]{4}){5,}(?:[A-Z\\d+\\-]{2}==|[A-Z\\d+\\-]{3}=)?\\s*$",
|
||||
flags: "i",
|
||||
args: ["A-Za-z0-9+\\-=", false]
|
||||
args: ["A-Za-z0-9+\\-=", true]
|
||||
},
|
||||
{
|
||||
match: "^(?:[A-Z\\d./]{4}){5,}(?:[A-Z\\d./]{2}==|[A-Z\\d./]{3}=)?$",
|
||||
match: "^\\s*(?:[A-Z\\d./]{4}){5,}(?:[A-Z\\d./]{2}==|[A-Z\\d./]{3}=)?\\s*$",
|
||||
flags: "i",
|
||||
args: ["./0-9A-Za-z=", false]
|
||||
args: ["./0-9A-Za-z=", true]
|
||||
},
|
||||
{
|
||||
match: "^[A-Z\\d_.]{20,}$",
|
||||
match: "^\\s*[A-Z\\d_.]{20,}\\s*$",
|
||||
flags: "i",
|
||||
args: ["A-Za-z0-9_.", false]
|
||||
args: ["A-Za-z0-9_.", true]
|
||||
},
|
||||
{
|
||||
match: "^(?:[A-Z\\d._]{4}){5,}(?:[A-Z\\d._]{2}--|[A-Z\\d._]{3}-)?$",
|
||||
match: "^\\s*(?:[A-Z\\d._]{4}){5,}(?:[A-Z\\d._]{2}--|[A-Z\\d._]{3}-)?\\s*$",
|
||||
flags: "i",
|
||||
args: ["A-Za-z0-9._-", false]
|
||||
args: ["A-Za-z0-9._-", true]
|
||||
},
|
||||
{
|
||||
match: "^(?:[A-Z\\d+/]{4}){5,}(?:[A-Z\\d+/]{2}==|[A-Z\\d+/]{3}=)?$",
|
||||
match: "^\\s*(?:[A-Z\\d+/]{4}){5,}(?:[A-Z\\d+/]{2}==|[A-Z\\d+/]{3}=)?\\s*$",
|
||||
flags: "i",
|
||||
args: ["0-9a-zA-Z+/=", false]
|
||||
args: ["0-9a-zA-Z+/=", true]
|
||||
},
|
||||
{
|
||||
match: "^(?:[A-Z\\d+/]{4}){5,}(?:[A-Z\\d+/]{2}==|[A-Z\\d+/]{3}=)?$",
|
||||
match: "^\\s*(?:[A-Z\\d+/]{4}){5,}(?:[A-Z\\d+/]{2}==|[A-Z\\d+/]{3}=)?\\s*$",
|
||||
flags: "i",
|
||||
args: ["0-9A-Za-z+/=", false]
|
||||
args: ["0-9A-Za-z+/=", true]
|
||||
},
|
||||
{
|
||||
match: "^[ !\"#$%&'()*+,\\-./\\d:;<=>?@A-Z[\\\\\\]^_]{20,}$",
|
||||
@@ -82,24 +83,24 @@ class FromBase64 extends Operation {
|
||||
args: [" -_", false]
|
||||
},
|
||||
{
|
||||
match: "^[A-Z\\d+\\-]{20,}$",
|
||||
match: "^\\s*[A-Z\\d+\\-]{20,}\\s*$",
|
||||
flags: "i",
|
||||
args: ["+\\-0-9A-Za-z", false]
|
||||
args: ["+\\-0-9A-Za-z", true]
|
||||
},
|
||||
{
|
||||
match: "^[!\"#$%&'()*+,\\-0-689@A-NP-VX-Z[`a-fh-mp-r]{20,}$",
|
||||
match: "^\\s*[!\"#$%&'()*+,\\-0-689@A-NP-VX-Z[`a-fh-mp-r]{20,}\\s*$",
|
||||
flags: "",
|
||||
args: ["!-,-0-689@A-NP-VX-Z[`a-fh-mp-r", false]
|
||||
args: ["!-,-0-689@A-NP-VX-Z[`a-fh-mp-r", true]
|
||||
},
|
||||
{
|
||||
match: "^(?:[N-ZA-M\\d+/]{4}){5,}(?:[N-ZA-M\\d+/]{2}==|[N-ZA-M\\d+/]{3}=)?$",
|
||||
match: "^\\s*(?:[N-ZA-M\\d+/]{4}){5,}(?:[N-ZA-M\\d+/]{2}==|[N-ZA-M\\d+/]{3}=)?\\s*$",
|
||||
flags: "i",
|
||||
args: ["N-ZA-Mn-za-m0-9+/=", false]
|
||||
args: ["N-ZA-Mn-za-m0-9+/=", true]
|
||||
},
|
||||
{
|
||||
match: "^[A-Z\\d./]{20,}$",
|
||||
match: "^\\s*[A-Z\\d./]{20,}\\s*$",
|
||||
flags: "i",
|
||||
args: ["./0-9A-Za-z", false]
|
||||
args: ["./0-9A-Za-z", true]
|
||||
},
|
||||
];
|
||||
}
|
||||
|
||||
105
src/core/operations/FromBase85.mjs
Normal file
105
src/core/operations/FromBase85.mjs
Normal file
@@ -0,0 +1,105 @@
|
||||
/**
|
||||
* @author PenguinGeorge [george@penguingeorge.com]
|
||||
* @copyright Crown Copyright 2018
|
||||
* @license Apache-2.0
|
||||
*/
|
||||
|
||||
import Operation from "../Operation";
|
||||
import OperationError from "../errors/OperationError";
|
||||
import Utils from "../Utils";
|
||||
import {alphabetName, ALPHABET_OPTIONS} from "../lib/Base85";
|
||||
|
||||
/**
|
||||
* From Base85 operation
|
||||
*/
|
||||
class FromBase85 extends Operation {
|
||||
|
||||
/**
|
||||
* From Base85 constructor
|
||||
*/
|
||||
constructor() {
|
||||
super();
|
||||
|
||||
this.name = "From Base85";
|
||||
this.module = "Default";
|
||||
this.description = "Base85 (also called Ascii85) is a notation for encoding arbitrary byte data. It is usually more efficient that Base64.<br><br>This operation decodes data from an ASCII string (with an alphabet of your choosing, presets included).<br><br>e.g. <code>BOu!rD]j7BEbo7</code> becomes <code>hello world</code><br><br>Base85 is commonly used in Adobe's PostScript and PDF file formats.";
|
||||
this.infoURL = "https://wikipedia.org/wiki/Ascii85";
|
||||
this.inputType = "string";
|
||||
this.outputType = "byteArray";
|
||||
this.args = [
|
||||
{
|
||||
name: "Alphabet",
|
||||
type: "editableOption",
|
||||
value: ALPHABET_OPTIONS
|
||||
},
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} input
|
||||
* @param {Object[]} args
|
||||
* @returns {byteArray}
|
||||
*/
|
||||
run(input, args) {
|
||||
const alphabet = Utils.expandAlphRange(args[0]).join(""),
|
||||
encoding = alphabetName(alphabet),
|
||||
result = [];
|
||||
|
||||
if (alphabet.length !== 85 ||
|
||||
[].unique.call(alphabet).length !== 85) {
|
||||
throw new OperationError("Alphabet must be of length 85");
|
||||
}
|
||||
|
||||
if (input.length === 0) return [];
|
||||
|
||||
const matches = input.match(/<~(.+?)~>/);
|
||||
if (matches !== null) input = matches[1];
|
||||
|
||||
let i = 0;
|
||||
let block, blockBytes;
|
||||
while (i < input.length) {
|
||||
if (encoding === "Standard" && input[i] === "z") {
|
||||
result.push(0, 0, 0, 0);
|
||||
i++;
|
||||
} else {
|
||||
let digits = [];
|
||||
digits = input
|
||||
.substr(i, 5)
|
||||
.split("")
|
||||
.map((chr, idx) => {
|
||||
const digit = alphabet.indexOf(chr);
|
||||
if (digit < 0 || digit > 84) {
|
||||
throw `Invalid character '${chr}' at index ${idx}`;
|
||||
}
|
||||
return digit;
|
||||
});
|
||||
|
||||
block =
|
||||
digits[0] * 52200625 +
|
||||
digits[1] * 614125 +
|
||||
(i + 2 < input.length ? digits[2] : 84) * 7225 +
|
||||
(i + 3 < input.length ? digits[3] : 84) * 85 +
|
||||
(i + 4 < input.length ? digits[4] : 84);
|
||||
|
||||
blockBytes = [
|
||||
(block >> 24) & 0xff,
|
||||
(block >> 16) & 0xff,
|
||||
(block >> 8) & 0xff,
|
||||
block & 0xff
|
||||
];
|
||||
|
||||
if (input.length < i + 5) {
|
||||
blockBytes.splice(input.length - (i + 5), 5);
|
||||
}
|
||||
|
||||
result.push.apply(result, blockBytes);
|
||||
i += 5;
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
export default FromBase85;
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user