diff options
author | Peter Palfrader <peter@palfrader.org> | 2012-12-10 15:07:57 +0000 |
---|---|---|
committer | weasel <weasel@bc3d92e2-beff-0310-a7cd-cc87d7ac0ede> | 2012-12-10 15:07:57 +0000 |
commit | 6a5f6f53f53d1b0715dbba7b43b0690ab854e4fd (patch) | |
tree | b497087d1d016ca9dd3a20b105b5df102c769636 /tor-exit-ssl-check | |
parent | d678d35e6875b1ca3b8497029815ad4f8034544b (diff) |
Add tor-exit-ssl-check
git-svn-id: svn+ssh://asteria.noreply.org/svn/weaselutils/trunk@560 bc3d92e2-beff-0310-a7cd-cc87d7ac0ede
Diffstat (limited to 'tor-exit-ssl-check')
-rwxr-xr-x | tor-exit-ssl-check | 196 |
1 files changed, 196 insertions, 0 deletions
diff --git a/tor-exit-ssl-check b/tor-exit-ssl-check new file mode 100755 index 0000000..823bb4f --- /dev/null +++ b/tor-exit-ssl-check @@ -0,0 +1,196 @@ +#!/bin/bash + +# Copyright (c) 2012 Peter Palfrader <peter@palfrader.org> +# +# Permission is hereby granted, free of charge, to any person obtaining +# a copy of this software and associated documentation files (the +# "Software"), to deal in the Software without restriction, including +# without limitation the rights to use, copy, modify, merge, publish, +# distribute, sublicense, and/or sell copies of the Software, and to +# permit persons to whom the Software is furnished to do so, subject to +# the following conditions: +# +# The above copyright notice and this permission notice shall be +# included in all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +# EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +# MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +# NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE +# LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +# OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +# WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +set -e +set -u + +usage() { + echo "Usage: $0 [-v [-v]] [-d <datadir>] <torserver fpr> <targethost> [<targetport>]" + echo " If datadir is -, a list of fingerprints is read from stdin" +} + +verbose=0 +datadir="" +while getopts "vhd:" OPTION +do + case "$OPTION" in + v) + verbose=$((verbose + 1)) + ;; + h) + usage + exit 0 + ;; + d) + datadir="$OPTARG" + ;; + *) + usage >&2 + exit 1 + esac +done +shift $(($OPTIND - 1)) + +if [ "${1:-}" = "--help" ]; then + usage + exit 0 +elif [ "$#" -lt 2 ]; then + usage >&2 + exit 1 +fi + + +torserver="$1"; shift +hostname="$1"; shift +port="${1:-443}" + +socksport=$((RANDOM % 40000 + 20000)) +mapaddr="192.0.2.1" + + +logpid="" +torpid="" +tmpdir="" + +cleanup() { + [ -z "$torpid" ] || kill "$torpid" || true + [ -z "$logpid" ] || kill "$logpid" || true + [ -z "$tmpdir" ] || rm -rf "$tmpdir" || true +} + +tmpdir=$(mktemp -d "/tmp/cert-check-XXXXXX") +trap 'cleanup' EXIT + +pidfile="$tmpdir/pid" +torlog="$tmpdir/log" +if [ "$verbose" -gt 0 ]; then + tail -F "$torlog" & + logpid=$! +fi + +if command -v tor > /dev/null; then + tor="tor" +elif [ -x /usr/sbin/tor ]; then + tor="/usr/sbin/tor" +else + echo >&2 "Cannot find tor executable" + exit 1 +fi + +if [ "$verbose" -gt 1 ]; then + loglevel="info" +else + loglevel="notice" +fi + +datadir=${datadir:-$tmpdir/tor} +cat > "$tmpdir/torrc" << EOF +DataDirectory $datadir +RunAsDaemon 1 +SocksPort $socksport +PidFile $pidfile +Log $loglevel file $torlog +SafeLogging 0 +# MapAddress $mapaddr $hostname.\$$torserver.exit +ControlSocket $tmpdir/sock +StrictNodes 1 +EOF + +cat > "$tmpdir/torsocks.conf" << EOF +server = 127.0.0.1 +server_port = $socksport +EOF + +mkdir -p -m 0700 "$datadir" +if [ "$verbose" -gt 0 ]; then hush=""; else hush="--hush"; fi +"$tor" $hush -f "$tmpdir/torrc" +torpid="$(cat $pidfile)" + + +eatdata() { + local fn="$1"; shift + if [ "$verbose" -gt 0 ]; then + tee "$fn" + else + cat > "$fn" + fi +} +expect_ok() { + local line + read code line <&${COPROC[0]} + line=$(echo "$line" | tr -d '\r') + if ! [ "$code" = "250" ]; then + echo >&2 "Tor said '$code $line' - no idea what that means" + exit 1 + fi +} + +[ "$verbose" = 0 ] || echo "Directly:" +openssl s_client -no_ticket -showcerts -connect "$hostname":"$port" < /dev/null 2>&1 | eatdata "$tmpdir/cert-direct" +egrep -v '(Session-ID|Master-Key|Start Time):' < "$tmpdir/cert-direct" > "$tmpdir/cert-direct.filtered" +[ "$verbose" = 0 ] || echo "====" + + +coproc socat UNIX-CONNECT:"$tmpdir/sock" - +echo 'AUTHENTICATE' >&${COPROC[1]} +expect_ok + +errors=0 +while : ; do + if [ "$torserver" = "-" ]; then + read server + [ -n "$server" ] || break + else + server="$torserver" + fi + + [ "$verbose" = 0 ] || echo "Setting ExitNodes $server" + echo "RESETCONF ExitNodes" >&${COPROC[1]} + expect_ok + echo "SETCONF ExitNodes=\$$server" >&${COPROC[1]} + expect_ok + + rm -f "$tmpdir/cert-tor" "$tmpdir/cert-tor.filtered" + + [ "$verbose" = 0 ] || echo "Via $server:" + TORSOCKS_CONF_FILE="$tmpdir/torsocks.conf" torify openssl s_client -no_ticket -showcerts -connect "$hostname":"$port" < /dev/null 2>&1 | eatdata "$tmpdir/cert-tor" + + egrep -v '(Session-ID|Master-Key|Start Time):' < "$tmpdir/cert-tor" > "$tmpdir/cert-tor.filtered" + + if diff "$tmpdir/cert-tor.filtered" "$tmpdir/cert-direct.filtered" > /dev/null; then + echo "RESULT: $server: No real differences." + [ "$verbose" = 0 ] || diff -U100 "$tmpdir/cert-tor" "$tmpdir/cert-direct" || true + elif egrep '^connect:errno=' "$tmpdir/cert-tor" > /dev/null; then + echo "RESULT: $server: Connect failed" + errors=1 + else + echo "RESULT: $server: differences!" + [ "$verbose" = 0 ] || echo "====" + [ "$verbose" = 0 ] || echo "Diff:" + diff -U100 "$tmpdir/cert-tor" "$tmpdir/cert-direct" || true + errors=1 + fi + + [ "$torserver" = "-" ] || break +done +exit "$errors" |