因為在樹莓派上寫腳本會有點卡,
就先在臺式機上寫寫看, 還能邊寫邊用瀏覽器查...
連校園網, 這次是用腳本實現的, 上次是用一個下載的軟件, 但是那個被我重新裝之后, 就不能用了,因為在以前沒有記錄下怎么配置的過程,
那現在, 用現在的方法,可以做到開機就連上網絡,
首先 先說一下, 這個撥號的過程,
- 學校的局域網內有個 192.168.254.1 的服務器是作為l2tp的server.
學生作為client, 可以和他建立vpn, 也就是l2tp隧道. - 在隧道建立完成之后, 會使用ppp協議作為載體, 把隧道內傳輸的數據按照ppp來打包, 然后這些ppp包就從這個隧道中發(fā)到server. 從而實現上網.
有個鏈接: 解釋了為啥還是在使用l2tp作為上網的認證手段,而不是用ppop啥的:
https://www.zhihu.com/question/26810403
簡單的說, 就是認證用戶是用ppp協議的, 但是宿舍到server不是一條線的, 中間要經過好多個路由啥的, 就不是peer to peer的了, 那么ppp的包就過不去了, 最后要借助l2tp這個在ip層的協議來幫助發(fā)送ppp包.
然后再來看怎么配置:
要下的軟件:
要建立l2tp連接, 那么就要用xl2tpd這個軟件.
要用ppp協議發(fā)送包, 那么就要用pppd這個軟件.
( 如果l2tp是要加密的話, 好像還要下載其他的東西, 但是我發(fā)現, 聯通的這個東西, 是不加密的, 密碼都是明文發(fā)送的......)
你可以用apt-get 來下載這兩個包.
給軟件的配置文件:
xl2tpd 的配置文件:
/etc/xl2tpd/xl2tpd.conf
內容:
[lac testvpn]
name = test
lns = 192.168.254.1
pppoptfile = /etc/ppp/peers/testvpn.l2tpd
ppp debug = yes
第一個name,這個選項不曉得干啥的,但是例子上有..
第二個就是遠端服務器的ip.
第三個是ppp協議的配置文件, 因為xl2tpd在建立完成隧道之后, 就會自己啟動pppd, 所以他就需要知道pppd的配置文件在哪里.
第4個是 是否要輸出ppp的詳細運行信息.
更多的有關配置的信息可以在這里找到:https://linux.die.net/man/5/xl2tpd.conf
配置是分lac 和lns和global的, global和lns的配置不用去管, lns是服務器的配置信息.
因為xl2tpd還是可以用作服務端的, 我們就只用到了作為客戶的功能.
然后就是要設置 pppd 的配置文件:
/etc/ppp/peers/testvpn.l2tpd
內容:
remotename testvpn
user "賬號"
passwrod 密碼
unit 0
nodeflate
noauth
persist
noaccomp
maxfail 5
usepeerdns
debug
這些參數可以用 man pppd來查詢,
這個option文件是我抄網上的教程后修修改改出來的,
有些東西也不知道為啥....
我發(fā)現, 我們的機器的ip和dns都是需要server告訴我們的, 所以加了 usepeerdns.
然后ppp 有兩種認證的方式PAP和CHAP, 我選的是PAP, 因為感覺chap比較高級, chap比較耗費運算??
這些認證過程可以/var/log/syslog文件中找到.
有個中文的翻譯:http://blog.csdn.net/chenliang0224/article/details/8572699
然后兩個文件設置完成之后, 就要啟動這個連接了.
首先啟動xl2tp:
xl2tpd -c /etc/xl2tpd/xl2tpd.conf -D
-c 是指定配置文件
你不加這個也可以, 因為xl2tpd的默認的配置文件就是這個目錄上的文件.
-D 是debug模式, 不加的話, xl2tpd就會變成后臺進程, 但可以用ps aux | grep xl2tpd 和 kill 殺死...
然后你就可以在當前的terminal中看到他的執(zhí)行情況了.
然后再發(fā)送連接指令給xl2tpd
echo 'c testvpn' > /var/run/xl2tpd/l2tp-control
這里的testvpn這個名字, 就是上面設置的remotename, 我不清楚這兩個名字是不是有關系的, 其實改一下就好知道, 但是太懶....
echo 'd testvpn' > /var/run/xl2tpd/l2tp-control 是斷開連接.
成功的話, 就可以在ifconfig中看到ppp0接口了.
如果不成功, 就需要查看日志來找出錯誤.
我碰到的大部分的錯誤是可以在 xl2tpd -D的那個terminal中可以看出來的,
我經常就是 ppp 的參數設置錯誤, 然后xl2tpd檢測到錯誤后就殺死了pppd啥的, 反正就改改配置文件后再來一邊試試看.
還有一個可以看到日志的地方就是 /var/log/message 或者 /var/log/syslog 文件.
你可以再開個窗口, 然后用 tail -f 看.
反正目標就是 看不到 fail的字樣. 要看到: 隧道成功建立和ppp認證成功.
這里是我的成功后的兩個日志的情況:

上圖是 syslog 的. 可以看到, 在l2tp連接建立之后, 就會有
Mar 8 18:08:11 dogegg-HP pppd[3618]: sent [LCP EchoReq id=0x2 magic=0x2a789e01]
Mar 8 18:08:11 dogegg-HP pppd[3618]: rcvd [LCP EchoRep id=0x2 magic=0x4dd4d216]
這樣子的收發(fā)信息, 這個是代表這個隧道是存在的,30s一次( 這個東西很重要, 和路由有關)
然后我們可以看到服務器發(fā)給我們, 我們的ip地址, 我們的主/次dns服務器地址, 還有他的地址.

上圖是xl2tpd進程的日志, 可以看到他一步步的把配置文件中的內容給解析出來, 如果有解析錯的, 那么肯定會打印出來的.
設置路由
這樣弄完之后, 網上的教程都說, 你就可以上網了, 但是我不行.....
因為是路由的問題.....
我們要讓電腦的所有流量都經過ppp0端口出去, 而不是原來的eth0啥的.
現在我們的情況是 我們和服務器連上了, 但是我們包還是從默認的路由默認的網關發(fā)送出去的.
用route -n看到的情況大概是這樣子的.
Destination Gateway Genmask Flags Metric Ref Use Iface
0.0.0.0 10.64.70.1 255.255.255.255 ?????????
10.64.70.0 0.0.0.0 255.255.255.0 U 100 0 0 enx000ec6d2bc57
101.68.75.84 0.0.0.0 255.255.255.255 UH 0 0 0 ppp0
169.254.0.0 0.0.0.0 255.255.0.0 U 1000 0 0 enx000ec6d2bc57
第一條的??參數是我忘記了... 就亂打上去.
destination是 0.0.0.0的那條是叫做default路由. 數據包不知道往哪里發(fā)的話, 就發(fā)那邊去.
我的路由表在 沒有連上ppp0之前就只有3個路由, 就是現在的去掉第三條的樣子.
最后一條169.254.0.0的是local-link, 查了百度, 也沒怎么弄清楚這是干啥的, 反正不影響.
如果想把流量都改了的話, 那么就應該把default給刪除再加上一條去ppp0的default,
但是, 并不是把所有的流量都給導過去, 我們和server的通訊是要走網卡的不能走ppp0.
所以, 就需要3條route命令來改:
echo 'add route to 192..'
route add -host 192.168.254.1 gw $getway dev enx000ec6d2bc57
echo 'del default'
route del default
echo 'add default to ppp0'
route add default gw $remote dev ppp0
這是腳本里面寫著的, 這樣子改完之后, 應該就好上網了.如果還不行...
可以試試看ping remote通不通. 然后ping那個dns服務器.
我本來以為加上 ping 的-I 參數 就可以跳過路由, 但是如果路由不對, 就算加上-I ppp0, ping的包好像也是不會順利的發(fā)送出去的.
下面是腳本:
#!/bin/bash
dir=/home/dogegg/Desktop/log.txt
#因為xl2tpd進程是自動隨著系統開機而運行的, 就不用寫入腳本了.
echo 'c testvpn' > /var/run/xl2tpd/l2tp-control
#在發(fā)送完連接命令之后, 就每隔2s檢查下有沒有ppp0的接口在ifconfig中出現. 次數超過10次就exit.
count=0
while [ $count -lt 10 ]; do
haveppp0=`ifconfig | grep ppp0`
if [[ $haveppp0 != "" ]];then
break
fi
echo 'check ppp0 is exist, time:'$count > $dir
let count=count+1
sleep 2s
done
if [[ $count == 10 ]];then
echo 'time out!' >> $dir
exit 0
fi
echo 'ppp0 is exist!' >> $dir
#匹配出 網關的地址.
getway=`ifconfig enx000ec6d2bc57 | grep 'inet addr'`
reg='.*inet addr\:([0-9]+\.[0-9]+\.[0-9]+\.)([0-9]+).*'
if [[ "$getway" =~ $reg ]];then
pre=${BASH_REMATCH[1]}
last=${BASH_REMATCH[2]}
else
exit 222
fi
getway=$pre'1'
# 匹配出 遠程server的地址
remote=`ifconfig ppp0 | grep 'P-t-P'`
reg='.*P-t-P:([0-9]+\.[0-9]+\.[0-9]+\.[0-9]+).*'
if [[ "$remote" =~ $reg ]];then
remote=${BASH_REMATCH[1]}
else
exit 223
fi
### debug!!
echo 'the getway is '$getway >> $dir
echo 'the remote is '$remote >> $dir
###
#改改路由:
echo 'add route to 192..' >> $dir
route add -host 192.168.254.1 gw $getway dev enx000ec6d2bc57
echo 'del default' >> $dir
route del default
echo 'add default to ppp0' >> $dir
route add default gw $remote dev ppp0
exit 0
最后就是配置開機了
在/etc/rc.local
文件中加入運行腳本的語句
如果 想知道一些出錯的信息, 我用的是笨辦法, 就是讓我的腳本里面的echo把字符串輸出到一個桌面的文件中($dir), 但是好像網上有比較優(yōu)雅的辦法, 看上去是改輸出流啥的:
exec 2> /tmp/rc.local.log
exec 1>&2
set -x
不懂.... 用不來, 但是在 /tmp/rc.local.log里面可以看到:
+ ./home/dogegg/Desktop/checkppp0.sh
+ exit 0
下一步就是把這個東西轉到樹梅pi上.