1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://opensource.org/licenses/CDDL-1.0. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 22 /* 23 * Copyright 2013 Saso Kiselkov. All rights reserved. 24 */ 25 26 /* 27 * This is just to keep the compiler happy about sys/time.h not declaring 28 * gettimeofday due to -D_KERNEL (we can do this since we're actually 29 * running in userspace, but we need -D_KERNEL for the remaining Edon-R code). 30 */ 31 #ifdef _KERNEL 32 #undef _KERNEL 33 #endif 34 35 #include <sys/edonr.h> 36 #include <stdlib.h> 37 #include <strings.h> 38 #include <stdio.h> 39 #include <sys/time.h> 40 41 /* 42 * Test messages from: 43 * http://csrc.nist.gov/groups/ST/toolkit/documents/Examples/SHA_All.pdf 44 */ 45 const char *test_msg0 = "abc"; 46 const char *test_msg1 = "abcdbcdecdefdefgefghfghighijhijkijkljklmklmn" 47 "lmnomnopnopq"; 48 const char *test_msg2 = "abcdefghbcdefghicdefghijdefghijkefghijklfghi" 49 "jklmghijklmnhijklmnoijklmnopjklmnopqklmnopqrlmnopqrsmnopqrstnopqrstu"; 50 51 /* 52 * Test digests computed by hand. There's no formal standard or spec for edonr. 53 */ 54 const uint8_t edonr_224_test_digests[][28] = { 55 { 56 // for test_msg0 57 0x56, 0x63, 0xc4, 0x93, 0x95, 0x20, 0xfa, 0xf6, 58 0x12, 0x31, 0x65, 0xa4, 0x66, 0xf2, 0x56, 0x01, 59 0x95, 0x2e, 0xa9, 0xe4, 0x24, 0xdd, 0xc9, 0x6b, 60 0xef, 0xd0, 0x40, 0x94 61 }, 62 { 63 // for test_msg1 64 0xd0, 0x13, 0xe4, 0x87, 0x4d, 0x06, 0x8d, 0xca, 65 0x4e, 0x14, 0xb9, 0x37, 0x2f, 0xce, 0x12, 0x20, 66 0x60, 0xf8, 0x5c, 0x0a, 0xfd, 0x7a, 0x7d, 0x97, 67 0x88, 0x2b, 0x05, 0x75 68 } 69 // no test vectorfor test_msg2 70 }; 71 72 const uint8_t edonr_256_test_digests[][32] = { 73 { 74 // for test_msg0 75 0x54, 0xd7, 0x8b, 0x13, 0xc7, 0x4e, 0xda, 0x5a, 76 0xed, 0xc2, 0x71, 0xcc, 0x88, 0x1f, 0xb2, 0x2f, 77 0x83, 0x99, 0xaf, 0xd3, 0x04, 0x0b, 0x6a, 0x39, 78 0x2d, 0x73, 0x94, 0x05, 0x50, 0x8d, 0xd8, 0x51 79 }, 80 { 81 // for test_msg1 82 0x49, 0x2d, 0x0b, 0x19, 0xab, 0x1e, 0xde, 0x3a, 83 0xea, 0x9b, 0xf2, 0x39, 0x3a, 0xb1, 0x21, 0xde, 84 0x21, 0xf6, 0x80, 0x1f, 0xad, 0xbe, 0x8b, 0x07, 85 0xc7, 0xfb, 0xe6, 0x99, 0x0e, 0x4d, 0x73, 0x63 86 } 87 // no test vectorfor test_msg2 88 }; 89 90 const uint8_t edonr_384_test_digests[][48] = { 91 { 92 // for test_msg0 93 0x0e, 0x7c, 0xd7, 0x85, 0x78, 0x77, 0xe0, 0x89, 94 0x5b, 0x1c, 0xdf, 0x49, 0xf4, 0x1d, 0x20, 0x9c, 95 0x72, 0x7d, 0x2e, 0x57, 0x9b, 0x9b, 0x9a, 0xdc, 96 0x60, 0x27, 0x97, 0x82, 0xb9, 0x90, 0x72, 0xec, 97 0x7e, 0xce, 0xd3, 0x16, 0x5f, 0x47, 0x75, 0x48, 98 0xfa, 0x60, 0x72, 0x7e, 0x01, 0xc7, 0x7c, 0xc6 99 }, 100 { 101 // no test vector for test_msg1 102 }, 103 { 104 // for test_msg2 105 0xe2, 0x34, 0xa1, 0x02, 0x83, 0x76, 0xae, 0xe6, 106 0x82, 0xd9, 0x38, 0x32, 0x0e, 0x00, 0x78, 0xd2, 107 0x34, 0xdb, 0xb9, 0xbd, 0xf0, 0x08, 0xa8, 0x0f, 108 0x63, 0x1c, 0x3d, 0x4a, 0xfd, 0x0a, 0xe9, 0x59, 109 0xdc, 0xd4, 0xce, 0xcd, 0x8d, 0x67, 0x6c, 0xea, 110 0xbb, 0x1a, 0x32, 0xed, 0x5c, 0x6b, 0xf1, 0x7f 111 } 112 }; 113 114 const uint8_t edonr_512_test_digests[][64] = { 115 { 116 // for test_msg0 117 0x1b, 0x14, 0xdb, 0x15, 0x5f, 0x1d, 0x40, 0x65, 118 0x94, 0xb8, 0xce, 0xf7, 0x0a, 0x43, 0x62, 0xec, 119 0x6b, 0x5d, 0xe6, 0xa5, 0xda, 0xf5, 0x0e, 0xc9, 120 0x99, 0xe9, 0x87, 0xc1, 0x9d, 0x30, 0x49, 0xe2, 121 0xde, 0x59, 0x77, 0xbb, 0x05, 0xb1, 0xbb, 0x22, 122 0x00, 0x50, 0xa1, 0xea, 0x5b, 0x46, 0xa9, 0xf1, 123 0x74, 0x0a, 0xca, 0xfb, 0xf6, 0xb4, 0x50, 0x32, 124 0xad, 0xc9, 0x0c, 0x62, 0x83, 0x72, 0xc2, 0x2b 125 }, 126 { 127 // no test vector for test_msg1 128 }, 129 { 130 // for test_msg2 131 0x53, 0x51, 0x07, 0x0d, 0xc5, 0x1c, 0x3b, 0x2b, 132 0xac, 0xa5, 0xa6, 0x0d, 0x02, 0x52, 0xcc, 0xb4, 133 0xe4, 0x92, 0x1a, 0x96, 0xfe, 0x5a, 0x69, 0xe7, 134 0x6d, 0xad, 0x48, 0xfd, 0x21, 0xa0, 0x84, 0x5a, 135 0xd5, 0x7f, 0x88, 0x0b, 0x3e, 0x4a, 0x90, 0x7b, 136 0xc5, 0x03, 0x15, 0x18, 0x42, 0xbb, 0x94, 0x9e, 137 0x1c, 0xba, 0x74, 0x39, 0xa6, 0x40, 0x9a, 0x34, 138 0xb8, 0x43, 0x6c, 0xb4, 0x69, 0x21, 0x58, 0x3c 139 } 140 }; 141 142 int 143 main(int argc, char *argv[]) 144 { 145 boolean_t failed = B_FALSE; 146 uint64_t cpu_mhz = 0; 147 148 if (argc == 2) 149 cpu_mhz = atoi(argv[1]); 150 151 #define EDONR_ALGO_TEST(_m, mode, testdigest) \ 152 do { \ 153 EdonRState ctx; \ 154 uint8_t digest[mode / 8]; \ 155 EdonRInit(&ctx, mode); \ 156 EdonRUpdate(&ctx, (const uint8_t *) _m, strlen(_m) * 8);\ 157 EdonRFinal(&ctx, digest); \ 158 printf("Edon-R-%-6sMessage: " #_m "\tResult: ", #mode); \ 159 if (bcmp(digest, testdigest, mode / 8) == 0) { \ 160 printf("OK\n"); \ 161 } else { \ 162 printf("FAILED!\n"); \ 163 failed = B_TRUE; \ 164 } \ 165 } while (0) 166 167 #define EDONR_PERF_TEST(mode) \ 168 do { \ 169 EdonRState ctx; \ 170 uint8_t digest[mode / 8]; \ 171 uint8_t block[131072]; \ 172 uint64_t delta; \ 173 double cpb = 0; \ 174 int i; \ 175 struct timeval start, end; \ 176 bzero(block, sizeof (block)); \ 177 gettimeofday(&start, NULL); \ 178 EdonRInit(&ctx, mode); \ 179 for (i = 0; i < 8192; i++) \ 180 EdonRUpdate(&ctx, block, sizeof (block) * 8); \ 181 EdonRFinal(&ctx, digest); \ 182 gettimeofday(&end, NULL); \ 183 delta = (end.tv_sec * 1000000llu + end.tv_usec) - \ 184 (start.tv_sec * 1000000llu + start.tv_usec); \ 185 if (cpu_mhz != 0) { \ 186 cpb = (cpu_mhz * 1e6 * ((double)delta / \ 187 1000000)) / (8192 * 128 * 1024); \ 188 } \ 189 printf("Edon-R-%-6s%llu us (%.02f CPB)\n", #mode, delta,\ 190 cpb); \ 191 } while (0) 192 193 194 printf("Running algorithm correctness tests:\n"); 195 EDONR_ALGO_TEST(test_msg0, 224, edonr_224_test_digests[0]); 196 EDONR_ALGO_TEST(test_msg1, 224, edonr_224_test_digests[1]); 197 EDONR_ALGO_TEST(test_msg0, 256, edonr_256_test_digests[0]); 198 EDONR_ALGO_TEST(test_msg1, 256, edonr_256_test_digests[1]); 199 EDONR_ALGO_TEST(test_msg0, 384, edonr_384_test_digests[0]); 200 EDONR_ALGO_TEST(test_msg2, 384, edonr_384_test_digests[2]); 201 EDONR_ALGO_TEST(test_msg0, 512, edonr_512_test_digests[0]); 202 EDONR_ALGO_TEST(test_msg2, 512, edonr_512_test_digests[2]); 203 if (failed) 204 return (1); 205 206 printf("Running performance tests (hashing 1024 MiB of data):\n"); 207 EDONR_PERF_TEST(256); 208 EDONR_PERF_TEST(512); 209 210 return (0); 211 }