- return token;
- }
-
-static unsigned char *ustrsep(char **p,const char *sep)
- { return (unsigned char *)sstrsep(p,sep); }
-
-static int test1_exit(int ec)
- {
- EXIT(ec);
- return(0); /* To keep some compilers quiet */
- }
-
-/* Test copying of contexts */
-static void test_ctx_replace(EVP_CIPHER_CTX **pctx)
- {
- /* Make copy of context and replace original */
- EVP_CIPHER_CTX *ctx_copy;
- ctx_copy = EVP_CIPHER_CTX_new();
- EVP_CIPHER_CTX_copy(ctx_copy, *pctx);
- EVP_CIPHER_CTX_free(*pctx);
- *pctx = ctx_copy;
- }
-
-static void test1(const EVP_CIPHER *c,const unsigned char *key,int kn,
- const unsigned char *iv,int in,
- const unsigned char *plaintext,int pn,
- const unsigned char *ciphertext,int cn,
- const unsigned char *aad,int an,
- const unsigned char *tag,int tn,
- int encdec)
- {
- EVP_CIPHER_CTX *ctx = NULL;
- unsigned char out[4096];
- int outl,outl2,mode;
-
- printf("Testing cipher %s%s\n",EVP_CIPHER_name(c),
- (encdec == 1 ? "(encrypt)" : (encdec == 0 ? "(decrypt)" : "(encrypt/decrypt)")));
- hexdump(stdout,"Key",key,kn);
- if(in)
- hexdump(stdout,"IV",iv,in);
- hexdump(stdout,"Plaintext",plaintext,pn);
- hexdump(stdout,"Ciphertext",ciphertext,cn);
- if (an)
- hexdump(stdout,"AAD",aad,an);
- if (tn)
- hexdump(stdout,"Tag",tag,tn);
- mode = EVP_CIPHER_mode(c);
- if(kn != EVP_CIPHER_key_length(c))
- {
- fprintf(stderr,"Key length doesn't match, got %d expected %lu\n",kn,
- (unsigned long)EVP_CIPHER_key_length(c));
- test1_exit(5);
- }
- ctx = EVP_CIPHER_CTX_new();
- EVP_CIPHER_CTX_set_flags(ctx,EVP_CIPHER_CTX_FLAG_WRAP_ALLOW);
- if (encdec != 0)
- {
- if ((mode == EVP_CIPH_GCM_MODE) || (mode == EVP_CIPH_OCB_MODE))
- {
- if(!EVP_EncryptInit_ex(ctx,c,NULL,NULL,NULL))
- {
- fprintf(stderr,"EncryptInit failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(10);
- }
- if(!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_SET_IVLEN, in, NULL))
- {
- fprintf(stderr,"IV length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(11);
- }
- if((mode == EVP_CIPH_OCB_MODE) &&
- !EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_OCB_SET_TAGLEN, tn, NULL))
- {
- fprintf(stderr,"Tag length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(15);
- }
- if(!EVP_EncryptInit_ex(ctx,NULL,NULL,key,iv))
- {
- fprintf(stderr,"Key/IV set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(12);
- }
- if (an && !EVP_EncryptUpdate(ctx,NULL,&outl,aad,an))
- {
- fprintf(stderr,"AAD set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(13);
- }
- }
- else if (mode == EVP_CIPH_CCM_MODE)
- {
- if(!EVP_EncryptInit_ex(ctx,c,NULL,NULL,NULL))
- {
- fprintf(stderr,"EncryptInit failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(10);
- }
- if(!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_CCM_SET_IVLEN, in, NULL))
- {
- fprintf(stderr,"IV length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(11);
- }
- if(!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_CCM_SET_TAG, tn, NULL))
- {
- fprintf(stderr,"Tag length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(11);
- }
- if(!EVP_EncryptInit_ex(ctx,NULL,NULL,key,iv))
- {
- fprintf(stderr,"Key/IV set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(12);
- }
- if (!EVP_EncryptUpdate(ctx,NULL,&outl,NULL,pn))
- {
- fprintf(stderr,"Plaintext length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(12);
- }
- if (an && !EVP_EncryptUpdate(ctx,NULL,&outl,aad,an))
- {
- fprintf(stderr,"AAD set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(13);
- }
- }
- else if (mode == EVP_CIPH_WRAP_MODE)
- {
- if(!EVP_EncryptInit_ex(ctx,c,NULL,key,in ? iv : NULL))
- {
- fprintf(stderr,"EncryptInit failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(10);
- }
- }
- else if(!EVP_EncryptInit_ex(ctx,c,NULL,key,iv))
- {
- fprintf(stderr,"EncryptInit failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(10);
- }
- EVP_CIPHER_CTX_set_padding(ctx,0);
-
- test_ctx_replace(&ctx);
-
- if(!EVP_EncryptUpdate(ctx,out,&outl,plaintext,pn))
- {
- fprintf(stderr,"Encrypt failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(6);
- }
- if(!EVP_EncryptFinal_ex(ctx,out+outl,&outl2))
- {
- fprintf(stderr,"EncryptFinal failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(7);
- }
-
- if(outl+outl2 != cn)
- {
- fprintf(stderr,"Ciphertext length mismatch got %d expected %d\n",
- outl+outl2,cn);
- test1_exit(8);
- }
-
- if(memcmp(out,ciphertext,cn))
- {
- fprintf(stderr,"Ciphertext mismatch\n");
- hexdump(stderr,"Got",out,cn);
- hexdump(stderr,"Expected",ciphertext,cn);
- test1_exit(9);
- }
- if ((mode == EVP_CIPH_GCM_MODE) || (mode == EVP_CIPH_OCB_MODE)
- || (mode == EVP_CIPH_CCM_MODE))
- {
- unsigned char rtag[16];
-
- if (!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_GET_TAG, tn, rtag))
- {
- fprintf(stderr,"Get tag failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(14);
- }
- if (memcmp(rtag, tag, tn))
- {
- fprintf(stderr,"Tag mismatch\n");
- hexdump(stderr,"Got",rtag,tn);
- hexdump(stderr,"Expected",tag,tn);
- test1_exit(9);
- }
- }
- }
-
- if (encdec <= 0)
- {
- if ((mode == EVP_CIPH_GCM_MODE) || (mode == EVP_CIPH_OCB_MODE))
- {
- if(!EVP_DecryptInit_ex(ctx,c,NULL,NULL,NULL))
- {
- fprintf(stderr,"DecryptInit failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(10);
- }
- if(!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_SET_IVLEN, in, NULL))
- {
- fprintf(stderr,"IV length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(11);
- }
- if((mode == EVP_CIPH_OCB_MODE) &&
- !EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_OCB_SET_TAGLEN, tn, NULL))
- {
- fprintf(stderr,"Tag length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(15);
- }
- if(!EVP_DecryptInit_ex(ctx,NULL,NULL,key,iv))
- {
- fprintf(stderr,"Key/IV set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(12);
- }
- if (!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_SET_TAG, tn, (void *)tag))
- {
- fprintf(stderr,"Set tag failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(14);
- }
- if (an && !EVP_DecryptUpdate(ctx,NULL,&outl,aad,an))
- {
- fprintf(stderr,"AAD set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(13);
- }
- }
- else if (mode == EVP_CIPH_CCM_MODE)
- {
- if(!EVP_DecryptInit_ex(ctx,c,NULL,NULL,NULL))
- {
- fprintf(stderr,"DecryptInit failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(10);
- }
- if(!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_CCM_SET_IVLEN, in, NULL))
- {
- fprintf(stderr,"IV length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(11);
- }
- if(!EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_CCM_SET_TAG, tn, (void *)tag))
- {
- fprintf(stderr,"Tag length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(11);
- }
- if(!EVP_DecryptInit_ex(ctx,NULL,NULL,key,iv))
- {
- fprintf(stderr,"Key/Nonce set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(12);
- }
- if (!EVP_DecryptUpdate(ctx,NULL,&outl,NULL,pn))
- {
- fprintf(stderr,"Plaintext length set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(12);
- }
- if (an && !EVP_EncryptUpdate(ctx,NULL,&outl,aad,an))
- {
- fprintf(stderr,"AAD set failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(13);
- }
- }
- else if (mode == EVP_CIPH_WRAP_MODE)
- {
- if(!EVP_DecryptInit_ex(ctx,c,NULL,key,in ? iv : NULL))
- {
- fprintf(stderr,"EncryptInit failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(10);
- }
- }
- else if(!EVP_DecryptInit_ex(ctx,c,NULL,key,iv))
- {
- fprintf(stderr,"DecryptInit failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(11);
- }
- EVP_CIPHER_CTX_set_padding(ctx,0);
-
- test_ctx_replace(&ctx);
-
- if(!EVP_DecryptUpdate(ctx,out,&outl,ciphertext,cn))
- {
- fprintf(stderr,"Decrypt failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(6);
- }
- if(mode != EVP_CIPH_CCM_MODE && !EVP_DecryptFinal_ex(ctx,out+outl,&outl2))
- {
- fprintf(stderr,"DecryptFinal failed\n");
- ERR_print_errors_fp(stderr);
- test1_exit(7);
- }
-
- if(outl+outl2 != pn)
- {
- fprintf(stderr,"Plaintext length mismatch got %d expected %d\n",
- outl+outl2,pn);
- test1_exit(8);
- }
-
- if(memcmp(out,plaintext,pn))
- {
- fprintf(stderr,"Plaintext mismatch\n");
- hexdump(stderr,"Got",out,pn);
- hexdump(stderr,"Expected",plaintext,pn);
- test1_exit(9);
- }
- }