Miskatonic University Press

Upgrading my Tor bridges

conforguration emacs privacy tor

The Tor Project announced the release of version of the Tor server, which meant it was time for me to upgrade the two relays I run, one of which I set up last week.

In brief

Here’s my Conforguration method:

  • I upgrade the version number to
  • I hit C-c C-v t to “tangle” a shell script
  • On a code block for copying scripts, I hit C-c C-c
  • I ssh to the remote machine
  • I run conforg/scripts/tor-install-system.sh
  • I run conforg/scripts/tor-run.sh

Aside from the time to compile the code, this takes under one minute.

The explanation

As I said in my earlier post, I use my own Conforguration tool to handle this sort of thing. It uses Org to edit and manage shell scripts that I can run locally or on remote servers. The list above is a great example of how Org can make things much easier if you’ve set things up just the way you want them, while remaining cryptic to non-Org users. Here’s an explanation of most of what’s going on.

In the Tor section of Conforguration, first I set a variable with the version number I want to install. Today I updated it.

| |

Under Install, I have this code block:

#+begin_src shell :tangle conforg/scripts/tor-install-system.sh :shebang "#!/bin/bash" :var TOR_VERSION=TOR_VERSION
cd /usr/local/src/tor/
curl --location --remote-name https://dist.torproject.org/tor-${TOR_VERSION}.tar.gz
tar --extract --verbose --gunzip --file tor-${TOR_VERSION}.tar.gz
cd tor-${TOR_VERSION}
./configure && make && sudo make install
echo "Now run ~/conforg/scripts/tor-run.sh"

(I say tar --extract --verbose --gunzip --file instead of tar xzvf because I like to use the most readable arguments in scripts. I do use short forms when I’m typing at the command line.)

The :tangle argument to the code block is covered under extracting source code in the manual. When I hit C-c C-v t (which runs org-babel-tangle) then that chunk of code is exported to the file named by the argument. It’s given a shebang and the TOR_VERSION variable is passed into it, resulting in this:

  declare -a TOR_VERSION=( '' )
  cd /usr/local/src/tor/
  curl --location --remote-name https://dist.torproject.org/tor-${TOR_VERSION}.tar.gz
  tar --extract --verbose --gunzip --file tor-${TOR_VERSION}.tar.gz
  cd tor-${TOR_VERSION}
  ./configure && make && sudo make install
  echo "Now run ~/conforg/scripts/tor-run.sh"

Now I need to get that script to one of the machines where I run a Tor relay. In my ssh configuration it’s aliased to the name tor, so I go down to this section of Conforguration and hit C-c C-c on the code block to execute:

Screenshot from Conforguration
Screenshot from Conforguration

In plain text:

:header-args: :var hostname="tor"

#+begin_src shell :results silent :noweb yes

The angle bracket thing is noweb syntax, which allows me to use this snippet of code that’s set up earlier in the file, with the hostname variable passed in:

#+NAME: install-conforg-remotely
#+begin_src shell
rsync --archive --compress --delete ~/src/conforguration/conforg/ ${hostname}:conforg/
ssh ${hostname} "conforg/dotfiles/link-dotfiles.sh"

That pushes the scripts and dot files to the other machine and freshens the symlinks for all the dot files. In other words, it refreshes everything on the remote machine—all by hitting C-c C-c.

Now ~/conforg/scripts/tor-install-system.sh is on the other machine. I could execute it remotely from inside Conforguration, but it takes a while to run, so I like to log in to the other machine and do it locally. I ssh over and run:


It downloads the source code and compiles it. When it’s done, it finishes up by installing files on the system, and then ends with:

make[1]: Leaving directory '/usr/local/src/tor/tor-'
Now run ~/conforg/scripts/tor-run.sh

I run:


This detects that a Tor tmux session is running, kills it off while waiting for the Tor daemon to die nicely, then sets it up again. When it starts fresh, the new Tor server is running.

Another way

For my bridge running on another machine, I could do the upgrade the same way, but to match how I’d installed it I did it like this (after upgrading the version number and pushing the commit to the repository):

  • cd src/conforguration
  • git pull
  • install/install.sh
  • ~/conforg/scripts/tor-install-system.sh
  • ~/conforg/scripts/tor-run.sh

There are other ways to handle configuration management and upgrading servers, but I’ve built one I really like.