我如何通过TOR路由TCP连接?

我正在读的是一个基本上是匿名聊天程序的torchat 。

这听起来很酷,所以我想尝试做我自己的。 首先我写了一个testing,以使用Http获取网页。 Sicne .NET不支持SOCKS4A / SOCKS5我用privoxy和我的应用程序工作。 然后我切换到TCP回声testing和privoxy不支持TCP,所以我search和安装6+代理应用程序(freecap,socat,freeproxy,委托是我可以记得从我的头顶,我也玩腻子BC知道它支持隧道和SOCK5),但我不能成功地让他们中的任何一个工作,更不用说让它运行我的HTTPtesting,privoxy轻松,无痛地做到了。

我可以使用什么来获得通过TOR的TCP连接? 我花了2个多小时没有成功。 我不知道我是否在寻找一个接力,隧道,货代,代理或代理链,这些都是在我的search中出现的。 我使用下面的configuration为.NET。 我需要TCP工作,但我第一次testing与http,因为我知道我有它使用privoxy工作。 我使用哪些应用程序和configuration来使TCP通过tor?

<?xml version="1.0" encoding="utf-8" ?> <configuration> <system.net> <defaultProxy enabled="true"> <proxy bypassonlocal="True" proxyaddress="http://127.0.0.1:8118"/> </defaultProxy> <settings> <httpWebRequest useUnsafeHeaderParsing="true"/> </settings> </system.net> </configuration> 

– 编辑 – 感谢Bernd我有一个解决scheme。 这是我写的代码。 这不是太好,但它的公平。

 static NetworkStream ConnectSocksProxy(string proxyDomain, short proxyPort, string host, short hostPort, TcpClient tc) { tc.Connect(proxyDomain, proxyPort); if (System.Text.RegularExpressions.Regex.IsMatch(host, @"[\:/\\]")) throw new Exception("Invalid Host name. Use FQDN such as www.google.com. Do not have http, a port or / in it"); NetworkStream ns = tc.GetStream(); var HostNameBuf = new ASCIIEncoding().GetBytes(host); var HostPortBuf = BitConverter.GetBytes(IPAddress.HostToNetworkOrder(hostPort)); if (true) //5 { var bufout = new byte[128]; var buflen = 0; ns.Write(new byte[] { 5, 1, 0 }, 0, 3); buflen = ns.Read(bufout, 0, bufout.Length); if (buflen != 2 || bufout[0] != 5 || bufout[1] != 0) throw new Exception(); var buf = new byte[] { 5, 1, 0, 3, (byte)HostNameBuf.Length }; var mem = new MemoryStream(); mem.Write(buf, 0, buf.Length); mem.Write(HostNameBuf, 0, HostNameBuf.Length); mem.Write(new byte[] { HostPortBuf[0], HostPortBuf[1] }, 0, 2); var memarr = mem.ToArray(); ns.Write(memarr, 0, memarr.Length); buflen = ns.Read(bufout, 0, bufout.Length); if (bufout[0] != 5 || bufout[1] != 0) throw new Exception(); } else //4a { var bufout = new byte[128]; var buflen = 0; var mem = new MemoryStream(); mem.WriteByte(4); mem.WriteByte(1); mem.Write(HostPortBuf, 0, 2); mem.Write(BitConverter.GetBytes(IPAddress.HostToNetworkOrder(1)), 0, 4); mem.WriteByte(0); mem.Write(HostNameBuf, 0, HostNameBuf.Length); mem.WriteByte(0); var memarr = mem.ToArray(); ns.Write(memarr, 0, memarr.Length); buflen = ns.Read(bufout, 0, bufout.Length); if (buflen != 8 || bufout[0] != 0 || bufout[1] != 90) throw new Exception(); } return ns; } 

用法

 using (TcpClient client = new TcpClient()) using (var ns = ConnectSocksProxy("127.0.0.1", 9050, "website.com", 80, client)) {...} 

Socks4a真的很简单。 你可以用5行代码手工完成socks4a。 看看袜子的RFC(或在维基百科更简单的解释)。

本质上,你只需要build立一个正常的TCP连接到socks代理(这意味着如果你只是连接到127.0.0.1端口9050,连接将被接受,然后你发送一个非常简单的请求在这个连接(例子给出RFC),然后在一段时间后,tor将会以8个字节来回答(第二个字节是状态,应该是90意味着成功)。

在这个连接上从Tor接收到成功的答案之后,你继续使用相同的连接,此时你已经通过这个套接字与另一方连接了,从现在开始,它的行为就像任何其他的TCP连接一样,您可以开始发送/接收,就像直接连接一样。

编辑:你不需要学习整个RFC,在维基百科上有一个很好的非常短的和完整的Socks 4a的描述(袜子5将是为你的需要矫枉过正,袜子4不能parsing主机名,所以4a是Tor的理想select) :

这是http://en.wikipedia.org/wiki/SOCKS#SOCKS4a