1da668aa1SThomas Huth /* 2da668aa1SThomas Huth * QEMU Crypto IV generator algorithms 3da668aa1SThomas Huth * 4da668aa1SThomas Huth * Copyright (c) 2015-2016 Red Hat, Inc. 5da668aa1SThomas Huth * 6da668aa1SThomas Huth * This library is free software; you can redistribute it and/or 7da668aa1SThomas Huth * modify it under the terms of the GNU Lesser General Public 8da668aa1SThomas Huth * License as published by the Free Software Foundation; either 9da668aa1SThomas Huth * version 2.1 of the License, or (at your option) any later version. 10da668aa1SThomas Huth * 11da668aa1SThomas Huth * This library is distributed in the hope that it will be useful, 12da668aa1SThomas Huth * but WITHOUT ANY WARRANTY; without even the implied warranty of 13da668aa1SThomas Huth * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14da668aa1SThomas Huth * Lesser General Public License for more details. 15da668aa1SThomas Huth * 16da668aa1SThomas Huth * You should have received a copy of the GNU Lesser General Public 17da668aa1SThomas Huth * License along with this library; if not, see <http://www.gnu.org/licenses/>. 18da668aa1SThomas Huth * 19da668aa1SThomas Huth */ 20da668aa1SThomas Huth 21da668aa1SThomas Huth #include "qemu/osdep.h" 22da668aa1SThomas Huth #include "qapi/error.h" 23da668aa1SThomas Huth #include "crypto/ivgen.h" 24da668aa1SThomas Huth 25da668aa1SThomas Huth 26da668aa1SThomas Huth struct QCryptoIVGenTestData { 27da668aa1SThomas Huth const char *path; 28da668aa1SThomas Huth uint64_t sector; 29da668aa1SThomas Huth QCryptoIVGenAlgorithm ivalg; 30ef834aa2SMarkus Armbruster QCryptoHashAlgo hashalg; 31*a092c513SMarkus Armbruster QCryptoCipherAlgo cipheralg; 32da668aa1SThomas Huth const uint8_t *key; 33da668aa1SThomas Huth size_t nkey; 34da668aa1SThomas Huth const uint8_t *iv; 35da668aa1SThomas Huth size_t niv; 36da668aa1SThomas Huth } test_data[] = { 37da668aa1SThomas Huth /* Small */ 38da668aa1SThomas Huth { 39da668aa1SThomas Huth "/crypto/ivgen/plain/1", 40da668aa1SThomas Huth .sector = 0x1, 41da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_PLAIN, 42da668aa1SThomas Huth .iv = (const uint8_t *)"\x01\x00\x00\x00\x00\x00\x00\x00" 43da668aa1SThomas Huth "\x00\x00\x00\x00\x00\x00\x00\x00", 44da668aa1SThomas Huth .niv = 16, 45da668aa1SThomas Huth }, 46da668aa1SThomas Huth /* Big ! */ 47da668aa1SThomas Huth { 48da668aa1SThomas Huth "/crypto/ivgen/plain/1f2e3d4c", 49da668aa1SThomas Huth .sector = 0x1f2e3d4cULL, 50da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_PLAIN, 51da668aa1SThomas Huth .iv = (const uint8_t *)"\x4c\x3d\x2e\x1f\x00\x00\x00\x00" 52da668aa1SThomas Huth "\x00\x00\x00\x00\x00\x00\x00\x00", 53da668aa1SThomas Huth .niv = 16, 54da668aa1SThomas Huth }, 55da668aa1SThomas Huth /* Truncation */ 56da668aa1SThomas Huth { 57da668aa1SThomas Huth "/crypto/ivgen/plain/1f2e3d4c5b6a7988", 58da668aa1SThomas Huth .sector = 0x1f2e3d4c5b6a7988ULL, 59da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_PLAIN, 60da668aa1SThomas Huth .iv = (const uint8_t *)"\x88\x79\x6a\x5b\x00\x00\x00\x00" 61da668aa1SThomas Huth "\x00\x00\x00\x00\x00\x00\x00\x00", 62da668aa1SThomas Huth .niv = 16, 63da668aa1SThomas Huth }, 64da668aa1SThomas Huth /* Small */ 65da668aa1SThomas Huth { 66da668aa1SThomas Huth "/crypto/ivgen/plain64/1", 67da668aa1SThomas Huth .sector = 0x1, 68da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_PLAIN64, 69da668aa1SThomas Huth .iv = (const uint8_t *)"\x01\x00\x00\x00\x00\x00\x00\x00" 70da668aa1SThomas Huth "\x00\x00\x00\x00\x00\x00\x00\x00", 71da668aa1SThomas Huth .niv = 16, 72da668aa1SThomas Huth }, 73da668aa1SThomas Huth /* Big ! */ 74da668aa1SThomas Huth { 75da668aa1SThomas Huth "/crypto/ivgen/plain64/1f2e3d4c", 76da668aa1SThomas Huth .sector = 0x1f2e3d4cULL, 77da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_PLAIN64, 78da668aa1SThomas Huth .iv = (const uint8_t *)"\x4c\x3d\x2e\x1f\x00\x00\x00\x00" 79da668aa1SThomas Huth "\x00\x00\x00\x00\x00\x00\x00\x00", 80da668aa1SThomas Huth .niv = 16, 81da668aa1SThomas Huth }, 82da668aa1SThomas Huth /* No Truncation */ 83da668aa1SThomas Huth { 84da668aa1SThomas Huth "/crypto/ivgen/plain64/1f2e3d4c5b6a7988", 85da668aa1SThomas Huth .sector = 0x1f2e3d4c5b6a7988ULL, 86da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_PLAIN64, 87da668aa1SThomas Huth .iv = (const uint8_t *)"\x88\x79\x6a\x5b\x4c\x3d\x2e\x1f" 88da668aa1SThomas Huth "\x00\x00\x00\x00\x00\x00\x00\x00", 89da668aa1SThomas Huth .niv = 16, 90da668aa1SThomas Huth }, 91da668aa1SThomas Huth /* Small */ 92da668aa1SThomas Huth { 93da668aa1SThomas Huth "/crypto/ivgen/essiv/1", 94da668aa1SThomas Huth .sector = 0x1, 95da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_ESSIV, 96*a092c513SMarkus Armbruster .cipheralg = QCRYPTO_CIPHER_ALGO_AES_128, 97ef834aa2SMarkus Armbruster .hashalg = QCRYPTO_HASH_ALGO_SHA256, 98da668aa1SThomas Huth .key = (const uint8_t *)"\x00\x01\x02\x03\x04\x05\x06\x07" 99da668aa1SThomas Huth "\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f", 100da668aa1SThomas Huth .nkey = 16, 101da668aa1SThomas Huth .iv = (const uint8_t *)"\xd4\x83\x71\xb2\xa1\x94\x53\x88" 102da668aa1SThomas Huth "\x1c\x7a\x2d\06\x2d\x0b\x65\x46", 103da668aa1SThomas Huth .niv = 16, 104da668aa1SThomas Huth }, 105da668aa1SThomas Huth /* Big ! */ 106da668aa1SThomas Huth { 107da668aa1SThomas Huth "/crypto/ivgen/essiv/1f2e3d4c", 108da668aa1SThomas Huth .sector = 0x1f2e3d4cULL, 109da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_ESSIV, 110*a092c513SMarkus Armbruster .cipheralg = QCRYPTO_CIPHER_ALGO_AES_128, 111ef834aa2SMarkus Armbruster .hashalg = QCRYPTO_HASH_ALGO_SHA256, 112da668aa1SThomas Huth .key = (const uint8_t *)"\x00\x01\x02\x03\x04\x05\x06\x07" 113da668aa1SThomas Huth "\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f", 114da668aa1SThomas Huth .nkey = 16, 115da668aa1SThomas Huth .iv = (const uint8_t *)"\x5d\x36\x09\x5d\xc6\x9e\x5e\xe9" 116da668aa1SThomas Huth "\xe3\x02\x8d\xd8\x7a\x3d\xe7\x8f", 117da668aa1SThomas Huth .niv = 16, 118da668aa1SThomas Huth }, 119da668aa1SThomas Huth /* No Truncation */ 120da668aa1SThomas Huth { 121da668aa1SThomas Huth "/crypto/ivgen/essiv/1f2e3d4c5b6a7988", 122da668aa1SThomas Huth .sector = 0x1f2e3d4c5b6a7988ULL, 123da668aa1SThomas Huth .ivalg = QCRYPTO_IVGEN_ALG_ESSIV, 124*a092c513SMarkus Armbruster .cipheralg = QCRYPTO_CIPHER_ALGO_AES_128, 125ef834aa2SMarkus Armbruster .hashalg = QCRYPTO_HASH_ALGO_SHA256, 126da668aa1SThomas Huth .key = (const uint8_t *)"\x00\x01\x02\x03\x04\x05\x06\x07" 127da668aa1SThomas Huth "\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f", 128da668aa1SThomas Huth .nkey = 16, 129da668aa1SThomas Huth .iv = (const uint8_t *)"\x58\xbb\x81\x94\x51\x83\x23\x23" 130da668aa1SThomas Huth "\x7a\x08\x93\xa9\xdc\xd2\xd9\xab", 131da668aa1SThomas Huth .niv = 16, 132da668aa1SThomas Huth }, 133da668aa1SThomas Huth }; 134da668aa1SThomas Huth 135da668aa1SThomas Huth 136da668aa1SThomas Huth static void test_ivgen(const void *opaque) 137da668aa1SThomas Huth { 138da668aa1SThomas Huth const struct QCryptoIVGenTestData *data = opaque; 139295736cfSDaniel P. Berrangé g_autofree uint8_t *iv = g_new0(uint8_t, data->niv); 140295736cfSDaniel P. Berrangé g_autoptr(QCryptoIVGen) ivgen = NULL; 141295736cfSDaniel P. Berrangé 142295736cfSDaniel P. Berrangé if (!qcrypto_cipher_supports(data->cipheralg, 143295736cfSDaniel P. Berrangé QCRYPTO_CIPHER_MODE_ECB)) { 144295736cfSDaniel P. Berrangé return; 145295736cfSDaniel P. Berrangé } 146295736cfSDaniel P. Berrangé 147295736cfSDaniel P. Berrangé ivgen = qcrypto_ivgen_new( 148da668aa1SThomas Huth data->ivalg, 149da668aa1SThomas Huth data->cipheralg, 150da668aa1SThomas Huth data->hashalg, 151da668aa1SThomas Huth data->key, 152da668aa1SThomas Huth data->nkey, 153da668aa1SThomas Huth &error_abort); 154da668aa1SThomas Huth 155da668aa1SThomas Huth qcrypto_ivgen_calculate(ivgen, 156da668aa1SThomas Huth data->sector, 157da668aa1SThomas Huth iv, 158da668aa1SThomas Huth data->niv, 159da668aa1SThomas Huth &error_abort); 160da668aa1SThomas Huth 161da668aa1SThomas Huth g_assert(memcmp(iv, data->iv, data->niv) == 0); 162da668aa1SThomas Huth } 163da668aa1SThomas Huth 164da668aa1SThomas Huth int main(int argc, char **argv) 165da668aa1SThomas Huth { 166da668aa1SThomas Huth size_t i; 167da668aa1SThomas Huth g_test_init(&argc, &argv, NULL); 168da668aa1SThomas Huth for (i = 0; i < G_N_ELEMENTS(test_data); i++) { 169da668aa1SThomas Huth if (test_data[i].ivalg == QCRYPTO_IVGEN_ALG_ESSIV && 170da668aa1SThomas Huth !qcrypto_hash_supports(test_data[i].hashalg)) { 171da668aa1SThomas Huth continue; 172da668aa1SThomas Huth } 173da668aa1SThomas Huth g_test_add_data_func(test_data[i].path, 174da668aa1SThomas Huth &(test_data[i]), 175da668aa1SThomas Huth test_ivgen); 176da668aa1SThomas Huth } 177da668aa1SThomas Huth return g_test_run(); 178da668aa1SThomas Huth } 179