/* * Demo on how to use /dev/crypto device for HMAC. * * Placed under public domain. * */ #include #include #include #include #include #include #include static int debug = 0; #define DATA_SIZE 4096 #define BLOCK_SIZE 16 #define KEY_SIZE 16 #define SHA1_HASH_LEN 20 static int test_crypto(int cfd) { struct { uint8_t in[DATA_SIZE], encrypted[DATA_SIZE], decrypted[DATA_SIZE], iv[BLOCK_SIZE], key[KEY_SIZE]; } data; struct session_op sess; #ifdef CIOCGSESSINFO struct session_info_op siop; #endif struct crypt_op cryp; uint8_t mac[AALG_MAX_RESULT_LEN]; uint8_t oldmac[AALG_MAX_RESULT_LEN]; uint8_t md5_hmac_out[] = "\x75\x0c\x78\x3e\x6a\xb0\xb5\x03\xea\xa8\x6e\x31\x0a\x5d\xb7\x38"; uint8_t sha1_out[] = "\x8f\x82\x03\x94\xf9\x53\x35\x18\x20\x45\xda\x24\xf3\x4d\xe5\x2b\xf8\xbc\x34\x32"; int i; memset(&sess, 0, sizeof(sess)); memset(&cryp, 0, sizeof(cryp)); /* Use the garbage that is on the stack :-) */ /* memset(&data, 0, sizeof(data)); */ /* SHA1 plain test */ memset(mac, 0, sizeof(mac)); sess.cipher = 0; sess.mac = CRYPTO_SHA1; if (ioctl(cfd, CIOCGSESSION, &sess)) { perror("ioctl(CIOCGSESSION)"); return 1; } #ifdef CIOCGSESSINFO siop.ses = sess.ses; if (ioctl(cfd, CIOCGSESSINFO, &siop)) { perror("ioctl(CIOCGSESSINFO)"); return 1; } if (debug) printf("requested mac CRYPTO_SHA1, got %s with driver %s\n", siop.hash_info.cra_name, siop.hash_info.cra_driver_name); #endif cryp.ses = sess.ses; cryp.len = sizeof("what do ya want for nothing?")-1; cryp.src = "what do ya want for nothing?"; cryp.mac = mac; cryp.op = COP_ENCRYPT; if (ioctl(cfd, CIOCCRYPT, &cryp)) { perror("ioctl(CIOCCRYPT)"); return 1; } if (memcmp(mac, sha1_out, 20)!=0) { printf("mac: "); for (i=0;i 1) debug = 1; /* Open the crypto device */ fd = open("/dev/crypto", O_RDWR, 0); if (fd < 0) { perror("open(/dev/crypto)"); return 1; } /* Clone file descriptor */ if (ioctl(fd, CRIOGET, &cfd)) { perror("ioctl(CRIOGET)"); return 1; } /* Set close-on-exec (not really neede here) */ if (fcntl(cfd, F_SETFD, 1) == -1) { perror("fcntl(F_SETFD)"); return 1; } /* Run the test itself */ if (test_crypto(cfd)) return 1; if (test_extras(cfd)) return 1; /* Close cloned descriptor */ if (close(cfd)) { perror("close(cfd)"); return 1; } /* Close the original descriptor */ if (close(fd)) { perror("close(fd)"); return 1; } return 0; }