The key here is to never touch ssl->cipher_list directly, but only
via SSL_get_ciphers(). But it's not so simple.
See, if there is no specialized cipher_list on the SSL object,
SSL_get_ciphers returns the cipher_list on the SSL_CTX. But we sure
don't want to modify that one! So we need to use
SSL_set_cipher_list first to make sure that we really have a cipher
list on the SSL object.
This field was only needed to work with the now-long-gone (I hope,
except for some horrible apples) openssl 0.9.8l; if your headers say
you have openssl 1.1, you won't even need it.
Incidently, this fixes a bug where the maximum value was never used when
only using crypto_rand_int(). For instance this example below in
rendservice.c never gets to INTRO_POINT_LIFETIME_MAX_SECONDS.
int intro_point_lifetime_seconds =
INTRO_POINT_LIFETIME_MIN_SECONDS +
crypto_rand_int(INTRO_POINT_LIFETIME_MAX_SECONDS -
INTRO_POINT_LIFETIME_MIN_SECONDS);
Signed-off-by: David Goulet <dgoulet@ev0ke.net>
apparantly, "pragma GCC diagnostic push/pop" don't exist with older versions.
Fixes bug in 740e592790f570c446cbb5e6d4a77f842f75; bug not in any
released Tor.
This function is supposed to construct a list of all the ciphers in
the "v2 link protocol cipher list" that are supported by Tor's
openssl. It does this by invoking ssl23_get_cipher_by_char on each
two-byte ciphersuite ID to see which ones give a match. But when
ssl23_get_cipher_by_char cannot find a match for a two-byte SSL3/TLS
ciphersuite ID, it checks to see whether it has a match for a
three-byte SSL2 ciphersuite ID. This was causing a read off the end
of the 'cipherid' array.
This was probably harmless in practice, but we shouldn't be having
any uninitialized reads.
(Using ssl23_get_cipher_by_char in this way is a kludge, but then
again the entire existence of the v2 link protocol is kind of a
kludge. Once Tor 0.2.2 clients are all gone, we can drop this code
entirely.)
Found by starlight. Fix on 0.2.4.8-alpha. Fixes bug 12227.
Found because LibreSSL has OPENSSL_NO_COMP always-on, but this
conflicts with the way that _we_ turn off compression. Patch from
dhill, who attributes it to "OpenBSD". Fixes bug 12602; bugfix on
0.2.1.1-alpha, which introduced this turn-compression-off code.
This function is supposed to construct a list of all the ciphers in
the "v2 link protocol cipher list" that are supported by Tor's
openssl. It does this by invoking ssl23_get_cipher_by_char on each
two-byte ciphersuite ID to see which ones give a match. But when
ssl23_get_cipher_by_char cannot find a match for a two-byte SSL3/TLS
ciphersuite ID, it checks to see whether it has a match for a
three-byte SSL2 ciphersuite ID. This was causing a read off the end
of the 'cipherid' array.
This was probably harmless in practice, but we shouldn't be having
any uninitialized reads.
(Using ssl23_get_cipher_by_char in this way is a kludge, but then
again the entire existence of the v2 link protocol is kind of a
kludge. Once Tor 0.2.2 clients are all gone, we can drop this code
entirely.)
Found by starlight. Fix on 0.2.4.8-alpha. Fixes bug 12227.
The server cipher list is (thanks to #11513) chosen systematically to
put the best choices for Tor first. The client cipher list is chosen
to resemble a browser. So let's set SSL_OP_CIPHER_SERVER_PREFERENCE
to have the servers pick according to their own preference order.
A new set of unit test cases are provided, as well as introducing
an alternative paradigm and macros to support it. Primarily, each test
case is given its own namespace, in order to isolate tests from each
other. We do this by in the usual fashion, by appending module and
submodule names to our symbols. New macros assist by reducing friction
for this and other tasks, like overriding a function in the global
namespace with one in the current namespace, or declaring integer
variables to assist tracking how many times a mock has been called.
A set of tests for a small-scale module has been included in this
commit, in order to highlight how the paradigm can be used. This
suite gives 100% coverage to status.c in test execution.
Back in 175b2678, we allowed servers to recognize clients who are
telling them the truth about their ciphersuites, and select the best
cipher from on that list. This implemented the server side of proposal
198.
In bugs 11492, 11498, and 11499, cypherpunks found a bunch of mistakes
and omissions and typos in the UNRESTRICTED_SERVER_CIPHER_LIST we had.
In #11513, I found a couple more.
Rather than try to hand-edit this list, I wrote a short python script
to generate our ciphersuite preferences from the openssl headers.
The new rules are:
* Require forward secrecy.
* Require RSA (since our servers only configure RSA keys)
* Require AES or 3DES. (This means, reject RC4, DES, SEED, CAMELLIA,
and NULL.)
* No export ciphersuites.
Then:
* Prefer AES to 3DES.
* If both suites have the same cipher, prefer ECDHE to DHE.
* If both suites have the same DHE group type, prefer GCM to CBC.
* If both suites have the same cipher mode, prefer SHA384 to SHA256
to SHA1.
* If both suites have the same digest, prefer AES256 to AES128.
Most of these are simple. The only nontrivial part is that our
pattern for using ENUM_BF was confusing doxygen by making declarations
that didn't look like declarations.
The previous commit from piet would have backed out some of proposal
198 and made servers built without the V2 handshake not use the
unrestricted cipher list from prop198.
Bug not in any released Tor.
According to the manpage, bridges use P256 for conformity and relays
use P224 for speed. But skruffy points out that we've gotten it
backwards in the code.
In this patch, we make the default P256 for everybody.
Fixes bug 9780; bugfix on 0.2.4.8-alpha.
To fix#6033, we disabled TLS 1.1 and 1.2. Eventually, OpenSSL fixed
the bug behind #6033.
I've considered alternate implementations that do more testing to see
if there's secretly an OpenSSL 1.0.1c or something that secretly has a
backport of the OpenSSL 1.0.1e fix, and decided against it on the
grounds of complexity.
We previously used FILENAME_PRIVATE identifiers mostly for
identifiers exposed only to the unit tests... but also for
identifiers exposed to the benchmarker, and sometimes for
identifiers exposed to a similar module, and occasionally for no
really good reason at all.
Now, we use FILENAME_PRIVATE identifiers for identifiers shared by
Tor and the unit tests. They should be defined static when we
aren't building the unit test, and globally visible otherwise. (The
STATIC macro will keep us honest here.)
For identifiers used only by the unit tests and never by Tor at all,
on the other hand, we wrap them in #ifdef TOR_UNIT_TESTS.
This is not the motivating use case for the split test/non-test
build system; it's just a test example to see how it works, and to
take a chance to clean up the code a little.
This is meant to avoid conflict with the built-in log() function in
math.h. It resolves ticket 7599. First reported by dhill.
This was generated with the following perl script:
#!/usr/bin/perl -w -i -p
s/\blog\(LOG_(ERR|WARN|NOTICE|INFO|DEBUG)\s*,\s*/log_\L$1\(/g;
s/\blog\(/tor_log\(/g;
This implements the server-side of proposal 198 by detecting when
clients lack the magic list of ciphersuites that indicates that
they're lying faking some ciphers they don't really have. When
clients lack this list, we can choose any cipher that we'd actually
like. The newly allowed ciphersuites are, currently, "All ECDHE-RSA
ciphers that openssl supports, except for ECDHE-RSA-RC4".
The code to detect the cipher list relies on on (ab)use of
SSL_set_session_secret_cb.
We already use this classification for deciding whether (as a server)
to do a v2/v3 handshake, and we're about to start using it for
deciding whether we can use good ciphersuites too.
This is less easy than you might think; we can't just look at the
client ciphers list, since openssl doesn't remember client ciphers if
it doesn't know about them. So we have to keep a list of the "v2"
ciphers, with the ones we don't know about removed.
Apparently some compilers like to eliminate memset() operations on
data that's about to go out-of-scope. I've gone with the safest
possible replacement, which might be a bit slow. I don't think this
is critical path in any way that will affect performance, but if it
is, we can work on that in 0.2.4.
Fixes bug 7352.
OpenSSL 1.0.0 added an implementation of TLS session tickets, a
"feature" that let session resumption occur without server-side state
by giving clients an encrypted "ticket" that the client could present
later to get the session going again with the same keys as before.
OpenSSL was giving the keys to decrypt these tickets the lifetime of
the SSL contexts, which would have been terrible for PFS if we had
long-lived SSL contexts. Fortunately, we don't. Still, it's pretty
bad. We should also drop these, since our use of the extension stands
out with our non-use of session cacheing.
Found by nextgens. Bugfix on all versions of Tor when built with
openssl 1.0.0 or later. Fixes bug 7139.
097 hasn't seen a new version since 2007; we can drop support too.
This lets us remove our built-in sha256 implementation, and some
checks for old bugs.
This is a feature removal: we no longer fake any ciphersuite other
than the not-really-standard SSL_RSA_FIPS_WITH_3DES_EDE_CBC_SHA
(0xfeff). This change will let servers rely on our actually
supporting what we claim to support, and thereby let Tor migrate to
better TLS ciphersuites.
As a drawback, Tor instances that use old openssl versions and
openssl builds with ciphers disabled will no longer give the
"firefox" cipher list.
Also, try to resolve some doxygen issues. First, define a magic
"This is doxygen!" macro so that we take the correct branch in
various #if/#else/#endifs in order to get the right documentation.
Second, add in a few grouping @{ and @} entries in order to get some
variables and fields to get grouped together.