Skip to content

Directly Using Ciphers

Bren2010 edited this page Nov 2, 2014 · 2 revisions

Ciphers are implemented as classes which are constructed with a secret key (not a password). Given an instance of a cipher, you can call the encrypt or decrypt methods to operate on one block at a time.

var prp = new sjcl.cipher.aes(key)

prp.encrypt([...])
prp.decrypt([...])

Cipher modes, on the other hand, are implemented as singletons exposing encrypt and decrypt methods. (See the technical documentation for more info.)

var prp = new sjcl.cipher.aes(key)

// Outputs a bitArray.
sjcl.mode.ccm.encrypt(prp, plaintext, iv, adata)
sjcl.mode.ccm.decrypt(prp, ciphertext, iv, adata)

Because the cipher modes do almost no packing for you, there's the upside that you can put everything you want to send in adata (leaving plaintext empty) and treat the encrypt function as a MAC. CBC-MAC (CCM), GMAC (GCM), and OCB2-MAC (OCB2) are all faster than usual HMACs. Even better, GMAC is half the size and CBC-MAC and OCB2-MAC are a quarter the size of HMAC-SHA256 if you stretch the shared secret key to a (key, IV) pair.

Of course, the downside is that you have to find a way to pack and parse the data yourself.

CBC

CBC mode is implemented, however it has to be included with the --with-cbc option and enabled at runtime by adding a disclaimer line of code:

sjcl.beware["CBC mode is dangerous because it doesn't protect message integrity."]()

Once the disclaimer has been added, CBC will show up in the sjcl.mode object. As made clear by the disclaimer, CBC mode doesn't protect message integrity or support associated data so it should be paired with an HMAC or any of the MACs discussed above if message integrity is desired.