1

As the title suggest i am having difficulty in passing the value of a nonce publicly through a form. I have tried using both a hidden field in the form and passing the value as a parameter in the url.

The nonce is created using:

$nonce = random_bytes(SODIUM_CRYPTO_SECRETBOX_NONCEBYTES)

When I try to use the retrieved value (eg sodium_crypto_secretbox_open) form either a hidden field (POST) or the url (GET) the following error is returned:

Uncaught SodiumException: nonce size should be SODIUM_CRYPTO_SECRETBOX_NONCEBYTES bytes

I appreciate that the size of the nonce string is being affected, but I have no idea how to counter this issue.

When I echo out the retrieved nonce it looks fine. There appears to be an issue after the nonce is echo'd out that it changes size and is deemed inappropriate to be used by sodium.

Any advice would be greatly appreciated.

noelmcg
  • 1,057
  • 3
  • 21
  • 44

2 Answers2

4

Binary values do not translate well when sent in the request so one thing you might consider would be to convert the raw nonce value using bin2hex, add as the hidden input and then to process reverse the process using hex2bin

$nonce = random_bytes(SODIUM_CRYPTO_SECRETBOX_NONCEBYTES);
$hex=bin2hex($nonce);
/* add the above $hex as the hidden input */

/* serverside decode the input*/
$bin=hex2bin($hex);


<form method='post'>
    <input type='hidden' name='nonce' value='<?php echo $hex;?>' />
    <!-- other elements -->
    <input type='submit' />
</form>


 /* serverside */   
 $bin=hex2bin( $_POST['nonce'] );

Update: Reading further on these native sodium methods sodium_hex2bin and sodium_bin2hex

Like sodium_bin2hex(), sodium_hex2bin() is resistant to side-channel attacks while hex2bin() is not.

Professor Abronsius
  • 33,063
  • 5
  • 32
  • 46
  • thats great, and it can work by creating a useable nonce that can be passed via the form. Am I correct in saying that it does change the original nonce by going bin2hex -> hex2bin. It appears to lose whitespace etc ... – noelmcg Apr 05 '19 at 13:03
  • Also, I now find myself with another issue. How to pass the encrypted message (the output of sodium_crypto_secretbox ) via a form. I can't use the above technique as it appears to alter the string – noelmcg Apr 05 '19 at 13:05
  • I think it encodes the whitespace from the binary / raw version. As for the 2nd point: as soon as you post the data it will be url encoded - did you factor that in before further processing? – Professor Abronsius Apr 05 '19 at 13:59
  • 2
    I have never used `sodium` before but just looked in the manual - it appears there is `sodium_bin2base64()` which might be of interst as base64 encoded strings can be passed in urls or form values easily. Looks like other methods might be of interest too such as `sodium_bin2hex` and `sodium_hex2bin` these last two presumably were created to deal with situaltions such as the one your have found yourself in now?! – Professor Abronsius Apr 05 '19 at 14:01
  • I've been going around in circles with this but it looks like those functions will be exactly what I am after. Thanks a million for finding those out, I will test and update you as to the progress. thanks again. – noelmcg Apr 05 '19 at 14:14
  • ````sodium_bin2hex```` and its inverse did the job, worked with nonce and encrypted message. Thanks for all of your help with this. cheers – noelmcg Apr 10 '19 at 12:58
  • glad to have been able to assist – Professor Abronsius Apr 10 '19 at 13:01
0

Use SODIUM_CRYPTO_BOX_NONCEBYTES and not SODIUM_CRYPTO_SECRETBOX_NONCEBYTES.