update
This commit is contained in:
parent
91465abf2a
commit
b9bdb02067
2
Makefile
2
Makefile
@ -22,6 +22,8 @@ install::
|
||||
test::
|
||||
echo src/${MOD}/check_digests.py
|
||||
TOR_CONTROLLER_PASSWORD=${PASS} src/${MOD}/check_digests.py
|
||||
echo src/${MOD}/connection_resolution.py
|
||||
sudo env TOR_CONTROLLER_PASSWORD=${PASS} src/${MOD}/connection_resolution.py
|
||||
# broken because this site fails: http://128.31.0.39:9131/tor/status-vote
|
||||
# ${PYTHON_EXE_MSYS} src/${MOD}/compare_flags.py
|
||||
# cant use from make: waits for the cmdline to to terminate
|
||||
|
@ -35,6 +35,13 @@ and maatuska, with a special interest in the 'Running' flag.
|
||||
|
||||
https://stem.torproject.org/tutorials/examples/compare_flags.html
|
||||
|
||||
### connection_resolution Connection Resolution
|
||||
|
||||
Connection information is a useful tool for learning more about network
|
||||
applications like Tor. Our stem.util.connection.get_connections() function
|
||||
provides an easy method for accessing this information.
|
||||
|
||||
|
||||
### exit_used Exit Used
|
||||
|
||||
Determine The Exit You're Using
|
||||
|
@ -122,5 +122,3 @@ if __name__ == '__main__':
|
||||
LOG.exception(f"Exception in iMain {e}")
|
||||
i = 1
|
||||
sys.exit(i)
|
||||
|
||||
|
||||
|
@ -18,7 +18,7 @@ import stem.descriptor
|
||||
import stem.descriptor.remote
|
||||
import stem.directory
|
||||
|
||||
from tor_controller import set_socks_proxy
|
||||
from tor_controller import set_socks_proxy, unset_socks_proxy
|
||||
|
||||
def iMain():
|
||||
# Query all authority votes asynchronously.
|
||||
@ -70,4 +70,10 @@ def iMain():
|
||||
|
||||
if __name__ == '__main__':
|
||||
set_socks_proxy()
|
||||
sys.exit(iMain())
|
||||
try:
|
||||
i = iMain()
|
||||
except KeyboardInterrupt as e:
|
||||
i = 0
|
||||
finally:
|
||||
unset_socks_proxy()
|
||||
sys.exit(i)
|
||||
|
77
src/stem_examples/connection_resolution.py
Normal file
77
src/stem_examples/connection_resolution.py
Normal file
@ -0,0 +1,77 @@
|
||||
__doc__ = """Connection Resolution
|
||||
|
||||
Connection information is a useful tool for learning more about network
|
||||
applications like Tor. Our stem.util.connection.get_connections() function
|
||||
provides an easy method for accessing this information, with a few caveats...
|
||||
|
||||
Connection resolvers are platform specific. We support several platforms but
|
||||
not all.
|
||||
|
||||
By default Tor runs with a feature called DisableDebuggerAttachment. This
|
||||
prevents debugging applications like gdb from analyzing Tor unless it is run as
|
||||
root. Unfortunately this also alters the permissions of the Tor process /proc
|
||||
contents breaking numerous system tools (including our resolvers). To use this
|
||||
function you need to either run as root (discouraged) or add
|
||||
DisableDebuggerAttachment 0 to your torrc.
|
||||
|
||||
Please note that if you operate an exit relay it is highly discouraged for you
|
||||
to look at or record this information. Not only is doing so eavesdropping, but
|
||||
likely also a violation of wiretap laws.
|
||||
|
||||
With that out of the way, how do you look up this information? Below is a
|
||||
simple script that dumps Tor's present connections.
|
||||
|
||||
https://stem.torproject.org/tutorials/east_of_the_sun.html
|
||||
"""
|
||||
|
||||
import os
|
||||
import sys
|
||||
import logging
|
||||
|
||||
from stem.util.connection import get_connections, system_resolvers
|
||||
from stem.util.system import pid_by_name
|
||||
|
||||
LOG = logging.getLogger()
|
||||
|
||||
def iMain (lArgs=None):
|
||||
resolvers = system_resolvers()
|
||||
|
||||
if not resolvers:
|
||||
LOG.error("Stem doesn't support any connection resolvers on our platform.")
|
||||
return 1
|
||||
|
||||
picked_resolver = resolvers[0] # lets just opt for the first
|
||||
LOG.info("Our platform supports connection resolution via: %s (picked %s)" % (', '.join(resolvers), picked_resolver))
|
||||
|
||||
tor_pids = pid_by_name('tor', multiple = True)
|
||||
|
||||
if not tor_pids:
|
||||
LOG.warn("Unable to get tor's pid. Is it running?")
|
||||
return 1
|
||||
|
||||
if len(tor_pids) > 1:
|
||||
LOG.info("You're running %i instances of tor, picking the one with pid %i" % (len(tor_pids), tor_pids[0]))
|
||||
else:
|
||||
LOG.info("Tor is running with pid %i" % tor_pids[0])
|
||||
|
||||
LOG.info("Connections:\n")
|
||||
|
||||
for conn in get_connections(picked_resolver, process_pid = tor_pids[0], process_name = 'tor'):
|
||||
LOG.info(" %s:%s => %s:%s" % (conn.local_address, conn.local_port, conn.remote_address, conn.remote_port))
|
||||
return 0
|
||||
|
||||
if __name__ == '__main__':
|
||||
from stem_examples.stem_utils import vsetup_logging
|
||||
if os.environ.get('DEBUG', ''):
|
||||
log_level = 10
|
||||
else:
|
||||
log_level = 20
|
||||
vsetup_logging(LOG, log_level)
|
||||
try:
|
||||
i = iMain(sys.argv[1:])
|
||||
except KeyboardInterrupt as e:
|
||||
i = 0
|
||||
except Exception as e:
|
||||
LOG.exception(f"Exception {e}")
|
||||
i = 1
|
||||
sys.exit(i)
|
@ -75,6 +75,7 @@ if __name__ == '__main__':
|
||||
except KeyboardInterrupt as e:
|
||||
i = 0
|
||||
except Exception as e:
|
||||
LOG.exception(f"Exception {e}")
|
||||
i = 1
|
||||
sys.exit(i)
|
||||
|
||||
|
@ -26,7 +26,6 @@ import logging
|
||||
from stem.control import Controller
|
||||
|
||||
from stem_examples.tor_controller import get_controller
|
||||
from stem_examples.stem_utils import vsetup_logging
|
||||
|
||||
LOG = logging.getLogger()
|
||||
|
||||
@ -76,6 +75,7 @@ def lMain(lArgs=None, timeout=None):
|
||||
return lRetval
|
||||
|
||||
if __name__ == '__main__':
|
||||
from stem_examples.stem_utils import vsetup_logging
|
||||
if os.environ.get('DEBUG', ''):
|
||||
log_level = 10
|
||||
else:
|
||||
@ -86,6 +86,7 @@ if __name__ == '__main__':
|
||||
if l: print(l)
|
||||
i = 0
|
||||
except KeyboardInterrupt as e:
|
||||
LOG.exception(f"Exception {e}")
|
||||
i = 0
|
||||
except Exception as e:
|
||||
i = 1
|
||||
|
@ -19,7 +19,7 @@ import os
|
||||
from stem import StreamStatus
|
||||
from stem.control import EventType, Controller
|
||||
|
||||
from tor_controller import set_socks_proxy
|
||||
# from tor_controller import set_socks_proxy, unset_socks_proxy
|
||||
|
||||
from stem_examples.tor_controller import get_controller
|
||||
from stem_examples.stem_utils import vsetup_logging
|
||||
|
@ -16,17 +16,15 @@ import logging
|
||||
from stem.descriptor.remote import DescriptorDownloader
|
||||
from stem.version import Version
|
||||
|
||||
from tor_controller import set_socks_proxy
|
||||
from tor_controller import set_socks_proxy, unset_socks_proxy
|
||||
|
||||
LOG = logging.getLogger()
|
||||
|
||||
def iMain():
|
||||
set_socks_proxy()
|
||||
downloader = DescriptorDownloader(use_mirrors=True)
|
||||
count, with_contact = 0, 0
|
||||
elts = downloader.get_server_descriptors()
|
||||
LOG.info(f"Checking for outdated relays len server_descriptors={len(list(elts))}...")
|
||||
print("")
|
||||
|
||||
for desc in elts:
|
||||
if desc.tor_version < Version('0.2.3.0'):
|
||||
@ -36,20 +34,18 @@ def iMain():
|
||||
LOG.info(' %-15s %s' % (desc.tor_version, desc.contact.decode("utf-8", "replace")))
|
||||
with_contact += 1
|
||||
|
||||
print("")
|
||||
LOG.info("%i outdated relays found, %i had contact information" % (count, with_contact))
|
||||
# http://vt5hknv6sblkgf22.onion/tutorials/examples/outdated_relays.htmlhttp://vt5hknv6sblkgf22.onion/tutorials/examples/outdated_relays.html
|
||||
return 0
|
||||
|
||||
if __name__ == '__main__':
|
||||
set_socks_proxy()
|
||||
from stem_examples.stem_utils import vsetup_logging
|
||||
LOG = logging.getLogger()
|
||||
if os.environ.get('DEBUG', ''):
|
||||
log_level = 10
|
||||
else:
|
||||
log_level = 20
|
||||
vsetup_logging(LOG, log_level)
|
||||
LOG.setLevel(logging.DEBUG)
|
||||
try:
|
||||
l = iMain()
|
||||
if l: print(l)
|
||||
@ -57,5 +53,8 @@ if __name__ == '__main__':
|
||||
except KeyboardInterrupt as e:
|
||||
i = 0
|
||||
except Exception as e:
|
||||
LOG.exception(f"Exception {e}")
|
||||
i = 1
|
||||
finally:
|
||||
unset_socks_proxy()
|
||||
sys.exit(i)
|
||||
|
@ -171,6 +171,7 @@ if __name__ == '__main__':
|
||||
except KeyboardInterrupt as e:
|
||||
i = 0
|
||||
except Exception as e:
|
||||
LOG.exception(f"Exception {e}")
|
||||
i = 1
|
||||
sys.exit(i)
|
||||
|
||||
|
@ -12,10 +12,14 @@ tor is at.
|
||||
import sys
|
||||
import os
|
||||
import re
|
||||
import logging
|
||||
import socket
|
||||
|
||||
from stem.connection import connect
|
||||
from stem_examples.tor_controller import get_controller
|
||||
|
||||
LOG = logging.getLogger()
|
||||
|
||||
def iMain(lArgs=None):
|
||||
password = os.environ.get('TOR_CONTROLLER_PASSWORD')
|
||||
if os.path.exists('/run/tor/control'):
|
||||
@ -23,10 +27,6 @@ def iMain(lArgs=None):
|
||||
else:
|
||||
controller = get_controller(password=password, port=9051)
|
||||
|
||||
# controller.connect()
|
||||
|
||||
bootstrap_status = controller.get_info("status/bootstrap-phase")
|
||||
|
||||
## Possible answer, if network cable has been removed:
|
||||
## 250-status/bootstrap-phase=WARN BOOTSTRAP PROGRESS=80 TAG=conn_or SUMMARY="Connecting to the Tor network" WARNING="No route to host" REASON=NOROUTE COUNT=26 RECOMMENDATION=warn
|
||||
|
||||
@ -38,18 +38,23 @@ def iMain(lArgs=None):
|
||||
|
||||
## TODO: parse the messages above.
|
||||
|
||||
try:
|
||||
bootstrap_status = controller.get_info("status/bootstrap-phase")
|
||||
LOG.info(format(bootstrap_status))
|
||||
|
||||
progress_percent = re.match('.* PROGRESS=([0-9]+).*', bootstrap_status)
|
||||
exit_code = int(progress_percent.group(1))
|
||||
|
||||
controller.close()
|
||||
|
||||
return exit_code
|
||||
except socket.error as e:
|
||||
# Error while receiving a control message (SocketClosed): received exception "read of closed file"
|
||||
return 0
|
||||
except Exception as e:
|
||||
raise
|
||||
return 0
|
||||
|
||||
if __name__ == '__main__':
|
||||
from stem_examples.stem_utils import vsetup_logging
|
||||
LOG = logging.getLogger()
|
||||
if os.environ.get('DEBUG', ''):
|
||||
log_level = 10
|
||||
else:
|
||||
@ -57,12 +62,10 @@ if __name__ == '__main__':
|
||||
vsetup_logging(LOG, log_level)
|
||||
LOG.setLevel(logging.DEBUG)
|
||||
try:
|
||||
l = iMain()
|
||||
if l: print(l)
|
||||
i = 0
|
||||
i = iMain()
|
||||
except KeyboardInterrupt as e:
|
||||
i = 0
|
||||
except Exception as e:
|
||||
LOG.exception(f"Exception {e}")
|
||||
i = 1
|
||||
sys.exit(i)
|
||||
|
||||
|
@ -12,7 +12,7 @@ def set_socks_proxy(SOCKS5_PROXY_HOST='127.0.0.1', SOCKS5_PROXY_PORT=9050):
|
||||
try:
|
||||
import socks # you need to install pysocks (see above)
|
||||
# Remove this if you don't plan to "deactivate" the proxy later
|
||||
default_socket = socket.socket
|
||||
socks._socket = socket.socket
|
||||
|
||||
# Set up a proxy
|
||||
socks.set_default_proxy(socks.SOCKS5, SOCKS5_PROXY_HOST, SOCKS5_PROXY_PORT)
|
||||
@ -21,6 +21,14 @@ def set_socks_proxy(SOCKS5_PROXY_HOST='127.0.0.1', SOCKS5_PROXY_PORT=9050):
|
||||
return False
|
||||
return True
|
||||
|
||||
def unset_socks_proxy():
|
||||
import socks # you need to install pysocks (see above)
|
||||
# Remove this if you don't plan to "deactivate" the proxy later
|
||||
socks.socket = socket._socket
|
||||
|
||||
# Set up a proxy
|
||||
socks.set_default_proxy(socks.SOCKS5, None, None)
|
||||
|
||||
def get_controller(password=None, address='127.0.0.1', port=9051, unix='/run/tor/control'):
|
||||
if unix and os.path.exists(unix):
|
||||
# print(unix)
|
||||
|
@ -3,28 +3,74 @@
|
||||
== stem_examples tor testing ==
|
||||
|
||||
This is a Python doctest file that is executable documentation.
|
||||
stem_examples is a set of small scripts that tell you about your
|
||||
running tor instance.
|
||||
|
||||
Pass the controller password if needed as an environment variable:
|
||||
Onionoo is a web-based protocol to learn about currently running Tor
|
||||
relays and bridges. Onionoo itself was not designed as a service for
|
||||
human beings---at least not directly. Onionoo provides the data for
|
||||
other applications and websites which in turn present Tor network
|
||||
status information to humans: https://metrics.torproject.org/onionoo.html
|
||||
|
||||
You can see the status of tor relays at https://torstatus.rueckgr.at/
|
||||
The code for that site is at https://github.com/paulchen/torstatus
|
||||
You can get a list of exit relays that are marked bad with:
|
||||
wget --post-data='SR=FBadExit&SO=Asc&FBadExit=1' 'https://torstatus.rueckgr.at/'
|
||||
|
||||
It is assumed that you are running a tor that has its torrc configured with:
|
||||
|
||||
ControlPort 127.0.0.1:9051
|
||||
|
||||
and/or
|
||||
|
||||
ControlSocket /run/tor/control
|
||||
ControlSocketsGroupWritable 1
|
||||
|
||||
We can authenticate with a password. To set a password first get its hash...
|
||||
|
||||
% tor --hash-password "my_password"
|
||||
16:E600ADC1B52C80BB6022A0E999A7734571A451EB6AE50FED489B72E3DF
|
||||
|
||||
and use that for the HashedControlPassword in your torrc.
|
||||
|
||||
HashedControlPassword 16:E600ADC1B52C80BB6022A0E999A7734571A451EB6AE50FED489B72E3DF
|
||||
|
||||
so that you have some security on the Control connection.
|
||||
Pass the controller password to these scripts as an environment variable:
|
||||
|
||||
>>> import os
|
||||
>>> assert os.environ['TOR_CONTROLLER_PASSWORD']
|
||||
|
||||
If you are using /run/tor/control you will also need to run the scripts as the user
|
||||
that has rw access to that socket, usually tor or debian-tor.
|
||||
|
||||
Add our code to the PYTHONPATH
|
||||
>>> import sys
|
||||
>>> sys.path.append(os.path.join(os.getcwd(), 'src', 'stem_examples'))
|
||||
|
||||
We'll need the settings defined in {{{/usr/local/etc/testforge/testforge.yml}}}
|
||||
We'll used the settings defined in {{{/usr/local/etc/testforge/testforge.yml}}}
|
||||
If you don't have one, make it with the settings from your torrc:
|
||||
|
||||
>>> print("yaml", file=sys.stderr)
|
||||
>>> import yaml
|
||||
>>> sFacts = open('/usr/local/etc/testforge/testforge.yml').read()
|
||||
>>> assert sFacts
|
||||
>>> dFacts = yaml.safe_load(sFacts)
|
||||
>>> try:
|
||||
... sFacts = open('/usr/local/etc/testforge/testforge.yml').read()
|
||||
... except:
|
||||
... dFacts = {
|
||||
... HTTPS_PROXYHOST: "127.0.0.1",
|
||||
... HTTPS_PROXYPORT: 9128,
|
||||
... HTTPS_PROXYTYPE: "http",
|
||||
... SOCKS_PROXYHOST: "127.0.0.1",
|
||||
... SOCKS_PROXYPORT: 9050,
|
||||
... SOCKS_PROXYTYPE: "socks5",
|
||||
... }
|
||||
... else:
|
||||
... assert sFacts
|
||||
... dFacts = yaml.safe_load(sFacts)
|
||||
|
||||
FixMe: use the settings for the ports and directories below.
|
||||
|
||||
>>> import os
|
||||
>>> os.environ['http_proxy'] = 'http://'+dFacts['HTTP_PROXYHOST']+':'+str(dFacts['HTTP_PROXYPORT'])
|
||||
>>> os.environ['https_proxy'] = 'http://'+dFacts['HTTPS_PROXYHOST']+':'+str(dFacts['HTTPS_PROXYPORT'])
|
||||
>>> os.environ['socks_proxy'] = 'socks5://'+dFacts['SOCKS_PROXYHOST']+':'+str(dFacts['SOCKS_PROXYPORT'])
|
||||
|
||||
@ -40,14 +86,15 @@ We test 3 known hidden services: Facebook, DuckDuckGo and .
|
||||
>>> lKNOWN_ONIONS = [
|
||||
... 'facebookwkhpilnemxj7asaniu7vnjjbiltxjqhye3mhbshg7kx5tfyd', # facebook
|
||||
... 'duckduckgogg42xjoc72x3sjasowoarfbgcmvfimaftt6twagswzczad', # ddg
|
||||
... 'zkaan2xfbuxia2wpf7ofnkbz6r5zdbbvxbunvp5g2iebopbfc4iqmbad', # hks
|
||||
... ]
|
||||
|
||||
We wil expect to get back the hidden service version, the descriptor-lifetime
|
||||
and then the descriptor-signing-key-cert:
|
||||
|
||||
>>> introduction_points.iMain(lKNOWN_ONIONS) #doctest: +ELLIPSIS +NORMALIZE_WHITESPACE
|
||||
hs-descriptor 3
|
||||
0
|
||||
|
||||
hs-descriptor 3
|
||||
descriptor-lifetime ...
|
||||
<BLANKLINE>
|
||||
|
||||
@ -69,11 +116,31 @@ The following provides a summary of your relay's inbound and outbound connection
|
||||
You must be root or tor to run this:
|
||||
relay_connections.iMain(["--ctrlport", "9051"])
|
||||
|
||||
## outdated_relays
|
||||
## connection_resolution Connection Resolution
|
||||
|
||||
Connection information is a useful tool for learning more about network
|
||||
applications like Tor. Our stem.util.connection.get_connections() function
|
||||
provides an easy method for accessing this information.
|
||||
|
||||
>>> print("connection_resolution", file=sys.stderr)
|
||||
>>> import connection_resolution
|
||||
>>> connection_resolution.iMain() #doctest: +ELLIPSIS +NORMALIZE_WHITESPACE
|
||||
0
|
||||
|
||||
INFO Our platform supports connection resolution via: ...
|
||||
<BLANKLINE>
|
||||
|
||||
## outdated_relays List Outdated Relays
|
||||
|
||||
Time marches on. Tor makes new releases, and at some point needs to drop
|
||||
support for old ones. Below is the script we used on ticket 9476 to reach out
|
||||
to relay operators that needed to upgrade.
|
||||
|
||||
>>> print("outdated_relays", file=sys.stderr)
|
||||
>>> import outdated_relays
|
||||
>>> outdated_relays.iMain() #doctest: +ELLIPSIS +NORMALIZE_WHITESPACE
|
||||
0
|
||||
|
||||
Checking for outdated relays ...
|
||||
<BLANKLINE>
|
||||
|
||||
@ -85,18 +152,9 @@ relay_connections.iMain(["--ctrlport", "9051"])
|
||||
A script by adrelanos@riseup.net to check what percentage of boostrapping
|
||||
tor is at. This fails under doctest but not from the cmdline
|
||||
|
||||
>> tor_bootstrap_check.iMain() #doctest: +ELLIPSIS +NORMALIZE_WHITESPACE
|
||||
NOTICE ...
|
||||
<BLANKLINE>
|
||||
>>> tor_bootstrap_check.iMain() #doctest: +ELLIPSIS +NORMALIZE_WHITESPACE
|
||||
0
|
||||
|
||||
control_port = stem.socket.ControlPort(address, port)
|
||||
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
|
||||
File "/usr/local/lib/python3.11/site-packages/stem/socket.py", line 503, in __init__
|
||||
self.connect()
|
||||
File "/usr/local/lib/python3.11/site-packages/stem/socket.py", line 172, in connect
|
||||
self._socket = self._make_socket()
|
||||
^^^^^^^^^^^^^^^^^^^
|
||||
File "/usr/local/lib/python3.11/site-packages/stem/socket.py", line 538, in _make_socket
|
||||
raise stem.SocketError(exc)
|
||||
stem.SocketError: Socket error: 0x01: General SOCKS server failure
|
||||
NOTICE ...
|
||||
<BLANKLINE>
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user