1: %%
    2: %% %CopyrightBegin%
    3: %%
    4: %% Copyright Ericsson AB 1999-2013. All Rights Reserved.
    5: %%
    6: %% The contents of this file are subject to the Erlang Public License,
    7: %% Version 1.1, (the "License"); you may not use this file except in
    8: %% compliance with the License. You should have received a copy of the
    9: %% Erlang Public License along with this software. If not, it can be
   10: %% retrieved online at http://www.erlang.org/.
   11: %%
   12: %% Software distributed under the License is distributed on an "AS IS"
   13: %% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
   14: %% the License for the specific language governing rights and limitations
   15: %% under the License.
   16: %%
   17: %% %CopyrightEnd%
   18: %%
   19: -module(crypto_SUITE).
   20: 
   21: -include_lib("common_test/include/ct.hrl").
   22: 
   23: %% Note: This directive should only be used in test suites.
   24: -compile(export_all).
   25: %%--------------------------------------------------------------------
   26: %% Common Test interface functions -----------------------------------
   27: %%--------------------------------------------------------------------
   28: 
   29: suite() -> [{ct_hooks,[ts_install_cth]}].
   30: 
   31: all() -> 
   32:     [app,
   33:      {group, md4},
   34:      {group, md5},
   35:      {group, ripemd160},
   36:      {group, sha},
   37:      {group, sha224},
   38:      {group, sha256},
   39:      {group, sha384},
   40:      {group, sha512},
   41:      {group, rsa},
   42:      {group, dss},
   43:      {group, ecdsa},
   44:      {group, dh},
   45:      {group, ecdh},
   46:      {group, srp},
   47:      {group, des_cbc},
   48:      {group, des_cfb},
   49:      {group, des3_cbc},
   50:      {group, des3_cbf},
   51:      {group, des_ede3},
   52:      {group, blowfish_cbc},
   53:      {group, blowfish_ecb},
   54:      {group, blowfish_cfb64},
   55:      {group, blowfish_ofb64},
   56:      {group, aes_cbc128},
   57:      {group, aes_cfb128},
   58:      {group, aes_cbc256},
   59:      {group, rc2_cbc},
   60:      {group, rc4}, 
   61:      {group, aes_ctr},
   62:      mod_pow,
   63:      exor,
   64:      rand_uniform
   65:     ].
   66: 
   67: groups() -> 
   68:     [{md4, [], [hash]},
   69:      {md5, [], [hash, hmac]},
   70:      {ripemd160, [], [hash]},
   71:      {sha, [], [hash, hmac]},
   72:      {sha224, [], [hash, hmac]},
   73:      {sha256, [], [hash, hmac]},
   74:      {sha384, [], [hash, hmac]},
   75:      {sha512, [], [hash, hmac]},
   76:      {rsa, [], [sign_verify, 
   77: 		public_encrypt
   78: 	       ]},
   79:      {dss, [], [sign_verify]},
   80:      {ecdsa, [], [sign_verify]},
   81:      {dh, [], [generate_compute]},
   82:      {ecdh, [], [compute]},
   83:      {srp, [], [generate_compute]},
   84:      {des_cbc, [], [block]},
   85:      {des_cfb, [], [block]},
   86:      {des3_cbc,[], [block]},
   87:      {des_ede3,[], [block]},
   88:      {des3_cbf,[], [block]},
   89:      {rc2_cbc,[], [block]},
   90:      {aes_cbc128,[], [block]},
   91:      {aes_cfb128,[], [block]},
   92:      {aes_cbc256,[], [block]},
   93:      {blowfish_cbc, [], [block]},
   94:      {blowfish_ecb, [], [block]},
   95:      {blowfish_cfb64, [], [block]},
   96:      {blowfish_ofb64,[], [block]},
   97:      {rc4, [], [stream]}, 
   98:      {aes_ctr, [], [stream]}
   99:     ].
  100: 
  101: %%-------------------------------------------------------------------
  102: init_per_suite(Config) ->
  103:     try crypto:start() of
  104: 	ok ->
  105: 	    Config
  106:     catch _:_ ->
  107: 	    {skip, "Crypto did not start"}
  108:     end.
  109: 
  110: end_per_suite(_Config) ->
  111:     application:stop(crypto).
  112: 
  113: %%-------------------------------------------------------------------
  114: init_per_group(GroupName, Config) ->
  115:     case is_supported(GroupName) of
  116: 	true ->
  117: 	    group_config(GroupName, Config);
  118: 	false ->
  119: 	    {skip, "Group not supported"}
  120:     end.
  121: 
  122: end_per_group(_GroupName, Config) ->
  123:     Config.
  124: 
  125: init_per_testcase(info, Config) ->
  126:     Config;
  127: init_per_testcase(_Name,Config) ->
  128:     Config.
  129: 
  130: end_per_testcase(info, Config) ->
  131:     Config;
  132: end_per_testcase(_Name,Config) ->
  133:     Config.
  134: 
  135: %%--------------------------------------------------------------------
  136: %% Test Cases --------------------------------------------------------
  137: %%--------------------------------------------------------------------
  138: app() ->
  139:     [{doc, "Test that the crypto app file is ok"}].
  140: app(Config) when is_list(Config) ->
  141:     ok = ?t:app_test(crypto).
  142: %%--------------------------------------------------------------------
  143: hash() ->
  144:     [{doc, "Test all different hash functions"}].
  145: hash(Config) when is_list(Config) ->
  146:     {Type, MsgsLE, Digests} = proplists:get_value(hash, Config),
  147:     Msgs = lazy_eval(MsgsLE),
  148:     [LongMsg | _] = lists:reverse(Msgs),
  149:     Inc = iolistify(LongMsg),
  150:     [IncrDigest | _] = lists:reverse(Digests),
  151:     hash(Type, Msgs, Digests),
  152:     hash(Type, lists:map(fun iolistify/1, Msgs), Digests),
  153:     hash_increment(Type, Inc, IncrDigest).
  154: %%-------------------------------------------------------------------- 
  155: hmac() ->
  156:      [{doc, "Test all different hmac functions"}].
  157: hmac(Config) when is_list(Config) ->
  158:     {Type, Keys, DataLE, Expected} = proplists:get_value(hmac, Config),
  159:     Data = lazy_eval(DataLE),
  160:     hmac(Type, Keys, Data, Expected),
  161:     hmac(Type, lists:map(fun iolistify/1, Keys), lists:map(fun iolistify/1, Data), Expected),
  162:     hmac_increment(Type).
  163: %%--------------------------------------------------------------------
  164: block() ->
  165:      [{doc, "Test block ciphers"}].
  166: block(Config) when is_list(Config) ->
  167:     Blocks = proplists:get_value(block, Config),
  168:     lists:foreach(fun block_cipher/1, Blocks),
  169:     lists:foreach(fun block_cipher/1, block_iolistify(Blocks)),
  170:     lists:foreach(fun block_cipher_increment/1, block_iolistify(Blocks)).
  171: 
  172: %%--------------------------------------------------------------------
  173: stream() ->
  174:       [{doc, "Test stream ciphers"}].
  175: stream(Config) when is_list(Config) ->
  176:     Streams = lazy_eval(proplists:get_value(stream, Config)),
  177: 
  178:     lists:foreach(fun stream_cipher/1, Streams),
  179:     lists:foreach(fun stream_cipher/1, stream_iolistify(Streams)),
  180:     lists:foreach(fun stream_cipher_incment/1, stream_iolistify(Streams)).
  181: 
  182: %%-------------------------------------------------------------------- 
  183: sign_verify() ->
  184:      [{doc, "Sign/verify digital signatures"}].
  185: sign_verify(Config) when is_list(Config) ->
  186:     SignVerify = proplists:get_value(sign_verify, Config),
  187:     lists:foreach(fun do_sign_verify/1, SignVerify).
  188: 
  189: %%-------------------------------------------------------------------- 
  190: public_encrypt() ->
  191:      [{doc, "Test public_encrypt/decrypt and private_encrypt/decrypt functions. "}].
  192: public_encrypt(Config) when is_list(Config) ->
  193:     Params = proplists:get_value(pub_priv_encrypt, Config),
  194:     lists:foreach(fun do_public_encrypt/1, Params),
  195:     lists:foreach(fun do_private_encrypt/1, Params).
  196: 
  197: %%--------------------------------------------------------------------
  198: generate_compute() ->
  199:      [{doc, " Test crypto:genarate_key and crypto:compute_key"}].
  200: generate_compute(Config) when is_list(Config) ->
  201:     GenCom = proplists:get_value(generate_compute, Config),
  202:     lists:foreach(fun do_generate_compute/1, GenCom).
  203: %%--------------------------------------------------------------------
  204: compute() ->
  205:      [{doc, " Test crypto:compute_key"}].
  206: compute(Config) when is_list(Config) ->
  207:     Gen = proplists:get_value(compute, Config),
  208:     lists:foreach(fun do_compute/1, Gen).
  209: %%--------------------------------------------------------------------
  210: mod_pow() ->
  211:     [{doc, "mod_pow testing (A ^ M % P with bignums)"}].
  212: mod_pow(Config) when is_list(Config) ->
  213:     mod_pow_aux_test(2, 5, 10, 8).
  214: %%--------------------------------------------------------------------
  215: exor() ->
  216:     [{doc, "Test the exor function"}].
  217: exor(Config) when is_list(Config) ->
  218:     do_exor(<<1, 2, 3, 4, 5, 6, 7, 8, 9, 10>>),
  219:     do_exor(term_to_binary(lists:seq(1, 1000000))).
  220: %%--------------------------------------------------------------------
  221: rand_uniform() ->
  222:     [{doc, "rand_uniform and random_bytes testing"}].
  223: rand_uniform(Config) when is_list(Config) ->
  224:     rand_uniform_aux_test(10),
  225:     10 = byte_size(crypto:rand_bytes(10)),
  226:     10 = byte_size(crypto:strong_rand_bytes(10)).
  227: 
  228: %%--------------------------------------------------------------------
  229: %% Internal functions ------------------------------------------------
  230: %%--------------------------------------------------------------------
  231: hash(_, [], []) ->
  232:     ok;
  233: hash(Type, [Msg | RestMsg], [Digest| RestDigest]) ->
  234:     case crypto:hash(Type, Msg) of
  235: 	Digest ->
  236: 	    hash(Type, RestMsg, RestDigest);
  237: 	Other ->
  238: 	    ct:fail({{crypto, hash, [Type, Msg]}, {expected, Digest}, {got, Other}})
  239:     end.
  240: 
  241: hash_increment(Type, Increments, Digest) ->
  242:     State = crypto:hash_init(Type),
  243:     case hash_increment(State, Increments) of
  244: 	Digest ->
  245: 	    ok;
  246: 	Other ->
  247: 	    ct:fail({{crypto, "hash_init/update/final", [Type, Increments]}, {expected, Digest}, {got, Other}})  
  248:     end.
  249: 
  250: hash_increment(State, []) ->
  251:     crypto:hash_final(State);
  252: hash_increment(State0, [Increment | Rest]) ->
  253:     State = crypto:hash_update(State0, Increment),
  254:     hash_increment(State, Rest).
  255: 
  256: hmac(_, [],[],[]) ->
  257:     ok;
  258: hmac(sha = Type, [Key | Keys], [ <<"Test With Truncation">> = Data| Rest], [Expected | Expects]) ->
  259:     case crypto:hmac(Type, Key, Data, 20) of
  260: 	Expected ->
  261: 	    ok;
  262: 	Other ->
  263: 	    ct:fail({{crypto, hmac, [Type, Key, Data]}, {expected, Expected}, {got, Other}})
  264:     end,  
  265:     hmac(Type, Keys, Rest, Expects);
  266: 
  267: hmac(Type, [Key | Keys], [ <<"Test With Truncation">> = Data| Rest], [Expected | Expects]) ->
  268:     case crypto:hmac(Type, Key, Data, 16) of
  269: 	Expected ->
  270: 	    ok;
  271: 	Other ->
  272: 	    ct:fail({{crypto, hmac, [Type, Key, Data]}, {expected, Expected}, {got, Other}})
  273:     end,  
  274:     hmac(Type, Keys, Rest, Expects);
  275: 
  276: hmac(Type, [Key | Keys], [Data| Rest], [Expected | Expects]) ->
  277:     case crypto:hmac(Type, Key, Data) of
  278: 	Expected ->
  279: 	    ok;
  280: 	Other ->
  281: 	    ct:fail({{crypto, hmac, [Type, Key, Data]}, {expected, Expected}, {got, Other}})
  282:     end,  
  283:     hmac(Type, Keys, Rest, Expects).
  284: 
  285: hmac_increment(Type) ->
  286:     Key = hmac_key(Type),
  287:     Increments = hmac_inc(Type),
  288:     Expected = crypto:hmac(Type, Key, lists:flatten(Increments)),
  289:     State = crypto:hmac_init(Type, Key),
  290:     case hmac_increment(State, Increments) of
  291: 	Expected ->
  292: 	    ok;
  293: 	Other ->
  294: 	    ct:fail({{crypto, "hmac_init/update/final", [Type, Increments]}, {expected, Expected}, {got, Other}})  
  295:     end.
  296: 
  297: hmac_increment(State, []) ->
  298:     crypto:hmac_final(State);
  299: hmac_increment(State0, [Increment | Rest]) ->
  300:     State = crypto:hmac_update(State0, Increment),
  301:     hmac_increment(State, Rest).
  302: 
  303: block_cipher({Type, Key,  PlainText}) ->
  304:     Plain = iolist_to_binary(PlainText),
  305:     CipherText = crypto:block_encrypt(Type, Key, PlainText),
  306:     case crypto:block_decrypt(Type, Key, CipherText) of
  307: 	Plain ->
  308: 	    ok;
  309: 	Other ->
  310: 	    ct:fail({{crypto, block_decrypt, [Type, Key, CipherText]}, {expected, Plain}, {got, Other}})
  311:     end;
  312: 
  313: block_cipher({Type, Key,  IV, PlainText}) ->
  314:     Plain = iolist_to_binary(PlainText),
  315:     CipherText = crypto:block_encrypt(Type, Key, IV, PlainText),
  316:     case crypto:block_decrypt(Type, Key, IV, CipherText) of
  317: 	Plain ->
  318: 	    ok;
  319: 	Other ->
  320: 	    ct:fail({{crypto, block_decrypt, [Type, Key, IV, CipherText]}, {expected, Plain}, {got, Other}})
  321:     end.
  322: 
  323: block_cipher_increment({Type, Key, IV, PlainTexts}) when Type == des_cbc;
  324: 							 Type == des3_cbc;
  325: 							 Type == aes_cbc; 
  326: 							 Type == des_cbf
  327: 							 ->
  328:      block_cipher_increment(Type, Key, IV, IV, PlainTexts, iolist_to_binary(PlainTexts), []);
  329: block_cipher_increment({_Type, _, _, _}) ->
  330:     ok;
  331: block_cipher_increment({_,_,_}) ->
  332:     ok.
  333: block_cipher_increment(Type, Key, IV0, _IV, [], Plain, Acc) ->
  334:     CipherText = iolist_to_binary(lists:reverse(Acc)),
  335:     case crypto:block_decrypt(Type, Key, IV0, CipherText) of
  336: 	Plain ->
  337: 	    ok;
  338: 	Other ->
  339: 	    ct:fail({{crypto, block_decrypt, [Type, Key, IV0, CipherText]}, {expected, Plain}, {got, Other}})
  340:     end;
  341: block_cipher_increment(Type, Key, IV0, IV, [PlainText | PlainTexts], Plain, Acc) ->
  342:     CipherText = crypto:block_encrypt(Type, Key, IV, PlainText),
  343:     NextIV = crypto:next_iv(Type, CipherText),
  344:     block_cipher_increment(Type, Key, IV0, NextIV, PlainTexts, Plain, [CipherText | Acc]).
  345: 
  346: stream_cipher({Type, Key, PlainText}) ->
  347:     Plain = iolist_to_binary(PlainText),
  348:     State = crypto:stream_init(Type, Key),
  349:     {_, CipherText} = crypto:stream_encrypt(State, PlainText),
  350:     case crypto:stream_decrypt(State, CipherText) of
  351: 	{_, Plain} ->
  352: 	    ok;
  353: 	Other ->
  354: 	    ct:fail({{crypto, stream_decrypt, [State, CipherText]}, {expected, PlainText}, {got, Other}})
  355:     end;
  356: stream_cipher({Type, Key, IV, PlainText}) ->
  357:     Plain = iolist_to_binary(PlainText),
  358:     State = crypto:stream_init(Type, Key, IV),
  359:     {_, CipherText} = crypto:stream_encrypt(State, PlainText),
  360:     case crypto:stream_decrypt(State, CipherText) of
  361: 	{_, Plain} ->
  362: 	    ok;
  363: 	Other ->
  364: 	    ct:fail({{crypto, stream_decrypt, [State, CipherText]}, {expected, PlainText}, {got, Other}})
  365:     end.
  366: 
  367: stream_cipher_incment({Type, Key, PlainTexts}) ->
  368:     State = crypto:stream_init(Type, Key),
  369:     stream_cipher_incment(State, State, PlainTexts, [], iolist_to_binary(PlainTexts));
  370: stream_cipher_incment({Type, Key, IV, PlainTexts}) ->
  371:     State = crypto:stream_init(Type, Key, IV),
  372:     stream_cipher_incment(State, State, PlainTexts, [], iolist_to_binary(PlainTexts)).
  373: 
  374: stream_cipher_incment(_State, OrigState, [], Acc, Plain) ->
  375:     CipherText = iolist_to_binary(lists:reverse(Acc)),
  376:     case crypto:stream_decrypt(OrigState, CipherText) of
  377: 	{_, Plain} ->
  378: 	    ok;
  379: 	Other ->
  380: 	    ct:fail({{crypto, stream_decrypt, [OrigState, CipherText]}, {expected, Plain}, {got, Other}})
  381:     end;
  382: stream_cipher_incment(State0, OrigState, [PlainText | PlainTexts], Acc, Plain) ->
  383:     {State, CipherText} = crypto:stream_encrypt(State0, PlainText),
  384:     stream_cipher_incment(State, OrigState, PlainTexts, [CipherText | Acc], Plain).
  385: 	
  386: do_sign_verify({Type, Hash, Public, Private, Msg}) ->
  387:     Signature = crypto:sign(Type, Hash, Msg, Private),
  388:     case crypto:verify(Type, Hash, Msg, Signature, Public) of
  389: 	true ->
  390: 	    negative_verify(Type, Hash, Msg, <<10,20>>, Public);
  391: 	false ->
  392: 	    ct:fail({{crypto, verify, [Type, Hash, Msg, Signature, Public]}})
  393:     end. 
  394: 
  395: negative_verify(Type, Hash, Msg, Signature, Public) ->
  396:     case crypto:verify(Type, Hash, Msg, Signature, Public) of
  397: 	true ->
  398: 	    ct:fail({{crypto, verify, [Type, Hash, Msg, Signature, Public]}, should_fail});
  399: 	false ->
  400: 	    ok
  401:     end.
  402: 
  403: do_public_encrypt({Type, Public, Private, Msg, Padding}) ->
  404:     PublicEcn = (catch crypto:public_encrypt(Type, Msg, Public, Padding)),
  405:     case crypto:private_decrypt(Type, PublicEcn, Private, Padding) of
  406: 	Msg ->
  407: 	    ok;
  408: 	Other ->
  409: 	    ct:fail({{crypto, private_decrypt, [Type, PublicEcn, Private, Padding]}, {expected, Msg}, {got, Other}})
  410:     end. 
  411: 
  412: do_private_encrypt({_Type, _Public, _Private, _Msg, rsa_pkcs1_oaep_padding}) ->
  413:     ok; %% Not supported by openssl
  414: do_private_encrypt({Type, Public, Private, Msg, Padding}) ->
  415:     PrivEcn = (catch crypto:private_encrypt(Type, Msg, Private, Padding)),
  416:     case crypto:public_decrypt(rsa, PrivEcn, Public, Padding) of
  417: 	Msg ->
  418: 	    ok;
  419: 	Other ->
  420: 	    ct:fail({{crypto, public_decrypt, [Type, PrivEcn, Public, Padding]}, {expected, Msg}, {got, Other}})
  421:     end.
  422:      
  423: do_generate_compute({srp = Type, UserPrivate, UserGenParams, UserComParams,
  424: 		     HostPublic, HostPrivate, HostGenParams, HostComParam, SessionKey}) ->
  425:     {UserPublic, UserPrivate} = crypto:generate_key(Type, UserGenParams, UserPrivate),
  426:     {HostPublic, HostPrivate} = crypto:generate_key(Type, HostGenParams, HostPrivate),
  427:     SessionKey = crypto:compute_key(Type, HostPublic, {UserPublic, UserPrivate},
  428:      				    UserComParams),
  429:     SessionKey = crypto:compute_key(Type, UserPublic, {HostPublic, HostPrivate},
  430: 				    HostComParam);
  431: do_generate_compute({dh, P, G}) ->
  432:     {UserPub, UserPriv} = crypto:generate_key(dh, [P, G]),
  433:     {HostPub, HostPriv} = crypto:generate_key(dh, [P, G]),
  434:     SharedSecret = crypto:compute_key(dh, HostPub, UserPriv, [P, G]),
  435:     SharedSecret = crypto:compute_key(dh, UserPub, HostPriv, [P, G]).
  436:     
  437: do_compute({ecdh = Type, Pub, Priv, Curve, SharedSecret}) ->
  438:     Secret = crypto:bytes_to_integer(crypto:compute_key(Type, Pub, Priv, Curve)),
  439:      case Secret of
  440: 	 SharedSecret ->
  441: 	     ok;
  442: 	 Other ->
  443: 	     ct:fail({{crypto, compute_key, [Type, Pub, Priv, Curve]}, {expected, SharedSecret}, {got, Other}})
  444:      end.
  445: 
  446: hexstr2bin(S) ->
  447:     list_to_binary(hexstr2list(S)).
  448: 
  449: hexstr2list([X,Y|T]) ->
  450:     [mkint(X)*16 + mkint(Y) | hexstr2list(T)];
  451: hexstr2list([]) ->
  452:     [].
  453: mkint(C) when $0 =< C, C =< $9 ->
  454:     C - $0;
  455: mkint(C) when $A =< C, C =< $F ->
  456:     C - $A + 10;
  457: mkint(C) when $a =< C, C =< $f ->
  458:     C - $a + 10.
  459: 
  460: is_supported(Group) ->
  461:     lists:member(Group, lists:append([Algo ||  {_, Algo}  <- crypto:supports()])). 
  462: 
  463: block_iolistify(Blocks) ->
  464:     lists:map(fun do_block_iolistify/1, Blocks).
  465: stream_iolistify(Streams) ->
  466:     lists:map(fun do_stream_iolistify/1, Streams).
  467: 
  468: do_stream_iolistify({Type, Key, PlainText}) ->
  469:     {Type, iolistify(Key), iolistify(PlainText)};
  470: do_stream_iolistify({Type, Key, IV, PlainText}) ->
  471:     {Type, iolistify(Key), IV, iolistify(PlainText)}.
  472: 
  473: do_block_iolistify({des_cbc = Type, Key, IV, PlainText}) ->
  474:     {Type, Key, IV, des_iolistify(PlainText)};
  475: do_block_iolistify({des3_cbc = Type, Key, IV, PlainText}) ->
  476:     {Type, Key, IV, des_iolistify(PlainText)};
  477: do_block_iolistify({des3_cbf = Type, Key, IV, PlainText}) ->
  478:     {Type, Key, IV, des_iolistify(PlainText)};
  479: do_block_iolistify({des_ede3 = Type, Key, IV, PlainText}) ->
  480:     {Type, Key, IV, des_iolistify(PlainText)};
  481: do_block_iolistify({Type, Key, PlainText}) ->
  482:     {Type, iolistify(Key), iolistify(PlainText)};
  483: do_block_iolistify({Type, Key, IV, PlainText}) ->
  484:     {Type, iolistify(Key), IV, iolistify(PlainText)}.
  485: 
  486: iolistify(<<"Test With Truncation">>)->
  487:     %% Do not iolistify as it spoils this special case
  488:     <<"Test With Truncation">>;
  489: iolistify(Msg) when is_binary(Msg) ->
  490:     Length = erlang:byte_size(Msg),
  491:     Split = Length div 2,
  492:     List0 = binary_to_list(Msg),
  493:    case lists:split(Split, List0) of
  494:        {[Element | List1], List2} ->
  495: 	   [[Element], List1, List2];
  496:        {List1, List2}->
  497: 	   [List1, List2]
  498:    end;
  499: iolistify(Msg) ->
  500:     iolistify(list_to_binary(Msg)).
  501: 
  502: des_iolistify(Msg) ->    
  503:     des_iolist(erlang:byte_size(Msg) div 8, Msg, []).
  504: 
  505: des_iolist(1, Msg, Acc) ->
  506:     lists:reverse([Msg | Acc]);
  507: des_iolist(Split, Msg, Acc) ->
  508:     <<Part:8/binary, Rest/binary>> = Msg,
  509:     des_iolist(Split-1, Rest, [Part | Acc]).
  510: 
  511: %%--------------------------------------------------------------------
  512: mod_pow_aux_test(_, _, _, 0) ->
  513:     ok;
  514: mod_pow_aux_test(B, E, M, N) ->
  515:     Result = crypto:bytes_to_integer(crypto:mod_pow(B, E, M)),
  516:     Result = ipow(B, E, M),
  517:     mod_pow_aux_test(B, E*E+1, M*M+1, N-1).
  518: 
  519: %% mod_exp in erlang (copied from jungerl's ssh_math.erl)
  520: ipow(A, B, M) when M > 0, B >= 0 ->
  521:     if A == 1 -> 
  522:  	    1;
  523:        true -> 
  524:  	    ipow(A, B, M, 1)
  525:     end.
  526: 
  527: ipow(A, 1, M, Prod) ->
  528:     (A*Prod) rem M;
  529: ipow(_A, 0, _M, Prod) ->
  530:     Prod;
  531: ipow(A, B, M, Prod)  ->
  532:     B1 = B bsr 1,
  533:     A1 = (A*A) rem M,
  534:     if B - B1 == B1 ->
  535: 	    ipow(A1, B1, M, Prod);
  536:        true ->
  537: 	    ipow(A1, B1, M, (A*Prod) rem M)
  538:     end.
  539: 
  540: do_exor(B) ->
  541:     Z1 = zero_bin(B),
  542:     Z1 = crypto:exor(B, B),
  543:     B1 = crypto:rand_bytes(100),
  544:     B2 = crypto:rand_bytes(100),
  545:     Z2 = zero_bin(B1),
  546:     Z2 = crypto:exor(B1, B1),
  547:     Z2 = crypto:exor(B2, B2),
  548:     R = xor_bytes(B1, B2),
  549:     R = crypto:exor(B1, B2).
  550: 
  551: zero_bin(N) when is_integer(N) ->
  552:     N8 = N * 8,
  553:     <<0:N8/integer>>;
  554: zero_bin(B) when is_binary(B) ->
  555:     zero_bin(size(B)).
  556: xor_bytes(Bin1, Bin2) when is_binary(Bin1), is_binary(Bin2) ->
  557:     L1 = binary_to_list(Bin1),
  558:     L2 = binary_to_list(Bin2),
  559:     list_to_binary(xor_bytes(L1, L2));
  560: xor_bytes(L1, L2) ->
  561:     xor_bytes(L1, L2, []).
  562: 
  563: xor_bytes([], [], Acc) ->
  564:     lists:reverse(Acc);
  565: xor_bytes([N1 | Tl1], [N2 | Tl2], Acc) ->
  566:     xor_bytes(Tl1, Tl2, [N1 bxor N2 | Acc]).
  567: rand_uniform_aux_test(0) ->
  568:     ok;
  569: rand_uniform_aux_test(N) ->
  570:     L = N*1000,
  571:     H = N*100000+1,
  572:     crypto_rand_uniform(L, H),
  573:     crypto_rand_uniform(-L, L),
  574:     crypto_rand_uniform(-H, -L),
  575:     crypto_rand_uniform(-H, L),
  576:     rand_uniform_aux_test(N-1).
  577: 
  578: crypto_rand_uniform(L,H) ->
  579:     R1 = crypto:rand_uniform(L, H),
  580:     case (R1 >= L) and (R1 < H) of
  581: 	true  ->
  582: 	    ok;
  583: 	false ->
  584: 	    ct:fail({"Not in interval", R1, L, H})
  585:     end.
  586: 
  587: %%--------------------------------------------------------------------
  588: %% Test data ------------------------------------------------
  589: %%--------------------------------------------------------------------
  590: group_config(md4 = Type, Config) ->
  591:     Msgs = rfc_1321_msgs(),
  592:     Digests = rfc_1321_md4_digests(),
  593:     [{hash, {Type, Msgs, Digests}} | Config];
  594: group_config(md5 = Type, Config) ->
  595:     Msgs = rfc_1321_msgs(),
  596:     Digests = rfc_1321_md5_digests(),
  597:     Keys = rfc_2202_md5_keys() ++ [long_hmac_key(md5)],
  598:     Data = rfc_2202_msgs() ++ [long_msg()],
  599:     Hmac = rfc_2202_hmac_md5()  ++ [long_hmac(md5)],
  600:     [{hash, {Type, Msgs, Digests}}, {hmac, {Type, Keys, Data, Hmac}} | Config];
  601: group_config(ripemd160 = Type, Config) ->
  602:     Msgs = ripemd160_msgs(),
  603:     Digests = ripemd160_digests(),
  604:    [{hash, {Type, Msgs, Digests}} | Config];
  605: group_config(sha = Type, Config) ->
  606:     Msgs = [rfc_4634_test1(), rfc_4634_test2_1(),long_msg()],
  607:     Digests = rfc_4634_sha_digests() ++ [long_sha_digest()],
  608:     Keys = rfc_2202_sha_keys() ++ [long_hmac_key(sha)],
  609:     Data = rfc_2202_msgs() ++ [long_msg()],
  610:     Hmac = rfc_2202_hmac_sha()  ++ [long_hmac(sha)],
  611:     [{hash, {Type, Msgs, Digests}}, {hmac, {Type, Keys, Data, Hmac}} | Config];
  612: group_config(sha224 = Type, Config) ->
  613:     Msgs = [rfc_4634_test1(), rfc_4634_test2_1()], 
  614:     Digests = rfc_4634_sha224_digests(),
  615:     Keys = rfc_4231_keys(),
  616:     Data = rfc_4231_msgs(),
  617:     Hmac = rfc4231_hmac_sha224(),
  618:    [{hash, {Type, Msgs, Digests}}, {hmac, {Type, Keys, Data, Hmac}}  | Config];
  619: group_config(sha256 = Type, Config) ->
  620:     Msgs =   [rfc_4634_test1(), rfc_4634_test2_1(), long_msg()],
  621:     Digests = rfc_4634_sha256_digests()  ++ [long_sha256_digest()],
  622:     Keys = rfc_4231_keys() ++ [long_hmac_key(sha256)],
  623:     Data = rfc_4231_msgs()  ++ [long_msg()],
  624:     Hmac = rfc4231_hmac_sha256()  ++ [long_hmac(sha256)],
  625:     [{hash, {Type, Msgs, Digests}}, {hmac, {Type, Keys, Data, Hmac}}  | Config];
  626: group_config(sha384 = Type, Config) ->
  627:     Msgs =  [rfc_4634_test1(), rfc_4634_test2(), long_msg()],
  628:     Digests = rfc_4634_sha384_digests()  ++ [long_sha384_digest()],
  629:     Keys = rfc_4231_keys() ++ [long_hmac_key(sha384)],
  630:     Data = rfc_4231_msgs()  ++ [long_msg()],
  631:     Hmac = rfc4231_hmac_sha384()  ++ [long_hmac(sha384)],
  632:     [{hash, {Type, Msgs, Digests}}, {hmac, {Type, Keys, Data, Hmac}}  | Config];
  633: group_config(sha512 = Type, Config) ->
  634:     Msgs =  [rfc_4634_test1(), rfc_4634_test2(), long_msg()],
  635:     Digests = rfc_4634_sha512_digests() ++ [long_sha512_digest()],
  636:     Keys = rfc_4231_keys() ++ [long_hmac_key(sha512)],
  637:     Data = rfc_4231_msgs() ++ [long_msg()],
  638:     Hmac = rfc4231_hmac_sha512() ++ [long_hmac(sha512)],
  639:     [{hash, {Type, Msgs, Digests}}, {hmac, {Type, Keys, Data, Hmac}}  | Config];
  640: group_config(rsa = Type, Config) ->
  641:     Msg = rsa_plain(),
  642:     Public = rsa_public(),
  643:     Private = rsa_private(),
  644:     PublicS = rsa_public_stronger(),
  645:     PrivateS = rsa_private_stronger(),
  646:     SignVerify = sign_verify_tests(Type, Msg, Public, Private, PublicS, PrivateS),
  647:     MsgPubEnc = <<"7896345786348 Asldi">>,
  648:     PubPrivEnc = [{rsa, Public, Private, MsgPubEnc, rsa_pkcs1_padding},
  649: 		  rsa_oaep(),
  650: 		  no_padding()
  651: 		 ],
  652:     [{sign_verify, SignVerify}, {pub_priv_encrypt, PubPrivEnc} | Config];
  653: group_config(dss = Type, Config) ->
  654:     Msg = dss_plain(),
  655:     Public = dss_params() ++ [dss_public()], 
  656:     Private = dss_params() ++ [dss_private()], 
  657:     SignVerify = [{Type, sha, Public, Private, Msg}],
  658:     [{sign_verify, SignVerify} | Config];
  659: 
  660: group_config(ecdsa = Type, Config) ->
  661:     {Private, Public} = ec_key_named(),
  662:     Msg = ec_msg(),
  663:     SignVerify = [{Type, sha, Public, Private, Msg}],
  664:     [{sign_verify, SignVerify} | Config];
  665: group_config(srp, Config) ->
  666:     GenerateCompute = [srp3(), srp6(), srp6a()],
  667:     [{generate_compute, GenerateCompute} | Config];
  668: group_config(ecdh, Config) ->
  669:     Compute = [ecdh()],
  670:     [{compute, Compute} | Config];
  671: group_config(dh, Config) ->
  672:     GenerateCompute = [dh()],
  673:     [{generate_compute, GenerateCompute} | Config];
  674: group_config(des_cbc, Config) ->
  675:     Block = des_cbc(),
  676:     [{block, Block} | Config];
  677: group_config(des_cfb, Config) ->
  678:     Block = des_cfb(),
  679:     [{block, Block} | Config];
  680: group_config(des3_cbc, Config) ->
  681:     Block = des3_cbc(),
  682:     [{block, Block} | Config];
  683: group_config(des3_cbf, Config) ->
  684:     Block = des3_cbf(),
  685:     [{block, Block} | Config];
  686: group_config(des_ede3, Config) ->
  687:     Block = des_ede3(),
  688:     [{block, Block} | Config];
  689: group_config(rc2_cbc, Config) ->
  690:     Block = rc2_cbc(),
  691:     [{block, Block} | Config];
  692: group_config(aes_cbc128, Config) ->
  693:     Block = aes_cbc128(),
  694:     [{block, Block} | Config];
  695: group_config(aes_cbc256, Config) ->
  696:     Block = aes_cbc256(),
  697:     [{block, Block} | Config];
  698: group_config(aes_cfb128, Config) ->
  699:     Block = aes_cfb128(),
  700:     [{block, Block} | Config];
  701: group_config(blowfish_cbc, Config) ->
  702:     Block = blowfish_cbc(),
  703:     [{block, Block} | Config];
  704: group_config(blowfish_ecb, Config) ->
  705:     Block = blowfish_ecb(),
  706:     [{block, Block} | Config];
  707: group_config(blowfish_cfb64, Config) ->
  708:     Block = blowfish_cfb64(),
  709:     [{block, Block} | Config];
  710: group_config(blowfish_ofb64, Config) ->
  711:     Block = blowfish_ofb64(),
  712:     [{block, Block} | Config];
  713: group_config(rc4, Config) ->
  714:     Stream = rc4(),
  715:     [{stream, Stream} | Config];
  716: group_config(aes_ctr, Config) ->
  717:     Stream = aes_ctr(),
  718:     [{stream, Stream} | Config];
  719: group_config(_, Config) ->
  720:     Config.
  721: 
  722: sign_verify_tests(Type, Msg, Public, Private, PublicS, PrivateS) ->
  723:     sign_verify_tests(Type, [md5, sha, sha224, sha256], Msg, Public, Private) ++
  724: 	sign_verify_tests(Type, [sha384, sha512], Msg, PublicS, PrivateS).
  725: 
  726: sign_verify_tests(Type, Hashs, Msg, Public, Private) ->
  727:     lists:foldl(fun(Hash, Acc) -> 
  728: 			case is_supported(Hash) of
  729: 			    true ->
  730: 				[{Type, Hash,  Public, Private, Msg}|Acc];
  731: 			    false ->
  732: 			      Acc
  733: 			end
  734: 		end, [], Hashs).
  735: 
  736: rfc_1321_msgs() ->
  737:     [<<"">>, 
  738:      <<"a">>,
  739:      <<"abc">>, 
  740:      <<"message digest">>,
  741:      <<"abcdefghijklmnopqrstuvwxyz">>,
  742:      <<"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789">>,
  743:      <<"12345678901234567890123456789012345678901234567890123456789012345678901234567890">>
  744:     ].
  745: 
  746: rfc_1321_md4_digests() ->
  747:     [hexstr2bin("31d6cfe0d16ae931b73c59d7e0c089c0"),
  748:      hexstr2bin("bde52cb31de33e46245e05fbdbd6fb24"),
  749:      hexstr2bin("a448017aaf21d8525fc10ae87aa6729d"),
  750:      hexstr2bin("d9130a8164549fe818874806e1c7014b"),
  751:      hexstr2bin("d79e1c308aa5bbcdeea8ed63df412da9"),
  752:      hexstr2bin("043f8582f241db351ce627e153e7f0e4"),
  753:      hexstr2bin("e33b4ddc9c38f2199c3e7b164fcc0536")].
  754: 
  755: rfc_1321_md5_digests() ->
  756:     [hexstr2bin("d41d8cd98f00b204e9800998ecf8427e"),
  757:      hexstr2bin("0cc175b9c0f1b6a831c399e269772661"),
  758:      hexstr2bin("900150983cd24fb0d6963f7d28e17f72"),
  759:      hexstr2bin("f96b697d7cb7938d525a2f31aaf161d0"),
  760:      hexstr2bin("c3fcd3d76192e4007dfb496cca67e13b"),
  761:      hexstr2bin("d174ab98d277d9f5a5611c2c9f419d9f"),
  762:      hexstr2bin("57edf4a22be3c955ac49da2e2107b67a")].
  763: 
  764: rfc_4634_test1() ->
  765:     <<"abc">>.
  766: rfc_4634_test2_1() ->
  767:     <<"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq">>.
  768: rfc_4634_test2_2a() ->
  769:     <<"abcdefghbcdefghicdefghijdefghijkefghijklfghijklmghijklmn">>.
  770: rfc_4634_test2_2b() ->
  771:     <<"hijklmnoijklmnopjklmnopqklmnopqrlmnopqrsmnopqrstnopqrstu">>.
  772: rfc_4634_test2() ->
  773:     A2 =rfc_4634_test2_2a(),
  774:     B2 = rfc_4634_test2_2b(),
  775:     <<A2/binary, B2/binary>>.
  776:  
  777: rfc_4634_sha_digests()->
  778:      [hexstr2bin("A9993E364706816ABA3E25717850C26C9CD0D89D"),
  779:       hexstr2bin("84983E441C3BD26EBAAE4AA1F95129E5E54670F1")].
  780: rfc_4634_sha224_digests() ->
  781:      [hexstr2bin("23097D223405D8228642A477BDA255B32AADBCE4BDA0B3F7E36C9DA7"),
  782:       hexstr2bin("75388B16512776CC5DBA5DA1FD890150B0C6455CB4F58B1952522525")].
  783: rfc_4634_sha256_digests() ->
  784:     [
  785:      hexstr2bin("BA7816BF8F01CFEA4141"
  786: 		"40DE5DAE2223B00361A396177A9CB410FF61F20015AD"),
  787:      hexstr2bin("248D6A61D20638B8"
  788: 		"E5C026930C3E6039A33CE45964FF2167F6ECEDD419DB06C1")
  789:     ].
  790: rfc_4634_sha384_digests() ->
  791:     [hexstr2bin("CB00753F45A35E8BB5A03D699AC65007272C32AB0EDED1631A8B605A43FF5BED8086072BA1E7CC2358BAECA134C825A7"),
  792:      hexstr2bin("09330C33F71147E83D192FC782CD1B4753111B173B3B05D22FA08086E3B0F712FCC7C71A557E2DB966C3E9FA91746039")
  793:     ].
  794: rfc_4634_sha512_digests() -> 
  795:     [hexstr2bin("DDAF35A193617ABACC417349AE20413112E6FA4E89A97EA2"
  796: 		"0A9EEEE64B55D39A2192992A274FC1A836BA3C23A3FEEBBD"
  797: 		"454D4423643CE80E2A9AC94FA54CA49F"),
  798:      hexstr2bin("8E959B75DAE313DA8CF4F72814FC143F8F7779C6EB9F7FA17299AEADB6889018501D289E4900F7E4331B99DEC4B5433AC7D329EEB6DD26545E96E55B874BE909")].
  799: 
  800: long_msg() ->
  801:     fun() -> lists:duplicate(1000000, $a) end.
  802: 
  803: %% Building huge terms (like long_msg/0) in init_per_group seems to cause
  804: %% test_server crash with 'no_answer_from_tc_supervisor' sometimes on some
  805: %% machines. Therefore lazy evaluation when test case has started.
  806: lazy_eval(F) when is_function(F) -> F();
  807: lazy_eval(Lst)  when is_list(Lst) -> lists:map(fun lazy_eval/1, Lst);
  808: lazy_eval(Tpl) when is_tuple(Tpl) -> list_to_tuple(lists:map(fun lazy_eval/1, tuple_to_list(Tpl)));
  809: lazy_eval(Term) -> Term.
  810: 
  811: long_sha_digest() ->
  812:     hexstr2bin("34aa973c" "d4c4daa4" "f61eeb2b" "dbad2731" "6534016f").
  813: 
  814: long_sha256_digest() ->
  815:     hexstr2bin("cdc76e5c" "9914fb92" "81a1c7e2" "84d73e67" "f1809a48" "a497200e" "046d39cc" "c7112cd0").
  816: 
  817: long_sha384_digest() ->
  818:     hexstr2bin("9d0e1809716474cb" "086e834e310a4a1c" "ed149e9c00f24852" "7972cec5704c2a5b"
  819: 	       "07b8b3dc38ecc4eb" "ae97ddd87f3d8985").
  820: 
  821: long_sha512_digest() ->
  822:     hexstr2bin("e718483d0ce76964" "4e2e42c7bc15b463" "8e1f98b13b204428" "5632a803afa973eb"
  823: 	       "de0ff244877ea60a" "4cb0432ce577c31b" "eb009c5c2c49aa2e" "4eadb217ad8cc09b").
  824: 
  825: ripemd160_msgs() ->
  826:     [<<"">>,
  827:      <<"a">>,
  828:      <<"abc">>,
  829:      <<"message digest">>,
  830:      <<"abcdefghijklmnopqrstuvwxyz">>,
  831:      <<"abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq">>,
  832:      <<"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789">>
  833:     ].
  834: 
  835: ripemd160_digests() ->
  836:     [hexstr2bin("9c1185a5c5e9fc54612808977ee8f548b2258d31"),
  837:      hexstr2bin("0bdc9d2d256b3ee9daae347be6f4dc835a467ffe"),
  838:      hexstr2bin("8eb208f7e05d987a9b044a8e98c6b087f15a0bfc"),
  839:      hexstr2bin("5d0689ef49d2fae572b881b123a85ffa21595f36"),
  840:      hexstr2bin("f71c27109c692c1b56bbdceb5b9d2865b3708dbc"),
  841:      hexstr2bin("12a053384a9c0c88e405a06c27dcf49ada62eb2b"),
  842:      hexstr2bin("b0e20b6e3116640286ed3a87a5713079b21f5189")
  843:     ].
  844: 
  845: ripemd160_incr_msgs() ->
  846:      [<<"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefg">>,<<"hijklmnopqrstuvwxyz0123456789">>].
  847: ripemd160_incr_digest() ->
  848:     hexstr2bin("b0e20b6e3116640286ed3a87a5713079b21f5189").
  849: 
  850: rfc_2202_md5_keys() ->
  851:     [binary:copy(<<16#0b>>, 16),
  852:      <<"Jefe">>,
  853:      binary:copy(<<16#aa>>, 16),
  854:      list_to_binary(lists:seq(1, 16#19)),
  855:      binary:copy(<<16#0c>>, 16),
  856:      binary:copy(<<16#aa>>, 80),
  857:      binary:copy(<<16#aa>>, 80)].
  858: 
  859: rfc_2202_sha_keys() ->
  860:     [binary:copy(<<16#0b>>, 20),
  861:      <<"Jefe">>,
  862:      binary:copy(<<16#aa>>, 20),
  863:      list_to_binary(lists:seq(1, 16#19)),
  864:      binary:copy(<<16#0c>>, 20),
  865:      binary:copy(<<16#aa>>, 80),
  866:      binary:copy(<<16#aa>>, 80)].
  867: 
  868: rfc_2202_msgs()->
  869:     [<<"Hi There">>,
  870:      <<"what do ya want for nothing?">>,
  871:      binary:copy(<<16#dd>>, 50),
  872:      binary:copy(<<16#cd>>, 50),
  873:      <<"Test With Truncation">>,
  874:      <<"Test Using Larger Than Block-Size Key - Hash Key First">>,
  875:      <<"Test Using Larger Than Block-Size Key and Larger Than One Block-Size Data">>
  876:     ].
  877: 
  878: hmac_key(md5) ->
  879:     [<<"A fine speach">>, <<"by a fine man!">>];
  880: hmac_key(_) ->
  881:     hexstr2bin("00010203101112132021222330313233"
  882: 	       "04050607141516172425262734353637"
  883: 	       "08090a0b18191a1b28292a2b38393a3b"
  884: 	       "0c0d0e0f1c1d1e1f2c2d2e2f3c3d3e3f").
  885: hmac_inc(_) ->
  886:     [<<"Sampl">>, <<"e #1">>].
  887: 
  888: %% https://www.cosic.esat.kuleuven.be/nessie/testvectors/
  889: long_hmac_key(Type) when Type == sha384;
  890: 			 Type == sha512 ->
  891:     hexstr2bin("00112233445566778899AABBCCDDEEFF"
  892: 	       "0123456789ABCDEF0011223344556677"
  893: 	       "8899AABBCCDDEEFF0123456789ABCDEF"
  894: 	       "00112233445566778899AABBCCDDEEFF");
  895: long_hmac_key(_) ->
  896:     hexstr2bin("0123456789ABCDEF0123456789ABCDEF"
  897: 	       "0123456789ABCDEF0123456789ABCDEF"
  898: 	       "0123456789ABCDEF0123456789ABCDEF"
  899: 	       "0123456789ABCDEF0123456789ABCDEF").
  900: long_hmac(md5) ->
  901:     hexstr2bin("82FDDA30202CB6ACC6F24D4F8A50EB7A");
  902: long_hmac(sha) ->
  903:     hexstr2bin("61D1D0B6459860755FDA892938C23DD401E54A7E");
  904: long_hmac(sha256) ->
  905:     hexstr2bin("50008B8DC7ED3926936347FDC1A01E9D"
  906: 	       "5220C6CC4B038B482C0F28A4CD88CA37");
  907: long_hmac(sha384) ->
  908:     hexstr2bin("C1EB08DAFA015833D3FC6B29A387558B"
  909: 	       "3F6FA1524AA1A8EB64798D5A76A39D6E"
  910: 	       "A1465525342E060EE996277B4FFCDDC9");
  911: long_hmac(sha512) ->
  912:     hexstr2bin("D116BF471AAE1264854F1906025E846A"
  913: 	       "61618A965FCA30B695220EA2D6E547E3"
  914: 	       "F3B5A4B54E6778928C26D5D3D810498E"
  915: 	       "8DF86CB3CC1E9F66A00419B13B6B0C9A").
  916: 
  917: rfc_2202_hmac_md5() ->
  918:     [
  919:      hexstr2bin("9294727a3638bb1c13f48ef8158bfc9d"),
  920:      hexstr2bin("750c783e6ab0b503eaa86e310a5db738"),
  921:      hexstr2bin("56be34521d144c88dbb8c733f0e8b3f6"),
  922:      hexstr2bin("697eaf0aca3a3aea3a75164746ffaa79"),
  923:      hexstr2bin("56461ef2342edc00f9bab995690efd4c"),
  924:      hexstr2bin("6b1ab7fe4bd7bf8f0b62e6ce61b9d0cd"),
  925:      hexstr2bin("6f630fad67cda0ee1fb1f562db3aa53e")
  926:     ].
  927: 
  928: rfc_2202_hmac_sha() ->
  929:     [
  930:      hexstr2bin("b617318655057264e28bc0b6fb378c8ef146be00"),
  931:      hexstr2bin("effcdf6ae5eb2fa2d27416d5f184df9c259a7c79"),
  932:      hexstr2bin("125d7342b9ac11cd91a39af48aa17b4f63f175d3"),
  933:      hexstr2bin("4c9007f4026250c6bc8414f9bf50c86c2d7235da"),
  934:      hexstr2bin("4c1a03424b55e07fe7f27be1d58bb9324a9a5a04"),
  935:      hexstr2bin("aa4ae5e15272d00e95705637ce8a3b55ed402112"),
  936:      hexstr2bin("e8e99d0f45237d786d6bbaa7965c7808bbff1a91")
  937:     ].
  938: 
  939: 
  940: rfc_4231_keys() ->
  941:     [binary:copy(<<16#0b>>, 20),
  942:      <<"Jefe">>,
  943:      binary:copy(<<16#aa>>, 20),
  944:      list_to_binary(lists:seq(1, 16#19)),
  945:      binary:copy(<<16#0c>>, 20),
  946:      binary:copy(<<16#aa>>, 131),
  947:      binary:copy(<<16#aa>>, 131)
  948:     ].
  949:     
  950: rfc_4231_msgs() ->
  951:     [<<"Hi There">>,
  952:      <<"what do ya want for nothing?">>,
  953:      binary:copy(<<16#dd>>, 50),
  954:      binary:copy(<<16#cd>>, 50),
  955:      <<"Test With Truncation">>,
  956:      <<"Test Using Larger Than Block-Size Key - Hash Key First">>,
  957:      <<"This is a test using a larger than block-size key and a larger t",
  958:        "han block-size data. The key needs to be hashed before being use",
  959:        "d by the HMAC algorithm.">>
  960:     ].
  961:     
  962: rfc4231_hmac_sha224() ->
  963:     [hexstr2bin("896fb1128abbdf196832107cd49df33f"
  964: 		       "47b4b1169912ba4f53684b22"),
  965:      hexstr2bin("a30e01098bc6dbbf45690f3a7e9e6d0f"
  966: 		       "8bbea2a39e6148008fd05e44"),
  967:      hexstr2bin("7fb3cb3588c6c1f6ffa9694d7d6ad264"
  968: 		       "9365b0c1f65d69d1ec8333ea"),
  969:      hexstr2bin("6c11506874013cac6a2abc1bb382627c"
  970: 		       "ec6a90d86efc012de7afec5a"),
  971:      hexstr2bin("0e2aea68a90c8d37c988bcdb9fca6fa8"),
  972:      hexstr2bin("95e9a0db962095adaebe9b2d6f0dbce2"
  973: 		       "d499f112f2d2b7273fa6870e"),
  974:      hexstr2bin("3a854166ac5d9f023f54d517d0b39dbd"
  975: 		"946770db9c2b95c9f6f565d1")].
  976: rfc4231_hmac_sha256() ->
  977:     [hexstr2bin("b0344c61d8db38535ca8afceaf0bf12b"
  978: 		"881dc200c9833da726e9376c2e32cff7"),
  979:      hexstr2bin("5bdcc146bf60754e6a042426089575c7"
  980: 		"5a003f089d2739839dec58b964ec3843"),
  981:      hexstr2bin("773ea91e36800e46854db8ebd09181a7"
  982: 		"2959098b3ef8c122d9635514ced565fe"),
  983:     hexstr2bin("82558a389a443c0ea4cc819899f2083a"
  984: 	       "85f0faa3e578f8077a2e3ff46729665b"),
  985:      hexstr2bin("a3b6167473100ee06e0c796c2955552b"),
  986:      hexstr2bin("60e431591ee0b67f0d8a26aacbf5b77f"
  987: 		"8e0bc6213728c5140546040f0ee37f54"),
  988:      hexstr2bin("9b09ffa71b942fcb27635fbcd5b0e944"
  989: 		"bfdc63644f0713938a7f51535c3a35e2")].
  990: 
  991: rfc4231_hmac_sha384() ->
  992:     [hexstr2bin("afd03944d84895626b0825f4ab46907f"
  993: 		"15f9dadbe4101ec682aa034c7cebc59c"
  994: 		"faea9ea9076ede7f4af152e8b2fa9cb6"),
  995:      hexstr2bin("af45d2e376484031617f78d2b58a6b1b"
  996: 		"9c7ef464f5a01b47e42ec3736322445e"
  997: 	       "8e2240ca5e69e2c78b3239ecfab21649"),
  998:      hexstr2bin("88062608d3e6ad8a0aa2ace014c8a86f"
  999: 	       "0aa635d947ac9febe83ef4e55966144b"
 1000: 		"2a5ab39dc13814b94e3ab6e101a34f27"),
 1001:      hexstr2bin("3e8a69b7783c25851933ab6290af6ca7"
 1002: 		"7a9981480850009cc5577c6e1f573b4e"
 1003: 		"6801dd23c4a7d679ccf8a386c674cffb"),
 1004:      hexstr2bin("3abf34c3503b2a23a46efc619baef897"),
 1005:      hexstr2bin("4ece084485813e9088d2c63a041bc5b4"
 1006: 		"4f9ef1012a2b588f3cd11f05033ac4c6"
 1007: 		"0c2ef6ab4030fe8296248df163f44952"),
 1008:      hexstr2bin("6617178e941f020d351e2f254e8fd32c"
 1009: 		"602420feb0b8fb9adccebb82461e99c5"
 1010: 		"a678cc31e799176d3860e6110c46523e")].
 1011: rfc4231_hmac_sha512() ->
 1012:     [hexstr2bin("87aa7cdea5ef619d4ff0b4241a1d6cb0"
 1013: 		"2379f4e2ce4ec2787ad0b30545e17cde"
 1014: 		"daa833b7d6b8a702038b274eaea3f4e4"
 1015: 		"be9d914eeb61f1702e696c203a126854"),
 1016:      hexstr2bin("164b7a7bfcf819e2e395fbe73b56e0a3"
 1017: 		"87bd64222e831fd610270cd7ea250554"
 1018: 		"9758bf75c05a994a6d034f65f8f0e6fd"
 1019: 		"caeab1a34d4a6b4b636e070a38bce737"),
 1020:      hexstr2bin("fa73b0089d56a284efb0f0756c890be9"
 1021: 		"b1b5dbdd8ee81a3655f83e33b2279d39"
 1022: 		"bf3e848279a722c806b485a47e67c807"
 1023: 		"b946a337bee8942674278859e13292fb"),
 1024:      hexstr2bin("b0ba465637458c6990e5a8c5f61d4af7"
 1025: 		"e576d97ff94b872de76f8050361ee3db"
 1026: 		"a91ca5c11aa25eb4d679275cc5788063"
 1027: 		"a5f19741120c4f2de2adebeb10a298dd"),
 1028:      hexstr2bin("415fad6271580a531d4179bc891d87a6"),
 1029:      hexstr2bin("80b24263c7c1a3ebb71493c1dd7be8b4"
 1030: 		"9b46d1f41b4aeec1121b013783f8f352"
 1031: 		"6b56d037e05f2598bd0fd2215d6a1e52"
 1032: 		"95e64f73f63f0aec8b915a985d786598"),
 1033:      hexstr2bin("e37b6a775dc87dbaa4dfa9f96e5e3ffd"
 1034: 		"debd71f8867289865df5a32d20cdc944"
 1035: 		"b6022cac3c4982b10d5eeb55c3e4de15"
 1036: 		"134676fb6de0446065c97440fa8c6a58")].
 1037: des_cbc() ->
 1038:     [{des_cbc, 
 1039:      hexstr2bin("0123456789abcdef"), 
 1040:      hexstr2bin("1234567890abcdef"),
 1041:      <<"Now is the time for all ">> }].
 1042:       
 1043: des_cfb() ->
 1044:     [{des_cfb, 
 1045:      hexstr2bin("0123456789abcdef"),
 1046:      hexstr2bin("1234567890abcdef"),
 1047:      <<"Now is the">>}].
 1048: 
 1049: des3_cbc() ->
 1050:     [{des3_cbc,
 1051:      [hexstr2bin("0123456789abcdef"), 
 1052:       hexstr2bin("fedcba9876543210"),
 1053:       hexstr2bin("0f2d4b6987a5c3e1")],
 1054:      hexstr2bin("1234567890abcdef"),
 1055:      <<"Now is the time for all ">>
 1056:      }].
 1057: 
 1058: des_ede3() ->
 1059:     [{des_ede3,
 1060:      [hexstr2bin("8000000000000000"),
 1061:       hexstr2bin("4000000000000000"),
 1062:       hexstr2bin("2000000000000000")],
 1063:       hexstr2bin("7AD16FFB79C45926"),
 1064:       hexstr2bin("0000000000000000")
 1065:      }].
 1066: 
 1067: des3_cbf() ->
 1068:     [{des3_cbf,
 1069:      [hexstr2bin("0123456789abcdef"), 
 1070:       hexstr2bin("fedcba9876543210"),
 1071:       hexstr2bin("0f2d4b6987a5c3e1")],
 1072:      hexstr2bin("1234567890abcdef"),
 1073:      <<"Now is the time for all ">>
 1074:      }].
 1075: 
 1076: rc2_cbc() ->
 1077:     [{rc2_cbc,
 1078:      <<146,210,160,124,215,227,153,239,227,17,222,140,3,93,27,191>>,
 1079:       <<72,91,135,182,25,42,35,210>>,
 1080:      <<36,245,206,158,168,230,58,69,148,137,32,192,250,41,237,181,181,251, 192,2,175,135,177,171,57,30,111,117,159,149,15,28,88,158,28,81,28,115, 85,219,241,82,117,222,91,85,73,117,164,25,182,52,191,64,123,57,26,19, 211,27,253,31,194,219,231,104,247,240,172,130,119,21,225,154,101,247, 32,216,42,216,133,169,78,22,97,27,227,26,196,224,172,168,17,9,148,55, 203,91,252,40,61,226,236,221,215,160,78,63,13,181,68,57,196,241,185, 207, 116,129,152,237,60,139,247,153,27,146,161,246,222,98,185,222,152, 187,135, 236,86,34,7,110,91,230,173,34,160,242,202,222,121,127,181,140, 101,203,195, 190,88,250,86,147,127,87,72,126,171,16,71,47,110,248,88, 14,29,143,161,152, 129,236,148,22,152,186,208,119,70,8,174,193,203,100, 193,203,200,117,102,242, 134,142,96,125,135,200,217,190,76,117,50,70, 209,186,101,241,200,91,40,193,54, 90,195,38,47,59,197,38,234,86,223,16, 51,253,204,129,20,171,66,21,241,26,135,216, 196,114,110,91,15,53,40, 164,201,136,113,95,247,51,181,208,241,68,168,98,151,36, 155,72,24,57, 42,191,14,125,204,10,167,214,233,138,115,125,234,121,134,227,26,247, 77,200,117,110,117,111,168,156,206,67,159,149,189,173,150,193,91,199, 216,153,22, 189,137,185,89,160,13,131,132,58,109,28,110,246,252,251,14, 232,91,38,52,29,101,188,69,123,50,0,130,178,93,73,239,118,7,77,35,59, 253,10,159,45,86,142,37,78,232,48>>
 1081:      }].
 1082: aes_cbc128() ->
 1083:     [{aes_cbc128,
 1084:       hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1085:       hexstr2bin("000102030405060708090a0b0c0d0e0f"),
 1086:       hexstr2bin("6bc1bee22e409f96e93d7e117393172a")},
 1087:      {aes_cbc128,
 1088:       hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1089:       hexstr2bin("7649ABAC8119B246CEE98E9B12E9197D"),
 1090:       hexstr2bin("ae2d8a571e03ac9c9eb76fac45af8e51")},
 1091:      {aes_cbc128,
 1092:       hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1093:       hexstr2bin("5086CB9B507219EE95DB113A917678B2"),
 1094:       hexstr2bin("30c81c46a35ce411e5fbc1191a0a52ef")},
 1095:      {aes_cbc128,
 1096:       hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1097:       hexstr2bin("73BED6B8E3C1743B7116E69E22229516"),
 1098:       hexstr2bin("f69f2445df4f9b17ad2b417be66c3710")}
 1099:     ].
 1100: 
 1101: aes_cbc256() -> 
 1102:     [{aes_cbc256,
 1103:       hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"), 
 1104:       hexstr2bin("000102030405060708090A0B0C0D0E0F"),
 1105:       hexstr2bin("6bc1bee22e409f96e93d7e117393172a")},
 1106:       {aes_cbc256,
 1107:        hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"), 
 1108:        hexstr2bin("F58C4C04D6E5F1BA779EABFB5F7BFBD6"),
 1109:        hexstr2bin("ae2d8a571e03ac9c9eb76fac45af8e51")},
 1110:       {aes_cbc256,
 1111:        hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"), 
 1112:        hexstr2bin("9CFC4E967EDB808D679F777BC6702C7D"),
 1113:        hexstr2bin("30c81c46a35ce411e5fbc1191a0a52ef")},
 1114:       {aes_cbc256,
 1115:        hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"), 
 1116:        hexstr2bin("39F23369A9D9BACFA530E26304231461"),
 1117:        hexstr2bin("f69f2445df4f9b17ad2b417be66c3710")}
 1118:      ].
 1119: 
 1120: aes_cfb128() -> 
 1121:     [{aes_cfb128,
 1122:       hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1123:       hexstr2bin("000102030405060708090a0b0c0d0e0f"),
 1124:       hexstr2bin("6bc1bee22e409f96e93d7e117393172a")},
 1125:       {aes_cfb128,
 1126:        hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1127:        hexstr2bin("3B3FD92EB72DAD20333449F8E83CFB4A"),
 1128:        hexstr2bin("ae2d8a571e03ac9c9eb76fac45af8e51")},
 1129:       {aes_cfb128,
 1130:        hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1131:        hexstr2bin("C8A64537A0B3A93FCDE3CDAD9F1CE58B"),
 1132:        hexstr2bin("30c81c46a35ce411e5fbc1191a0a52ef")},
 1133:       {aes_cfb128,
 1134:        hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1135:        hexstr2bin("26751F67A3CBB140B1808CF187A4F4DF"),
 1136:        hexstr2bin("f69f2445df4f9b17ad2b417be66c3710")}
 1137:      ].
 1138: 
 1139: blowfish_cbc() ->
 1140:     [{blowfish_cbc,
 1141:       hexstr2bin("0123456789ABCDEFF0E1D2C3B4A59687"), 
 1142:       hexstr2bin("FEDCBA9876543210"),
 1143:       hexstr2bin("37363534333231204E6F77206973207468652074696D6520666F722000000000")
 1144:      }].
 1145: 
 1146: blowfish_ecb() ->
 1147:     [
 1148:      {blowfish_ecb,
 1149:       hexstr2bin("0000000000000000"), 
 1150:       hexstr2bin("0000000000000000")},
 1151:      {blowfish_ecb,
 1152:       hexstr2bin("FFFFFFFFFFFFFFFF"), 
 1153:       hexstr2bin("FFFFFFFFFFFFFFFF")},
 1154:      {blowfish_ecb,
 1155:       hexstr2bin("3000000000000000"), 
 1156:       hexstr2bin("1000000000000001")},
 1157:      {blowfish_ecb,
 1158:       hexstr2bin("1111111111111111"), 
 1159:       hexstr2bin("1111111111111111")},
 1160:      {blowfish_ecb,
 1161:       hexstr2bin("0123456789ABCDEF"), 
 1162:       hexstr2bin("1111111111111111")},
 1163:      {blowfish_ecb,
 1164:       hexstr2bin("0000000000000000"), 
 1165:       hexstr2bin("0000000000000000")},
 1166:      {blowfish_ecb,
 1167:       hexstr2bin("FEDCBA9876543210"), 
 1168:       hexstr2bin("0123456789ABCDEF")},
 1169:      {blowfish_ecb,
 1170:       hexstr2bin("7CA110454A1A6E57"), 
 1171:       hexstr2bin("01A1D6D039776742")},
 1172:      {blowfish_ecb,
 1173:       hexstr2bin("0131D9619DC1376E"), 
 1174:       hexstr2bin("5CD54CA83DEF57DA")},
 1175:      {blowfish_ecb,
 1176:       hexstr2bin("07A1133E4A0B2686"), 
 1177:       hexstr2bin("0248D43806F67172")},
 1178:      {blowfish_ecb,
 1179:       hexstr2bin("3849674C2602319E"), 
 1180:       hexstr2bin("51454B582DDF440A")},
 1181:      {blowfish_ecb,
 1182:       hexstr2bin("04B915BA43FEB5B6"), 
 1183:       hexstr2bin("42FD443059577FA2")},
 1184:      {blowfish_ecb,
 1185:       hexstr2bin("0113B970FD34F2CE"), 
 1186:       hexstr2bin("059B5E0851CF143A")},
 1187:      {blowfish_ecb,
 1188:       hexstr2bin("0170F175468FB5E6"), 
 1189:       hexstr2bin("0756D8E0774761D2")},
 1190:      {blowfish_ecb,
 1191:       hexstr2bin("43297FAD38E373FE"), 
 1192:       hexstr2bin("762514B829BF486A")},
 1193:      {blowfish_ecb,
 1194:       hexstr2bin("07A7137045DA2A16"), 
 1195:       hexstr2bin("3BDD119049372802")},
 1196:      {blowfish_ecb,
 1197:       hexstr2bin("04689104C2FD3B2F"), 
 1198:       hexstr2bin("26955F6835AF609A")},
 1199:      {blowfish_ecb,
 1200:       hexstr2bin("37D06BB516CB7546"), 
 1201:       hexstr2bin("164D5E404F275232")},
 1202:      {blowfish_ecb,
 1203:       hexstr2bin("1F08260D1AC2465E"), 
 1204:       hexstr2bin("6B056E18759F5CCA")},
 1205:      {blowfish_ecb,
 1206:       hexstr2bin("584023641ABA6176"), 
 1207:       hexstr2bin("004BD6EF09176062")},
 1208:      {blowfish_ecb,
 1209:       hexstr2bin("025816164629B007"), 
 1210:       hexstr2bin("480D39006EE762F2")},
 1211:      {blowfish_ecb,
 1212:       hexstr2bin("49793EBC79B3258F"), 
 1213:       hexstr2bin("437540C8698F3CFA")},
 1214:      {blowfish_ecb,
 1215:       hexstr2bin("018310DC409B26D6"), 
 1216:       hexstr2bin("1D9D5C5018F728C2")},
 1217:      {blowfish_ecb,
 1218:       hexstr2bin("1C587F1C13924FEF"), 
 1219:       hexstr2bin("305532286D6F295A")},
 1220:      {blowfish_ecb,
 1221:       hexstr2bin("0101010101010101"), 
 1222:       hexstr2bin("0123456789ABCDEF")},
 1223:      {blowfish_ecb,
 1224:       hexstr2bin("1F1F1F1F0E0E0E0E"), 
 1225:       hexstr2bin("0123456789ABCDEF")},
 1226:      {blowfish_ecb,
 1227:       hexstr2bin("E0FEE0FEF1FEF1FE"), 
 1228:       hexstr2bin("0123456789ABCDEF")},
 1229:      {blowfish_ecb,
 1230:       hexstr2bin("0000000000000000"), 
 1231:       hexstr2bin("FFFFFFFFFFFFFFFF")},
 1232:      {blowfish_ecb,
 1233:       hexstr2bin("FFFFFFFFFFFFFFFF"), 
 1234:       hexstr2bin("0000000000000000")},
 1235:      {blowfish_ecb,
 1236:       hexstr2bin("0123456789ABCDEF"), 
 1237:       hexstr2bin("0000000000000000")},
 1238:      {blowfish_ecb,
 1239:       hexstr2bin("FEDCBA9876543210"), 
 1240:       hexstr2bin("FFFFFFFFFFFFFFFF")}
 1241:     ].
 1242: 
 1243: blowfish_cfb64() ->
 1244:     [{blowfish_cfb64,
 1245:       hexstr2bin("0123456789ABCDEFF0E1D2C3B4A59687"), 
 1246:       hexstr2bin("FEDCBA9876543210"),
 1247:       hexstr2bin("37363534333231204E6F77206973207468652074696D6520666F722000")
 1248:      }].
 1249: blowfish_ofb64() ->
 1250:     [{blowfish_ofb64,
 1251:       hexstr2bin("0123456789ABCDEFF0E1D2C3B4A59687"), 
 1252:       hexstr2bin("FEDCBA9876543210"),
 1253:       hexstr2bin("37363534333231204E6F77206973207468652074696D6520666F722000")
 1254:      }].
 1255: 
 1256: rc4() ->
 1257:     [{rc4, <<"apaapa">>, <<"Yo baby yo">>},
 1258:      {rc4, <<"apaapa">>, list_to_binary(lists:seq(0, 255))},
 1259:      {rc4, <<"apaapa">>, long_msg()}
 1260:     ].
 1261: 
 1262: aes_ctr() ->
 1263:     [  %% F.5.3  CTR-AES192.Encrypt
 1264:        {aes_ctr, hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1265: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff"), 
 1266: 	hexstr2bin("6bc1bee22e409f96e93d7e117393172a")},
 1267:        {aes_ctr, hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1268: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff00"), 
 1269: 	hexstr2bin("ae2d8a571e03ac9c9eb76fac45af8e51")},
 1270:        {aes_ctr, hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1271: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff01"), 
 1272: 	hexstr2bin("30c81c46a35ce411e5fbc1191a0a52ef") },
 1273:        {aes_ctr, hexstr2bin("2b7e151628aed2a6abf7158809cf4f3c"), 
 1274: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff02"), 
 1275: 	hexstr2bin("f69f2445df4f9b17ad2b417be66c3710")},
 1276:        
 1277:        %% F.5.3  CTR-AES192.Encrypt
 1278:        {aes_ctr, hexstr2bin("8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b"), 
 1279: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff"), 
 1280: 	hexstr2bin("6bc1bee22e409f96e93d7e117393172a")},
 1281:        {aes_ctr, hexstr2bin("8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b"), 
 1282: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff00"), 
 1283: 	hexstr2bin("ae2d8a571e03ac9c9eb76fac45af8e51")},
 1284:        {aes_ctr, hexstr2bin("8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b"), 
 1285: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff01"), 
 1286: 	hexstr2bin("30c81c46a35ce411e5fbc1191a0a52ef")},
 1287:        {aes_ctr, hexstr2bin("8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b"), 
 1288: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff02"), 
 1289: 	hexstr2bin("f69f2445df4f9b17ad2b417be66c3710")},
 1290:        
 1291:        %% F.5.5  CTR-AES256.Encrypt
 1292:        {aes_ctr, hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"), 
 1293: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff"), 
 1294: 	hexstr2bin("6bc1bee22e409f96e93d7e117393172a")},
 1295:        {aes_ctr, hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"), 
 1296: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff00"), 
 1297: 	hexstr2bin("ae2d8a571e03ac9c9eb76fac45af8e51")},
 1298:        {aes_ctr, hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"), 
 1299: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff01"), 
 1300: 	hexstr2bin("30c81c46a35ce411e5fbc1191a0a52ef")},
 1301:        {aes_ctr, hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"), 
 1302: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdff02"), 
 1303: 	hexstr2bin("f69f2445df4f9b17ad2b417be66c3710")},
 1304: 
 1305:        {aes_ctr,  hexstr2bin("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4"),
 1306: 	hexstr2bin("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff"),
 1307: 	long_msg()}
 1308:     ].
 1309: 
 1310: rsa_plain() ->
 1311:     <<"7896345786348756234 Hejsan Svejsan, erlang crypto debugger"
 1312:       "09812312908312378623487263487623412039812 huagasd">>.
 1313: rsa_public() ->
 1314:     [65537, 7919488123861148172698919999061127847747888703039837999377650217570191053151807772962118671509138346758471459464133273114654252861270845708312601272799123].
 1315: rsa_private() ->
 1316:     rsa_public() ++ [7531712708607620783801185371644749935066152052780368689827275932079815492940396744378735701395659435842364793962992309884847527234216715366607660219930945].
 1317: 
 1318: rsa_public_stronger() ->
 1319:     [65537, 24629450921918866883077380602720734920775458960049554761386137065662137652635369332143446151320538248280934442179850504891395344346514465469955766163141133564033962851182759993807898821114734943339732032639891483186089941567854227407119560631150779000222837755424893038740314247760600374970909894211201220612920040986106639419467243909950276018045907029941478599124238353052062083560294570722081552510960894164859765695309596889747541376908786225647625736062865138957717982693312699025417086612046330464651009693307624955796202070510577399561730651967517158452930742355327167632521808183383868100102455048819375344881].
 1320: 
 1321: rsa_private_stronger() ->
 1322:     rsa_public_stronger() ++ [13565232776562604620467234237694854016819673873109064019820773052201665024482754648718278717031083946624786145611240731564761987114634269887293030432042088547345315212418830656522115993209293567218379960177754901461542373481136856927955012596579314262051109321754382091434920473734937991286600905464814063189230779981494358415076362038786197620360127262110530926733754185204773610295221669711309000953136320804528874719105049753061737780710448207922456570922652651354760939379096788728229638142403068102990416717272880560951246813789730402978652924934794503277969128609831043469924881848849409122972426787999886557185].
 1323: 
 1324: dss_plain() ->
 1325:     rsa_plain().
 1326: dss_public() ->
 1327:     25854665488880835237281628794585130313500176551981812527054397586638455298000483144002221850980183404910190346416063318160497344811383498859129095184158800144312512447497510551471331451396405348497845813002058423110442376886564659959543650802132345311573634832461635601376738282831340827591903548964194832978.
 1328: dss_private() ->
 1329:     441502407453038284293378221372000880210588566361.  
 1330: dss_params() ->
 1331:     [109799869232806890760655301608454668257695818999841877165019612946154359052535682480084145133201304812979481136659521529774182959764860329095546511521488413513097576425638476458000255392402120367876345280670101492199681798674053929238558140260669578407351853803102625390950534052428162468100618240968893110797,
 1332:      1349199015905534965792122312016505075413456283393,
 1333:      18320614775012672475365915366944922415598782131828709277168615511695849821411624805195787607930033958243224786899641459701930253094446221381818858674389863050420226114787005820357372837321561754462061849169568607689530279303056075793886577588606958623645901271866346406773590024901668622321064384483571751669].
 1334: 
 1335: ec_key_named() ->
 1336:     {D2_pub, D2_priv} = crypto:generate_key(ecdh, sect113r2),
 1337:     {[D2_priv, sect113r2], [D2_pub, sect113r2]}.  
 1338: 
 1339: ec_msg() ->
 1340:     <<99,234,6,64,190,237,201,99,80,248,58,40,70,45,149,218,5,246,242,63>>.
 1341: 
 1342: srp3() ->
 1343:     Username = <<"alice">>,
 1344:     Password = <<"password123">>,
 1345:     Salt = hexstr2bin("2857827A19266A1F2BC6"),
 1346:     Prime = hexstr2bin("EEAF0AB9ADB38DD69C33F80AFA8FC5E86072618775FF3C0B9EA2314C"
 1347: 		       "9C256576D674DF7496EA81D3383B4813D692C6E0E0D5D8E250B98BE4"
 1348: 		       "8E495C1D6089DAD15DC7D7B46154D6B6CE8EF4AD69B15D4982559B29"
 1349: 		       "7BCF1885C529F566660E57EC68EDBC3C05726CC02FD4CBF4976EAA9A"
 1350: 		       "FD5138FE8376435B9FC61D2FC0EB06E3"),
 1351:     Generator = <<2>>,
 1352:     Version = '3',
 1353:     Scrambler = hexstr2bin("02E2476A"),
 1354: 
 1355:     %% X = hexstr2bin("96E54AB0CD4C5123EDCFA4A1502918AAD3C9E2A8"),
 1356:     Verifier = hexstr2bin("96EB5F13621D911AA1CA405DE9C64217D4108EEEECAFFE500034FE0E"
 1357: 			  "C031E42C8714667C161BCE0E7996F7DDE1B63824C130D2D7286C08C0"
 1358: 			  "49758420735961347112AE102A3F23B3F687F8FEE0DF2BFAF933C608"
 1359: 			  "D6FE5B5EEE3116FE54016E065BF8E8C9FDBBC08719231AC215149140"
 1360: 			  "519E8FDD9AA4F410C28A58AF42974D2D"),
 1361:     ClientPrivate = hexstr2bin("6411DE75538BED8170677D577D0608F39112BC95B503C447EB6AC945"
 1362: 			  "49C75C7B"),
 1363:     ServerPrivate = hexstr2bin("85E44A6F694DBE676145DB245A045CD37C99F05C562C7840A31F270D"
 1364: 			  "9AADCF8B"),
 1365:     ClientPublic = hexstr2bin("B22B1FFA2244B8CB94F3A9080F419CAEAB0DBA93EA1965B5E84587EE"
 1366: 			 "55C79E7A118865DC59B9D0353362C2A8261E7C1B0D221A0E233C2AD1"
 1367: 			 "640DACBB8664CBC9733EAC392DA7800142860380C3FC573C3C064329"
 1368: 			 "CF54063FD114C7210E9CB3A611EA8002B1844B698F930D95D143899B"
 1369: 			 "948A090E0C25938E5F84067D1883DC63"),
 1370:     ServerPublic = hexstr2bin("93A8C4D8B7F7395ADCFD4ABA37B015124513D3F37B3E85EB23064BE5"
 1371: 			 "F53C0AE32FFB9D8C0AA0DCFFA74D632DD67DEBB5C35AAE9812286CC8"
 1372: 			 "C43CC176ECBC6D3F447594D9554E995B2509127BF88FADDDA4982D03"
 1373: 			 "8EC3001320712D3B1269308CE70F319B2295FA57674F03A2D993CFB1"
 1374: 			 "F84C35B7D0C012FA73CD4C8F7D5A71C7"),
 1375: 
 1376:     SessionKey = hexstr2bin("C29A986C4D521BBC66428ED11D994CD7431574A6184B83CDCC345092"
 1377: 			    "791E75748A1D38CAC4BD14760F0D2694B711236419240FF2F172454C"
 1378: 			    "46ABF4FF39498DAFDD2C82924F7D7BD76CDFCE688C77D93F18A65409"
 1379: 			    "9176A9192615DC0277AE7C12F1F6A7F6563FCA11675D809AF578BDE5"
 1380: 			    "2B51E05D440B63099A017A0B45044801"),
 1381:     UserPassHash = crypto:hash(sha, [Salt, crypto:hash(sha, [Username, <<$:>>, Password])]),
 1382:     Verifier = crypto:mod_pow(Generator, UserPassHash, Prime), 
 1383:     ClientPublic = crypto:mod_pow(Generator, ClientPrivate, Prime), 
 1384:     srp(ClientPrivate, Generator, Prime, Version, Verifier, ServerPublic, ServerPrivate, UserPassHash, Scrambler, SessionKey).
 1385: 
 1386: srp6() ->
 1387:     Username = <<"alice">>,
 1388:     Password = <<"password123">>,
 1389:     Salt = hexstr2bin("2857827A19266A1F2BC6"),
 1390:     Prime = hexstr2bin("EEAF0AB9ADB38DD69C33F80AFA8FC5E86072618775FF3C0B9EA2314C"
 1391: 		       "9C256576D674DF7496EA81D3383B4813D692C6E0E0D5D8E250B98BE4"
 1392: 		       "8E495C1D6089DAD15DC7D7B46154D6B6CE8EF4AD69B15D4982559B29"
 1393: 		       "7BCF1885C529F566660E57EC68EDBC3C05726CC02FD4CBF4976EAA9A"
 1394: 		       "FD5138FE8376435B9FC61D2FC0EB06E3"),
 1395:     Generator = <<2>>,
 1396:     Version = '6',
 1397:     Scrambler = hexstr2bin("0A2534C0BF52A0DA9001EEC62CF2A546AB0908A7"),
 1398:     Verifier = hexstr2bin("96EB5F13621D911AA1CA405DE9C64217D4108EEEECAFFE500034FE0E"
 1399: 			  "C031E42C8714667C161BCE0E7996F7DDE1B63824C130D2D7286C08C0"
 1400: 			  "49758420735961347112AE102A3F23B3F687F8FEE0DF2BFAF933C608"
 1401: 			  "D6FE5B5EEE3116FE54016E065BF8E8C9FDBBC08719231AC215149140"
 1402: 			  "519E8FDD9AA4F410C28A58AF42974D2D"),
 1403:     ClientPrivate = hexstr2bin("6411DE75538BED8170677D577D0608F39112BC95B503C447EB6AC945"
 1404: 			  "49C75C7B"),
 1405:     ServerPrivate = hexstr2bin("85E44A6F694DBE676145DB245A045CD37C99F05C562C7840A31F270D"
 1406: 			  "9AADCF8B"),
 1407:     ClientPublic = hexstr2bin("B22B1FFA2244B8CB94F3A9080F419CAEAB0DBA93EA1965B5E84587EE"
 1408: 			 "55C79E7A118865DC59B9D0353362C2A8261E7C1B0D221A0E233C2AD1"
 1409: 			 "640DACBB8664CBC9733EAC392DA7800142860380C3FC573C3C064329"
 1410: 			 "CF54063FD114C7210E9CB3A611EA8002B1844B698F930D95D143899B"
 1411: 			 "948A090E0C25938E5F84067D1883DC63"),
 1412:     ServerPublic = hexstr2bin("D2D07845CE7ECDB9845DD36B10ACD3598CC29049DE9F467F84CE16B6"
 1413: 			 "D97A6DC567AF8B0F9FEDF74962400AD5C357951E64E67B641246F264"
 1414: 			 "C8DE6D9A72E554D6C8D3194548780A0C438A0FCC509CA88A14AA1DEB"
 1415: 			 "C0F09E4B37A965D1545DB4AD361346F3189B0EA569C06D326C4E4797"
 1416: 			 "9E381C748293B7C0591BE0BE419E053E"),
 1417: 
 1418:     SessionKey = hexstr2bin("19D22C19612874EBF1F2581F8EFCFDC44C6FDA3B87B0A73823D7E962"
 1419: 				 "554295D4E48D3A336523ADBDDD0EC8FB0F02687109E97E01C17C93CC"
 1420: 				 "7216F9CD8A4AC39F0429857D8D1023066614BDFCBCB89F59A0FEB81C"
 1421: 				 "72E992AAD89095A84B6A5FADA152369AB1E350A03693BEF044DF3EDF"
 1422: 				 "0C34741F4696C30E9F675D09F58ACBEB"),
 1423:     UserPassHash = crypto:hash(sha, [Salt, crypto:hash(sha, [Username, <<$:>>, Password])]),
 1424:     Verifier = crypto:mod_pow(Generator, UserPassHash, Prime), 
 1425:     ClientPublic = crypto:mod_pow(Generator, ClientPrivate, Prime),
 1426:     srp(ClientPrivate, Generator, Prime, Version, Verifier, ServerPublic, ServerPrivate, UserPassHash, Scrambler, SessionKey).
 1427: 
 1428: srp6a() ->
 1429:     Username = <<"alice">>,
 1430:     Password = <<"password123">>,
 1431:     Salt = hexstr2bin("BEB25379D1A8581EB5A727673A2441EE"),
 1432:     Prime = hexstr2bin("EEAF0AB9ADB38DD69C33F80AFA8FC5E86072618775FF3C0B9EA2314C"
 1433: 		       "9C256576D674DF7496EA81D3383B4813D692C6E0E0D5D8E250B98BE4"
 1434: 		       "8E495C1D6089DAD15DC7D7B46154D6B6CE8EF4AD69B15D4982559B29"
 1435: 		       "7BCF1885C529F566660E57EC68EDBC3C05726CC02FD4CBF4976EAA9A"
 1436: 		       "FD5138FE8376435B9FC61D2FC0EB06E3"),
 1437:     Generator = <<2>>,
 1438:     Version = '6a',
 1439:     Scrambler = hexstr2bin("CE38B9593487DA98554ED47D70A7AE5F462EF019"),
 1440:     Verifier = hexstr2bin("7E273DE8696FFC4F4E337D05B4B375BEB0DDE1569E8FA00A9886D812"
 1441: 			  "9BADA1F1822223CA1A605B530E379BA4729FDC59F105B4787E5186F5"
 1442: 			  "C671085A1447B52A48CF1970B4FB6F8400BBF4CEBFBB168152E08AB5"
 1443: 			  "EA53D15C1AFF87B2B9DA6E04E058AD51CC72BFC9033B564E26480D78"
 1444: 			  "E955A5E29E7AB245DB2BE315E2099AFB"),
 1445:     ClientPrivate = hexstr2bin("60975527035CF2AD1989806F0407210BC81EDC04E2762A56AFD529DD"
 1446: 			  "DA2D4393"),
 1447:     ServerPrivate = hexstr2bin("E487CB59D31AC550471E81F00F6928E01DDA08E974A004F49E61F5D1"
 1448: 			  "05284D20"),
 1449:     ClientPublic = hexstr2bin("61D5E490F6F1B79547B0704C436F523DD0E560F0C64115BB72557EC4"
 1450: 			      "4352E8903211C04692272D8B2D1A5358A2CF1B6E0BFCF99F921530EC"
 1451: 			      "8E39356179EAE45E42BA92AEACED825171E1E8B9AF6D9C03E1327F44"
 1452: 			      "BE087EF06530E69F66615261EEF54073CA11CF5858F0EDFDFE15EFEA"
 1453: 			      "B349EF5D76988A3672FAC47B0769447B"),
 1454:     ServerPublic = hexstr2bin("BD0C61512C692C0CB6D041FA01BB152D4916A1E77AF46AE105393011"
 1455: 			      "BAF38964DC46A0670DD125B95A981652236F99D9B681CBF87837EC99"
 1456: 			      "6C6DA04453728610D0C6DDB58B318885D7D82C7F8DEB75CE7BD4FBAA"
 1457: 			      "37089E6F9C6059F388838E7A00030B331EB76840910440B1B27AAEAE"
 1458: 			      "EB4012B7D7665238A8E3FB004B117B58"),
 1459:     
 1460:     SessionKey = hexstr2bin("B0DC82BABCF30674AE450C0287745E7990A3381F63B387AAF271A10D"
 1461: 			    "233861E359B48220F7C4693C9AE12B0A6F67809F0876E2D013800D6C"
 1462: 			    "41BB59B6D5979B5C00A172B4A2A5903A0BDCAF8A709585EB2AFAFA8F"
 1463: 			    "3499B200210DCC1F10EB33943CD67FC88A2F39A4BE5BEC4EC0A3212D"
 1464: 			    "C346D7E474B29EDE8A469FFECA686E5A"),
 1465:     UserPassHash = crypto:hash(sha, [Salt, crypto:hash(sha, [Username, <<$:>>, Password])]),
 1466:     Verifier = crypto:mod_pow(Generator, UserPassHash, Prime), 
 1467:     ClientPublic = crypto:mod_pow(Generator, ClientPrivate, Prime), 
 1468:     srp(ClientPrivate, Generator, Prime, Version, Verifier, ServerPublic, ServerPrivate, UserPassHash, Scrambler, SessionKey).
 1469: 
 1470: srp(ClientPrivate, Generator, Prime, Version, Verifier, ServerPublic, ServerPrivate, UserPassHash, Scrambler, SessionKey)->
 1471:     {srp, ClientPrivate, 
 1472:      {user, [Generator, Prime, Version]}, {user, [UserPassHash, Prime, Generator, Version, Scrambler]}, 
 1473:      ServerPublic, ServerPrivate, {host, [Verifier, Generator, Prime, Version]},
 1474:      {host, [Verifier, Prime, Version, Scrambler]},
 1475:      SessionKey}.
 1476: ecdh() ->
 1477:     {ecdh, 10053111454769593468622878414300213417816614162107065345116848162553478019161427871683337786549966,
 1478:      1373339791687564785573162818422814591820885704654,
 1479:      secp160r1, 990333295438215762119481641129490894973766052278}.
 1480: 
 1481: dh() ->
 1482:     {dh, 0087761979513264537414556992123116644042638206717762626089877284926656954974893442000747478454809111207351620687968672207938731607963470779396984752680274820156266685080223616226905101126463253150237669547023934604953898814222890239130021414026118792251620881355456432549881723310342870016961804255746630219, 2}.
 1483: 
 1484: rsa_oaep() ->
 1485:     %% ftp://ftp.rsa.com/pub/rsalabs/tmp/pkcs1v15crypt-vectors.txt
 1486:     Public = [hexstr2bin("010001"),
 1487: 	      hexstr2bin("a8b3b284af8eb50b387034a860f146c4919f318763cd6c5598c8ae4811a1e0abc4c7e0b082d693a5e7fced675cf4668512772c0cbc64a742c6c630f533c8cc72f62ae833c40bf25842e984bb78bdbf97c0107d55bdb662f5c4e0fab9845cb5148ef7392dd3aaff93ae1e6b667bb3d4247616d4f5ba10d4cfd226de88d39f16fb")],
 1488:     Private = Public ++ [hexstr2bin("53339cfdb79fc8466a655c7316aca85c55fd8f6dd898fdaf119517ef4f52e8fd8e258df93fee180fa0e4ab29693cd83b152a553d4ac4d1812b8b9fa5af0e7f55fe7304df41570926f3311f15c4d65a732c483116ee3d3d2d0af3549ad9bf7cbfb78ad884f84d5beb04724dc7369b31def37d0cf539e9cfcdd3de653729ead5d1"),
 1489: 			 hexstr2bin("d32737e7267ffe1341b2d5c0d150a81b586fb3132bed2f8d5262864a9cb9f30af38be448598d413a172efb802c21acf1c11c520c2f26a471dcad212eac7ca39d"),
 1490: 			 hexstr2bin("cc8853d1d54da630fac004f471f281c7b8982d8224a490edbeb33d3e3d5cc93c4765703d1dd791642f1f116a0dd852be2419b2af72bfe9a030e860b0288b5d77"),
 1491: 			 hexstr2bin("0e12bf1718e9cef5599ba1c3882fe8046a90874eefce8f2ccc20e4f2741fb0a33a3848aec9c9305fbecbd2d76819967d4671acc6431e4037968db37878e695c1"),
 1492: 			 hexstr2bin("95297b0f95a2fa67d00707d609dfd4fc05c89dafc2ef6d6ea55bec771ea333734d9251e79082ecda866efef13c459e1a631386b7e354c899f5f112ca85d71583"),
 1493: 			 hexstr2bin("4f456c502493bdc0ed2ab756a3a6ed4d67352a697d4216e93212b127a63d5411ce6fa98d5dbefd73263e3728142743818166ed7dd63687dd2a8ca1d2f4fbd8e1")],
 1494:     %%Msg = hexstr2bin("6628194e12073db03ba94cda9ef9532397d50dba79b987004afefe34"),
 1495:     Msg =  hexstr2bin("750c4047f547e8e41411856523298ac9bae245efaf1397fbe56f9dd5"),
 1496:     {rsa, Public, Private, Msg, rsa_pkcs1_oaep_padding}.
 1497: 
 1498: no_padding() ->
 1499:     Public = [_, Mod] = rsa_public(),
 1500:     Private = rsa_private(),
 1501:     MsgLen = erlang:byte_size(int_to_bin(Mod)),
 1502:     Msg = list_to_binary(lists:duplicate(MsgLen, $X)),
 1503:     {rsa, Public, Private, Msg, rsa_no_padding}.
 1504: 
 1505: int_to_bin(X) when X < 0 -> int_to_bin_neg(X, []);
 1506: int_to_bin(X) -> int_to_bin_pos(X, []).
 1507: 
 1508: int_to_bin_pos(0,Ds=[_|_]) ->
 1509:     list_to_binary(Ds);
 1510: int_to_bin_pos(X,Ds) ->
 1511:     int_to_bin_pos(X bsr 8, [(X band 255)|Ds]).
 1512: 
 1513: int_to_bin_neg(-1, Ds=[MSB|_]) when MSB >= 16#80 ->
 1514:     list_to_binary(Ds);
 1515: int_to_bin_neg(X,Ds) ->
 1516:     int_to_bin_neg(X bsr 8, [(X band 255)|Ds]).