Thursday, November 29, 2012

越狱iPhone下 VPS+Shadowsocks+PAC翻墙

这篇已经过时,请参考这里的最新版

提要: 在这之前一直用SSH Tunnel 配合PAC翻墙,这也是一种大家最常用的方法,没什么大的问题,但是SSH原本不是用来做代理翻墙的工具,所以效率上并不是太好,而且作为iPhone来讲,后台运行一个SSH Tunnel会一直保持与SSH Server的连接,会严重影响iPhone的续航,而且由于手机经常会在edge/3G/wifi下切换,每次切换,SSH就会需要重新连接服务器,连接是需要花时间的,连不上还会一直连,所以很耗电。最近研究出来一个非常好的方法,耗电量和延迟会大大降低,实现了无缝翻墙。

实现条件:
a, 一个国外的VPS服务器
b, 一个越狱了的iPhone
c, 用Python建立SOCKS Proxy的代码Shadowsocks,VPS和iPhone上都要安装
d, PAC以及随时随地添加被GFW的网站到PAC的一个Bash脚本。

具体过程:

a 建立代理
a1  VPS服务器端安装Python程序,这个无需多说。
a2, iPhone上安装Python程序,最新版在这里,安装方法很简单:
打开iPhone的 mobileterminal, 或者ssh到iphone,运行下列命令:
wget https://yangapp.googlecode.com/files/python_2.7.3-3_iphoneos-arm.deb
dpkg -i python_2.7.3-3_iphoneos-arm.deb
安装完成
a3 下载Python代码 Shadowsocks,作者项目主页,点这里下载
a4 部署python代码 Shadowsocks,代码分为服务器端server.py和iPhone端local.py,server.py放在VPS服务器,local.py放在iPhone。
a4.1 在服务器端,修改server.py的代码,如下红色部分改成自己的其余地方不需要变动。
PORT = 9999
KEY = "123456789"
说明:PORT 随便什么端口都行,但要跟下面iPhone端的local.py相同。KEY 随便什么密码都行(为了安全起见,尽可能长且乱),但要跟下面iPhone端的local.py相同

然后在VPS服务器终端运行:
nohup python server.py > /dev/null 2>&1 &
这条命令会让这个python代码在后台运行且不输出任何历史记录。


a4.2 在iPhone端,修改local.py的下面几个地方:
SERVERS = [
        ('yourvpsipaddress', 9999),
    ]

PORT = 8080
KEY = "123456789"
说明:
SERVERS:填入你的vps的ip地址和上面server.py设置的PORT。
PORT:是建立本地SOCKS代理的端口,比如我设置8080,那么建立的SOCKS代理就是 127.0.0.1:8080
KEY要跟server.py里面的一致
然后在iPhone下面运行:
nohup python local.py > /dev/null 2>&1 & 

好了,iPhone后台就已经建立了一个SOCKS代理127.0.0.1:8080,这个代理可以供下面要介绍的PAC文件使用。

b 建立iPhone用的PAC文件
PAC= Proxy Auto Config,就是自动代理,它的作用就是决定哪些网站直连,哪些网站走SOCKS代理
在iPhone终端(或者ssh进入iphone)下面运行以下命令:
su (取得root权限,需要输入密码,默认密码是alpine)
touch /var/root/pac (建立空白文件)
chmod 777 /var/root/pac (改变文件权限为任何程序可读可写可执行)
chown mobile:mobile /var/root/pac (改变文件的所有者和组为mobile)
然后用nano(或者vim)编辑这个pac文件:
nano -w /var/root/pac
复制下面的代码到这个文件并保存:
function FindProxyForURL(url, host)

var PROXY = "SOCKS 127.0.0.1:8080";
//added by hand
if (dnsDomainIs(host, "img.ly")) return PROXY;
if (dnsDomainIs(host, "googlevideo.com")) return PROXY;
if (dnsDomainIs(host, "github.com")) return PROXY;
if (dnsDomainIs(host, "igfw.net")) return PROXY;
if (dnsDomainIs(host, "t.co")) return PROXY;
if (dnsDomainIs(host, "webkit.org")) return PROXY;
if (dnsDomainIs(host, "limelinx.com")) return PROXY;
if (dnsDomainIs(host, "slingfile.com")) return PROXY;
if (dnsDomainIs(host, "sendspace.com")) return PROXY;
if (dnsDomainIs(host, "j.mp")) return PROXY;
if (dnsDomainIs(host, "myrepospace.com")) return PROXY;
if (dnsDomainIs(host, "xsellize.com")) return PROXY;
if (dnsDomainIs(host, "hackulo.us")) return PROXY;
if (dnsDomainIs(host, "saurik.com")) return PROXY;
if (dnsDomainIs(host, "thebigboss.org")) return PROXY;
if (dnsDomainIs(host, "fb.me")) return PROXY;
if (dnsDomainIs(host, "getfoxyproxy.org")) return PROXY;
if (dnsDomainIs(host, "4share.com")) return PROXY;
if (dnsDomainIs(host, "posterous.com")) return PROXY;
if (dnsDomainIs(host, "foursquare.com")) return PROXY;
if (dnsDomainIs(host, "twitpic.com")) return PROXY;
if (dnsDomainIs(host, "vimeo.com")) return PROXY;
if (dnsDomainIs(host, "mobile01.com")) return PROXY;
if (dnsDomainIs(host, "tiananmenmother.org")) return PROXY;
if (dnsDomainIs(host, "bannedbook.org")) return PROXY;
if (dnsDomainIs(host, "dwnews.com")) return PROXY;
if (dnsDomainIs(host, "ntdtv.com")) return PROXY;
if (dnsDomainIs(host, "soundofhope.org")) return PROXY;
if (dnsDomainIs(host, "boxun.com")) return PROXY;
if (dnsDomainIs(host, "epochtimes.com")) return PROXY;
if (dnsDomainIs(host, "fangbinxing.com")) return PROXY;
if (dnsDomainIs(host, "ruanyifeng.com")) return PROXY;
if (dnsDomainIs(host, "wuala.com")) return PROXY;
if (dnsDomainIs(host, "dupola.com")) return PROXY;
if (dnsDomainIs(host, "scribd.com")) return PROXY;
if (dnsDomainIs(host, "gfw.org.uk")) return PROXY;
if (dnsDomainIs(host, "chinadigitaltimes.net")) return PROXY;
if (dnsDomainIs(host, "kenengba.com")) return PROXY;
if (dnsDomainIs(host, "dbanotes.net")) return PROXY;
if (dnsDomainIs(host, "chinagfw.org")) return PROXY;
if (dnsDomainIs(host, "friendfeed.com")) return PROXY;
if (dnsDomainIs(host, "ijailbreaknow.com")) return PROXY;
if (dnsDomainIs(host, "ksu.edu.tw")) return PROXY;
if (dnsDomainIs(host, "vbird.org")) return PROXY;
if (dnsDomainIs(host, "pornhub.com")) return PROXY;
if (dnsDomainIs(host, "youporn.com")) return PROXY;
if (dnsDomainIs(host, "google.com.tw")) return PROXY;
if (dnsDomainIs(host, "mediawiki.org")) return PROXY;
if (dnsDomainIs(host, "wikitionary.com")) return PROXY;
if (dnsDomainIs(host, "wikimediafoundation.org")) return PROXY;
if (dnsDomainIs(host, "wikimedia.org")) return PROXY;
if (dnsDomainIs(host, "yahoo.com")) return PROXY;
if (dnsDomainIs(host, "yimg.com")) return PROXY;
if (dnsDomainIs(host, "flickr.com")) return PROXY;
if (dnsDomainIs(host, "dropbox.com")) return PROXY;
if (dnsDomainIs(host, "akamaihd.net")) return PROXY;
if (dnsDomainIs(host, "facebook.net")) return PROXY;
if (dnsDomainIs(host, "fbcdn.net")) return PROXY;
if (dnsDomainIs(host, "ggpht.com")) return PROXY;
if (dnsDomainIs(host, "gstatic.com")) return PROXY;
if (dnsDomainIs(host, "googleusercontent.com")) return PROXY;
if (dnsDomainIs(host, "goo.gle")) return PROXY;
if (dnsDomainIs(host, "feedburner.com")) return PROXY;
if (dnsDomainIs(host, "googlelabs.com")) return PROXY;
if (dnsDomainIs(host, "googlesyndication.com")) return PROXY;
if (dnsDomainIs(host, "chrome.com")) return PROXY;
if (dnsDomainIs(host, "android.com")) return PROXY;
if (dnsDomainIs(host, "chromium.org")) return PROXY;
if (dnsDomainIs(host, "keyhole.com")) return PROXY;
if (dnsDomainIs(host, "googlesource.com")) return PROXY;
if (dnsDomainIs(host, "googleapis.com")) return PROXY;
if (dnsDomainIs(host, "twimg.com")) return PROXY;
if (dnsDomainIs(host, "ytimg.com")) return PROXY;
if (dnsDomainIs(host, "gmail.com")) return PROXY;
if (dnsDomainIs(host, "blogger.com")) return PROXY;
if (dnsDomainIs(host, "blogspot.com")) return PROXY;
if (dnsDomainIs(host, "appspot.com")) return PROXY;
if (dnsDomainIs(host, "bit.ly")) return PROXY;
if (dnsDomainIs(host, "wikipedia.org")) return PROXY;
if (dnsDomainIs(host, "twitter.com")) return PROXY;
if (dnsDomainIs(host, "facebook.com")) return PROXY;
if (dnsDomainIs(host, "google.com.hk")) return PROXY;
if (dnsDomainIs(host, "youtube.com")) return PROXY;
//以上部分说明这些网站需要走SOCKS代理
if (isPlainHostName(host) ||
        shExpMatch(host, "*.local") ||
        isInNet(dnsResolve(host), "10.0.0.0", "255.0.0.0") ||
        isInNet(dnsResolve(host), "172.16.0.0",  "255.240.0.0") ||
        isInNet(dnsResolve(host), "192.168.0.0",  "255.255.0.0") ||
        isInNet(dnsResolve(host), "127.0.0.0", "255.255.255.0")) return "DIRECT";
//以上部分告知本地的网络直连
                  return "DIRECT";
//以上部分告知如果代理走不通,就直连
}

OK,现在用于iPhone自动代理的pac文件建立好了,可以看到,上面添加了很多被GFW了的网站,这些都是我用一个脚本添加的,没有用gfwlist,因为我觉得gfwlist的语法写的太烂了,一点都不干净,而且漏掉了很多被GFW的网站,又不方便自己添加,所以我自己做了一个。
以上的pac文件每行一个代码,可以根据自己的需求删减。但是一定不要删掉红色代码部分,因为这个下面的脚本要用到。

c 添加新的被墙网站到这个pac文件
为此我做了一个脚本,下面是生成这个脚本的命令, 在iPhone终端:
su
touch /usr/bin/agfw
nano -w /usr/bin/agfw
复制下面的代码,并保存
#!/bin/bash
domain=$1
ed -s /var/root/pac << EOF
/\/\/added by hand/a
if (dnsDomainIs(host, "${domain}")) return PROXY;
.
w
EOF
说明:运行这个脚本需要安装ed这个软件

然后iPhone终端下面运行,让这个脚本可执行:
chmod +x /usr/bin/agfw
如果发现某个网站例如twitter.com你用safari打不开,那么只需要在iPhone终端下面运行:
agfw twitter.com
然后关闭safari(调出多任务,长按,xx掉safari)再运行一次safari就能立马打开了。
这个脚本的意思是,读取agfw这个命令后面的参数,按照脚本里面的一定的规则,写入到/var/root/pac文件中 //added by hand 这部分的下面。

d 让WIFI/EDGE/3G 使用PAC文件

好了,现在Python的服务端和客户端都正常运行了,SOCKS代理也有了,PAC文件也建立好了,怎么用呢?

WIFI:
很简单,在iPhone的wifi的HTTP代理设置部分,点自动,然后填入下面的地址:
file:///var/root/pac
注意是三个斜杠。

3G/EDGE:
需要修改iPhone的一个文件,用iFile打开:
/var/preferences/SystemConfiguration/preferences.plist
找到如下灰色部分,注意一定要找准地方,不能找错了,添加红色的代码:

<string>com.apple.CommCenter (ip1)</string>
 </dict>
 <key>Proxies</key> 
<dict>
 <key>ProxyAutoConfigEnable</key>
 <integer>1</integer> 
<key>ProxyAutoConfigURLString</key>
 <string>file:///var/root/pac</string>
 </dict> 
<key>UserDefinedName</key>
 <string>com.apple.CommCenter (ip1)</string>

保存后重启iphone


现在WIFI/edge/3G都能用上这个PAC文件了。

e 总结:

以上是全部过程,简单来讲就是两个东西
1 在服务器端和iphone端安装python程序并执行代理的python代码
2 在iPhone端设置PAC和使用PAC

f 优点:

1 可以看到,server.py 已经在vps上建立了一个代理接口,local.py负责连接这个接口,相比较ssh tunnel方式,这种没有登录过程,只有link的过程,所以反应相当迅速,且基本不耗电,local.py在iphone占用内存5M左右,要知道一个电话程序,常驻后台,占内存都10M了。
2 有了agfw这个脚本,随时随地添加被GFW的网站,不用等gfwlist
3 iPhone是手机,手机不免要经常切换网络,这个代理完全不受网络切换的影响,可以说是24h在线。相比较ssh tunnel和vpn来说,iphone如果切换了网络或者进入休眠状态,99%是需要重新连接的。
4 pac文件在iphone是全局的,并且我的这个pac文件好处就是,任何网站(包括pac里的list)如果socks代理走不通,会自动跳到直连,也就是说如果socks 代理挂了,原来你不用代理能打开的网站照样能打开。真正的无缝!


有任何问题,可以在twitter上找到我 @cattyhouse
END

Monday, November 26, 2012

iphone下面通过bash script 自动添加被墙网站到pac文件

最近研究pac文件疯了,我iphone里面有一个autoproxy2pac项目生成的pac文件

这个文件是基于gfwlist的,gfwlist也会有漏网之鱼,所以有时候需要手动添加

但是在iphone下面用ifile编辑这个pac文件是非常痛苦的事情,所以我研究是不是有bash script能更好的帮助我更新这个pac文件

研究结果出来了,完全可行,感谢 irc.freenode.net  #bash 频道的三位国外大神的帮助

首先几个前提:
1 我已经有一个基础的 pac文件位于 /var/root/ap , 且权限为 777,所有者和组为 mobile,所有手动添加的被墙网站我都会放在文件里面一句 //added by hand 下面。(注意下面的脚本用到了这句话,以确保加入到pac的代码能在合适的位置)
2 说到bash,那肯定是要在命令行下面执行的,所以需要ssh进入iphone
3 这个script需要用到ed,所以安装ed,用 apt-get ed


脚本内容:

#!/bin/bash
domain=${1//./\\.}
ed -s /var/root/ap << EOF
/\/\/added by hand/a
if(/\.${domain}/i.test(url)) return PROXY;
if(/^[\w\-]+:\/+(?!\/)(?:[^\/]+\.)?${domain}/i.test(url)) return PROXY;
if(/^https?:\/\/[^\/]+${domain}/i.test(url)) return PROXY;
.
w
EOF


将以上内容保存到 /usr/bin/upac
并运行 chmod +x /usr/bin/upac

以后要添加被墙网站到pac 就直接终端运行:

upac twitter.com
upac google.com
upac google.com.hk
upac bit.ly

等等等等!!!

我的PAC文件,有兴趣可以以此为基础添加今后可能会被墙的网站

https://www.dropbox.com/s/u6u6rsy5m22jf8u/ap

update:
已经有更简洁的方式了,不需要依赖任何gfwlist 见:
http://catty-house.blogspot.com/2012/11/iphonevpspythonpac.html






Thursday, November 22, 2012

windows 7 wifi 热点

目的:

将windows 7 PC的有线连接共享给无线网卡,同时让无线网卡作为AP,供iPhone使用。

方法:

以下命令逐条执行(需administrators组权限):
netsh wlan set hostednetwork mode=allow
netsh wlan set hostednetwork ssid=yourssid key=yourpasswd keyUsage=persistent
netsh wlan start hostednetwork
此时 位于 Control Panel\Network and Internet\Network Connections 会出现一个:
Wireless Network Connection 2

然后到 Local Area Connection 属性界面,开启共享,共享给 Wireless Network Connection 2

用iPhone连接此无线即可上网。

Monday, October 15, 2012

iPhne/iPad 通过SSH终极翻墙解决方案

此文写的比较简洁,并没有将所有细节都写出来,相信在PC上翻墙过的人,都能看懂,某些地方看不懂的,自行google一下相关知识吧。
有朋友说道goagent,这个东西首先用的是google app engine,但是gae本身就不稳定,经常被墙,而且goagent需要安装一堆东西。
此方法通过autossh连接的tunnel即使在mobileterminal被关闭的情况下,连接还有效,甚至respring了,连接还有效。只是重启了之后才需要重连,非常稳定的说。
用过很多种翻墙的工具,本人觉的SSH是目前仅次于VPN的最安全,最快速,最稳定的翻墙方式。

准备工作:

1 越狱
2 SSH帐号一枚
3 安装mobile terminal, openssh, automatic ssh,iFile.

配置过程:

1 建立ssh socks tunnel:
1.1 生成id_rsa,放到到 /var/mobile/.ssh/ 以便连接ssh无需输入密码
1.2 在mobile terminal下运行 ssh username@yoursshserver.com 生成know_hosts文件
1.3 在mobile terminal下运行autossh -M 20000 -D 9090 -Nfq username@yourserver.com 建立不会中断的ssh socks tunnel

2 利用gfwlist生成自动代理pac文件

2.1 配置好google chrome的插件switchysharp,保证chrome能利用gfwlist翻墙
2.2 在switchysharp配置里面导出成pac文件,比如sp.pac
2.3 用文本编辑器编辑 sp.pac,替换掉里面的 ‘SOCKS5 127.0.0.1:9090’ 为 “SOCKS 127.0.0.1:9090”  (PS: 不这样做的话,iphone上使用这个pac会有问题)
2.4 将sp.pac 放入iphone的 /var/root/
2.5 用iFile编辑sp.pac 属性,将用户,组,其他的权限全部设置为可读可写可执行



2 生成pac文件 (见这里b,c部分)

3 将pac植入 edge/3G的配置文件中
3.1  用iFile编辑文件: /private/var/preferences/systemconfiguration/preferences.plist
在如下位置插入红色部分代码:

<string>com.apple.CommCenter (ip1)</string> 
</dict> 
<key>Proxies</key>  
<dict> 
<key>ProxyAutoConfigEnable</key> 
<integer>1</integer>  
<key>ProxyAutoConfigURLString</key> 
<string>file:///var/root/pac</string> </dict> 
<key>UserDefinedName</key> 
<string>com.apple.CommCenter (ip1)</string>

3.2 重启iOS设备

4 上网设置:

无论哪种方式上网,首先运行: autossh -M 0 -D 9090 -Nfq username@yourserver.com(或者ip地址)

edge/3G 上网:试着打开下facebook,测试成功!

wifi 上网:连接wifi,在wifi设置里面,找到自动代理,填入: file:///var/root/pac

注意事项1:

在ssh连接部分,暂时无法实现edge/3g 与 wifi自动切换,意思就是,有2种情况:
1 edge打开wifi关闭情况下,连接autossh,如果再打开wifi,这时候,国内流量走的是wifi,而被墙网站走的是edge流量,此时只需要在mobile terminal下面执行 killall autossh,再运行上文提到的autossh连接命令,这时候,所有流量都走wifi。

2 wifi和edge同时开启,连接autossh,此时所有流量都走wifi,但是如果在此时把wifi关闭,由于autossh无法自动切换到edge连接上去,此时的socks tunnel实际上是没有建立成功的,用edge只能访问国内网站,被墙的会因为找不到代理接口而无法访问,但还是如 1提到的解决方法,先kill掉autossh再重连。

这是目前此方法唯一的缺点,其他的都工作的很好,因为pac是基于gfwlist转换而来的,所以能达到gfwlist的效果,也就是被墙网站走ssh,没有被墙网站不走ssh,保证了所有网站可访问,同时保证了速度!

update 1:

ssh 有个配置选项可以解决网络切换的问题
编辑iPhone/iPad下的 /etc/ssh/ssh_config
添加如下代码
ServerAliveInterval 10
如果ssh在30s内没有数据传输,就会自己中断,autossh就会检测到,于是重连。所以在wifi切换到edge的时候,或者一个wifi切换到另外一个wifi的时候,都可以自行切换


update 2 : 如果开启了 ServerAliveInterval 则可以关闭TCPKeepAlive 同样编辑iPhone/iPad下的 /etc/ssh/ssh_config
添加: TCPKeepAlive no
同时可以设置 autossh的参数 -M 0 (替代原来的-M 20000)


注意事项2:
pac 文件一定要放到 /var/root/ 文件夹下面,经过n此测试,不放在这里,很多程序便无法读取到这个pac文件。也许是iOS的sandbox在作怪。网上有很多教程把这个文件放在/var/mobile 是不行的,但是他们居然还敢发文。。。

技巧:
上面连接autossh的命令比较长,在iphone下面输入会比较麻烦,还好 mobileterminal有shortcut功能,可以将这段代码放到shortcut里面去,下次只需要触摸下菜单,回车就运行了。其他需要在mobileterminal下面执行的命令以此类推。 update 3

其实iphone也可以用alias的,我现在已经不怎么用以上的mobile terminal快捷方式了
alias在此处设置 /etc/profile.d/coreutils.sh
alias proxy = 'autossh -M 0 -D 9090 -Nfq username@yourserver.com
然后保存,再在iPhone/iPad 上运行:
source /etc/profile.d/coreutils.sh
然后只需要运行
proxy  
就能启动ssh tunnel

Sunday, July 29, 2012

script that automatically mount flash disk and execute commands on plugged in (插入优盘自动挂载并执行命令)

Tags: udev, UUID.

1 Find out unique ID of the flash disk for udev :
$ udevadm info -a -p  $(udevadm info -q path -n /dev/sdc) |grep  serial
Here is the output:
serialATTRS{serial}=="2004290613079860C679"
(change /dev/sdc for your condition)

2 create udev rules
$ sudo vim /etc/udev/rules.d/81-sandisk.rules
Put the following in this file :
KERNEL=="sd*", ATTRS{serial}=="2004290613079860C679", SYMLINK+="sandisk", RUN+="/bin/bash /home/j/script/sandisk.sh"

3 Find out the unique ID of the flash disk for linux filesystem
ls /dev/disk/by-uuid/
Here is one of the output:
48DD-2448 -> ../../sdc1

4 Create a script
$ cd ~/script/ (note this path must be in $PATH)
$ vim sandisk.sh
Put the following into the script:
#!/bin/bash
device=`ls /dev/disk/by-uuid/48DD-2448 -l | awk -F/ '{print $NF}'`  #assign a variable to $device, because the location of flash disk changes often, sometimes /dev/sdb, sometimes /dev/sdc...
sudo mount -t vfat /dev/$device /mnt/sandisk/ # mount the flash disk
# add your stuff below, ie, tar /etc/ ~/ and mv to the flash disk
# script END
4.1 $ sudo chmod +x sandisk.sh

5 Point:
5.1 what? mount and execute commands as flash disk be blugged in
5.2 why? udev and filesystem both has it's unique id for a special disk, that makes sense
5.3 connection between UUID and udev is possible :)
5.4 this script will work only on THE flash disk, because udev attrs serial and uuid are UNIQUE

Have Fun!

Source:
1 udev
2 uuid



Saturday, July 21, 2012

在DD-WRT下面建立 SSH Tunnel (Socks5 Dynamic Port Forwarding) 翻墙

在DD-WRT下面建立 SSH Tunnel (Socks5 Dynamic Port Forwarding)

1 看标题就知道了,通常情况下建立SSH Tunnel都是用一些电脑上的软件,比如bitvise tunnelier,putty,myentunnel,以及Linux和OS X上的openssh,现在我要在安装了DD-WRT的路由器上建立,这样无论你连接路由器的设备是什么,都可以很方便的用上这个Tunnel翻墙或者看一些国内无法访问的网站。

2 首先需要的软件和硬件:
 2.1 一个位于国外的服务器,且提供ssh接入,这里假设为 server.com, 用户名密码分别为: username, password
 2.2 一台刷了DD-WRT的路由器,这里假设路由器的ip地址为 192.168.2.1,路由器能够连接外网
 2.3 路由器里面需要安装的软件 zlib, libopenssl,openssh-client,autossh (顺次安装)
 2.4 安装这些软件的工具: ipkg (DD-WRT自带)
 2.5 安装这些软件的条件:开启jffs支持,进入dd-wrt网页界面-管理-jffs开启(因为dd-wrt的系统是只读的,装了任何软件重启就消失了,而jffs是将路由器的空闲空间挂在到dd-wrt上,第三方软件都装在这里)

3 安装软件
 3.1 telnet 192.168.2.1 or ssh root@192.168.2.1,两种方式都可以登入dd-wrt内部,用户名为root,密码为设置的路由器密码
 3.2 cd /jffs && mkdir -p tmp/ipkg && ipkg update
 3.3 ipkg -force-depends  install zlib libopenssh (这两个软件自动安装)
 3.4 wget http://downloads.openwrt.org/whiterussian/packages/openssh-client_4.4p1-1_mipsel.ipk && ipkg -force-depends install openssh-client_4.4p1-1_mipsel.ipk (这个软件要手动安装且加上 -force-depends,否则会出错)
 3.5 wget http://downloads.openwrt.org/backports/rc5/autossh_1.3-1_mipsel.ipk && ipkg -force-depends install autossh_1.3-1_mipsel.ipk  (同上原因)
 3.6 以上软件都安装在 /jffs/usr/bin/

4 配置dd-wrt端的ssh
 4.1 配置有点纠结,因为autossh和openssh是作为第三方软件安装的,且安装路径不一定在系统的path里面,所以所有命令的运行都要指定绝对路径
 4.2 先运行一个ssh命令试试看是否能够作tunnel
 /jffs/usr/bin/ssh -D 192.168.2.1:7070  username@server.com
等几秒,输入password,连接成功,表示可以连接
 4.2 总不能每次都输入密码把,所以这里要建立一个 id_rsa文件 (详见 ssh-keygen),且放到/jffs/etc/ssh/这里,然后无须输入密码实现tunnel的ssh命令就变成这样:
  /jffs/usr/bin/ssh -D 192.168.2.1:7070 -Nfqn -i /jffs/etc/ssh/id_rsa username@server.com,加入了几个参数,这样程序就后台运行,且不执行其它命令。
 4.3 openssh的命令是不支持断线重新连接的,所以这里需要 autossh,首先4.1提到的,要先定义autossh能够使用的ssh的绝对路径,这里用export:
 export AUTOSSH_PATH="/jffs/usr/bin/ssh" ,然后运行:
 /jffs/usr/bin/autossh autossh -M  20000 -D 192.168.2.1:7070 -Nfqn -i /jffs/etc/ssh/id_rsa username@server.com
4.4 综合以上,执行一个ssh tunnel需要敲入两次命令,一次是export 定义变量,一次是autossh,为了方便,这里建立一个脚本文件:
 vi /jffs/usr/bin/startssh.sh 里面内容如下:
 #! /bin/sh
 export AUTOSSH_PATH="/jffs/usr/bin/ssh"
 /jffs/usr/bin/autossh  -M  20000 -D 192.168.2.1:7070 -Nfqn -i /jffs/etc/ssh/id_rsa username@server.com
 保存后让这个脚本变成可执行文件:
 chmod +x  /jffs/usr/bin/startssh.sh
4.5 ok,基本上成功了要启动ssh tunnel,只需要运行 /jffs/usr/bin/startssh.sh
4.6 路由器重启了怎么办?将以上的脚本改名为 startssh.startup 放入: /jffs/etc/config/ 下面,路由器开机就会自动启动,注意扩展名(参考这里

5 电脑连接上路由器之后的一些代理设置:
 firefox : 安装 foxyproxy,代理设置为 socks5 192.168.2.1 端口 7070
 chrome: 安装 switchy, 代理设置为  socks5 192.168.2.1 端口 7070

6 ipad,iphone 也可以用的上吗?
当然,这里要用到pac文件,将ssh tunnel的socks5代理转换为http代理,方法如下
 6.1 生成文件 pac.pac ,内容如下:
   
function FindProxyForURL(url, host) 
return "SOCKS 192.168.2.1:7070"; 
  6.2 将这个pac.pac文件保存到http web服务器上去,保证能访问,比如保存到这个地方:
 
 http://server.com/pac.pac
  6.3 打开iphone/ipad的wifi设置,进入你连接的哪个wifi设置,设置自动代理,地址填入:
 http://server.com/pac.pac

至此,所有连接到这台dd-wrt的路由器的设备,都可以无缝的翻墙了!


7 补充说明:

另外的方式启动脚本
建立文件 abc.sesbutton
内容:

#! /bin/sh
 export AUTOSSH_PATH="/jffs/usr/bin/ssh"
 /jffs/usr/bin/autossh  -M  20000 -D 192.168.2.1:7070 -Nfqn -i /jffs/etc/ssh/id_rsa username@server.com
将这个文件放入 /jffs/etc/config/
然后就可以通过按路由器上的那个一键加密的键启动这个脚本
参考这里
试过了 wanup, startup,prewall 等方式都不行。

update:

DDWRT真的不适合干这事情,还是openwrt方便

Awesome Gentoo

Awesome Gentoo!
it's super fast! stable! cute!
with firefox, google chrome, fluxbox, openbox installed
only 4GB for normal usage!