-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
60895de
commit db0cf40
Showing
3 changed files
with
444 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,187 @@ | ||
{ | ||
"name": "PASETO v4 Test Vectors", | ||
"tests": [ | ||
{ | ||
"name": "4-E-1", | ||
"expect-fail": false, | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"nonce": "0000000000000000000000000000000000000000000000000000000000000000", | ||
"token": "v4.local.AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAr68PS4AXe7If_ZgesdkUMvSwscFlAl1pk5HC0e8kApeaqMfGo_7OpBnwJOAbY9V7WU6abu74MmcUE8YWAiaArVI8XJ5hOb_4v9RmDkneN0S92dx0OW4pgy7omxgf3S8c3LlQg", | ||
"payload": "{\"data\":\"this is a secret message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-E-2", | ||
"expect-fail": false, | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"nonce": "0000000000000000000000000000000000000000000000000000000000000000", | ||
"token": "v4.local.AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAr68PS4AXe7If_ZgesdkUMvS2csCgglvpk5HC0e8kApeaqMfGo_7OpBnwJOAbY9V7WU6abu74MmcUE8YWAiaArVI8XIemu9chy3WVKvRBfg6t8wwYHK0ArLxxfZP73W_vfwt5A", | ||
"payload": "{\"data\":\"this is a hidden message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-E-3", | ||
"expect-fail": false, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.32VIErrEkmY4JVILovbmfPXKW9wT1OdQepjMTC_MOtjA4kiqw7_tcaOM5GNEcnTxl60WkwMsYXw6FSNb_UdJPXjpzm0KW9ojM5f4O2mRvE2IcweP-PRdoHjd5-RHCiExR1IK6t6-tyebyWG6Ov7kKvBdkrrAJ837lKP3iDag2hzUPHuMKA", | ||
"payload": "{\"data\":\"this is a secret message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-E-4", | ||
"expect-fail": false, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.32VIErrEkmY4JVILovbmfPXKW9wT1OdQepjMTC_MOtjA4kiqw7_tcaOM5GNEcnTxl60WiA8rd3wgFSNb_UdJPXjpzm0KW9ojM5f4O2mRvE2IcweP-PRdoHjd5-RHCiExR1IK6t4gt6TiLm55vIH8c_lGxxZpE3AWlH4WTR0v45nsWoU3gQ", | ||
"payload": "{\"data\":\"this is a hidden message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-E-5", | ||
"expect-fail": false, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.32VIErrEkmY4JVILovbmfPXKW9wT1OdQepjMTC_MOtjA4kiqw7_tcaOM5GNEcnTxl60WkwMsYXw6FSNb_UdJPXjpzm0KW9ojM5f4O2mRvE2IcweP-PRdoHjd5-RHCiExR1IK6t4x-RMNXtQNbz7FvFZ_G-lFpk5RG3EOrwDL6CgDqcerSQ.eyJraWQiOiJ6VmhNaVBCUDlmUmYyc25FY1Q3Z0ZUaW9lQTlDT2NOeTlEZmdMMVc2MGhhTiJ9", | ||
"payload": "{\"data\":\"this is a secret message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "{\"kid\":\"zVhMiPBP9fRf2snEcT7gFTioeA9COcNy9DfgL1W60haN\"}", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-E-6", | ||
"expect-fail": false, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.32VIErrEkmY4JVILovbmfPXKW9wT1OdQepjMTC_MOtjA4kiqw7_tcaOM5GNEcnTxl60WiA8rd3wgFSNb_UdJPXjpzm0KW9ojM5f4O2mRvE2IcweP-PRdoHjd5-RHCiExR1IK6t6pWSA5HX2wjb3P-xLQg5K5feUCX4P2fpVK3ZLWFbMSxQ.eyJraWQiOiJ6VmhNaVBCUDlmUmYyc25FY1Q3Z0ZUaW9lQTlDT2NOeTlEZmdMMVc2MGhhTiJ9", | ||
"payload": "{\"data\":\"this is a hidden message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "{\"kid\":\"zVhMiPBP9fRf2snEcT7gFTioeA9COcNy9DfgL1W60haN\"}", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-E-7", | ||
"expect-fail": false, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.32VIErrEkmY4JVILovbmfPXKW9wT1OdQepjMTC_MOtjA4kiqw7_tcaOM5GNEcnTxl60WkwMsYXw6FSNb_UdJPXjpzm0KW9ojM5f4O2mRvE2IcweP-PRdoHjd5-RHCiExR1IK6t40KCCWLA7GYL9KFHzKlwY9_RnIfRrMQpueydLEAZGGcA.eyJraWQiOiJ6VmhNaVBCUDlmUmYyc25FY1Q3Z0ZUaW9lQTlDT2NOeTlEZmdMMVc2MGhhTiJ9", | ||
"payload": "{\"data\":\"this is a secret message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "{\"kid\":\"zVhMiPBP9fRf2snEcT7gFTioeA9COcNy9DfgL1W60haN\"}", | ||
"implicit-assertion": "{\"test-vector\":\"4-E-7\"}" | ||
}, | ||
{ | ||
"name": "4-E-8", | ||
"expect-fail": false, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.32VIErrEkmY4JVILovbmfPXKW9wT1OdQepjMTC_MOtjA4kiqw7_tcaOM5GNEcnTxl60WiA8rd3wgFSNb_UdJPXjpzm0KW9ojM5f4O2mRvE2IcweP-PRdoHjd5-RHCiExR1IK6t5uvqQbMGlLLNYBc7A6_x7oqnpUK5WLvj24eE4DVPDZjw.eyJraWQiOiJ6VmhNaVBCUDlmUmYyc25FY1Q3Z0ZUaW9lQTlDT2NOeTlEZmdMMVc2MGhhTiJ9", | ||
"payload": "{\"data\":\"this is a hidden message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "{\"kid\":\"zVhMiPBP9fRf2snEcT7gFTioeA9COcNy9DfgL1W60haN\"}", | ||
"implicit-assertion": "{\"test-vector\":\"4-E-8\"}" | ||
}, | ||
{ | ||
"name": "4-E-9", | ||
"expect-fail": false, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.32VIErrEkmY4JVILovbmfPXKW9wT1OdQepjMTC_MOtjA4kiqw7_tcaOM5GNEcnTxl60WiA8rd3wgFSNb_UdJPXjpzm0KW9ojM5f4O2mRvE2IcweP-PRdoHjd5-RHCiExR1IK6t6tybdlmnMwcDMw0YxA_gFSE_IUWl78aMtOepFYSWYfQA.YXJiaXRyYXJ5LXN0cmluZy10aGF0LWlzbid0LWpzb24", | ||
"payload": "{\"data\":\"this is a hidden message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "arbitrary-string-that-isn't-json", | ||
"implicit-assertion": "{\"test-vector\":\"4-E-9\"}" | ||
}, | ||
{ | ||
"name": "4-S-1", | ||
"expect-fail": false, | ||
"public-key": "1eb9dbbbbc047c03fd70604e0071f0987e16b28b757225c11f00415d0e20b1a2", | ||
"secret-key": "b4cbfb43df4ce210727d953e4a713307fa19bb7d9f85041438d9e11b942a37741eb9dbbbbc047c03fd70604e0071f0987e16b28b757225c11f00415d0e20b1a2", | ||
"secret-key-seed": "b4cbfb43df4ce210727d953e4a713307fa19bb7d9f85041438d9e11b942a3774", | ||
"secret-key-pem": "-----BEGIN PRIVATE KEY-----\nMC4CAQAwBQYDK2VwBCIEILTL+0PfTOIQcn2VPkpxMwf6Gbt9n4UEFDjZ4RuUKjd0\n-----END PRIVATE KEY-----", | ||
"public-key-pem": "-----BEGIN PUBLIC KEY-----\nMCowBQYDK2VwAyEAHrnbu7wEfAP9cGBOAHHwmH4Wsot1ciXBHwBBXQ4gsaI=\n-----END PUBLIC KEY-----", | ||
"token": "v4.public.eyJkYXRhIjoidGhpcyBpcyBhIHNpZ25lZCBtZXNzYWdlIiwiZXhwIjoiMjAyMi0wMS0wMVQwMDowMDowMCswMDowMCJ9bg_XBBzds8lTZShVlwwKSgeKpLT3yukTw6JUz3W4h_ExsQV-P0V54zemZDcAxFaSeef1QlXEFtkqxT1ciiQEDA", | ||
"payload": "{\"data\":\"this is a signed message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-S-2", | ||
"expect-fail": false, | ||
"public-key": "1eb9dbbbbc047c03fd70604e0071f0987e16b28b757225c11f00415d0e20b1a2", | ||
"secret-key": "b4cbfb43df4ce210727d953e4a713307fa19bb7d9f85041438d9e11b942a37741eb9dbbbbc047c03fd70604e0071f0987e16b28b757225c11f00415d0e20b1a2", | ||
"secret-key-seed": "b4cbfb43df4ce210727d953e4a713307fa19bb7d9f85041438d9e11b942a3774", | ||
"secret-key-pem": "-----BEGIN PRIVATE KEY-----\nMC4CAQAwBQYDK2VwBCIEILTL+0PfTOIQcn2VPkpxMwf6Gbt9n4UEFDjZ4RuUKjd0\n-----END PRIVATE KEY-----", | ||
"public-key-pem": "-----BEGIN PUBLIC KEY-----\nMCowBQYDK2VwAyEAHrnbu7wEfAP9cGBOAHHwmH4Wsot1ciXBHwBBXQ4gsaI=\n-----END PUBLIC KEY-----", | ||
"token": "v4.public.eyJkYXRhIjoidGhpcyBpcyBhIHNpZ25lZCBtZXNzYWdlIiwiZXhwIjoiMjAyMi0wMS0wMVQwMDowMDowMCswMDowMCJ9v3Jt8mx_TdM2ceTGoqwrh4yDFn0XsHvvV_D0DtwQxVrJEBMl0F2caAdgnpKlt4p7xBnx1HcO-SPo8FPp214HDw.eyJraWQiOiJ6VmhNaVBCUDlmUmYyc25FY1Q3Z0ZUaW9lQTlDT2NOeTlEZmdMMVc2MGhhTiJ9", | ||
"payload": "{\"data\":\"this is a signed message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "{\"kid\":\"zVhMiPBP9fRf2snEcT7gFTioeA9COcNy9DfgL1W60haN\"}", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-S-3", | ||
"expect-fail": false, | ||
"public-key": "1eb9dbbbbc047c03fd70604e0071f0987e16b28b757225c11f00415d0e20b1a2", | ||
"secret-key": "b4cbfb43df4ce210727d953e4a713307fa19bb7d9f85041438d9e11b942a37741eb9dbbbbc047c03fd70604e0071f0987e16b28b757225c11f00415d0e20b1a2", | ||
"secret-key-seed": "b4cbfb43df4ce210727d953e4a713307fa19bb7d9f85041438d9e11b942a3774", | ||
"secret-key-pem": "-----BEGIN PRIVATE KEY-----\nMC4CAQAwBQYDK2VwBCIEILTL+0PfTOIQcn2VPkpxMwf6Gbt9n4UEFDjZ4RuUKjd0\n-----END PRIVATE KEY-----", | ||
"public-key-pem": "-----BEGIN PUBLIC KEY-----\nMCowBQYDK2VwAyEAHrnbu7wEfAP9cGBOAHHwmH4Wsot1ciXBHwBBXQ4gsaI=\n-----END PUBLIC KEY-----", | ||
"token": "v4.public.eyJkYXRhIjoidGhpcyBpcyBhIHNpZ25lZCBtZXNzYWdlIiwiZXhwIjoiMjAyMi0wMS0wMVQwMDowMDowMCswMDowMCJ9NPWciuD3d0o5eXJXG5pJy-DiVEoyPYWs1YSTwWHNJq6DZD3je5gf-0M4JR9ipdUSJbIovzmBECeaWmaqcaP0DQ.eyJraWQiOiJ6VmhNaVBCUDlmUmYyc25FY1Q3Z0ZUaW9lQTlDT2NOeTlEZmdMMVc2MGhhTiJ9", | ||
"payload": "{\"data\":\"this is a signed message\",\"exp\":\"2022-01-01T00:00:00+00:00\"}", | ||
"footer": "{\"kid\":\"zVhMiPBP9fRf2snEcT7gFTioeA9COcNy9DfgL1W60haN\"}", | ||
"implicit-assertion": "{\"test-vector\":\"4-S-3\"}" | ||
}, | ||
{ | ||
"name": "4-F-1", | ||
"expect-fail": true, | ||
"public-key": "1eb9dbbbbc047c03fd70604e0071f0987e16b28b757225c11f00415d0e20b1a2", | ||
"secret-key": "b4cbfb43df4ce210727d953e4a713307fa19bb7d9f85041438d9e11b942a37741eb9dbbbbc047c03fd70604e0071f0987e16b28b757225c11f00415d0e20b1a2", | ||
"secret-key-seed": "b4cbfb43df4ce210727d953e4a713307fa19bb7d9f85041438d9e11b942a3774", | ||
"secret-key-pem": "-----BEGIN PRIVATE KEY-----\nMC4CAQAwBQYDK2VwBCIEILTL+0PfTOIQcn2VPkpxMwf6Gbt9n4UEFDjZ4RuUKjd0\n-----END PRIVATE KEY-----", | ||
"public-key-pem": "-----BEGIN PUBLIC KEY-----\nMCowBQYDK2VwAyEAHrnbu7wEfAP9cGBOAHHwmH4Wsot1ciXBHwBBXQ4gsaI=\n-----END PUBLIC KEY-----", | ||
"token": "v4.local.vngXfCISbnKgiP6VWGuOSlYrFYU300fy9ijW33rznDYgxHNPwWluAY2Bgb0z54CUs6aYYkIJ-bOOOmJHPuX_34Agt_IPlNdGDpRdGNnBz2MpWJvB3cttheEc1uyCEYltj7wBQQYX.YXJiaXRyYXJ5LXN0cmluZy10aGF0LWlzbid0LWpzb24", | ||
"payload": null, | ||
"footer": "arbitrary-string-that-isn't-json", | ||
"implicit-assertion": "{\"test-vector\":\"4-F-1\"}" | ||
}, | ||
{ | ||
"name": "4-F-2", | ||
"expect-fail": true, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.public.eyJpbnZhbGlkIjoidGhpcyBzaG91bGQgbmV2ZXIgZGVjb2RlIn22Sp4gjCaUw0c7EH84ZSm_jN_Qr41MrgLNu5LIBCzUr1pn3Z-Wukg9h3ceplWigpoHaTLcwxj0NsI1vjTh67YB.eyJraWQiOiJ6VmhNaVBCUDlmUmYyc25FY1Q3Z0ZUaW9lQTlDT2NOeTlEZmdMMVc2MGhhTiJ9", | ||
"payload": null, | ||
"footer": "{\"kid\":\"zVhMiPBP9fRf2snEcT7gFTioeA9COcNy9DfgL1W60haN\"}", | ||
"implicit-assertion": "{\"test-vector\":\"4-F-2\"}" | ||
}, | ||
{ | ||
"name": "4-F-3", | ||
"expect-fail": true, | ||
"nonce": "26f7553354482a1d91d4784627854b8da6b8042a7966523c2b404e8dbbe7f7f2", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v3.local.23e_2PiqpQBPvRFKzB0zHhjmxK3sKo2grFZRRLM-U7L0a8uHxuF9RlVz3Ic6WmdUUWTxCaYycwWV1yM8gKbZB2JhygDMKvHQ7eBf8GtF0r3K0Q_gF1PXOxcOgztak1eD1dPe9rLVMSgR0nHJXeIGYVuVrVoLWQ.YXJiaXRyYXJ5LXN0cmluZy10aGF0LWlzbid0LWpzb24", | ||
"payload": null, | ||
"footer": "arbitrary-string-that-isn't-json", | ||
"implicit-assertion": "{\"test-vector\":\"4-F-3\"}" | ||
}, | ||
{ | ||
"name": "4-F-4", | ||
"expect-fail": true, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAQAr68PS4AXe7If_ZgesdkUMvSwscFlAl1pk5HC0e8kApeaqMfGo_7OpBnwJOAbY9V7WU6abu74MmcUE8YWAiaArVI8XJ5hOb_4v9RmDkneN0S92dx0OW4pgy7omxgf3S8c3LlQh", | ||
"payload": null, | ||
"footer": "", | ||
"implicit-assertion": "" | ||
}, | ||
{ | ||
"name": "4-F-5", | ||
"expect-fail": true, | ||
"nonce": "df654812bac492663825520ba2f6e67cf5ca5bdc13d4e7507a98cc4c2fcc3ad8", | ||
"key": "707172737475767778797a7b7c7d7e7f808182838485868788898a8b8c8d8e8f", | ||
"token": "v4.local.32VIErrEkmY4JVILovbmfPXKW9wT1OdQepjMTC_MOtjA4kiqw7_tcaOM5GNEcnTxl60WkwMsYXw6FSNb_UdJPXjpzm0KW9ojM5f4O2mRvE2IcweP-PRdoHjd5-RHCiExR1IK6t4x-RMNXtQNbz7FvFZ_G-lFpk5RG3EOrwDL6CgDqcerSQ==.eyJraWQiOiJ6VmhNaVBCUDlmUmYyc25FY1Q3Z0ZUaW9lQTlDT2NOeTlEZmdMMVc2MGhhTiJ9", | ||
"payload": null, | ||
"footer": "{\"kid\":\"zVhMiPBP9fRf2snEcT7gFTioeA9COcNy9DfgL1W60haN\"}", | ||
"implicit-assertion": "" | ||
} | ||
] | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,193 @@ | ||
package paseto | ||
|
||
import ( | ||
"crypto/hmac" | ||
"crypto/rand" | ||
"errors" | ||
"fmt" | ||
"io" | ||
"strings" | ||
|
||
"golang.org/x/crypto/blake2b" | ||
"golang.org/x/crypto/chacha20" | ||
) | ||
|
||
const ( | ||
v4locHeader = "v4.local." | ||
v4locKey = 32 | ||
v4locNonce = 32 | ||
v4locMac = 32 | ||
v4locKDF = 32 | ||
) | ||
|
||
func V4Encrypt(key []byte, payload, footer any, implicit string, randBytes []byte) (string, error) { | ||
payloadBytes, err := toBytes(payload) | ||
if err != nil { | ||
return "", fmt.Errorf("encode payload: %w", err) | ||
} | ||
|
||
footerBytes, err := toBytes(footer) | ||
if err != nil { | ||
return "", fmt.Errorf("encode footer: %w", err) | ||
} | ||
|
||
if randBytes == nil { | ||
randBytes = make([]byte, v4locNonce) | ||
if _, err := io.ReadFull(rand.Reader, randBytes); err != nil { | ||
return "", fmt.Errorf("read from crypto/rand.Reader: %w", err) | ||
} | ||
} | ||
|
||
// step 0. | ||
m := payloadBytes | ||
k := key | ||
f := footerBytes | ||
i := []byte(implicit) | ||
|
||
// step 1. | ||
if !constTimeEq(int32(len(k)), v4locKey) { | ||
return "", errors.New("bad key") | ||
} | ||
|
||
// step 2. | ||
h := []byte(v4locHeader) | ||
|
||
// step 3. | ||
n := randBytes | ||
if n == nil { | ||
n = make([]byte, v4locNonce) | ||
if _, err := io.ReadFull(rand.Reader, n); err != nil { | ||
return "", fmt.Errorf("read from crypto/rand.Reader: %w", err) | ||
} | ||
} | ||
|
||
// step 4. | ||
ek, n2, ak, err := v4locSplitKey(key, n) | ||
if err != nil { | ||
return "", fmt.Errorf("create enc and auth keys: %w", err) | ||
} | ||
|
||
// step 5. | ||
c := make([]byte, len(m)) | ||
|
||
ciph, err := chacha20.NewUnauthenticatedCipher(ek, n2) | ||
if err != nil { | ||
return "", fmt.Errorf("create chacha20 cipher: %w", err) | ||
} | ||
ciph.XORKeyStream(c, m) | ||
|
||
// step 6. | ||
preAuth := pae(h, n, c, f, i) | ||
|
||
// step 7. | ||
mac, err := blake2b.New(v4locMac, ak) | ||
if err != nil { | ||
return "", fmt.Errorf("unable to in initialize MAC kdf: %w", err) | ||
} | ||
mac.Write(preAuth) | ||
t := mac.Sum(nil) | ||
|
||
// step 8. | ||
body := make([]byte, 0, len(n)+len(c)+len(t)) | ||
body = append(body, n...) | ||
body = append(body, c...) | ||
body = append(body, t...) | ||
|
||
return buildToken(h, body, f), nil | ||
} | ||
|
||
func V4Decrypt(token string, key []byte, payload, footer any, implicit string) error { | ||
// step 0. | ||
k := key | ||
i := []byte(implicit) | ||
|
||
// step 1. | ||
// step 2. | ||
|
||
// step 3. | ||
if !strings.HasPrefix(token, v4locHeader) { | ||
return ErrIncorrectTokenFormat | ||
} | ||
h := []byte(v4locHeader) | ||
|
||
// step 4. | ||
body, footerBytes, err := splitToken(token, v4locHeader) | ||
if err != nil { | ||
return fmt.Errorf("decode token: %w", err) | ||
} | ||
if len(body) < v4locNonce+v4locMac { | ||
return ErrIncorrectTokenFormat | ||
} | ||
f := footerBytes | ||
n := body[:v4locNonce] | ||
c := body[v4locNonce : len(body)-v4locMac] | ||
t := body[v4locNonce+len(c):] | ||
|
||
// step 5. | ||
ek, n2, ak, err := v4locSplitKey(k, n) | ||
if err != nil { | ||
return fmt.Errorf("create enc and auth keys: %w", err) | ||
} | ||
|
||
// step 6. | ||
preAuth := pae(h, n, c, f, i) | ||
|
||
// step 7. | ||
hasher, err := blake2b.New(v4locMac, ak) | ||
if err != nil { | ||
return fmt.Errorf("create blake2b hash: %w", err) | ||
} | ||
hasher.Write(preAuth) | ||
t2 := hasher.Sum(nil) | ||
|
||
// step 8. | ||
if !hmac.Equal(t, t2) { | ||
return ErrInvalidTokenAuth | ||
} | ||
|
||
// step 9. | ||
ciph, err := chacha20.NewUnauthenticatedCipher(ek, n2) | ||
if err != nil { | ||
return fmt.Errorf("create chacha20 cipher: %w", err) | ||
} | ||
|
||
p := make([]byte, len(c)) | ||
ciph.XORKeyStream(p, c) | ||
|
||
// step 10. | ||
if payload != nil { | ||
if err := fromBytes(p, payload); err != nil { | ||
return fmt.Errorf("decode payload: %w", err) | ||
} | ||
} | ||
|
||
if footer != nil { | ||
if err := fromBytes(f, footer); err != nil { | ||
return fmt.Errorf("decode footer: %w", err) | ||
} | ||
} | ||
return nil | ||
} | ||
|
||
func v4locSplitKey(key, n []byte) (ek, n2, ak []byte, err error) { | ||
encKDF, err := blake2b.New(56, key) | ||
if err != nil { | ||
return nil, nil, nil, err | ||
} | ||
|
||
encKDF.Write([]byte("paseto-encryption-key")) | ||
encKDF.Write(n) | ||
tmp := encKDF.Sum(nil) | ||
ek, n2 = tmp[:v4locKDF], tmp[v4locKDF:] | ||
|
||
authKDF, err := blake2b.New(32, key) | ||
if err != nil { | ||
return nil, nil, nil, err | ||
} | ||
|
||
authKDF.Write([]byte("paseto-auth-key-for-aead")) | ||
authKDF.Write(n) | ||
ak = authKDF.Sum(nil) | ||
|
||
return ek, n2, ak, nil | ||
} |
Oops, something went wrong.