1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90
|
Notes on strategy, message format, algorithm, and future work:
Strategy: Incoming messages:
The plugin intercepts incoming messages, and looks for the
CRYPT_HEADER at the beginning of the message. Tagged messages
are either an incoming public key, a request to send a public
key, or an encrypted message. Incoming keys are stored,
and encrypted messages are decrypted with your private key.
NEW: when a key comes in, it looks through a list of all of the
protocols that it knows about, and sees which one wants to
claim the key. That protocol is then "attached" to the key
and is used for all further encryptions with that key.
Outgoing messages:
are also intercepted, and if the user wants the message encrypted,
it is. The message is then sent directly (not passed back to the
caller) and displayed directly, as otherwise the sender will see
the encrypted text. This intercept is now done through
event_displayed_sent, so it should happen _after_ all other
plugins get their shot at the message.
Messages have CRYPT_HEADER pre-pended, and CRYPT_FOOTER appended.
Message format:
Since CRYPT_HEADER is the start of an HTML block, and
CRYPT_FOOTER is the end of it, a non-encrypted-plugin client
will see some text telling them to load their encryption plugin
rather than a block of garbage.
Encrypted blocks are sent Base64 encoded.
Algorithm:
Uses Mozilla's NSS libraries to do RSA encryption. All padding
on encryption is done with OAEP, all signatures are done with PSS.
Signs the outgoing message with your private key, then
encrypts with other user's public key. This gives us both encryption
and authentication (no man in the middle attacks, if our
original key transmissions were not fooled with).
Note: this isn't really the way that RSA is normally used.
Usually, you only use RSA to send a session key across,
then you use that session key with a symmetric cypher
like Blowfish or AES. There are a few reasons that folks
do this:
1) Speed. RSA is slow. Symmetric cyphers are fast.
2) RSA has some weaknesses with chosen plaintext attacks.
ie: if I can pick the text that you will sign with
your private key, then from the result I can deduce
your private key. Bad!
1) really isn't a problem here on a standard computer.
if you want to send large files through IM, it might
be a problem, though.
2) As long as we don't allow someone else to specify the
text we send, there can't be any chosen plaintext
attacks. Running an echo-bot on your encrypted link
would be bad, but otherwise, we're ok.
There are some small reasons for us _not_ to use the
symmetric cypher approach: Say the other party logs out,
then logs back in. A symmetric cypher approach needs to
re-negotiate a session key; we don't. Another way of putting
it: without session keys, we are more stateless, which gives
us some flexibility.
Almost everything described below (for my old RSA algorithm)
is done better by the OpenSSL crypto library. It is faster,
does its padding in a standard way (PKCS1_OAEP), and uses
the hardware entropy in most OS'es. In addition, it offers
"blinding" to prevent timing attacks, although I suspect that
a timing attack would be fairly difficult for a remote
opponent to implement in most IM situations.
Keys are saved into the user's .pidgin directory.
Todo:
We should probably have a help button on the key accept dialogs
and on the config dialog, telling people what things mean.
Why:
Because I don't like sending root passwords to people in plain
text.
Plus, the startup I was with folded, and I had some free time :)
Bill Tompkins- Email: bill(at)icarion.com, BillTompkins2 on AIM
|