Package: release.debian.org Severity: normal User: [email protected] Usertags: pu
Hi! I'd like to fix CVE-2011-0766 (see http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=628456 for details) in a point update. The debdiff for a new version is attached. -- System Information: Debian Release: 6.0.3 APT prefers proposed-updates APT policy: (990, 'proposed-updates'), (990, 'stable') Architecture: i386 (i686) Kernel: Linux 2.6.32-5-686-bigmem (SMP w/8 CPU cores) Locale: LANG=C, LC_CTYPE=C (charmap=ANSI_X3.4-1968) Shell: /bin/sh linked to /bin/bash
diff -u erlang-14.a-dfsg/debian/changelog erlang-14.a-dfsg/debian/changelog --- erlang-14.a-dfsg/debian/changelog +++ erlang-14.a-dfsg/debian/changelog @@ -1,3 +1,10 @@ +erlang (1:14.a-dfsg-3squeeze1) stable; urgency=low + + * Added patch by upstream which fixed CVE-2011-0766 (cryptographic weakness) + in Erlang SSH application (closes: #628456). + + -- Sergei Golovan <[email protected]> Tue, 03 Jan 2012 14:06:44 +0400 + erlang (1:14.a-dfsg-3) unstable; urgency=low * Fixed a few spelling errors in packages descriptions and Debian changelog diff -u erlang-14.a-dfsg/debian/patches/series erlang-14.a-dfsg/debian/patches/series --- erlang-14.a-dfsg/debian/patches/series +++ erlang-14.a-dfsg/debian/patches/series @@ -14,4 +14,5 @@ ssl_old.patch odbc.patch +cve-2011-0766.patch #native.patch #build-options.patch only in patch2: unchanged: --- erlang-14.a-dfsg.orig/debian/patches/cve-2011-0766.patch +++ erlang-14.a-dfsg/debian/patches/cve-2011-0766.patch @@ -0,0 +1,345 @@ +Description: Patch fixes CVE-2011-0766 (cryptographic weakness) vulnerability + in Erlang SSH application. It is taken from upstream git repository + https://github.com/erlang/otp/commit/f228601de45c5 +Author: Upstream +Bug-Debian: http://bugs.debian.org/cgi-bin/bugreport.cgi?bug=628456 +Last-Updated: Tue, 03 Jan 2012 14:05:07 +0400 + +--- erlang-14.a-dfsg.orig/lib/crypto/c_src/crypto.c ++++ erlang-14.a-dfsg/lib/crypto/c_src/crypto.c +@@ -127,7 +127,9 @@ + static ERL_NIF_TERM des_ede3_cbc_crypt(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); + static ERL_NIF_TERM aes_cfb_128_crypt(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); + static ERL_NIF_TERM rand_bytes_1(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); ++static ERL_NIF_TERM strong_rand_bytes_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); + static ERL_NIF_TERM rand_bytes_3(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); ++static ERL_NIF_TERM strong_rand_mpint_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); + static ERL_NIF_TERM rand_uniform_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); + static ERL_NIF_TERM mod_exp_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); + static ERL_NIF_TERM dss_verify(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]); +@@ -195,7 +197,9 @@ + {"des_ede3_cbc_crypt", 6, des_ede3_cbc_crypt}, + {"aes_cfb_128_crypt", 4, aes_cfb_128_crypt}, + {"rand_bytes", 1, rand_bytes_1}, ++ {"strong_rand_bytes_nif", 1, strong_rand_bytes_nif}, + {"rand_bytes", 3, rand_bytes_3}, ++ {"strong_rand_mpint_nif", 3, strong_rand_mpint_nif}, + {"rand_uniform_nif", 2, rand_uniform_nif}, + {"mod_exp_nif", 3, mod_exp_nif}, + {"dss_verify", 4, dss_verify}, +@@ -667,6 +671,22 @@ + ERL_VALGRIND_MAKE_MEM_DEFINED(data, bytes); + return ret; + } ++static ERL_NIF_TERM strong_rand_bytes_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) ++{/* (Bytes) */ ++ unsigned bytes; ++ unsigned char* data; ++ ERL_NIF_TERM ret; ++ if (!enif_get_uint(env, argv[0], &bytes)) { ++ return enif_make_badarg(env); ++ } ++ data = enif_make_new_binary(env, bytes, &ret); ++ if ( RAND_bytes(data, bytes) != 1) { ++ return atom_false; ++ } ++ ERL_VALGRIND_MAKE_MEM_DEFINED(data, bytes); ++ return ret; ++} ++ + static ERL_NIF_TERM rand_bytes_3(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) + {/* (Bytes, TopMask, BottomMask) */ + unsigned bytes; +@@ -687,6 +707,47 @@ + } + return ret; + } ++static ERL_NIF_TERM strong_rand_mpint_nif(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[]) ++{/* (Bytes, TopMask, BottomMask) */ ++ unsigned bits; ++ BIGNUM *bn_rand; ++ int top, bottom; ++ unsigned char* data; ++ unsigned dlen; ++ ERL_NIF_TERM ret; ++ if (!enif_get_uint(env, argv[0], &bits) ++ || !enif_get_int(env, argv[1], &top) ++ || !enif_get_int(env, argv[2], &bottom)) { ++ return enif_make_badarg(env); ++ } ++ if (! (top == -1 || top == 0 || top == 1) ) { ++ return enif_make_badarg(env); ++ } ++ if (! (bottom == 0 || bottom == 1) ) { ++ return enif_make_badarg(env); ++ } ++ ++ bn_rand = BN_new(); ++ if (! bn_rand ) { ++ return enif_make_badarg(env); ++ } ++ ++ /* Get a (bits) bit random number */ ++ if (!BN_rand(bn_rand, bits, top, bottom)) { ++ ret = atom_false; ++ } ++ else { ++ /* Copy the bignum into an erlang mpint binary. */ ++ dlen = BN_num_bytes(bn_rand); ++ data = enif_make_new_binary(env, dlen+4, &ret); ++ put_int32(data, dlen); ++ BN_bn2bin(bn_rand, data+4); ++ ERL_VALGRIND_MAKE_MEM_DEFINED(data+4, dlen); ++ } ++ BN_free(bn_rand); ++ ++ return ret; ++} + + static int get_bn_from_mpint(ErlNifEnv* env, ERL_NIF_TERM term, BIGNUM** bnp) + { +--- erlang-14.a-dfsg.orig/lib/crypto/doc/src/crypto.xml ++++ erlang-14.a-dfsg/lib/crypto/doc/src/crypto.xml +@@ -587,6 +587,21 @@ + </desc> + </func> + <func> ++ <name>strong_rand_bytes(N) -> binary()</name> ++ <fsummary>Generate a binary of random bytes</fsummary> ++ <type> ++ <v>N = integer()</v> ++ </type> ++ <desc> ++ <p>Generates N bytes randomly uniform 0..255, and returns the ++ result in a binary. Uses a cryptographically secure prng seeded and ++ periodically mixed with operating system provided entropy. By default ++ this is the <c>RAND_bytes</c> method from OpenSSL.</p> ++ <p>May throw exception <c>low_entropy</c> in case the random generator ++ failed due to lack of secure "randomness".</p> ++ </desc> ++ </func> ++ <func> + <name>rand_uniform(Lo, Hi) -> N</name> + <fsummary>Generate a random number</fsummary> + <type> +@@ -601,6 +616,31 @@ + </desc> + </func> + <func> ++ <name>strong_rand_mpint(N, Top, Bottom) -> Mpint</name> ++ <fsummary>Generate an N bit random number</fsummary> ++ <type> ++ <v>N = non_neg_integer()</v> ++ <v>Top = -1 | 0 | 1</v> ++ <v>Bottom = 0 | 1</v> ++ <v>Mpint = binary()</v> ++ </type> ++ <desc> ++ <p>Generate an N bit random number using OpenSSL's ++ cryptographically strong pseudo random number generator ++ <c>BN_rand</c>.</p> ++ <p>The parameter <c>Top</c> places constraints on the most ++ significant bits of the generated number. If <c>Top</c> is 1, then the ++ two most significant bits will be set to 1, if <c>Top</c> is 0, the ++ most significant bit will be 1, and if <c>Top</c> is -1 then no ++ constraints are applied and thus the generated number may be less than ++ N bits long.</p> ++ <p>If <c>Bottom</c> is 1, then the generated number is ++ constrained to be odd.</p> ++ <p>May throw exception <c>low_entropy</c> in case the random generator ++ failed due to lack of secure "randomness".</p> ++ </desc> ++ </func> ++ <func> + <name>mod_exp(N, P, M) -> Result</name> + <fsummary>Perform N ^ P mod M</fsummary> + <type> +--- erlang-14.a-dfsg.orig/lib/crypto/src/crypto.erl ++++ erlang-14.a-dfsg/lib/crypto/src/crypto.erl +@@ -46,6 +46,7 @@ + -export([rsa_private_encrypt/3, rsa_public_decrypt/3]). + -export([dh_generate_key/1, dh_generate_key/2, dh_compute_key/3]). + -export([rand_bytes/1, rand_bytes/3, rand_uniform/2]). ++-export([strong_rand_bytes/1, strong_rand_mpint/3]). + -export([mod_exp/3, mpint/1, erlint/1]). + %% -export([idea_cbc_encrypt/3, idea_cbc_decrypt/3]). + -export([aes_cbc_128_encrypt/3, aes_cbc_128_decrypt/3]). +@@ -67,6 +68,8 @@ + des_ede3_cbc_encrypt, des_ede3_cbc_decrypt, + aes_cfb_128_encrypt, aes_cfb_128_decrypt, + rand_bytes, ++ strong_rand_bytes, ++ strong_rand_mpint, + rand_uniform, + mod_exp, + dss_verify,dss_sign, +@@ -340,12 +343,32 @@ + %% RAND - pseudo random numbers using RN_ functions in crypto lib + %% + -spec rand_bytes(non_neg_integer()) -> binary(). ++-spec strong_rand_bytes(non_neg_integer()) -> binary(). + -spec rand_uniform(crypto_integer(), crypto_integer()) -> + crypto_integer(). ++-spec strong_rand_mpint(Bits::non_neg_integer(), ++ Top::-1..1, ++ Bottom::0..1) -> binary(). + + rand_bytes(_Bytes) -> ?nif_stub. ++ ++strong_rand_bytes(Bytes) -> ++ case strong_rand_bytes_nif(Bytes) of ++ false -> erlang:error(low_entropy); ++ Bin -> Bin ++ end. ++strong_rand_bytes_nif(_Bytes) -> ?nif_stub. ++ + rand_bytes(_Bytes, _Topmask, _Bottommask) -> ?nif_stub. + ++strong_rand_mpint(Bits, Top, Bottom) -> ++ case strong_rand_mpint_nif(Bits,Top,Bottom) of ++ false -> erlang:error(low_entropy); ++ Bin -> Bin ++ end. ++strong_rand_mpint_nif(_Bits, _Top, _Bottom) -> ?nif_stub. ++ ++ + rand_uniform(From,To) when is_binary(From), is_binary(To) -> + case rand_uniform_nif(From,To) of + <<Len:32/integer, MSB, Rest/binary>> when MSB > 127 -> +--- erlang-14.a-dfsg.orig/lib/ssh/src/ssh.appup.src ++++ erlang-14.a-dfsg/lib/ssh/src/ssh.appup.src +@@ -19,8 +19,40 @@ + + {"%VSN%", + [ ++ {"2.0.3", [{load_module, ssh_bits, soft_purge, soft_purge, []}, ++ {load_module, ssh_connection_handler, soft_purge, soft_purge, []}, ++ {load_module, ssh_file, soft_purge, soft_purge, []}, ++ {load_module, ssh, soft_purge, soft_purge, []}, ++ {load_module, ssh_rsa, soft_purge, soft_purge, []}, ++ {load_module, ssh_acceptor, soft_purge, soft_purge, []}, ++ {load_module, ssh_transport, soft_purge, soft_purge, []}, ++ {load_module, ssh_connection_manager, soft_purge, soft_purge, []}]}, ++ {"2.0.2", [{load_module, ssh_bits, soft_purge, soft_purge, []}, ++ {load_module, ssh_connection_handler, soft_purge, soft_purge, []}, ++ {load_module, ssh_file, soft_purge, soft_purge, []}, ++ {load_module, ssh, soft_purge, soft_purge, []}, ++ {load_module, ssh_rsa, soft_purge, soft_purge, []}, ++ {load_module, ssh_acceptor, soft_purge, soft_purge, []}, ++ {load_module, ssh_transport, soft_purge, soft_purge, []}, ++ {load_module, ssh_connection_manager, soft_purge, soft_purge, []}]} + ], + [ ++ {"2.0.3", [{load_module, ssh_bits, soft_purge, soft_purge, []}, ++ {load_module, ssh_connection_handler, soft_purge, soft_purge, []}, ++ {load_module, ssh_file, soft_purge, soft_purge, []}, ++ {load_module, ssh, soft_purge, soft_purge, []}, ++ {load_module, ssh_rsa, soft_purge, soft_purge, []}, ++ {load_module, ssh_acceptor, soft_purge, soft_purge, []}, ++ {load_module, ssh_transport, soft_purge, soft_purge, []}, ++ {load_module, ssh_connection_manager, soft_purge, soft_purge, []}]}, ++ {"2.0.2", [{load_module, ssh_bits, soft_purge, soft_purge, []}, ++ {load_module, ssh_connection_handler, soft_purge, soft_purge, []}, ++ {load_module, ssh_file, soft_purge, soft_purge, []}, ++ {load_module, ssh, soft_purge, soft_purge, []}, ++ {load_module, ssh_rsa, soft_purge, soft_purge, []}, ++ {load_module, ssh_acceptor, soft_purge, soft_purge, []}, ++ {load_module, ssh_transport, soft_purge, soft_purge, []}, ++ {load_module, ssh_connection_manager, soft_purge, soft_purge, []}]} + ] + }. + +--- erlang-14.a-dfsg.orig/lib/ssh/src/ssh_bits.erl ++++ erlang-14.a-dfsg/lib/ssh/src/ssh_bits.erl +@@ -34,7 +34,7 @@ + %% integer utils + -export([isize/1]). + -export([irandom/1, irandom/3]). +--export([random/1, random/3]). ++-export([random/1]). + -export([xor_bits/2, fill_bits/2]). + -export([i2bin/2, bin2i/1]). + +@@ -401,9 +401,6 @@ + irandom(Bits) -> + irandom(Bits, 1, 0). + +-%% irandom_odd(Bits) -> +-%% irandom(Bits, 1, 1). +- + %% + %% irandom(N, Top, Bottom) + %% +@@ -414,57 +411,16 @@ + %% Bot = 0 - do not set the least signifcant bit + %% Bot = 1 - set the least signifcant bit (i.e always odd) + %% +-irandom(0, _Top, _Bottom) -> +- 0; +-irandom(Bits, Top, Bottom) -> +- Bytes = (Bits+7) div 8, +- Skip = (8-(Bits rem 8)) rem 8, +- TMask = case Top of +- 0 -> 0; +- 1 -> 16#80; +- 2 -> 16#c0 +- end, +- BMask = case Bottom of +- 0 -> 0; +- 1 -> (1 bsl Skip) +- end, +- <<X:Bits/big-unsigned-integer, _:Skip>> = random(Bytes, TMask, BMask), +- X. ++irandom(Bits, Top, Bottom) when is_integer(Top), ++ 0 =< Top, Top =< 2 -> ++ crypto:erlint(crypto:strong_rand_mpint(Bits, Top - 1, Bottom)). + + %% + %% random/1 + %% Generate N random bytes + %% + random(N) -> +- random(N, 0, 0). +- +-random(N, TMask, BMask) -> +- list_to_binary(rnd(N, TMask, BMask)). +- +-%% random/3 +-%% random(Bytes, TopMask, BotMask) +-%% where +-%% Bytes is the number of bytes to generate +-%% TopMask is bitwised or'ed to the first byte +-%% BotMask is bitwised or'ed to the last byte +-%% +-rnd(0, _TMask, _BMask) -> +- []; +-rnd(1, TMask, BMask) -> +- [(rand8() bor TMask) bor BMask]; +-rnd(N, TMask, BMask) -> +- [(rand8() bor TMask) | rnd_n(N-1, BMask)]. +- +-rnd_n(1, BMask) -> +- [rand8() bor BMask]; +-rnd_n(I, BMask) -> +- [rand8() | rnd_n(I-1, BMask)]. +- +-rand8() -> +- (rand32() bsr 8) band 16#ff. +- +-rand32() -> +- random:uniform(16#100000000) -1. ++ crypto:strong_rand_bytes(N). + + %% + %% Base 64 encode/decode +--- erlang-14.a-dfsg.orig/lib/ssh/src/ssh_connection_handler.erl ++++ erlang-14.a-dfsg/lib/ssh/src/ssh_connection_handler.erl +@@ -106,8 +106,6 @@ + %% initialize. + %%-------------------------------------------------------------------- + init([Role, Manager, Socket, SshOpts]) -> +- {A,B,C} = erlang:now(), +- random:seed(A, B, C), + {NumVsn, StrVsn} = ssh_transport:versions(Role, SshOpts), + ssh_bits:install_messages(ssh_transport:transport_messages(NumVsn)), + {Protocol, Callback, CloseTag} =

