💾 Archived View for thrig.me › blog › 2024 › 06 › 20 › bad-encryption.gmi captured on 2024-07-09 at 01:46:10. Gemini links have been rewritten to link to archived content

View Raw

More Information

-=-=-=-=-=-=-

Bad Encryption

/blog/2024/04/27/abba-encryption.gmi

ABBA isn't very good when both AB and BA can decrypt the message, and the intent is that one of those pairs cannot decrypt what they just encrypted, which is probably mentioned in the libsodium documentation but is easy enough to miss, though is mentioned in

https://flak.tedunangst.com/post/reop

which can be confirmed with some test code.

    #include <err.h>
    #include <sodium.h>

    #define MESSAGE (const unsigned char *) "blub"
    #define MESSAGE_LEN 4
    #define CIPHERTEXT_LEN (crypto_box_MACBYTES + MESSAGE_LEN)

    int
    main(int argc, char *argv[])
    {
        unsigned char alice_pub[crypto_box_PUBLICKEYBYTES];
        unsigned char bobby_pub[crypto_box_PUBLICKEYBYTES];
        unsigned char alice_key[crypto_box_SECRETKEYBYTES];
        unsigned char bobby_key[crypto_box_SECRETKEYBYTES];

        if (sodium_init()) err(1, "sodium_init");

        if (crypto_box_keypair(alice_pub, alice_key))
            errx(1, "crypto_box_keypair");
        if (crypto_box_keypair(bobby_pub, bobby_key))
            errx(1, "crypto_box_keypair");

        unsigned char nonce[crypto_box_NONCEBYTES];
        randombytes_buf(nonce, sizeof nonce);

        unsigned char ciphertext[CIPHERTEXT_LEN];
        unsigned char decrypted[MESSAGE_LEN];

        if (crypto_box_easy(ciphertext, MESSAGE, MESSAGE_LEN, nonce, bobby_pub,
                            alice_key))
            errx(1, "crypto_box_easy");

        if (crypto_box_open_easy(decrypted, ciphertext, CIPHERTEXT_LEN, nonce,
                                 alice_pub, bobby_key)) {
            errx(1, "crypto_box_open_easy");
        }
        printf("%.*s\n", MESSAGE_LEN, decrypted);
        // but can Alice also read it? yes!
        if (crypto_box_open_easy(decrypted, ciphertext, CIPHERTEXT_LEN, nonce,
                                 bobby_pub, alice_key)) {
            errx(1, "crypto_box_open_easy");
        }
        printf("%.*s\n", MESSAGE_LEN, decrypted);
    }

asymmetric.c

    $ CFLAGS=`pkg-config --cflags --libs libsodium` make asymmetric
    cc -I/usr/local/include -L/usr/local/lib -lsodium   -o asymmetric asymmetric.c
    $ ./asymmetric
    blub
    blub

Whoops!

There is a "crypto_box_seal" in libsodium that will prevent (or better prevent—someone could be stealing the ephemeral keys from memory, but if they can do that then they can probably also read what is being encrypted at the moment) the sender from being able to decrypt files pending pickup by the recipient.

Now to rewrite some code… maybe I should ditch libsodium and only use LibreSSL functions?