1 /* $NetBSD: test_bulk.c,v 1.2 2017/01/28 21:31:47 christos Exp $ */ 2 3 /* 4 * Copyright (c) 2006 Kungliga Tekniska Högskolan 5 * (Royal Institute of Technology, Stockholm, Sweden). 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 12 * 1. Redistributions of source code must retain the above copyright 13 * notice, this list of conditions and the following disclaimer. 14 * 15 * 2. Redistributions in binary form must reproduce the above copyright 16 * notice, this list of conditions and the following disclaimer in the 17 * documentation and/or other materials provided with the distribution. 18 * 19 * 3. Neither the name of the Institute nor the names of its contributors 20 * may be used to endorse or promote products derived from this software 21 * without specific prior written permission. 22 * 23 * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND 24 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 25 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 26 * ARE DISCLAIMED. IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE 27 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 28 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 29 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 30 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 31 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 32 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 33 * SUCH DAMAGE. 34 */ 35 36 #include <config.h> 37 #include <krb5/roken.h> 38 #include <assert.h> 39 #include <krb5/getarg.h> 40 41 #include <evp.h> 42 #include <evp-hcrypto.h> 43 #include <evp-cc.h> 44 #if defined(_WIN32) 45 #include <evp-w32.h> 46 #endif 47 #include <evp-pkcs11.h> 48 #include <krb5/hex.h> 49 #include <err.h> 50 51 #ifdef WIN32 52 #define STATS_START(M) \ 53 LARGE_INTEGER StartingTime, EndingTime, ElapsedMicroseconds; \ 54 LARGE_INTEGER Frequency; \ 55 \ 56 QueryPerformanceFrequency(&Frequency); \ 57 QueryPerformanceCounter(&StartingTime); 58 59 #define STATS_END(M) \ 60 QueryPerformanceCounter(&EndingTime); \ 61 ElapsedMicroseconds.QuadPart = EndingTime.QuadPart - StartingTime.QuadPart; \ 62 ElapsedMicroseconds.QuadPart *= 1000000; \ 63 ElapsedMicroseconds.QuadPart /= Frequency.QuadPart; \ 64 \ 65 M += (ElapsedMicroseconds.QuadPart - M) / (i + 1); 66 #else 67 #define STATS_START(M) \ 68 struct timeval StartingTime, EndingTime; \ 69 \ 70 gettimeofday(&StartingTime, NULL); 71 72 #define STATS_END(M) \ 73 gettimeofday(&EndingTime, NULL); \ 74 timevalsub(&EndingTime, &StartingTime); \ 75 M += (EndingTime.tv_sec * 1000000 + EndingTime.tv_usec - M) / (i + 1); 76 #endif 77 78 static int version_flag; 79 static int help_flag; 80 static int len = 1; 81 static int loops = 20; 82 static char *provider = "hcrypto"; 83 static unsigned char *d; 84 85 #ifdef __APPLE__ 86 #define PROVIDER_USAGE "hcrypto|cc" 87 #elif defined(WIN32) 88 #define PROVIDER_USAGE "hcrypto|w32crypto" 89 #elif __sun || defined(PKCS11_MODULE_PATH) 90 #define PROVIDER_USAGE "hcrypto|pkcs11" 91 #else 92 #define PROVIDER_USAGE "hcrypto" 93 #endif 94 95 static struct getargs args[] = { 96 { "provider", 0, arg_string, &provider, 97 "crypto provider", PROVIDER_USAGE }, 98 { "loops", 0, arg_integer, &loops, 99 "number of loops", "loops" }, 100 { "size", 0, arg_integer, &len, 101 "size (KB)", NULL }, 102 { "version", 0, arg_flag, &version_flag, 103 "print version", NULL }, 104 { "help", 0, arg_flag, &help_flag, 105 NULL, NULL } 106 }; 107 108 static void 109 usage (int ret) 110 { 111 arg_printusage (args, 112 sizeof(args)/sizeof(*args), 113 NULL, 114 ""); 115 exit (ret); 116 } 117 118 static int 119 test_bulk_cipher(const char *cname, const EVP_CIPHER *c) 120 { 121 static unsigned char key[16]; 122 static unsigned char iv[16]; 123 int i; 124 int64_t M = 0; 125 126 if (c == NULL) { 127 printf("%s not supported\n", cname); 128 return 0; 129 } 130 131 for (i = 0; i < loops; i++) { 132 EVP_CIPHER_CTX ectx; 133 EVP_CIPHER_CTX dctx; 134 135 STATS_START(M) 136 137 EVP_CIPHER_CTX_init(&ectx); 138 EVP_CIPHER_CTX_init(&dctx); 139 140 if (EVP_CipherInit_ex(&ectx, c, NULL, NULL, NULL, 1) != 1) 141 errx(1, "can't init encrypt"); 142 if (EVP_CipherInit_ex(&dctx, c, NULL, NULL, NULL, 0) != 1) 143 errx(1, "can't init decrypt"); 144 145 EVP_CIPHER_CTX_set_key_length(&ectx, sizeof(key)); 146 EVP_CIPHER_CTX_set_key_length(&dctx, sizeof(key)); 147 148 if (EVP_CipherInit_ex(&ectx, NULL, NULL, key, iv, 1) != 1) 149 errx(1, "can't init encrypt"); 150 if (EVP_CipherInit_ex(&dctx, NULL, NULL, key, iv, 0) != 1) 151 errx(1, "can't init decrypt"); 152 153 if (!EVP_Cipher(&ectx, d, d, len)) 154 errx(1, "can't encrypt"); 155 if (!EVP_Cipher(&dctx, d, d, len)) 156 errx(1, "can't decrypt"); 157 158 EVP_CIPHER_CTX_cleanup(&ectx); 159 EVP_CIPHER_CTX_cleanup(&dctx); 160 161 STATS_END(M); 162 163 if (d[0] != 0x00 || d[len - 1] != ((len - 1) & 0xff)) 164 errx(1, "encrypt/decrypt inconsistent"); 165 } 166 167 printf("%s: mean time %llu usec%s\n", cname, (unsigned long long)M, 168 (M == 1) ? "" : "s"); 169 170 return 0; 171 } 172 173 static int 174 test_bulk_digest(const char *cname, const EVP_MD *md) 175 { 176 char digest[EVP_MAX_MD_SIZE]; 177 int i; 178 unsigned int tmp = sizeof(digest); 179 int64_t M = 0; 180 181 if (md == NULL) { 182 printf("%s not supported\n", cname); 183 return 0; 184 } 185 186 for (i = 0; i < loops; i++) { 187 STATS_START(M); 188 EVP_Digest(d, len, digest, &tmp, md, NULL); 189 STATS_END(M); 190 } 191 192 printf("%s: mean time %llu usec%s\n", cname, (unsigned long long)M, 193 (M == 1) ? "" : "s"); 194 195 return 0; 196 } 197 198 static void 199 test_bulk_provider_hcrypto(void) 200 { 201 test_bulk_cipher("hcrypto_aes_256_cbc", EVP_hcrypto_aes_256_cbc()); 202 #if 0 203 test_bulk_cipher("hcrypto_aes_256_cfb8", EVP_hcrypto_aes_256_cfb8()); 204 #endif 205 test_bulk_cipher("hcrypto_rc4", EVP_hcrypto_rc4()); 206 test_bulk_digest("hcrypto_md2", EVP_hcrypto_md2()); 207 test_bulk_digest("hcrypto_md4", EVP_hcrypto_md4()); 208 test_bulk_digest("hcrypto_md5", EVP_hcrypto_md5()); 209 test_bulk_digest("hcrypto_sha1", EVP_hcrypto_sha1()); 210 test_bulk_digest("hcrypto_sha256", EVP_hcrypto_sha256()); 211 test_bulk_digest("hcrypto_sha384", EVP_hcrypto_sha384()); 212 test_bulk_digest("hcrypto_sha512", EVP_hcrypto_sha512()); 213 } 214 215 #ifdef __APPLE__ 216 static void 217 test_bulk_provider_cc(void) 218 { 219 test_bulk_cipher("cc_aes_256_cbc", EVP_cc_aes_256_cbc()); 220 #if 0 221 test_bulk_cipher("cc_aes_256_cfb8", EVP_cc_aes_256_cfb8()); 222 #endif 223 test_bulk_cipher("cc_rc4", EVP_cc_rc4()); 224 test_bulk_digest("cc_md2", EVP_cc_md2()); 225 test_bulk_digest("cc_md4", EVP_cc_md4()); 226 test_bulk_digest("cc_md5", EVP_cc_md5()); 227 test_bulk_digest("cc_sha1", EVP_cc_sha1()); 228 test_bulk_digest("cc_sha256", EVP_cc_sha256()); 229 test_bulk_digest("cc_sha384", EVP_cc_sha384()); 230 test_bulk_digest("cc_sha512", EVP_cc_sha512()); 231 } 232 #endif /* __APPLE__ */ 233 234 #ifdef WIN32 235 static void 236 test_bulk_provider_w32crypto(void) 237 { 238 test_bulk_cipher("w32crypto_aes_256_cbc", EVP_w32crypto_aes_256_cbc()); 239 #if 0 240 test_bulk_cipher("w32crypto_aes_256_cfb8", EVP_w32crypto_aes_256_cfb8()); 241 #endif 242 test_bulk_cipher("w32crypto_rc4", EVP_w32crypto_rc4()); 243 test_bulk_digest("w32crypto_md2", EVP_w32crypto_md2()); 244 test_bulk_digest("w32crypto_md4", EVP_w32crypto_md4()); 245 test_bulk_digest("w32crypto_md5", EVP_w32crypto_md5()); 246 test_bulk_digest("w32crypto_sha1", EVP_w32crypto_sha1()); 247 test_bulk_digest("w32crypto_sha256", EVP_w32crypto_sha256()); 248 test_bulk_digest("w32crypto_sha384", EVP_w32crypto_sha384()); 249 test_bulk_digest("w32crypto_sha512", EVP_w32crypto_sha512()); 250 } 251 #endif /* WIN32 */ 252 253 #if __sun || defined(PKCS11_MODULE_PATH) 254 static void 255 test_bulk_provider_pkcs11(void) 256 { 257 test_bulk_cipher("pkcs11_aes_256_cbc", EVP_pkcs11_aes_256_cbc()); 258 test_bulk_cipher("pkcs11_rc4", EVP_pkcs11_rc4()); 259 test_bulk_digest("pkcs11_md5", EVP_pkcs11_md5()); 260 test_bulk_digest("pkcs11_sha1", EVP_pkcs11_sha1()); 261 test_bulk_digest("pkcs11_sha256", EVP_pkcs11_sha256()); 262 test_bulk_digest("pkcs11_sha384", EVP_pkcs11_sha384()); 263 test_bulk_digest("pkcs11_sha512", EVP_pkcs11_sha512()); 264 } 265 #endif /* __sun || PKCS11_MODULE_PATH */ 266 267 int 268 main(int argc, char **argv) 269 { 270 int ret = 0; 271 int idx = 0; 272 int i; 273 274 setprogname(argv[0]); 275 276 if(getarg(args, sizeof(args) / sizeof(args[0]), argc, argv, &idx)) 277 usage(1); 278 279 if (help_flag) 280 usage(0); 281 282 if(version_flag) { 283 print_version(NULL); 284 exit(0); 285 } 286 287 argc -= idx; 288 argv += idx; 289 290 len *= 1024; 291 292 d = emalloc(len); 293 for (i = 0; i < len; i++) 294 d[i] = i & 0xff; 295 296 if (strcmp(provider, "hcrypto") == 0) 297 test_bulk_provider_hcrypto(); 298 #ifdef __APPLE__ 299 else if (strcmp(provider, "cc") == 0) 300 test_bulk_provider_cc(); 301 #endif 302 #ifdef WIN32 303 else if (strcmp(provider, "w32crypto") == 0) 304 test_bulk_provider_w32crypto(); 305 #endif 306 #if __sun || defined(PKCS11_MODULE_PATH) 307 else if (strcmp(provider, "pkcs11") == 0) 308 test_bulk_provider_pkcs11(); 309 #endif 310 else 311 usage(1); 312 313 free(d); 314 315 return ret; 316 } 317