diff --git a/lib/compiler/src/v3_core.erl b/lib/compiler/src/v3_core.erl index 727029f9c5d0..74c81e339e3a 100644 --- a/lib/compiler/src/v3_core.erl +++ b/lib/compiler/src/v3_core.erl @@ -1965,6 +1965,7 @@ preprocess_quals(Line, [{zip,Anno,Gens}|Qs], St, Acc) -> acc_guard=AccGuard}, Zip1 = preprocess_zip_generators(Gens1, Zip0), Zip2 = Zip1#izip{skip_pats=preprocess_skip(Zip1#izip.nomatch_total,Zip1#izip.nomatch_pats,Zip1#izip.acc_pats), + tail_pats=preprocess_tail(Zip1#izip.nomatch_total,Zip1#izip.nomatch_pats,Zip1#izip.tail_pats,[]), nomatch_total=get_nomatch_total(Zip1#izip.nomatch_total)}, preprocess_quals(Line, Qs, St1, [Zip2|Acc]); preprocess_quals(Line, [Q|Qs0], St0, Acc) -> @@ -2035,6 +2036,15 @@ preprocess_skip(NomatchModes, NomatchPats, AccPats) -> end || {NomatchMode, NomatchPat, AccPat} <:- lists:zip3(NomatchModes, NomatchPats, AccPats)]. +preprocess_tail([skip|NomatchModes], [_|NomatchPats], [TailPat|TailPats], Acc) -> + preprocess_tail(NomatchModes, NomatchPats, TailPats, [TailPat|Acc]); +preprocess_tail([_|NomatchModes], [_|NomatchPats], [#ibinary{}=A|TailPats], Acc) -> + preprocess_tail(NomatchModes, NomatchPats, TailPats, [A#ibinary{segments=[]}|Acc]); +preprocess_tail([_|NomatchModes], [_|NomatchPats], [TailPat|TailPats], Acc) -> + preprocess_tail(NomatchModes, NomatchPats, TailPats, [TailPat|Acc]); +preprocess_tail([], [], [], Acc) -> + reverse(Acc). + is_generator({generate,_,_,_}) -> true; is_generator({generate_strict,_,_,_}) -> true; is_generator({b_generate,_,_,_}) -> true; diff --git a/lib/compiler/test/zlc_SUITE.erl b/lib/compiler/test/zlc_SUITE.erl index 63efbba7a560..7fbb9f9b34cd 100644 --- a/lib/compiler/test/zlc_SUITE.erl +++ b/lib/compiler/test/zlc_SUITE.erl @@ -249,6 +249,14 @@ strict_list(Config) when is_list(Config) -> {'EXIT',{{bad_generators,{[a],[],<<>>}},_}} = catch strict_list_strict_2([a], [], <<>>), + [] = strict_list_strict_3([], <<>>), + [45] = strict_list_strict_3([{i,42}], <<3>>), + {'EXIT',{{bad_generators,{[],<<0:7>>}},_}} = catch strict_list_strict_3([], <<0:7>>), + [] = strict_list_strict_4([], <<>>), + [100] = strict_list_strict_4([{i,100}], <<42>>), + {'EXIT',{{bad_generators,{[{i,100}],<<0>>}},_}} = catch strict_list_strict_4([{i,100}], <<0>>), + {'EXIT',{{bad_generators,{[{i,100}],<<>>}},_}} = catch strict_list_strict_4([{i,100}], <<>>), + ok. strict_list_mixed_1(X, Y) -> @@ -264,13 +272,27 @@ strict_list_strict_1(X, Y) -> strict_list_strict_2(X, Y, Z) -> [A * B + C || {i,A} <:- X && {i,B} <:- Y && <> <:= Z]. +strict_list_strict_3(List, Bin) -> + [A + B || {i,A} <:- List && <> <:= Bin]. + +strict_list_strict_4(List, Bin) -> + [A || {i,A} <:- List && <<42:8>> <:= Bin]. + strict_binary(Config) when is_list(Config) -> <<2,4,6>> = << <<(X+Y)>> || X <:- [1,2,3] && <> <= <<1,2,3>>>>, <<2,4>> = << <<(X+Y)>> || <> <:= <<1,2,3>> && {X, Y} <- [{1,1},{2,2},{2,3}]>>, <<2,24>> = << <<(X*Y*Z)>> || X := Y <:- #{1 => 2, 3 => 4} && <> <:= <<1,2>> >>, + <<>> = strict_binary_1(#{}, <<>>), + <<24:64>> = strict_binary_1(#{2 => {val,3}}, <<4:8>>), + {'EXIT',{{bad_generators,{none,<<42:8>>}},_}} = catch strict_binary_1(#{}, <<42:8>>), + {'EXIT',{{bad_generators,{none,<<42:7>>}},_}} = catch strict_binary_1(#{}, <<42:7>>), + {'EXIT',{{bad_generators,{none,<<0:4>>}},_}} = catch strict_binary_1(#{2 => {val,3}}, <<0,0:4>>), ok. +strict_binary_1(Map, Bin) -> + << <<(X*Y*Z):64>> || X := {val,Y} <:- Map && <> <:= Bin >>. + nomatch(Config) when is_list(Config) -> [] = do_nomatch_1([], []), [] = do_nomatch_1([1], [a]), diff --git a/lib/debugger/test/zlc_SUITE.erl b/lib/debugger/test/zlc_SUITE.erl index a34b7ad6e6d2..651102115db7 100644 --- a/lib/debugger/test/zlc_SUITE.erl +++ b/lib/debugger/test/zlc_SUITE.erl @@ -246,6 +246,14 @@ strict_list(Config) when is_list(Config) -> {'EXIT',{{bad_generators,{[a],[],<<>>}},_}} = catch strict_list_strict_2([a], [], <<>>), + [] = strict_list_strict_3([], <<>>), + [45] = strict_list_strict_3([{i,42}], <<3>>), + {'EXIT',{{bad_generators,{[],<<0:7>>}},_}} = catch strict_list_strict_3([], <<0:7>>), + [] = strict_list_strict_4([], <<>>), + [100] = strict_list_strict_4([{i,100}], <<42>>), + {'EXIT',{{bad_generators,{[{i,100}],<<0>>}},_}} = catch strict_list_strict_4([{i,100}], <<0>>), + {'EXIT',{{bad_generators,{[{i,100}],<<>>}},_}} = catch strict_list_strict_4([{i,100}], <<>>), + ok. strict_list_mixed_1(X, Y) -> @@ -261,13 +269,27 @@ strict_list_strict_1(X, Y) -> strict_list_strict_2(X, Y, Z) -> [A * B + C || {i,A} <:- X && {i,B} <:- Y && <> <:= Z]. +strict_list_strict_3(List, Bin) -> + [A + B || {i,A} <:- List && <> <:= Bin]. + +strict_list_strict_4(List, Bin) -> + [A || {i,A} <:- List && <<42:8>> <:= Bin]. + strict_binary(Config) when is_list(Config) -> <<2,4,6>> = << <<(X+Y)>> || X <:- [1,2,3] && <> <= <<1,2,3>>>>, <<2,4>> = << <<(X+Y)>> || <> <:= <<1,2,3>> && {X, Y} <- [{1,1},{2,2},{2,3}]>>, <<2,24>> = << <<(X*Y*Z)>> || X := Y <:- #{1 => 2, 3 => 4} && <> <:= <<1,2>> >>, + <<>> = strict_binary_1(#{}, <<>>), + <<24:64>> = strict_binary_1(#{2 => {val,3}}, <<4:8>>), + {'EXIT',{{bad_generators,{none,<<42:8>>}},_}} = catch strict_binary_1(#{}, <<42:8>>), + {'EXIT',{{bad_generators,{none,<<42:7>>}},_}} = catch strict_binary_1(#{}, <<42:7>>), + {'EXIT',{{bad_generators,{none,<<0:4>>}},_}} = catch strict_binary_1(#{2 => {val,3}}, <<0,0:4>>), ok. +strict_binary_1(Map, Bin) -> + << <<(X*Y*Z):64>> || X := {val,Y} <:- Map && <> <:= Bin >>. + nomatch(Config) when is_list(Config) -> [] = do_nomatch_1([], []), [] = do_nomatch_1([1], [a]), diff --git a/lib/stdlib/src/erl_error.erl b/lib/stdlib/src/erl_error.erl index a864ec924ced..c5ae309ce12d 100644 --- a/lib/stdlib/src/erl_error.erl +++ b/lib/stdlib/src/erl_error.erl @@ -353,9 +353,6 @@ explain_reason({badfun,Term}, error=Cl, [], PF, S, _Enc, CL) -> explain_reason({badmatch,Term}, error=Cl, [], PF, S, _Enc, CL) -> Str = <<"no match of right hand side value ">>, format_value(Term, Str, Cl, PF, S, CL); -explain_reason({badmatches,Terms}, error=Cl, [], PF, S, _Enc, CL) -> - Str = <<"no match of right hand side values ">>, - format_value(Terms, Str, Cl, PF, S, CL); explain_reason({case_clause,V}, error=Cl, [], PF, S, _Enc, CL) -> %% "there is no case clause with a true guard sequence and a %% pattern matching..."