折腾起源
把自己从csdn上写的文章搬过来了喵!
最近偶然发现宿舍网虽然没ipv4,但是有ipv6地址,查了相关资料,还问了客服,发现宿舍里ipv6的地址能直接从公网访问。
客服回答
还有这种好事?好时代来临辣!
我随便建了个测速网站试了试,发现可以直接通过公网ip地址+端口访问,格式为[xxx:xxx:xxx:xx]:xxxx,如图
ipv6地址格式
ipv6访问的speedtest
当然我还得考虑本机当然可以直接访问这个网页,我用手机开5G流量试了一下,自然也是可
以连通 (现在开4G或者5G流量一般都自带ipv6)
这里测试结果就不放了,本人只是小小的宿舍50M带宽,放出来怕丢人。
既然公网IP来了,这不得弄个ddns伺候一下?
直接设置华硕DDNS,虽然会有ipv6地址ddns绑定,但是他会优先ipv4访问,我的ipv4地址是内网,这里只能想办法用单栈DDNS绑定的域名,于是开始折腾
设置ipv6
本来有点想略过ipv6设置的,但是因为本人也是小白,刚接触的时候找资料很麻烦,这里顺便一起写了吧。
首先简单的进路由器后台不用说了吧,好假设你不知道,win+r,输入cmd回车
输入
ipconfig
找到你的默认网关
这就是你路由器后台的地址,这里以我的路由器ac68u为例
打开浏览器输入192.168.50.1
输入账号密码以后进入路由器后台
点ipv6的设置
这里有两种,一种是你是光猫桥接,路由器拨号,一种是光猫拨号。
如果你是第二种,最好改光猫工作模式为桥接,省去后面不必要的麻烦,接下来以我这种校园网为例
我的校园网是第一种,但是之前我有试过这个路由器当二级路由,也就变成了第二种,这里先说第一种设置方法
联机类型选Native,接口选ppp,DHCP-PD打开,其他设置默认即可
如果你是第二种,联机类型改成passthrough,其他默认
应用之后随便找个测试ipv6连通性网站,我这里找的是ipw.cn
这里显示ipv6访问优先就可以了
如果你是第二种,也许不能正常获取ipv6地址,这种情况建议改桥接;或者有ipv6地址显示ipv4优先,这种情况可以尝试先访问ipv6.ipw.cn,如果可以获取到ipv6地址就不要再折腾了,如果不行再尝试如下设置
手动设置dns,我当时设置的是阿里的dns
2400:3200::1
2400:3200:baba::1
或者用这个公共的dns
240c::6666
240c::6644
我这里的网络是设置了以后,有时候连不上网,而且图片加载速度极慢,可能是我设置问题,还是建议改成第一种方案
至此成功获取ipv6地址,接下来开始第二步设置ddns单栈
DDNS设置部分
如果你是openwrt,ddns设置界面应该是有单ipv6的,直接套用就好。
如果你是华硕固件又不想太折腾刷openwrt,那我建议你刷梅林固件,因为梅林固件自带个crond服务,还有他的脚本,可以将代码套用到里面实现ddns
这里路由器的系统真的很让人烦躁,因为所有的东西基本都在tmp文件夹下,包括root文件夹,包括iptables设置,包括crond设置文件。我刚进来的时候真的束手无策,不知道怎么搞。之后我折腾出两种方法,都是基于ssh进入系统后写脚本
打开ssh端口及服务
华硕原固件也是可以打开的,在web管理界面下,高级设置–》系统管理–》系统设置–》启用ssh,默认端口是1025,账号密码默认就是你登陆web的账号密码
进入ssh界面
这里为了方便直接用powershell自带的ssh即可
ssh <你的用户名>@192.168.50.1 -p 1025
之后输入密码就进到后台了
如果想用xshell自己设置一下就行,会用xshell应该不用多说了。
方法一:套用jffs下自带的启动脚本
这个地方我是思路很清晰,但是不知道他自带的启动脚本在哪,百度半天才知道,最小linux系统真的很难用。
目录为:/jffs/scripts
这里我用的是wan-start这个脚本
cd /jffs/scripts
vi ./wan-start
不知道写什么?等会再说,先说方法二,因为按照程序思维这里不能放脚本,这里放了方法二就会报错的,要放在两个方法外面
方法二:在梅林固件默认启动脚本目录下自建脚本
这里是自己一边百度摸出来的,随便乱逛koolshare目录,看到有很多S开头和K开头的文件,熟悉linux的同学应该就知道这里是干啥的了,但是我不知道,我还百度了一下,命名格式一定要对才能自启,目录为:/jffs/.koolshare/init.d
脚本格式为:S+两位数字+任意名字.sh
例如我的:
脚本实现部分
话不多说,先直接上主逻辑
#!bin/sh
ip=$(curl ipv6.ipw.cn)
curl -s -X POST https://dnsapi.cn/Record.Modify -d 'login_token=123456,asdklqwejlkasczxcd&format=json&record_line=默认&domain_id=123123123&value='$ip'&record_type=AAAA&record_id=123123123&sub_domain=r'
解释一下,这里是先通过访问获取ipv6地址的网站获取ipv6地址,之后调用你域名的api实现ddns,相关api你要去看文档自己去实现,我这里只能以腾讯域名商dnspod为例(8块钱先买一个dns域名一年,这和花生壳的内网穿透域名不一样,这种方法是不限速的,只取决于你自己的带宽)
DDNS实现
dnspod文档网址
为了速成,这里先把必要的列出来
首先是每次请求必带的参数
login_token | String | 用于鉴权的 API Token。 | 是 |
下面是修改必带的参数
domain_id 或 domain | 是 | Integer 或 String | 分别对应域名ID和域名, 提交其中一个即可。 |
record_id | 是 | Integer | 记录ID。 |
record_type | 是 | String | 记录类型,通过API记录类型获得,大写英文,比如:A。 |
record_line | 是 | String | 记录线路,通过API记录线路获得,中文,比如:默认。 |
value | 是 | String | 记录值, 如 IP:200.200.200.200, CNAME: cname.dnspod.com., MX: mail.dnspod.com. 。 |
mx {1-20} | 是 | Integer | MX优先级, 当记录类型是 MX 时有效,范围1-20。 |
mx{1-20}如果你不是MX记录就不必要,这里我们是AAAA记录就不用管它
record_line_id | 否 | String | 线路的ID,通过API记录线路获得,英文字符串,比如:‘10=1’。record_line 和 record_line_id 二者传其一即可,系统优先取 record_line_id。 |
如果你的shell不支持中文,就把record_type换成record_line_id,默认对应的参数为0
请求网址和方法如下
这里为了避免麻烦,我们先创建一个AAAA记录便于之后修改,开始的值可以随便填,按ipv6的格式就行
login_token获取
网页右上角找到API密钥
既然他都说了就用DNSPod Token吧
创建密钥后显示如下
注意!login_token一定是ID+逗号+Token的形式写进请求body里,不然一定会返回登陆失败的code
domain_id获取
record_id获取
先修改一次记录,修改刚才创建好的AAAA记录,在操作日志里可以找到record_id
箭头指向括号内的就是record_id
接下来就简单了,拼接body即可
现成的如下
vi S20myddnsd.sh
#!bin/sh
ip=$(curl ipv6.ipw.cn)
curl -s -X POST https://dnsapi.cn/Record.Modify -d 'login_token=<数字>,<一串字母>&format=json&record_line=默认&domain_id=<域名id>&value='$ip'&record_type=AAAA&record_id=<你的记录id>&sub_domain=<你想要的域名开头>'
#我本人自己用的的可以往上翻就能看到
:wq保存退出以后记得修改脚本权限
chmod +x S20myddnsd.sh
踩坑阶段
设置好了脚本以后就开始试试能不能用了,先直接运行试试效果
/bin/sh /jffs/.koolshare/init.d/S20myddnsd.sh
由于是路由器直接用脚本发送请求,ipv6对应的地址就是路由器的地址,用手机5G网shell试试域名+端口能不能连
成功连上啦
再试试web远程网页管理,连不上捏😭😭
问题出在哪呢,我第一反应想到防火墙没关,于是关闭了ipv6的防火墙
再试试,还是连不上捏😭😭😭
但是ssh正常外网访问
重启也连不上,这里应该是梅林固件有问题,于是想到去看看ip6tables设置
打开ssh
ip6tables-save
很好,没远程管理的端口,加上就解决
ip6tables -I INPUT -p tcp -m tcp --dport 8443 -j ACCEPT
ip6tables-save #查看是否成功加入端口
注意这里一定要是-I而不是-A 不然会添加到-A INPUT -j DROP后面导致规则无效,除非你删除那条-A INPUT -j DROP
你也可以这样
ip6tables -L INPUT -n --line-number
得到DROP在第15号,删除它
ip6tables -D INPUT 15
再输入命令看看是否删除
ip6tables -L INPUT -n --line-number
已经成功删掉了
然后再试试连接web管理端
还是失败
原因是梅林固件的web端只对应了ipv4的请求,即TCP4,要将ipv6的请求端口转发到ipv4对应对款上
这里使用socat实现
socat TCP6-LISTEN:8442,reuseaddr,fork TCP4:192.168.50.1:8443&
#&为后台运行
尝试从公网访问
这下终于成功了!
接下来重启路由器试试
路由器重启完毕直接兴冲冲的连接web管理端,发现又不行了,这是怎么一回事呢
手动排查一下
ps
没有socat的进程
ip6tables-save
没有发现防火墙开启的端口8442
经过半天折腾后终于知道原因如下:
1.这个自启脚本启动的时候还是没有网的,自然也就获取不到ipv6地址,更别说调用api了,而且ip6tables服务也没有完全启动
2.socat的端口监听需要占用一个shell,关闭shell的同时也就关闭了socat端口转发
于是在重新创建一个脚本S20bindport.sh添加个延时命令,在下面添加端口并且执行S20myddnsd.sh解决这个问题,S20bindport.sh如下
#!/bin/sh
socat TCP6-LISTEN:8442,reuseaddr,fork TCP4:192.168.50.1:8443&
sleep 1m
/jffs/.koolshare/S23myddnsd.sh
ip6tables -I INPUT -p tcp --dport 8442 -j ACCEPT
同样:wq保存退出并且添加权限x
chmod +x S20bindport.sh
这里考虑到S20myddnsd.sh放在init.d下可能会重复执行,于是把S20myddnsd.sh改名为S23myddnsd.sh,并将它移入上一级目录/jffs/.koolshare/下
cd /jffs/.koolshare/init.d
cp S20myddnsd.sh /jffs/.koolshare/S23myddnsd.sh
rm -rf S20myddnsd.sh
重启路由器试试
https端口8842访问web端
终于成功啦
锦上添花一:用crond服务定时更新ddns
ipv6地址可能在一段时间内会变化,这里直接用crond实现就好了
这里已经测试过脚本加载不用延时直接可以添加任务,于是直接在sleep 1m前面加上一句即可
echo '1 * * * * /bin/sh /jffs/.koolshare/S23myddnsd.sh'|cat >/tmp/var/spool/cron/crontabs/<你的登陆用户名> &
crontab这里也是在tmp目录下的,每次重启都会重置,折腾死我了,后边自己摸索出来的这个方法,先echo然后管道链接cat写入文件
锦上添花二:远程开机
电脑在没开机之前是没有ipv6公网ip的,可以通过路由器转发udp实现
windows设置如下:
打开设备管理器
找到网卡
bios设置,以我微星主板为例,PCIE设备唤醒设置为允许,唤醒事件管理设置为BIOS
路由器转发设置如下,在/jffs/.koolshare/init.d/S20bindport.sh中sleep 1m前面添加如下语句
socat UDP6-LISTEN:2333,reuseaddr,fork UDP4:192.168.50.59:9&
arp -s 192.168.50.59 d8:bb:c1:3f:d5:dd
这里d8:bb:c1:3f:d5:dd是我本机的mac地址,192…168.50.59是我路由器设置的静态ip地址
如果少了一条arp绑定,只在web管理页面设置绑定,可能在第一次开机之前没法唤醒,路由器需要等电脑开机一次才能匹配ip和mac,但是web界面能直接唤醒,使用别的软件不行
路由器设置如下
手机上随便下一个WOL软件,设置如下
尝试开机
成功啦
脚本源码部分
S20bindport.sh
socat TCP6-LISTEN:8442,reuseaddr,fork TCP4:192.168.50.1:8443&
socat UDP6-LISTEN:2333,reuseaddr,fork UDP4:192.168.50.59:9&
echo '1 * * * * /bin/sh /jffs/.koolshare/S23myddnsd.sh'|cat >/tmp/var/spool/cron/crontabs/xxx &
arp -s 192.168.50.59 d8:bb:c1:3f:d5:dd
sleep 1m
/jffs/.koolshare/S23myddnsd.sh
ip6tables -I INPUT -p udp --dport 2333 -j ACCEPT
ip6tables -I INPUT -p tcp --dport 8442 -j ACCEPT
S23myddnsd.sh
#!bin/sh
ip=$(curl ipv6.ipw.cn)
curl -s -X POST https://dnsapi.cn/Record.Modify -d 'login_token=xxx,xxxxxxxxxx&format=json&record_line=默认&domain_id=xxxxxx&value='$ip'&record_type=AAAA&record_id=xxx&sub_domain=xxxx'
后记
谢谢你能够耐心看完,这是我第一次写博客,如果发现什么问题,欢迎批评指正。写这篇博客的初衷是为了记录,如果能顺便帮到你,我会很开心的。