File 0349-Fix-bug-in-binary-encode_unsigned-causing-a-read-of-.patch of Package erlang

From 1df3d85824601e3c07d12ca9811866c2ef334e76 Mon Sep 17 00:00:00 2001
From: Kjell Winblad <kjellwinblad@gmail.com>
Date: Tue, 29 Jan 2019 12:33:19 +0100
Subject: [PATCH] Fix bug in binary:encode_unsigned causing a read of
 uninitialized memory
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit

The bug could be seen by running the test that is added by this commit
in a valgrind enabled emulator.

Co-authored-by: John Högberg <john@erlang.org>
---
 erts/emulator/beam/erl_bif_binary.c     | 18 +++++++-----------
 lib/stdlib/test/binary_module_SUITE.erl | 15 +++++++++++++--
 2 files changed, 20 insertions(+), 13 deletions(-)

diff --git a/erts/emulator/beam/erl_bif_binary.c b/erts/emulator/beam/erl_bif_binary.c
index a2610bf2e1..ae1bf6e652 100644
--- a/erts/emulator/beam/erl_bif_binary.c
+++ b/erts/emulator/beam/erl_bif_binary.c
@@ -2762,7 +2762,7 @@ static BIF_RETTYPE do_encode_unsigned(Process *p, Eterm uns, Eterm endianess)
 	dsize_t num_parts = BIG_SIZE(bigp);
 	Eterm res;
 	byte *b;
-	ErtsDigit d;
+	ErtsDigit d = 0;
 
 	if(BIG_SIGN(bigp)) {
 	    goto badarg;
@@ -2778,26 +2778,22 @@ static BIF_RETTYPE do_encode_unsigned(Process *p, Eterm uns, Eterm endianess)
 	if (endianess == am_big) {
 	    Sint i,j;
 	    j = 0;
-	    d = BIG_DIGIT(bigp,0);
 	    for (i=n-1;i>=0;--i) {
-		b[i] = d & 0xFF;
-		if (!((++j) % sizeof(ErtsDigit))) {
+                if (!((j++) % sizeof(ErtsDigit))) {
 		    d = BIG_DIGIT(bigp,j / sizeof(ErtsDigit));
-		} else {
-		    d >>= 8;
 		}
+                b[i] = d & 0xFF;
+                d >>= 8;
 	    }
 	} else {
 	    Sint i,j;
 	    j = 0;
-	    d = BIG_DIGIT(bigp,0);
 	    for (i=0;i<n;++i) {
-		b[i] = d & 0xFF;
-		if (!((++j) % sizeof(ErtsDigit))) {
+                if (!((j++) % sizeof(ErtsDigit))) {
 		    d = BIG_DIGIT(bigp,j / sizeof(ErtsDigit));
-		} else {
-		    d >>= 8;
 		}
+                b[i] = d & 0xFF;
+                d >>= 8;
 	    }
 
 	}
diff --git a/lib/stdlib/test/binary_module_SUITE.erl b/lib/stdlib/test/binary_module_SUITE.erl
index c5cfea5e9e..e0811f19cf 100644
--- a/lib/stdlib/test/binary_module_SUITE.erl
+++ b/lib/stdlib/test/binary_module_SUITE.erl
@@ -23,7 +23,8 @@
 	 init_per_group/2,end_per_group/2, 
 	 interesting/1,scope_return/1,random_ref_comp/1,random_ref_sr_comp/1,
 	 random_ref_fla_comp/1,parts/1, bin_to_list/1, list_to_bin/1,
-	 copy/1, referenced/1,guard/1,encode_decode/1,badargs/1,longest_common_trap/1]).
+	 copy/1, referenced/1,guard/1,encode_decode/1,badargs/1,longest_common_trap/1,
+         check_no_invalid_read_bug/1]).
 
 -export([random_number/1, make_unaligned/1]).
 
@@ -71,7 +72,7 @@ all() ->
     [scope_return,interesting, random_ref_fla_comp, random_ref_sr_comp,
      random_ref_comp, parts, bin_to_list, list_to_bin, copy,
      referenced, guard, encode_decode, badargs,
-     longest_common_trap].
+     longest_common_trap, check_no_invalid_read_bug].
 
 groups() -> 
     [].
@@ -1421,3 +1422,13 @@ make_unaligned2(Bin0) when is_binary(Bin0) ->
     Bin.
 
 id(I) -> I.
+
+check_no_invalid_read_bug(Config) when is_list(Config) ->
+    check_no_invalid_read_bug(24);
+check_no_invalid_read_bug(60) ->
+    ok;
+check_no_invalid_read_bug(I) ->
+    N = 1 bsl I,
+    binary:encode_unsigned(N+N),
+    binary:encode_unsigned(N+N, little),
+    check_no_invalid_read_bug(I+1).
-- 
2.16.4

openSUSE Build Service is sponsored by