1: %%
    2: %% %CopyrightBegin%
    3: %% 
    4: %% Copyright Ericsson AB 2002-2011. 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(evil_SUITE).
   20: 
   21: -export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1, 
   22: 	 init_per_group/2,end_per_group/2,
   23: 	 init_per_testcase/2,end_per_testcase/2,
   24: 	 heap_frag/1,
   25: 	 encode_decode_ext/1,
   26: 	 decode_integer_ext/1,
   27: 	 decode_small_big_ext/1,
   28: 	 decode_large_big_ext/1,
   29: 	 decode_small_big_ext_neg/1,
   30: 	 decode_large_big_ext_neg/1,
   31: 	 decode_too_small/1,
   32: 	 decode_pos_neg_zero/1
   33: 	]).
   34: 
   35: -include_lib("test_server/include/test_server.hrl").
   36: 
   37: suite() -> [{ct_hooks,[ts_install_cth]}].
   38: 
   39: all() -> 
   40:     [heap_frag, encode_decode_ext, decode_integer_ext,
   41:      decode_small_big_ext, decode_large_big_ext,
   42:      decode_small_big_ext_neg, decode_large_big_ext_neg,
   43:      decode_too_small, decode_pos_neg_zero].
   44: 
   45: groups() -> 
   46:     [].
   47: 
   48: init_per_suite(Config) ->
   49:     Config.
   50: 
   51: end_per_suite(_Config) ->
   52:     ok.
   53: 
   54: init_per_group(_GroupName, Config) ->
   55:     Config.
   56: 
   57: end_per_group(_GroupName, Config) ->
   58:     Config.
   59: 
   60: 
   61: init_per_testcase(_Case, Config) ->
   62:     ?line Dog = test_server:timetrap(?t:minutes(0.5)),
   63:     [{watchdog, Dog}|Config].
   64: 
   65: end_per_testcase(_Case, Config) ->
   66:     Dog=?config(watchdog, Config),
   67:     test_server:timetrap_cancel(Dog),
   68:     ok.
   69: 
   70: heap_frag(Config) when is_list(Config) ->
   71:     N = 512,
   72:     Self = self(),
   73:     ?line Pid = spawn_link(fun() -> appender(Self, N) end),
   74:     receive
   75: 	{Pid,Res} ->
   76: 	    ?line Res = my_appender(N);
   77: 	Garbage ->
   78: 	    io:format("Garbage: ~p\n", [Garbage]),
   79: 	    ?line ?t:fail(got_garbage)
   80:     end.
   81: 
   82: 
   83: %% ######################################################################## %%
   84: 
   85: %% "Interesting" integers taken from erl_interface ei_decode_SUITE.erl
   86: %% These test cases are not "evil" but the next test case is....
   87: 
   88: encode_decode_ext(Config) when is_list(Config) ->
   89:     ?line enc_dec( 2,   0),               % SMALL_INTEGER_EXT smallest
   90:     ?line enc_dec( 2, 255),           	  % SMALL_INTEGER_EXT largest
   91:     ?line enc_dec( 5, 256),           	  % INTEGER_EXT smallest pos (*)
   92:     ?line enc_dec( 5,  -1),            	  % INTEGER_EXT largest  neg
   93: 
   94:     ?line enc_dec( 5, 16#07ffffff),  	  % INTEGER_EXT largest (28 bits)
   95:     ?line enc_dec( 5,-16#08000000),  	  % INTEGER_EXT smallest
   96:     ?line enc_dec( 7, 16#08000000),  	  % SMALL_BIG_EXT smallest pos(*)
   97:     ?line enc_dec( 7,-16#08000001),  	  % SMALL_BIG_EXT largest neg (*)
   98: 
   99:     ?line enc_dec( 7, 16#7fffffff),  	  % SMALL_BIG_EXT largest  i32
  100:     ?line enc_dec( 7,-16#80000000),  	  % SMALL_BIG_EXT smallest i32
  101: 
  102:     ?line enc_dec( 7, 16#80000000),  	  % SMALL_BIG_EXT u32
  103:     ?line enc_dec( 7, 16#ffffffff),  	  % SMALL_BIG_EXT largest u32
  104: 
  105:     ?line enc_dec( 9, 16#7fffffffffff),     % largest  i48
  106:     ?line enc_dec( 9,-16#800000000000),     % smallest i48
  107:     ?line enc_dec( 9, 16#ffffffffffff),     % largest  u48
  108:     ?line enc_dec(11, 16#7fffffffffffffff), % largest  i64
  109:     ?line enc_dec(11,-16#8000000000000000), % smallest i64
  110:     ?line enc_dec(11, 16#ffffffffffffffff), % largest  u64
  111: 
  112:     ok.
  113: 
  114: 
  115: %% ######################################################################## %%
  116: 
  117: %% "Interesting" integers taken from erl_interface ei_decode_SUITE.erl
  118: %% These test the decoding "unusual", i.e. integers packed according
  119: %% to "erts/emulator/internal_doc/erl_ext_dist.txt" but not the way
  120: %% the emulator or erl_interface encode them.
  121: %%
  122: %% NOTE!!!! The comments below after a decode line is how it currently
  123: %% is encoded in the external format by the emulator and
  124: %% erl_interface, i.e. not how it is encoded in the test case below.
  125: 
  126: decode_integer_ext(Config) when is_list(Config) ->
  127:     ?line decode(  0, <<131,98,  0:32>>),	% SMALL_INTEGER_EXT
  128:     ?line decode( 42, <<131,98, 42:32>>),	% SMALL_INTEGER_EXT
  129:     ?line decode(255, <<131,98,255:32>>),	% SMALL_INTEGER_EXT
  130:     ?line decode( 16#08000000, <<131,98, 16#08000000:32>>), % SMALL_BIG_EXT
  131:     ?line decode(-16#08000001, <<131,98,-16#08000001:32>>), % SMALL_BIG_EXT
  132:     ?line decode( 16#7fffffff, <<131,98, 16#7fffffff:32>>), % SMALL_BIG_EXT
  133:     ?line decode(-16#80000000, <<131,98,-16#80000000:32>>), % SMALL_BIG_EXT
  134:     ok.
  135: 
  136: decode_small_big_ext(Config) when is_list(Config) ->
  137:     ?line decode(256,<<131,110,2,0,0,1>>),	% INTEGER_EXT
  138:     ?line decode(16#07ffffff,<<131,110,4,0,255,255,255,7>>), % INTEGER_EXT
  139:     ?line decode(16#7fffffff,<<131,110,4,0,255,255,255,127>>), % SMALL_BIG_EXT
  140: 
  141:     ?line decode(42,<<131,110,1,0,42>>),	% SMALL_INTEGER_EXT
  142:     ?line decode(42,<<131,110,2,0,42,0>>),	% Redundant zeros from now on
  143:     ?line decode(42,<<131,110,3,0,42,0,0>>),
  144:     ?line decode(42,<<131,110,4,0,42,0,0,0>>),
  145:     ?line decode(42,<<131,110,5,0,42,0,0,0,0>>),
  146:     ?line decode(42,<<131,110,6,0,42,0,0,0,0,0>>),
  147:     ?line decode(42,<<131,110,7,0,42,0,0,0,0,0,0>>),
  148:     ?line decode(42,<<131,110,8,0,42,0,0,0,0,0,0,0>>),
  149:     ok.
  150: 
  151: decode_large_big_ext(Config) when is_list(Config) ->
  152:     ?line decode(256,<<131,111,2:32,0,0,1>>), % INTEGER_EXT
  153:     ?line decode(16#07ffffff,<<131,111,4:32,0,255,255,255,7>>), % INTEG_EXT
  154:     ?line decode(16#7fffffff,<<131,111,4:32,0,255,255,255,127>>), % SMA_BIG
  155:     ?line decode(16#ffffffff,<<131,111,4:32,0,255,255,255,255>>), % SMA_BIG
  156: 
  157:     N = largest_small_big(),
  158:     ?line decode(N,<<131,111,255:32,0,N:2040/little>>), % SMALL_BIG_EXT
  159: 
  160:     ?line decode(42,<<131,111,1:32,0,42>>),
  161:     ?line decode(42,<<131,111,2:32,0,42,0>>), % Redundant zeros from now on
  162:     ?line decode(42,<<131,111,3:32,0,42,0,0>>),
  163:     ?line decode(42,<<131,111,4:32,0,42,0,0,0>>),
  164:     ?line decode(42,<<131,111,5:32,0,42,0,0,0,0>>),
  165:     ?line decode(42,<<131,111,6:32,0,42,0,0,0,0,0>>),
  166:     ?line decode(42,<<131,111,7:32,0,42,0,0,0,0,0,0>>),
  167:     ?line decode(42,<<131,111,8:32,0,42,0,0,0,0,0,0,0>>),
  168:     ok.
  169: 
  170: decode_small_big_ext_neg(Config) when is_list(Config) ->
  171:     ?line decode(-1,<<131,110,1,1,1>>),		% INTEGER_EXT
  172:     ?line decode(-16#08000000,<<131,110,4,1,0,0,0,8>>), % INTEGER_EXT
  173:     ?line decode(-16#80000000,<<131,110,4,1,0,0,0,128>>), % SMALL_BIG_EXT
  174:     ?line decode(-16#ffffffff,<<131,110,4,1,255,255,255,255>>), % SMALL_BIG_EXT
  175: 
  176:     N = largest_small_big(),
  177:     ?line decode(-N,<<131,111,255:32,1,N:2040/little>>), % SMALL_BIG_EXT
  178: 
  179:     ?line decode(-42,<<131,110,1,1,42>>),
  180:     ?line decode(-42,<<131,110,2,1,42,0>>),	% Redundant zeros from now on
  181:     ?line decode(-42,<<131,110,3,1,42,0,0>>),
  182:     ?line decode(-42,<<131,110,4,1,42,0,0,0>>),
  183:     ?line decode(-42,<<131,110,5,1,42,0,0,0,0>>),
  184:     ?line decode(-42,<<131,110,6,1,42,0,0,0,0,0>>),
  185:     ?line decode(-42,<<131,110,7,1,42,0,0,0,0,0,0>>),
  186:     ?line decode(-42,<<131,110,8,1,42,0,0,0,0,0,0,0>>),
  187:     ok.
  188: 
  189: decode_large_big_ext_neg(Config) when is_list(Config) ->
  190:     ?line decode(-1,<<131,111,1:32,1,1>>),	% INTEGER_EXT
  191:     ?line decode(-16#08000000,<<131,111,4:32,1,0,0,0,8>>), % INTEGER_EXT
  192:     ?line decode(-16#80000000,<<131,111,4:32,1,0,0,0,128>>), % SMALL_BIG_EXT
  193: 
  194:     ?line decode(-42,<<131,111,1:32,1,42>>),
  195:     ?line decode(-42,<<131,111,2:32,1,42,0>>), % Redundant zeros from now on
  196:     ?line decode(-42,<<131,111,3:32,1,42,0,0>>),
  197:     ?line decode(-42,<<131,111,4:32,1,42,0,0,0>>),
  198:     ?line decode(-42,<<131,111,5:32,1,42,0,0,0,0>>),
  199:     ?line decode(-42,<<131,111,6:32,1,42,0,0,0,0,0>>),
  200:     ?line decode(-42,<<131,111,7:32,1,42,0,0,0,0,0,0>>),
  201:     ?line decode(-42,<<131,111,8:32,1,42,0,0,0,0,0,0,0>>),
  202:     ok.
  203: 
  204: decode_pos_neg_zero(Config) when is_list(Config) ->
  205:     ?line decode( 0, <<131,110,0,0>>),		% SMALL_BIG_EXT (positive zero)
  206:     ?line decode( 0, <<131,110,1,0,0>>),	% SMALL_BIG_EXT (positive zero)
  207:     ?line decode( 0, <<131,110,0,1>>),		% SMALL_BIG_EXT (negative zero)
  208:     ?line decode( 0, <<131,110,1,1,0>>),	% SMALL_BIG_EXT (negative zero)
  209: 
  210:     ?line decode( 0, <<131,111,0:32,0>>),	% SMALL_BIG_EXT (positive zero)
  211:     ?line decode( 0, <<131,111,1:32,0,0>>),	% SMALL_BIG_EXT (positive zero)
  212:     ?line decode( 0, <<131,111,0:32,1>>),	% SMALL_BIG_EXT (negative zero)
  213:     ?line decode( 0, <<131,111,1:32,1,0>>),	% SMALL_BIG_EXT (negative zero)
  214: 
  215:     N = largest_small_big(),
  216:     ?line decode( N,<<131,110,255,0,N:2040/little>>), % largest SMALL_BIG_EXT
  217:     ?line decode(-N,<<131,110,255,1,N:2040/little>>), % largest SMALL_BIG_EXT
  218: 
  219:     ok.
  220: 
  221: %% Test to decode uncompleted encodings for all in "erl_ext_dist.txt"
  222: 
  223: decode_too_small(Config) when is_list(Config) ->
  224:     ?line decode_badarg(<<131, 97>>),
  225:     ?line decode_badarg(<<131, 98>>),
  226:     ?line decode_badarg(<<131, 98, 0>>),
  227:     ?line decode_badarg(<<131, 98, 0, 0>>),
  228:     ?line decode_badarg(<<131, 98, 0, 0, 0>>),
  229:     ?line decode_badarg(<<131, 99>>),
  230:     ?line decode_badarg(<<131, 99, 0>>),
  231:     ?line decode_badarg(<<131, 99, 0:240>>),
  232: 
  233:     ?line decode_badarg(<<131,100>>),
  234:     ?line decode_badarg(<<131,100, 1:16/big>>),
  235:     ?line decode_badarg(<<131,100, 2:16/big>>),
  236:     ?line decode_badarg(<<131,100, 2:16/big, "A">>),
  237: 
  238:     % FIXME node name "A" seem ok, should it be?
  239: %    ?line decode_badarg(<<131,101,100,1:16/big,"A",42:32/big,0>>),
  240: 
  241:     ?line decode_badarg(<<131,101>>),
  242:     ?line decode_badarg(<<131,101,106>>),
  243:     ?line decode_badarg(<<131,101,255>>),
  244:     ?line decode_badarg(<<131,101,106,42:8/big>>),
  245:     ?line decode_badarg(<<131,101,106,42:16/big>>),
  246:     ?line decode_badarg(<<131,101,255,42:24/big>>),
  247:     ?line decode_badarg(<<131,101,255,42:32/big,0>>),
  248:     ?line decode_badarg(<<131,101,100,1:16/big,"A">>),
  249:     ?line decode_badarg(<<131,101,100,1:16/big,"A",42:32/big>>),
  250: 
  251:     ?line decode_badarg(<<131,102>>),
  252:     ?line decode_badarg(<<131,102,106,42:32/big,0>>),
  253:     ?line decode_badarg(<<131,102,255,42:32/big,0>>),
  254:     ?line decode_badarg(<<131,102,100,1:16/big,"A">>),
  255:     ?line decode_badarg(<<131,102,100,1:16/big,"A",42:32/big>>),
  256: 
  257:     ?line decode_badarg(<<131,103>>),
  258:     ?line decode_badarg(<<131,103,106,42:32/big,0>>),
  259:     ?line decode_badarg(<<131,103,255,42:32/big,0>>),
  260:     ?line decode_badarg(<<131,103,100,1:16/big,"A">>),
  261:     ?line decode_badarg(<<131,103,100,1:16/big,"A",42:32/big>>),
  262:     ?line decode_badarg(<<131,103,100,1:16/big,"A",4:32/big,2:32/big>>),
  263: 
  264:     ?line decode_badarg(<<131,104>>),
  265:     ?line decode_badarg(<<131,104, 1>>),
  266:     ?line decode_badarg(<<131,104, 2, 106>>),
  267:     ?line decode_badarg(<<131,105, 1:32/big>>),
  268:     ?line decode_badarg(<<131,105, 2:32/big, 106>>),
  269: 
  270:     ?line decode_badarg(<<131,107>>),
  271:     ?line decode_badarg(<<131,107, 1:16/big>>),
  272:     ?line decode_badarg(<<131,107, 2:16/big>>),
  273:     ?line decode_badarg(<<131,107, 2:16/big, "A">>),
  274: 
  275:     ?line decode_badarg(<<131,108>>),
  276:     ?line decode_badarg(<<131,108, 1:32/big>>),
  277:     ?line decode_badarg(<<131,108, 2:32/big>>),
  278:     ?line decode_badarg(<<131,108, 2:32/big, 106>>), % FIXME don't use NIL
  279: 
  280:     ?line decode_badarg(<<131,109>>),
  281:     ?line decode_badarg(<<131,109, 1:32/big>>),
  282:     ?line decode_badarg(<<131,109, 2:32/big>>),
  283:     ?line decode_badarg(<<131,109, 2:32/big, 42>>),
  284: 
  285:     N = largest_small_big(),
  286: 
  287:     ?line decode_badarg(<<131,110>>),
  288:     ?line decode_badarg(<<131,110,1>>),
  289:     ?line decode_badarg(<<131,110,1,0>>),
  290:     ?line decode_badarg(<<131,110,1,1>>),
  291:     ?line decode_badarg(<<131,110,2,0,42>>),
  292:     ?line decode_badarg(<<131,110,2,1,42>>),
  293:     ?line decode_badarg(<<131,110,255,0,N:2032/little>>),
  294:     ?line decode_badarg(<<131,110,255,1,N:2032/little>>),
  295: 
  296:     ?line decode_badarg(<<131,111>>),
  297:     ?line decode_badarg(<<131,111,  1:32/big>>),
  298:     ?line decode_badarg(<<131,111,  1:32/big,0>>),
  299:     ?line decode_badarg(<<131,111,  1:32/big,1>>),
  300:     ?line decode_badarg(<<131,111,  2:32/big,0,42>>),
  301:     ?line decode_badarg(<<131,111,  2:32/big,1,42>>),
  302:     ?line decode_badarg(<<131,111,256:32/big,0,N:2032/little>>),
  303:     ?line decode_badarg(<<131,111,256:32/big,1,N:2032/little>>),
  304:     ?line decode_badarg(<<131,111,256:32/big,0,N:2040/little>>),
  305:     ?line decode_badarg(<<131,111,256:32/big,1,N:2040/little>>),
  306:     ?line decode_badarg(<<131,111,257:32/big,0,N:2048/little>>),
  307:     ?line decode_badarg(<<131,111,257:32/big,1,N:2048/little>>),
  308: 
  309:     % Emulator dies if trying to create large bignum....
  310: %    ?line decode_badarg(<<131,111,16#ffffffff:32/big,0>>),
  311: %    ?line decode_badarg(<<131,111,16#ffffffff:32/big,1>>),
  312: 
  313:     ?line decode_badarg(<<131, 78>>),
  314:     ?line decode_badarg(<<131, 78, 42>>),
  315:     ?line decode_badarg(<<131, 78, 42, 1>>),
  316:     ?line decode_badarg(<<131, 78, 42, 1:16/big>>),
  317:     ?line decode_badarg(<<131, 78, 42, 2:16/big>>),
  318:     ?line decode_badarg(<<131, 78, 42, 2:16/big, "A">>),
  319: 
  320:     ?line decode_badarg(<<131, 67>>),
  321: 
  322:     ?line decode_badarg(<<131,114>>),
  323:     ?line decode_badarg(<<131,114,0>>),
  324:     ?line decode_badarg(<<131,114,1:16/big>>),
  325:     ?line decode_badarg(<<131,114,1:16/big,100>>),
  326:     ?line decode_badarg(<<131,114,1:16/big,100,1:16/big>>),
  327:     ?line decode_badarg(<<131,114,1:16/big,100,1:16/big,"A">>),
  328:     ?line decode_badarg(<<131,114,1:16/big,100,1:16/big,"A",0>>),
  329:     ?line decode_badarg(<<131,114,1:16/big,100,1:16/big,"A",0,42:8>>),
  330:     ?line decode_badarg(<<131,114,1:16/big,100,1:16/big,"A",0,42:16>>),
  331:     ?line decode_badarg(<<131,114,1:16/big,100,1:16/big,"A",0,42:24>>),
  332: 
  333:     ?line decode_badarg(<<131,117>>),		% FIXME needs more tests
  334: 
  335:     ok.
  336: 
  337: %% ######################################################################## %%
  338: 
  339: decode_badarg(Bin) ->
  340:     io:format("Trying ~w\n",[Bin]),
  341:     {'EXIT',{badarg,_}} = (catch binary_to_term(Bin)).
  342: 
  343: enc_dec(_Size, Term) ->
  344:     Bin = term_to_binary(Term),
  345:     Term = binary_to_term(Bin),
  346:     ok.
  347: 
  348: decode(Term, Binary) ->
  349:     io:format("Encoding ~w to ~w ... ",[Binary,Term]),
  350:     NewTerm = binary_to_term(Binary),
  351:     io:format("got ~w\n",[NewTerm]),
  352:     Term = NewTerm.
  353: 
  354: largest_small_big() ->
  355:     List  = lists:duplicate(255,255),
  356:     Limbs = list_to_binary(List),
  357:     binary_to_term(<<131,110,255,0,Limbs/binary>>).
  358: 
  359: %% ######################################################################## %%
  360: 
  361: appender(Parent, N) ->
  362:     seed(),
  363:     Res = appender_1(N, {}),
  364:     Parent ! {self(),Res}.
  365: 
  366: appender_1(0, T) -> T;
  367: appender_1(N, T0) ->
  368:     U = rnd_term(),
  369:     T = erlang:append_element(T0, U),
  370:     appender_1(N-1, T).
  371: 
  372: my_appender(N) ->
  373:     seed(),
  374:     my_appender_1(N, []).
  375: 
  376: my_appender_1(0, T) ->
  377:     list_to_tuple(lists:reverse(T));
  378: my_appender_1(N, T0) ->
  379:     U = rnd_term(),
  380:     T = [U|T0],
  381:     my_appender_1(N-1, T).
  382:     
  383: seed() ->
  384:     random:seed(3172, 9815, 20129).
  385: 
  386: rnd_term() ->
  387:     U0 = random:uniform(),
  388:     B = <<U0/float>>,
  389:     {U0,U0 * 2.5 + 3.14,[U0*2.3,B]}.
  390: