You are viewing a plain text version of this content. The canonical link for it is here.
Posted to user@guacamole.apache.org by Caleb Coverdale <ca...@me.com.INVALID> on 2022/02/02 19:07:05 UTC
RE: Encrypted JSON with Javascript
Here is a copy of the fixed code incase anyone has anymore issues:
const crypto = require("crypto");
const key = "KEYHERE";
const iv = "00000000000000000000000000000000";
// convert key to binary
const keyBin = Buffer.from(key, "hex");
const ivBin = Buffer.from(iv, "hex");
// Sign the JSON using the key with the authString using sha256/hmac
function encryptSign(keyBin, ivBin, username, url) {
const calculateTime = Math.floor(Date.now() / 1000) + 300;
const expiration = calculateTime + "000";
const authString = `{"username":"${username}","expires":"${expiration}","connections":{"${expiration}":{"protocol":"rdp","parameters":{"hostname":"IPHERE","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
const signature = crypto
.createHmac("sha256", keyBin)
.update(authString)
.digest("binary");
const signatureReturn = signature + authString;
// AES-128-CBC encrypt signatureReturn using keyBin and ivBin return it in base64
const cipher = crypto.createCipheriv("aes-128-cbc", keyBin, ivBin);
const encrypted = cipher.update(signatureReturn, "binary", "base64");
const encryptedSignature = encrypted + cipher.final("base64");
// convert encryptedSignature to base64
const urlencodedSignature = encodeURIComponent(encryptedSignature);
const returnValue = `${url}${urlencodedSignature}`;
return returnValue;
}
On 2022/01/26 21:00:16 Caleb Coverdale wrote:
> Hey there!
>
> I have been banging my head against the wall trying to get the EncryptedJSON script working in Javascript.
>
> I was wondering if anyone has been down the rabbit hole and got it working?
>
>
> Any help would be appreciated…
>
>
> Here’s what I have so far:
>
>
>
> const crypto = require("crypto");
> const guacjson = `{"username":"MyUser","connections":{"MyConnection":{"protocol":"rdp","parameters":{"hostname":"10.0.0.41","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
> const secretkey = "fe57526d73a1e5116bbbefad1c91b38f";
>
> // sign the contents of guacjson with secret key using HMAC/SHA-256 out in binary
> function cryptedmessage() {
> const hmac = crypto.createHmac("sha256", secretkey);
> hmac.update(guacjson);
> // output the hmac in binary followed by guacjson
> signature = hmac.digest("binary") + guacjson;
> return signature;
> }
>
> const INITIALIZATION_VECTOR = "0000000000000000";
>
> class Crypt {
> static encrypt128(data, key) {
> const cipher = crypto.createCipheriv(
> "aes-128-cbc",
> Buffer.from(key, "hex"),
> Buffer.from(INITIALIZATION_VECTOR)
> );
> // return cipher encoded as bas64
> console.log(data);
> const encrypted =
> cipher.update(data, "utf8", "base64") + cipher.final("base64");
> return encrypted;
> }
> }
>
> const key = "fe57526d73a1e5116bbbefad1c91b38f";
>
> const cipher = Crypt.encrypt128(cryptedmessage(), key);
>
> console.log(cipher);
Re: Encrypted JSON with Javascript
Posted by Craig Sawyer <cs...@yumaunion.org>.
cleaning up localStorage shouldn't be hard: localStorage.removeItem(key);
On Wed, Feb 2, 2022 at 12:27 PM Caleb Coverdale
<ca...@me.com.invalid> wrote:
> Any chance you happen to know how to sign a user out via HTTP requests? Or
> if I were to use the URL such as:
> http://localhost:8080/#/api/tokens?data=JSONENCRYPTEDHERE
>
> Every time I try to connect using that URL it is picking up LocalStorage
> and doesn’t throw me a new connection/user….. I am just trying to flush out
> the local storage and make it so every time I load a new URL from a page,
> it dynamically creates a per browser window of each guacamole connection…..
>
>
> On Feb 2, 2022, at 1:24 PM, Craig Sawyer <cs...@yumaunion.org> wrote:
>
> Interesting! Like I said, not a guac-crypto expert. I read the thread,
> but did not read the code, but as Chris Wheeler mentions in the linked
> thread, looks like the safe approach is to add a randomized nonce in your
> message, it should produce no differences in compatibility(per him), but
> enforce that no messages will ever be sent identically across the wire.
> i.e. in your authString, just add a key "nonce" with a random value.
>
> Glad you found that thread! Goes to show security and cryptography are
> hard. :)
>
>
>
> On Wed, Feb 2, 2022 at 11:50 AM Caleb Coverdale <
> calebcoverdale@me.com.invalid> wrote:
>
>> From what I understood in this discussion here:
>> [GUACAMOLE-1286] Support a custom IV in guacamole-auth-json - ASF JIRA
>> (apache.org)
>> <https://issues.apache.org/jira/projects/GUACAMOLE/issues/GUACAMOLE-1286?filter=allopenissues>
>>
>> There was discussion for allowing a non-null IV.
>>
>>
>> guacamole-client/CryptoService.java at master · apache/guacamole-client
>> (github.com)
>> <https://github.com/apache/guacamole-client/blob/master/extensions/guacamole-auth-json/src/main/java/org/apache/guacamole/auth/json/CryptoService.java>
>> In the CryptoService.js there is a comment regarding how they use the
>> signature as the IV for decryption:
>>
>> /**
>> * IV which is all null bytes (all binary zeroes). Usually, using a null IV
>> * is a horrible idea. As our plaintext will always be prepended with the
>> * HMAC signature of the rest of the message, we are effectively using the
>> * HMAC signature itself as the IV. For our purposes, where the encrypted
>> * value becomes an authentication token, this is OK.
>> */
>>
>>
>> So to me everything looks okay….
>>
>> So may not be the best to use the NULL IV, but there is still some
>> security regarding the signature and decryption
>>
>>
>> On Feb 2, 2022, at 12:44 PM, Craig Sawyer <cs...@yumaed.org> wrote:
>>
>> Glad you got it figured out!
>>
>> I'm not up to date with Guac's crypto code-base, but in case you
>> didn't know, you def. don't want to deploy with an iv of all 0's as a
>> static value. If this is just a proof of concept, no worries. Also
>> you don't check any error conditions, which for production crypto code
>> you most definitely will want to do.
>>
>> IV's are not secret, but they do need to be random(not technically,
>> but practically) and never re-used.
>>
>> Also, this is by no means considered an audit, I don't write JS(and
>> barely read the code) and am not trying to do that, just pointing out
>> some glaring errors, if you were not aware, or for others trying to
>> copy what you are doing down the road and not realizing IV's are
>> required to match the security promises of AES-128-CBC.
>>
>> Good Luck.
>>
>> On Wed, Feb 2, 2022 at 11:07 AM Caleb Coverdale
>> <ca...@me.com.invalid> wrote:
>>
>>
>> Here is a copy of the fixed code incase anyone has anymore issues:
>>
>> const crypto = require("crypto");
>>
>> const key = "KEYHERE";
>> const iv = "00000000000000000000000000000000";
>> // convert key to binary
>> const keyBin = Buffer.from(key, "hex");
>> const ivBin = Buffer.from(iv, "hex");
>>
>> // Sign the JSON using the key with the authString using sha256/hmac
>> function encryptSign(keyBin, ivBin, username, url) {
>> const calculateTime = Math.floor(Date.now() / 1000) + 300;
>> const expiration = calculateTime + "000";
>> const authString =
>> `{"username":"${username}","expires":"${expiration}","connections":{"${expiration}":{"protocol":"rdp","parameters":{"hostname":"IPHERE","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
>> const signature = crypto
>> .createHmac("sha256", keyBin)
>>
>> .update(authString)
>> .digest("binary");
>> const signatureReturn = signature + authString;
>>
>> // AES-128-CBC encrypt signatureReturn using keyBin and ivBin return it
>> in base64
>> const cipher = crypto.createCipheriv("aes-128-cbc", keyBin, ivBin);
>> const encrypted = cipher.update(signatureReturn, "binary", "base64");
>> const encryptedSignature = encrypted + cipher.final("base64");
>> // convert encryptedSignature to base64
>>
>> const urlencodedSignature = encodeURIComponent(encryptedSignature);
>> const returnValue = `${url}${urlencodedSignature}`;
>> return returnValue;
>> }
>>
>> On 2022/01/26 21:00:16 Caleb Coverdale wrote:
>>
>> Hey there!
>>
>> I have been banging my head against the wall trying to get the
>> EncryptedJSON script working in Javascript.
>>
>> I was wondering if anyone has been down the rabbit hole and got it
>> working?
>>
>>
>> Any help would be appreciated…
>>
>>
>> Here’s what I have so far:
>>
>>
>>
>> const crypto = require("crypto");
>> const guacjson =
>> `{"username":"MyUser","connections":{"MyConnection":{"protocol":"rdp","parameters":{"hostname":"10.0.0.41","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
>> const secretkey = "fe57526d73a1e5116bbbefad1c91b38f";
>>
>> // sign the contents of guacjson with secret key using HMAC/SHA-256 out
>> in binary
>> function cryptedmessage() {
>> const hmac = crypto.createHmac("sha256", secretkey);
>> hmac.update(guacjson);
>> // output the hmac in binary followed by guacjson
>> signature = hmac.digest("binary") + guacjson;
>> return signature;
>> }
>>
>> const INITIALIZATION_VECTOR = "0000000000000000";
>>
>> class Crypt {
>> static encrypt128(data, key) {
>> const cipher = crypto.createCipheriv(
>> "aes-128-cbc",
>> Buffer.from(key, "hex"),
>> Buffer.from(INITIALIZATION_VECTOR)
>> );
>> // return cipher encoded as bas64
>> console.log(data);
>> const encrypted =
>> cipher.update(data, "utf8", "base64") + cipher.final("base64");
>> return encrypted;
>> }
>> }
>>
>> const key = "fe57526d73a1e5116bbbefad1c91b38f";
>>
>> const cipher = Crypt.encrypt128(cryptedmessage(), key);
>>
>> console.log(cipher);
>>
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: user-unsubscribe@guacamole.apache.org
>> <us...@guacamole.apache.org>
>> For additional commands, e-mail: user-help@guacamole.apache.org
>> <us...@guacamole.apache.org>
>>
>>
>>
>
Re: Encrypted JSON with Javascript
Posted by Caleb Coverdale <ca...@me.com.INVALID>.
Any chance you happen to know how to sign a user out via HTTP requests? Or if I were to use the URL such as:
http://localhost:8080/#/api/tokens?data=JSONENCRYPTEDHERE <http://localhost:8080/#/api/tokens?data=JSONENCRYPTEDHERE>
Every time I try to connect using that URL it is picking up LocalStorage and doesn’t throw me a new connection/user….. I am just trying to flush out the local storage and make it so every time I load a new URL from a page, it dynamically creates a per browser window of each guacamole connection…..
> On Feb 2, 2022, at 1:24 PM, Craig Sawyer <cs...@yumaunion.org> wrote:
>
> Interesting! Like I said, not a guac-crypto expert. I read the thread, but did not read the code, but as Chris Wheeler mentions in the linked thread, looks like the safe approach is to add a randomized nonce in your message, it should produce no differences in compatibility(per him), but enforce that no messages will ever be sent identically across the wire. i.e. in your authString, just add a key "nonce" with a random value.
>
> Glad you found that thread! Goes to show security and cryptography are hard. :)
>
>
>
> On Wed, Feb 2, 2022 at 11:50 AM Caleb Coverdale <ca...@me.com.invalid> wrote:
> From what I understood in this discussion here:
> [GUACAMOLE-1286] Support a custom IV in guacamole-auth-json - ASF JIRA (apache.org) <https://issues.apache.org/jira/projects/GUACAMOLE/issues/GUACAMOLE-1286?filter=allopenissues>
>
> There was discussion for allowing a non-null IV.
>
>
> guacamole-client/CryptoService.java at master · apache/guacamole-client (github.com) <https://github.com/apache/guacamole-client/blob/master/extensions/guacamole-auth-json/src/main/java/org/apache/guacamole/auth/json/CryptoService.java>
> In the CryptoService.js there is a comment regarding how they use the signature as the IV for decryption:
>
> /**
> * IV which is all null bytes (all binary zeroes). Usually, using a null IV
> * is a horrible idea. As our plaintext will always be prepended with the
> * HMAC signature of the rest of the message, we are effectively using the
> * HMAC signature itself as the IV. For our purposes, where the encrypted
> * value becomes an authentication token, this is OK.
> */
>
>
> So to me everything looks okay….
>
> So may not be the best to use the NULL IV, but there is still some security regarding the signature and decryption
>
>
>> On Feb 2, 2022, at 12:44 PM, Craig Sawyer <csawyer@yumaed.org <ma...@yumaed.org>> wrote:
>>
>> Glad you got it figured out!
>>
>> I'm not up to date with Guac's crypto code-base, but in case you
>> didn't know, you def. don't want to deploy with an iv of all 0's as a
>> static value. If this is just a proof of concept, no worries. Also
>> you don't check any error conditions, which for production crypto code
>> you most definitely will want to do.
>>
>> IV's are not secret, but they do need to be random(not technically,
>> but practically) and never re-used.
>>
>> Also, this is by no means considered an audit, I don't write JS(and
>> barely read the code) and am not trying to do that, just pointing out
>> some glaring errors, if you were not aware, or for others trying to
>> copy what you are doing down the road and not realizing IV's are
>> required to match the security promises of AES-128-CBC.
>>
>> Good Luck.
>>
>> On Wed, Feb 2, 2022 at 11:07 AM Caleb Coverdale
>> <calebcoverdale@me.com.invalid <ma...@me.com.invalid>> wrote:
>>>
>>> Here is a copy of the fixed code incase anyone has anymore issues:
>>>
>>> const crypto = require("crypto");
>>>
>>> const key = "KEYHERE";
>>> const iv = "00000000000000000000000000000000";
>>> // convert key to binary
>>> const keyBin = Buffer.from(key, "hex");
>>> const ivBin = Buffer.from(iv, "hex");
>>>
>>> // Sign the JSON using the key with the authString using sha256/hmac
>>> function encryptSign(keyBin, ivBin, username, url) {
>>> const calculateTime = Math.floor(Date.now() / 1000) + 300;
>>> const expiration = calculateTime + "000";
>>> const authString = `{"username":"${username}","expires":"${expiration}","connections":{"${expiration}":{"protocol":"rdp","parameters":{"hostname":"IPHERE","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
>>> const signature = crypto
>>> .createHmac("sha256", keyBin)
>>>
>>> .update(authString)
>>> .digest("binary");
>>> const signatureReturn = signature + authString;
>>>
>>> // AES-128-CBC encrypt signatureReturn using keyBin and ivBin return it in base64
>>> const cipher = crypto.createCipheriv("aes-128-cbc", keyBin, ivBin);
>>> const encrypted = cipher.update(signatureReturn, "binary", "base64");
>>> const encryptedSignature = encrypted + cipher.final("base64");
>>> // convert encryptedSignature to base64
>>>
>>> const urlencodedSignature = encodeURIComponent(encryptedSignature);
>>> const returnValue = `${url}${urlencodedSignature}`;
>>> return returnValue;
>>> }
>>>
>>> On 2022/01/26 21:00:16 Caleb Coverdale wrote:
>>>> Hey there!
>>>>
>>>> I have been banging my head against the wall trying to get the EncryptedJSON script working in Javascript.
>>>>
>>>> I was wondering if anyone has been down the rabbit hole and got it working?
>>>>
>>>>
>>>> Any help would be appreciated…
>>>>
>>>>
>>>> Here’s what I have so far:
>>>>
>>>>
>>>>
>>>> const crypto = require("crypto");
>>>> const guacjson = `{"username":"MyUser","connections":{"MyConnection":{"protocol":"rdp","parameters":{"hostname":"10.0.0.41","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
>>>> const secretkey = "fe57526d73a1e5116bbbefad1c91b38f";
>>>>
>>>> // sign the contents of guacjson with secret key using HMAC/SHA-256 out in binary
>>>> function cryptedmessage() {
>>>> const hmac = crypto.createHmac("sha256", secretkey);
>>>> hmac.update(guacjson);
>>>> // output the hmac in binary followed by guacjson
>>>> signature = hmac.digest("binary") + guacjson;
>>>> return signature;
>>>> }
>>>>
>>>> const INITIALIZATION_VECTOR = "0000000000000000";
>>>>
>>>> class Crypt {
>>>> static encrypt128(data, key) {
>>>> const cipher = crypto.createCipheriv(
>>>> "aes-128-cbc",
>>>> Buffer.from(key, "hex"),
>>>> Buffer.from(INITIALIZATION_VECTOR)
>>>> );
>>>> // return cipher encoded as bas64
>>>> console.log(data);
>>>> const encrypted =
>>>> cipher.update(data, "utf8", "base64") + cipher.final("base64");
>>>> return encrypted;
>>>> }
>>>> }
>>>>
>>>> const key = "fe57526d73a1e5116bbbefad1c91b38f";
>>>>
>>>> const cipher = Crypt.encrypt128(cryptedmessage(), key);
>>>>
>>>> console.log(cipher);
>>
>> ---------------------------------------------------------------------
>> To unsubscribe, e-mail: user-unsubscribe@guacamole.apache.org <ma...@guacamole.apache.org>
>> For additional commands, e-mail: user-help@guacamole.apache.org <ma...@guacamole.apache.org>
>>
>
Re: Encrypted JSON with Javascript
Posted by Craig Sawyer <cs...@yumaunion.org>.
Interesting! Like I said, not a guac-crypto expert. I read the thread, but
did not read the code, but as Chris Wheeler mentions in the linked thread,
looks like the safe approach is to add a randomized nonce in your message,
it should produce no differences in compatibility(per him), but enforce
that no messages will ever be sent identically across the wire. i.e. in
your authString, just add a key "nonce" with a random value.
Glad you found that thread! Goes to show security and cryptography are
hard. :)
On Wed, Feb 2, 2022 at 11:50 AM Caleb Coverdale
<ca...@me.com.invalid> wrote:
> From what I understood in this discussion here:
> [GUACAMOLE-1286] Support a custom IV in guacamole-auth-json - ASF JIRA
> (apache.org)
> <https://issues.apache.org/jira/projects/GUACAMOLE/issues/GUACAMOLE-1286?filter=allopenissues>
>
> There was discussion for allowing a non-null IV.
>
>
> guacamole-client/CryptoService.java at master · apache/guacamole-client
> (github.com)
> <https://github.com/apache/guacamole-client/blob/master/extensions/guacamole-auth-json/src/main/java/org/apache/guacamole/auth/json/CryptoService.java>
> In the CryptoService.js there is a comment regarding how they use the
> signature as the IV for decryption:
>
> /**
> * IV which is all null bytes (all binary zeroes). Usually, using a null IV
> * is a horrible idea. As our plaintext will always be prepended with the
> * HMAC signature of the rest of the message, we are effectively using the
> * HMAC signature itself as the IV. For our purposes, where the encrypted
> * value becomes an authentication token, this is OK.
> */
>
>
> So to me everything looks okay….
>
> So may not be the best to use the NULL IV, but there is still some
> security regarding the signature and decryption
>
>
> On Feb 2, 2022, at 12:44 PM, Craig Sawyer <cs...@yumaed.org> wrote:
>
> Glad you got it figured out!
>
> I'm not up to date with Guac's crypto code-base, but in case you
> didn't know, you def. don't want to deploy with an iv of all 0's as a
> static value. If this is just a proof of concept, no worries. Also
> you don't check any error conditions, which for production crypto code
> you most definitely will want to do.
>
> IV's are not secret, but they do need to be random(not technically,
> but practically) and never re-used.
>
> Also, this is by no means considered an audit, I don't write JS(and
> barely read the code) and am not trying to do that, just pointing out
> some glaring errors, if you were not aware, or for others trying to
> copy what you are doing down the road and not realizing IV's are
> required to match the security promises of AES-128-CBC.
>
> Good Luck.
>
> On Wed, Feb 2, 2022 at 11:07 AM Caleb Coverdale
> <ca...@me.com.invalid> wrote:
>
>
> Here is a copy of the fixed code incase anyone has anymore issues:
>
> const crypto = require("crypto");
>
> const key = "KEYHERE";
> const iv = "00000000000000000000000000000000";
> // convert key to binary
> const keyBin = Buffer.from(key, "hex");
> const ivBin = Buffer.from(iv, "hex");
>
> // Sign the JSON using the key with the authString using sha256/hmac
> function encryptSign(keyBin, ivBin, username, url) {
> const calculateTime = Math.floor(Date.now() / 1000) + 300;
> const expiration = calculateTime + "000";
> const authString =
> `{"username":"${username}","expires":"${expiration}","connections":{"${expiration}":{"protocol":"rdp","parameters":{"hostname":"IPHERE","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
> const signature = crypto
> .createHmac("sha256", keyBin)
>
> .update(authString)
> .digest("binary");
> const signatureReturn = signature + authString;
>
> // AES-128-CBC encrypt signatureReturn using keyBin and ivBin return it in
> base64
> const cipher = crypto.createCipheriv("aes-128-cbc", keyBin, ivBin);
> const encrypted = cipher.update(signatureReturn, "binary", "base64");
> const encryptedSignature = encrypted + cipher.final("base64");
> // convert encryptedSignature to base64
>
> const urlencodedSignature = encodeURIComponent(encryptedSignature);
> const returnValue = `${url}${urlencodedSignature}`;
> return returnValue;
> }
>
> On 2022/01/26 21:00:16 Caleb Coverdale wrote:
>
> Hey there!
>
> I have been banging my head against the wall trying to get the
> EncryptedJSON script working in Javascript.
>
> I was wondering if anyone has been down the rabbit hole and got it working?
>
>
> Any help would be appreciated…
>
>
> Here’s what I have so far:
>
>
>
> const crypto = require("crypto");
> const guacjson =
> `{"username":"MyUser","connections":{"MyConnection":{"protocol":"rdp","parameters":{"hostname":"10.0.0.41","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
> const secretkey = "fe57526d73a1e5116bbbefad1c91b38f";
>
> // sign the contents of guacjson with secret key using HMAC/SHA-256 out in
> binary
> function cryptedmessage() {
> const hmac = crypto.createHmac("sha256", secretkey);
> hmac.update(guacjson);
> // output the hmac in binary followed by guacjson
> signature = hmac.digest("binary") + guacjson;
> return signature;
> }
>
> const INITIALIZATION_VECTOR = "0000000000000000";
>
> class Crypt {
> static encrypt128(data, key) {
> const cipher = crypto.createCipheriv(
> "aes-128-cbc",
> Buffer.from(key, "hex"),
> Buffer.from(INITIALIZATION_VECTOR)
> );
> // return cipher encoded as bas64
> console.log(data);
> const encrypted =
> cipher.update(data, "utf8", "base64") + cipher.final("base64");
> return encrypted;
> }
> }
>
> const key = "fe57526d73a1e5116bbbefad1c91b38f";
>
> const cipher = Crypt.encrypt128(cryptedmessage(), key);
>
> console.log(cipher);
>
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: user-unsubscribe@guacamole.apache.org
> <us...@guacamole.apache.org>
> For additional commands, e-mail: user-help@guacamole.apache.org
> <us...@guacamole.apache.org>
>
>
>
Re: Encrypted JSON with Javascript
Posted by Caleb Coverdale <ca...@me.com.INVALID>.
From what I understood in this discussion here:
[GUACAMOLE-1286] Support a custom IV in guacamole-auth-json - ASF JIRA (apache.org) <https://issues.apache.org/jira/projects/GUACAMOLE/issues/GUACAMOLE-1286?filter=allopenissues>
There was discussion for allowing a non-null IV.
guacamole-client/CryptoService.java at master · apache/guacamole-client (github.com) <https://github.com/apache/guacamole-client/blob/master/extensions/guacamole-auth-json/src/main/java/org/apache/guacamole/auth/json/CryptoService.java>
In the CryptoService.js there is a comment regarding how they use the signature as the IV for decryption:
/**
* IV which is all null bytes (all binary zeroes). Usually, using a null IV
* is a horrible idea. As our plaintext will always be prepended with the
* HMAC signature of the rest of the message, we are effectively using the
* HMAC signature itself as the IV. For our purposes, where the encrypted
* value becomes an authentication token, this is OK.
*/
So to me everything looks okay….
So may not be the best to use the NULL IV, but there is still some security regarding the signature and decryption
> On Feb 2, 2022, at 12:44 PM, Craig Sawyer <cs...@yumaed.org> wrote:
>
> Glad you got it figured out!
>
> I'm not up to date with Guac's crypto code-base, but in case you
> didn't know, you def. don't want to deploy with an iv of all 0's as a
> static value. If this is just a proof of concept, no worries. Also
> you don't check any error conditions, which for production crypto code
> you most definitely will want to do.
>
> IV's are not secret, but they do need to be random(not technically,
> but practically) and never re-used.
>
> Also, this is by no means considered an audit, I don't write JS(and
> barely read the code) and am not trying to do that, just pointing out
> some glaring errors, if you were not aware, or for others trying to
> copy what you are doing down the road and not realizing IV's are
> required to match the security promises of AES-128-CBC.
>
> Good Luck.
>
> On Wed, Feb 2, 2022 at 11:07 AM Caleb Coverdale
> <ca...@me.com.invalid> wrote:
>>
>> Here is a copy of the fixed code incase anyone has anymore issues:
>>
>> const crypto = require("crypto");
>>
>> const key = "KEYHERE";
>> const iv = "00000000000000000000000000000000";
>> // convert key to binary
>> const keyBin = Buffer.from(key, "hex");
>> const ivBin = Buffer.from(iv, "hex");
>>
>> // Sign the JSON using the key with the authString using sha256/hmac
>> function encryptSign(keyBin, ivBin, username, url) {
>> const calculateTime = Math.floor(Date.now() / 1000) + 300;
>> const expiration = calculateTime + "000";
>> const authString = `{"username":"${username}","expires":"${expiration}","connections":{"${expiration}":{"protocol":"rdp","parameters":{"hostname":"IPHERE","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
>> const signature = crypto
>> .createHmac("sha256", keyBin)
>>
>> .update(authString)
>> .digest("binary");
>> const signatureReturn = signature + authString;
>>
>> // AES-128-CBC encrypt signatureReturn using keyBin and ivBin return it in base64
>> const cipher = crypto.createCipheriv("aes-128-cbc", keyBin, ivBin);
>> const encrypted = cipher.update(signatureReturn, "binary", "base64");
>> const encryptedSignature = encrypted + cipher.final("base64");
>> // convert encryptedSignature to base64
>>
>> const urlencodedSignature = encodeURIComponent(encryptedSignature);
>> const returnValue = `${url}${urlencodedSignature}`;
>> return returnValue;
>> }
>>
>> On 2022/01/26 21:00:16 Caleb Coverdale wrote:
>>> Hey there!
>>>
>>> I have been banging my head against the wall trying to get the EncryptedJSON script working in Javascript.
>>>
>>> I was wondering if anyone has been down the rabbit hole and got it working?
>>>
>>>
>>> Any help would be appreciated…
>>>
>>>
>>> Here’s what I have so far:
>>>
>>>
>>>
>>> const crypto = require("crypto");
>>> const guacjson = `{"username":"MyUser","connections":{"MyConnection":{"protocol":"rdp","parameters":{"hostname":"10.0.0.41","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
>>> const secretkey = "fe57526d73a1e5116bbbefad1c91b38f";
>>>
>>> // sign the contents of guacjson with secret key using HMAC/SHA-256 out in binary
>>> function cryptedmessage() {
>>> const hmac = crypto.createHmac("sha256", secretkey);
>>> hmac.update(guacjson);
>>> // output the hmac in binary followed by guacjson
>>> signature = hmac.digest("binary") + guacjson;
>>> return signature;
>>> }
>>>
>>> const INITIALIZATION_VECTOR = "0000000000000000";
>>>
>>> class Crypt {
>>> static encrypt128(data, key) {
>>> const cipher = crypto.createCipheriv(
>>> "aes-128-cbc",
>>> Buffer.from(key, "hex"),
>>> Buffer.from(INITIALIZATION_VECTOR)
>>> );
>>> // return cipher encoded as bas64
>>> console.log(data);
>>> const encrypted =
>>> cipher.update(data, "utf8", "base64") + cipher.final("base64");
>>> return encrypted;
>>> }
>>> }
>>>
>>> const key = "fe57526d73a1e5116bbbefad1c91b38f";
>>>
>>> const cipher = Crypt.encrypt128(cryptedmessage(), key);
>>>
>>> console.log(cipher);
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: user-unsubscribe@guacamole.apache.org
> For additional commands, e-mail: user-help@guacamole.apache.org
>
Re: Encrypted JSON with Javascript
Posted by Craig Sawyer <cs...@yumaed.org>.
Glad you got it figured out!
I'm not up to date with Guac's crypto code-base, but in case you
didn't know, you def. don't want to deploy with an iv of all 0's as a
static value. If this is just a proof of concept, no worries. Also
you don't check any error conditions, which for production crypto code
you most definitely will want to do.
IV's are not secret, but they do need to be random(not technically,
but practically) and never re-used.
Also, this is by no means considered an audit, I don't write JS(and
barely read the code) and am not trying to do that, just pointing out
some glaring errors, if you were not aware, or for others trying to
copy what you are doing down the road and not realizing IV's are
required to match the security promises of AES-128-CBC.
Good Luck.
On Wed, Feb 2, 2022 at 11:07 AM Caleb Coverdale
<ca...@me.com.invalid> wrote:
>
> Here is a copy of the fixed code incase anyone has anymore issues:
>
> const crypto = require("crypto");
>
> const key = "KEYHERE";
> const iv = "00000000000000000000000000000000";
> // convert key to binary
> const keyBin = Buffer.from(key, "hex");
> const ivBin = Buffer.from(iv, "hex");
>
> // Sign the JSON using the key with the authString using sha256/hmac
> function encryptSign(keyBin, ivBin, username, url) {
> const calculateTime = Math.floor(Date.now() / 1000) + 300;
> const expiration = calculateTime + "000";
> const authString = `{"username":"${username}","expires":"${expiration}","connections":{"${expiration}":{"protocol":"rdp","parameters":{"hostname":"IPHERE","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
> const signature = crypto
> .createHmac("sha256", keyBin)
>
> .update(authString)
> .digest("binary");
> const signatureReturn = signature + authString;
>
> // AES-128-CBC encrypt signatureReturn using keyBin and ivBin return it in base64
> const cipher = crypto.createCipheriv("aes-128-cbc", keyBin, ivBin);
> const encrypted = cipher.update(signatureReturn, "binary", "base64");
> const encryptedSignature = encrypted + cipher.final("base64");
> // convert encryptedSignature to base64
>
> const urlencodedSignature = encodeURIComponent(encryptedSignature);
> const returnValue = `${url}${urlencodedSignature}`;
> return returnValue;
> }
>
> On 2022/01/26 21:00:16 Caleb Coverdale wrote:
> > Hey there!
> >
> > I have been banging my head against the wall trying to get the EncryptedJSON script working in Javascript.
> >
> > I was wondering if anyone has been down the rabbit hole and got it working?
> >
> >
> > Any help would be appreciated…
> >
> >
> > Here’s what I have so far:
> >
> >
> >
> > const crypto = require("crypto");
> > const guacjson = `{"username":"MyUser","connections":{"MyConnection":{"protocol":"rdp","parameters":{"hostname":"10.0.0.41","port":"3389","security":"nla","ignore-cert":"true"}}}}`;
> > const secretkey = "fe57526d73a1e5116bbbefad1c91b38f";
> >
> > // sign the contents of guacjson with secret key using HMAC/SHA-256 out in binary
> > function cryptedmessage() {
> > const hmac = crypto.createHmac("sha256", secretkey);
> > hmac.update(guacjson);
> > // output the hmac in binary followed by guacjson
> > signature = hmac.digest("binary") + guacjson;
> > return signature;
> > }
> >
> > const INITIALIZATION_VECTOR = "0000000000000000";
> >
> > class Crypt {
> > static encrypt128(data, key) {
> > const cipher = crypto.createCipheriv(
> > "aes-128-cbc",
> > Buffer.from(key, "hex"),
> > Buffer.from(INITIALIZATION_VECTOR)
> > );
> > // return cipher encoded as bas64
> > console.log(data);
> > const encrypted =
> > cipher.update(data, "utf8", "base64") + cipher.final("base64");
> > return encrypted;
> > }
> > }
> >
> > const key = "fe57526d73a1e5116bbbefad1c91b38f";
> >
> > const cipher = Crypt.encrypt128(cryptedmessage(), key);
> >
> > console.log(cipher);
---------------------------------------------------------------------
To unsubscribe, e-mail: user-unsubscribe@guacamole.apache.org
For additional commands, e-mail: user-help@guacamole.apache.org