Golang BoxThe Go Box package supports the encryption and authentication of short messages, using Curve25519, XSalsa20 and Poly1305. |
Outline
The Box package works in a similar way to PGP email, and where Bob generates a symmetric key and uses the XSala20 encryption method to encrypt the message. Bob then takes a hash of this message, and encrypt it with his private key, and this is included in the encrypted message. Bob then encrypts the XSala20 key with Alice’s public key. He then send the encrypted message to her, and she will decrypt the key used to encrypt the message with her private key. She can then read them message. Now see checks the signature. For this she takes Bob’s public key, and then decrypts the hash. If she can decrypt it, she checks the hash against the hash that she gets, and if they are the same, she knows that it was Bob who send the message, and that the message is unchanged:
The Go Box package supports the encryption and authentication of short messages, using Curve25519, XSalsa20 and Poly1305. In this case we generate a public and private key for Bob and also for Alice. The public key is displayed as the x-co-ordinate of the public key point. The following is a sample of the code:
The Box package works in a similar way to PGP email, and where Bob generates a symmetric key and uses the XSalsa20 encryption method to encrypt the message. Bob then takes a hash of this message, and encrypt it with his private key, and this is included in the encrypted message. Bob then encrypts the XSalsa20 key with Alice’s public key. He then sends the encrypted message to her, and she will decrypt the key used to encrypt the message with her private key. She can then read the message. Now she checks the signature. For this, she takes Bob’s public key and then decrypts the hash. If she can decrypt it, she checks the hash against the hash that she gets, and if they are the same, she knows that it was Bob who sent the message, and that the message is unchanged:
package main import ( "golang.org/x/crypto/nacl/box" "crypto/rand" "io" "fmt" "flag" ) func main() { flag.Parse() args := flag.Args() message:=args[0] AlicePublicKey, AlicePrivateKey, _ := box.GenerateKey(rand.Reader) fmt.Printf("Alice private %x\n",*AlicePrivateKey) fmt.Printf("Alice public (x-co-ord) %x\n",*AlicePublicKey) BobPublicKey, BobPrivateKey, _ := box.GenerateKey(rand.Reader) fmt.Printf("\nBob private %x\n",*BobPrivateKey) fmt.Printf("Bob public (x-co-ord) %x\n",*BobPublicKey) var nonce [24]byte io.ReadFull(rand.Reader, nonce[:]) msg := []byte(message) encrypted := box.Seal(nonce[:], msg, &nonce, BobPublicKey, AlicePrivateKey) var decryptNonce [24]byte copy(decryptNonce[:], encrypted[:24]) decrypted, _ := box.Open(nil, encrypted[24:], &decryptNonce, AlicePublicKey, BobPrivateKey) fmt.Printf("\nMessage: %s\n",message) fmt.Printf("\nEncrypted: %x\n\n",encrypted) fmt.Printf("Decrypted %s",string(decrypted)) }
The following is a sample run:
Alice private 3b4d6f7784b997ac262071c78a1a605af93f6e32e76ddeed3119fcabbd3b829f Alice public (x-co-ord) 5c999ef6915b5cec518861303e67de37d9e1b842218c2820cebff4e547912329 Bob private aa1ba56956c75523c8a7f926d0356989c040ea7092cd7d16d25d1aadddda09da Bob public (x-co-ord) b70cfc4613bf35eed81d58a5d211e4197d207c1a88ee494a3ecd4bd5d85dcb26 Message: abc Encrypted: 06686a97f5e4fb11d9c90befac2d283cc5730df6942e58d6e6548a3b76c7dd17a4d107a525ca468a85e98d Decrypted abc
We see that Alice takes the the message, and the nonce, and then signs the message with her private key. Next she will encrypt the message and the signature with Bob's public key:
encrypted := box.Seal(nonce[:], msg, &nonce, BobPublicKey, AlicePrivateKey)
Bob will then take the first 24 bytes of the encrypted data, and use this as the nonce, and the rest as the cipher stream. He will then decrypt with his private key, and checks the signature using Alice's public key.
decrypted, _ := box.Open(nil, encrypted[24:], &decryptNonce, AlicePublicKey, BobPrivateKey)
In this way we have security (using Bob's public and private keys) and authenication of Alice and her message (using Alice's public and private keys). The way it works is that we use an XSala20 symmetric key to encrypt the message, and which is encrypted with Alice's public key. Only she can then decrypt this key, and thus decrypt the encrypted message.