Skip to content

Commit

Permalink
Merge branch 'bjorn/bs-zero-width-bug/OTP-8997' into dev
Browse files Browse the repository at this point in the history
* bjorn/bs-zero-width-bug/OTP-8997:
  Fix type-checking of variable used in zero-width bit syntax construction
  • Loading branch information
bjorng committed Dec 21, 2010
2 parents f026b83 + b36c9d1 commit 2d69a4f
Show file tree
Hide file tree
Showing 3 changed files with 39 additions and 12 deletions.
14 changes: 8 additions & 6 deletions erts/emulator/beam/erl_bits.c
Expand Up @@ -555,10 +555,11 @@ fmt_int(byte *buf, Uint sz, Eterm val, Uint size, Uint flags)
{
unsigned long offs;

ASSERT(size != 0);
offs = BIT_OFFSET(size);
if (is_small(val)) {
Sint v = signed_val(val);

ASSERT(size != 0); /* Tested by caller */
if (flags & BSF_LITTLE) { /* Little endian */
sz--;
COPY_VAL(buf,1,v,sz);
Expand All @@ -578,6 +579,9 @@ fmt_int(byte *buf, Uint sz, Eterm val, Uint size, Uint flags)
ErtsDigit* dp = big_v(val);
int n = MIN(sz,ds);

if (size == 0) {
return 0;
}
if (flags & BSF_LITTLE) {
sz -= n; /* pad with this amount */
if (sign) {
Expand Down Expand Up @@ -729,15 +733,13 @@ erts_new_bs_put_integer(ERL_BITS_PROTO_3(Eterm arg, Uint num_bits, unsigned flag
Uint b;
byte *iptr;

if (num_bits == 0) {
return 1;
}

bit_offset = BIT_OFFSET(bin_offset);
if (is_small(arg)) {
Uint rbits = 8 - bit_offset;

if (bit_offset + num_bits <= 8) {
if (num_bits == 0) {
return 1;
} else if (bit_offset + num_bits <= 8) {
/*
* All bits are in the same byte.
*/
Expand Down
21 changes: 18 additions & 3 deletions erts/emulator/test/bs_construct_SUITE.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
%% Copyright Ericsson AB 1999-2009. All Rights Reserved.
%% Copyright Ericsson AB 1999-2010. All Rights Reserved.
%%
%% The contents of this file are subject to the Erlang Public License,
%% Version 1.1, (the "License"); you may not use this file except in
Expand All @@ -27,7 +27,7 @@
mem_leak/1, coerce_to_float/1, bjorn/1,
huge_float_field/1, huge_binary/1, system_limit/1, badarg/1,
copy_writable_binary/1, kostis/1, dynamic/1, bs_add/1,
otp_7422/1]).
otp_7422/1, zero_width/1]).

-include("test_server.hrl").

Expand All @@ -36,7 +36,7 @@ all(suite) ->
not_used, in_guard, mem_leak, coerce_to_float, bjorn,
huge_float_field, huge_binary, system_limit, badarg,
copy_writable_binary, kostis, dynamic, bs_add,
otp_7422].
otp_7422, zero_width].

big(1) ->
57285702734876389752897683.
Expand Down Expand Up @@ -786,5 +786,20 @@ otp_7422_bin(N) when N < 512 ->
end),
otp_7422_bin(N+1);
otp_7422_bin(_) -> ok.

zero_width(Config) when is_list(Config) ->
?line Z = id(0),
Small = id(42),
Big = id(1 bsl 128),
?line <<>> = <<Small:Z>>,
?line <<>> = <<Small:0>>,
?line <<>> = <<Big:Z>>,
?line <<>> = <<Big:0>>,

?line {'EXIT',{badarg,_}} = (catch <<not_a_number:0>>),
?line {'EXIT',{badarg,_}} = (catch <<(id(not_a_number)):Z>>),
?line {'EXIT',{badarg,_}} = (catch <<(id(not_a_number)):0>>),

ok.

id(I) -> I.
16 changes: 13 additions & 3 deletions lib/stdlib/test/erl_eval_SUITE.erl
@@ -1,7 +1,7 @@
%%
%% %CopyrightBegin%
%%
%% Copyright Ericsson AB 1998-2009. All Rights Reserved.
%% Copyright Ericsson AB 1998-2010. All Rights Reserved.
%%
%% The contents of this file are subject to the Erlang Public License,
%% Version 1.1, (the "License"); you may not use this file except in
Expand Down Expand Up @@ -38,7 +38,8 @@
otp_8133/1,
funs/1,
try_catch/1,
eval_expr_5/1]).
eval_expr_5/1,
zero_width/1]).

%%
%% Define to run outside of test server
Expand Down Expand Up @@ -76,7 +77,8 @@ all(suite) ->
[guard_1, guard_2, match_pattern, string_plusplus, pattern_expr,
match_bin, guard_3, guard_4,
lc, simple_cases, unary_plus, apply_atom, otp_5269, otp_6539, otp_6543,
otp_6787, otp_6977, otp_7550, otp_8133, funs, try_catch, eval_expr_5].
otp_6787, otp_6977, otp_7550, otp_8133, funs, try_catch, eval_expr_5,
zero_width].

guard_1(doc) ->
["(OTP-2405)"];
Expand Down Expand Up @@ -1326,6 +1328,14 @@ eval_expr_5(Config) when is_list(Config) ->
ok
end.

zero_width(Config) when is_list(Config) ->
?line check(fun() ->
{'EXIT',{badarg,_}} = (catch <<not_a_number:0>>),
ok
end, "begin {'EXIT',{badarg,_}} = (catch <<not_a_number:0>>), "
"ok end.", ok),
ok.

%% Check the string in different contexts: as is; in fun; from compiled code.
check(F, String, Result) ->
check1(F, String, Result),
Expand Down

0 comments on commit 2d69a4f

Please sign in to comment.