1%%
2%% %CopyrightBegin%
3%%
4%% Copyright Ericsson AB 2006-2018. All Rights Reserved.
5%%
6%% Licensed under the Apache License, Version 2.0 (the "License");
7%% you may not use this file except in compliance with the License.
8%% You may obtain a copy of the License at
9%%
10%%     http://www.apache.org/licenses/LICENSE-2.0
11%%
12%% Unless required by applicable law or agreed to in writing, software
13%% distributed under the License is distributed on an "AS IS" BASIS,
14%% WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15%% See the License for the specific language governing permissions and
16%% limitations under the License.
17%%
18%% %CopyrightEnd%
19%%
20%% Originally based on Per Gustafsson's test suite.
21%%
22
23-module(bs_bit_binaries_SUITE).
24
25-export([all/0, suite/0,groups/0,init_per_suite/1, end_per_suite/1,
26	 init_per_group/2,end_per_group/2,
27	 misc/1,horrid_match/1,test_bitstr/1,test_bit_size/1,asymmetric_tests/1,
28	 big_asymmetric_tests/1,binary_to_and_from_list/1,
29	 big_binary_to_and_from_list/1,send_and_receive/1,
30	 send_and_receive_alot/1]).
31
32-include_lib("common_test/include/ct.hrl").
33
34suite() -> [{ct_hooks,[ts_install_cth]}].
35
36all() ->
37    [{group,p}].
38
39groups() ->
40    [{p,[parallel],
41      [misc,horrid_match,test_bitstr,test_bit_size,
42       asymmetric_tests,big_asymmetric_tests,
43       binary_to_and_from_list,big_binary_to_and_from_list,
44       send_and_receive,send_and_receive_alot]}].
45
46
47init_per_suite(Config) ->
48    test_lib:recompile(?MODULE),
49    Config.
50
51end_per_suite(_Config) ->
52    ok.
53
54init_per_group(_GroupName, Config) ->
55    Config.
56
57end_per_group(_GroupName, Config) ->
58    Config.
59
60
61misc(Config) when is_list(Config) ->
62    <<1:100>> = <<1:100>>,
63    {ok,ok} = {match(7),match(9)},
64    {ok,ok} = {match1(15),match1(31)},
65    ok.
66
67
68match(N) ->
69  <<0:N>> = <<0:N>>,
70  ok.
71
72match1(N) ->
73  <<42:N/little>> = <<42:N/little>>,
74  ok.
75
76test_bit_size(Config) when is_list(Config) ->
77    101 = erlang:bit_size(<<1:101>>),
78    1001 = erlang:bit_size(<<1:1001>>),
79    1001 = erlang:bit_size(<<-10:1001>>),
80    80 = erlang:bit_size(<<1:80>>),
81    800 = erlang:bit_size(<<1:800>>),
82    Bin = <<0:16#1000000>>,
83    BigBin = list_to_bitstring([Bin||_ <- lists:seq(1,16#10)]++[<<1:1>>]),
84    16#10000001 = erlang:bit_size(BigBin),
85    %% Only run these on computers with lots of memory
86    %% HugeBin = list_to_bitstring([BigBin||_ <- lists:seq(1,16#10)]++[<<1:1>>]),
87    %% 16#100000011 = erlang:bit_size(HugeBin),
88    0 = erlang:bit_size(<<>>),
89    ok.
90
91horrid_match(Config) when is_list(Config) ->
92    <<1:4,B:24/bitstring>> = <<1:4,42:24/little>>,
93    <<42:24/little>> = B,
94    ok.
95
96test_bitstr(Config) when is_list(Config) ->
97    <<1:7,B/bitstring>> = <<1:7,<<1:1,6>>/bitstring>>,
98    <<1:1,6>> = B,
99    B = <<1:1,6>>,
100  ok.
101
102asymmetric_tests(Config) when is_list(Config) ->
103    <<1:12>> = <<0,1:4>>,
104    <<0,1:4>> = <<1:12>>,
105    <<1:1,X/bitstring>> = <<128,255,0,0:2>>,
106    <<1,254,0,0:1>> = X,
107    X = <<1,254,0,0:1>>,
108    <<1:1,X1:25/bitstring>> = <<128,255,0,0:2>>,
109    <<1,254,0,0:1>> = X1,
110    X1 = <<1,254,0,0:1>>,
111    ok.
112
113big_asymmetric_tests(Config) when is_list(Config) ->
114    <<1:875,1:12>> = <<1:875,0,1:4>>,
115    <<1:875,0,1:4>> = <<1:875,1:12>>,
116    <<1:1,X/bitstring>> = <<128,255,0,0:2,1:875>>,
117    <<1,254,0,0:1,1:875>> = X,
118    X = <<1,254,0,0:1,1:875>>,
119    <<1:1,X1:900/bitstring>> = <<128,255,0,0:2,1:875>>,
120    <<1,254,0,0:1,1:875>> = X1,
121    X1 = <<1,254,0,0:1,1:875>>,
122  ok.
123
124binary_to_and_from_list(Config) when is_list(Config) ->
125    <<1,2,3,4,1:1>> = list_to_bitstring(bitstring_to_list(<<1,2,3,4,1:1>>)),
126    [1,2,3,4,<<1:1>>] = bitstring_to_list(<<1,2,3,4,1:1>>),
127    <<1:1,1,2,3,4>> = list_to_bitstring([<<1:1>>,1,2,3,4]),
128    [128,129,1,130,<<0:1>>] = bitstring_to_list(<<1:1,1,2,3,4>>),
129    ok.
130
131big_binary_to_and_from_list(Config) when is_list(Config) ->
132    <<1:800,2,3,4,1:1>> =
133	list_to_bitstring(bitstring_to_list(<<1:800,2,3,4,1:1>>)),
134    [1,2,3,4|_Rest1] = bitstring_to_list(<<1,2,3,4,1:800,1:1>>),
135    <<1:801,1,2,3,4>> = list_to_bitstring([<<1:801>>,1,2,3,4]),
136    ok.
137
138send_and_receive(Config) when is_list(Config) ->
139    Bin = <<1,2:7>>,
140    Pid = spawn_link(fun() -> receiver(Bin) end),
141    Pid ! {self(),<<1:7,8:5,Bin/bitstring>>},
142    receive
143	ok ->
144	    ok
145    end.
146
147receiver(Bin) ->
148    receive
149	{Pid,<<1:7,8:5,Bin/bitstring>>} ->
150	    Pid ! ok
151  end.
152
153send_and_receive_alot(Config) when is_list(Config) ->
154    Bin = <<1:1000001>>,
155    Pid = spawn_link(fun() -> receiver_alot(Bin) end),
156    spamalot(100,Bin,Pid).
157
158spamalot(N,Bin,Pid) when N > 0 ->
159    Pid ! {self(),<<1:7,8:5,Bin/bitstring>>},
160    receive
161	ok ->
162	    ok
163    end,
164    spamalot(N-1,Bin,Pid);
165spamalot(0,_Bin,Pid) ->
166    Pid ! no_more,
167    ok.
168
169receiver_alot(Bin) ->
170    receive
171	{Pid,<<1:7,8:5,Bin/bitstring>>} ->
172	    Pid ! ok;
173	no_more -> ok
174    end,
175    receiver_alot(Bin).
176
177
178
179