Tor.NETを使ってC#からTorしてみる

# Tor.NET
Torネットワーク管理ライブラリ
[Tor.NET - A managed Tor network library - CodeProject](http://www.codeproject.com/Articles/1072864/Tor-NET-A-managed-Tor-network-library)
> A managed library to launch and/or connect to the Tor network for SOCKS5 communications, and for middle-man proxy hosting.

# Tor
言わずと知れた通信経路匿名化ソフトウェア
[Tor Project: Anonymity Online](https://www.torproject.org/)
[Tor - Wikipedia](https://ja.wikipedia.org/wiki/Tor)

[Tor.NET](http://www.codeproject.com/Articles/1072864/Tor-NET-A-managed-Tor-network-library)のページでもTor自体やプロトコルについての解説があります。

# 使ってみよう

とりあえずは接続ができることを確認するコードを書く。

## 準備

### Tor.NET
[Tor.NET - A managed Tor network library - CodeProject](http://www.codeproject.com/Articles/1072864/Tor-NET-A-managed-Tor-network-library)よりダウンロード
TorプロジェクトをReleaseビルドしておく。

### Tor
Torの実行ファイルと国とIPをひも付けているファイルを[Download Tor](https://www.torproject.org/download/download.html.en)よりダウンロード（Microsoft Windows - Expert Bundle）

```
+---Data
|   \---Tor
|           geoip
|           geoip6
|
\---Tor
        libeay32.dll
        libevent-2-0-5.dll
        libevent_core-2-0-5.dll
        libevent_extra-2-0-5.dll
        libgcc_s_sjlj-1.dll
        libssp-0.dll
        ssleay32.dll
        tor.exe
        zlib1.dll
```

### コード
[ipify - A Simple Public IP Address API](https://www.ipify.org/)
:arrow_up: のAPIを利用し、Tor経由と直接接続した際のレスポンスを確認してみる。

```csharp:Program.cs
using System;
using System.Diagnostics;
using System.IO;
using System.Net;
using System.Net.Http;
using Tor;
using Tor.Config;
using static System.Console;

namespace TorClient
{
    class Program
    {
        static void Main(string[] args)
        {
            using (var client = CreateClient())
            {
                // Tor経由
                GetIPAddress(client);
                // 直接接続
                GetIPAddress();
                ReadKey();
            }
        }

        private static void GetIPAddress(Client client = null)
        {
            var ch = new HttpClientHandler();

            if (client != null)
            {
                // ch.Proxy = client.Proxy.WebProxy;
                // ↑でイケルと思ったらproxyスルーされたので↓でとりあえず
                ch.Proxy = new WebProxy(string.Format("http://127.0.0.1:{0}", client.Proxy.Port));
                ch.UseProxy = true;
            }
            using (var hc = new HttpClient(ch))
            using (var task = hc.GetStringAsync("https://api.ipify.org/"))
            {
                task.Wait();
                WriteLine(task.Result);
            }
        }

        private static Client CreateClient()
        {
            // 古いTorインスタンスをkill
            Process[] previous = Process.GetProcessesByName("tor");


            if (previous != null && previous.Length > 0)
            {
                foreach (Process process in previous)
                    process.Kill();
            }

            // 接続設定
            ClientCreateParams createParams = new ClientCreateParams();
            createParams.ConfigurationFile = "";
            createParams.DefaultConfigurationFile = "";
            createParams.ControlPassword = "";
            createParams.ControlPort = 9051;
            createParams.Path = Path.Combine(Environment.CurrentDirectory, @"Tor\Tor\tor.exe");

            createParams.SetConfig(ConfigurationNames.AvoidDiskWrites, true);
            createParams.SetConfig(ConfigurationNames.GeoIPFile, Path.Combine(Environment.CurrentDirectory, @"Tor\Data\Tor\geoip"));
            createParams.SetConfig(ConfigurationNames.GeoIPv6File, Path.Combine(Environment.CurrentDirectory, @"Tor\Data\Tor\geoip6"));

            // クライアント生成
            var client = Client.Create(createParams);

            // Router取得
            client.Status.GetAllRouters();

            return client;
        }
    }
}
```

#### 構成
Tor.dll(TOR.NET)は参照追加しておく。

```
|   App.config
|   Program.cs
|   TorClient.csproj
|
+---lib
|       Tor.dll
|       Tor.pdb
|
\---Tor
    +---Data
    |   \---Tor
    |           geoip # 接続設定のSetConfig - GeoIPFile
    |           geoip6 # 接続設定のSetConfig - GeoIPv6File
    |
    \---Tor
            libeay32.dll
            libevent-2-0-5.dll
            libevent_core-2-0-5.dll
            libevent_extra-2-0-5.dll
            libgcc_s_sjlj-1.dll
            libssp-0.dll
            ssleay32.dll
            tor.exe # 接続設定のPath
            zlib1.dll
```