1
2#define TEST_NAME "box_easy2"
3#include "cmptest.h"
4
5static const unsigned char small_order_p[crypto_box_PUBLICKEYBYTES] = {
6    0xe0, 0xeb, 0x7a, 0x7c, 0x3b, 0x41, 0xb8, 0xae, 0x16, 0x56, 0xe3,
7    0xfa, 0xf1, 0x9f, 0xc4, 0x6a, 0xda, 0x09, 0x8d, 0xeb, 0x9c, 0x32,
8    0xb1, 0xfd, 0x86, 0x62, 0x05, 0x16, 0x5f, 0x49, 0xb8, 0x00
9};
10
11int
12main(void)
13{
14    unsigned char *alicepk;
15    unsigned char *alicesk;
16    unsigned char *bobpk;
17    unsigned char *bobsk;
18    unsigned char *mac;
19    unsigned char *nonce;
20    unsigned char *k1;
21    unsigned char *k2;
22    unsigned char *m;
23    unsigned char *m2;
24    unsigned char *c;
25    size_t         mlen;
26    size_t         i;
27    size_t         m_size;
28    size_t         m2_size;
29    size_t         c_size;
30    int            ret;
31
32    m2_size = m_size = 7U + randombytes_uniform(1000);
33    c_size           = crypto_box_MACBYTES + m_size;
34    m                = (unsigned char *) sodium_malloc(m_size);
35    m2               = (unsigned char *) sodium_malloc(m2_size);
36    c                = (unsigned char *) sodium_malloc(c_size);
37    alicepk = (unsigned char *) sodium_malloc(crypto_box_PUBLICKEYBYTES);
38    alicesk = (unsigned char *) sodium_malloc(crypto_box_SECRETKEYBYTES);
39    bobpk   = (unsigned char *) sodium_malloc(crypto_box_PUBLICKEYBYTES);
40    bobsk   = (unsigned char *) sodium_malloc(crypto_box_SECRETKEYBYTES);
41    mac     = (unsigned char *) sodium_malloc(crypto_box_MACBYTES);
42    nonce   = (unsigned char *) sodium_malloc(crypto_box_NONCEBYTES);
43    k1      = (unsigned char *) sodium_malloc(crypto_box_BEFORENMBYTES);
44    k2      = (unsigned char *) sodium_malloc(crypto_box_BEFORENMBYTES);
45    crypto_box_keypair(alicepk, alicesk);
46    crypto_box_keypair(bobpk, bobsk);
47    mlen = (size_t) randombytes_uniform((uint32_t) m_size) + 1U;
48    randombytes_buf(m, mlen);
49    randombytes_buf(nonce, crypto_box_NONCEBYTES);
50    ret = crypto_box_easy(c, m, mlen, nonce, bobpk, alicesk);
51    assert(ret == 0);
52    if (crypto_box_open_easy(m2, c,
53                             (unsigned long long) mlen + crypto_box_MACBYTES,
54                             nonce, alicepk, bobsk) != 0) {
55        printf("open() failed");
56        return 1;
57    }
58    printf("%d\n", memcmp(m, m2, mlen));
59
60    for (i = 0; i < mlen + crypto_box_MACBYTES - 1; i++) {
61        if (crypto_box_open_easy(m2, c, (unsigned long long) i, nonce, alicepk,
62                                 bobsk) == 0) {
63            printf("short open() should have failed");
64            return 1;
65        }
66    }
67    memcpy(c, m, mlen);
68    ret =
69        crypto_box_easy(c, c, (unsigned long long) mlen, nonce, bobpk, alicesk);
70    assert(ret == 0);
71    printf("%d\n", memcmp(m, c, mlen) == 0);
72    printf("%d\n", memcmp(m, c + crypto_box_MACBYTES, mlen) == 0);
73    if (crypto_box_open_easy(c, c,
74                             (unsigned long long) mlen + crypto_box_MACBYTES,
75                             nonce, alicepk, bobsk) != 0) {
76        printf("crypto_box_open_easy() failed\n");
77    }
78
79    ret = crypto_box_beforenm(k1, small_order_p, bobsk);
80    assert(ret == -1);
81    ret = crypto_box_beforenm(k2, small_order_p, alicesk);
82    assert(ret == -1);
83
84    ret = crypto_box_beforenm(k1, alicepk, bobsk);
85    assert(ret == 0);
86    ret = crypto_box_beforenm(k2, bobpk, alicesk);
87    assert(ret == 0);
88
89    memset(m2, 0, m2_size);
90
91    if (crypto_box_easy_afternm(c, m, 0, nonce, k1) != 0) {
92        printf(
93            "crypto_box_easy_afternm() with a null ciphertext should have "
94            "worked\n");
95    }
96    crypto_box_easy_afternm(c, m, (unsigned long long) mlen, nonce, k1);
97    if (crypto_box_open_easy_afternm(
98            m2, c, (unsigned long long) mlen + crypto_box_MACBYTES, nonce,
99            k2) != 0) {
100        printf("crypto_box_open_easy_afternm() failed\n");
101    }
102    printf("%d\n", memcmp(m, m2, mlen));
103    if (crypto_box_open_easy_afternm(m2, c, crypto_box_MACBYTES - 1U, nonce,
104                                     k2) == 0) {
105        printf(
106            "crypto_box_open_easy_afternm() with a huge ciphertext should have "
107            "failed\n");
108    }
109    memset(m2, 0, m2_size);
110    ret = crypto_box_detached(c, mac, m, (unsigned long long) mlen, nonce,
111                              small_order_p, bobsk);
112    assert(ret == -1);
113    ret = crypto_box_detached(c, mac, m, (unsigned long long) mlen, nonce,
114                              alicepk, bobsk);
115    assert(ret == 0);
116    if (crypto_box_open_detached(m2, c, mac, (unsigned long long) mlen, nonce,
117                                 small_order_p, alicesk) != -1) {
118        printf("crypto_box_open_detached() with a weak key passed\n");
119    }
120    if (crypto_box_open_detached(m2, c, mac, (unsigned long long) mlen, nonce,
121                                 bobpk, alicesk) != 0) {
122        printf("crypto_box_open_detached() failed\n");
123    }
124    printf("%d\n", memcmp(m, m2, mlen));
125
126    memset(m2, 0, m2_size);
127    crypto_box_detached_afternm(c, mac, m, (unsigned long long) mlen, nonce,
128                                k1);
129    if (crypto_box_open_detached_afternm(m2, c, mac, (unsigned long long) mlen,
130                                         nonce, k2) != 0) {
131        printf("crypto_box_open_detached_afternm() failed\n");
132    }
133    printf("%d\n", memcmp(m, m2, mlen));
134
135    sodium_free(alicepk);
136    sodium_free(alicesk);
137    sodium_free(bobpk);
138    sodium_free(bobsk);
139    sodium_free(mac);
140    sodium_free(nonce);
141    sodium_free(k1);
142    sodium_free(k2);
143    sodium_free(m);
144    sodium_free(m2);
145    sodium_free(c);
146    printf("OK\n");
147
148    return 0;
149}
150