JavaScript and crypto

2011/08/30 — 3 Comments

After reading this thought-provoking post: http://www.matasano.com/articles/javascript-cryptography/ I thought I would enumerate some of the concerns raised and try to explain how DOMCrypt handles at least some of problems that are inherent in JavaScript cryptography.

  • DOMCrypt is not a low-level crypto API. DOMCrypt is very high-level, making it much harder to ‘do it wrong’. The only configuration is telling DOMCrypt what algorithm to use. See: https://wiki.mozilla.org/Privacy/Features/DOMCryptAPISpec/Latest
  • Private key material is never exposed to content JS. Each keypair is represented by an ID. This keeps the key material in a secure key store outside of content. (In the case of Firefox, the key material will be stored in NSS’ key database)
  • Each domain/origin will have its own keypair. You will have to know the ‘KeyID’ to use the domain’s keypair to encrypt data. Being able to handle secret key material in content is ‘doing it wrong’. The original DOMCrypt prototype code as well as all of the crypto libraries do this. Not good.
  • All algorithms are well designed, well tested and maintained crypto functions created by tried and true cryptographers (In the case of Firefox’s implementation we have NSS under the covers). Millions of users have depended on this underlying crypto for a decade plus. Part of the motivation for DOMCrypt is that each site might roll their own crypto implementation, or use an implementation that is out in the wild, which are likely to be subtly wrong.  By providing DOMCrypt, we can leverage all the careful scrutiny that has already gone into browser crypto implementations. We are not re-building the wheel. (Random numbers are truly random as we are calling into NSS or other system crypto depending on the browser implementation)
  • Fast. This is not a concern in the Matasano article, but I think it is a valid point. DOMCrypt calls crypto functions written in C, so all of the crypto operations are quite fast.

There are, of course, still many concerns even with a built in crypto API, but I think it is a step in the right direction. Moving all of the heavy crypto operations into the browser itself and exposing only a high-level API to consumers is the beginning. Making encryption as trustworthy as possible in a malleable content JavaScript environment will take some additional work.

 

*thanks to Adam Barth for input

3 responses to JavaScript and crypto

  1. 

    I like the way this has progressed… very focused on providing something simple and coherent.
    I’ve got a quick question…

    What’s the plan around privacy/identification? getPublicKey() looks like it provides a powerful user tracking feature.

    • 

      It is still unclear whether or not we will need to have getPublicKey() as generateKeyPair() will return the public key when the keypair is generated. Something to keep in mind: the public key for foobar.com can only be used on foobar.com. Each user will have a unique public key for each domain where the API is used – in which case, there is not a “super cookie”. The current extension (prototype) implementation has only a single keypair, which could be used for tracking.

      • 

        Sure, but it’s easy enough to serve up JS in an iframe which sends the result of getPublicKey back to the server.

        My gut feel is:
        – that there shouldn’t be a getPublicKey, or it should take the ID as a param
        – that generateKeyPair should be (more clearly) specced to overwrite any existing key
        – that private browsing mode behaviour should be specced – presumably the obvious behaviour

        Another spec thought..
        – the encrypt/decrypt/sign/verify calls should have a defined backoff to prevent guesses at the keyID

Leave a comment