在Linux下使用Cisco Anyconnect客户端连接VPN后,局域网无法访问,无论如何设置路由,路由表始终无法改变
网上搜了一下,原因是Anyconnect客户端监听路由表,一旦改变,通过一个回调再改回去
解决办法:Anyconnect监听路由表的回调代码位于一个so共享库,可以通过LD_PRELOAD阻止Anyconnect加载原来的监听回调
创建hack.c
#include <sys/socket.h> #include <linux/netlink.h> int _ZN27CInterfaceRouteMonitorLinux20routeCallbackHandlerEv() { int fd=50; // max fd to try char buf[8192]; struct sockaddr_nl sa; socklen_t len = sizeof(sa); while (fd) { if (!getsockname(fd, (struct sockaddr *)&sa, &len)) { if (sa.nl_family == AF_NETLINK) { ssize_t n = recv(fd, buf, sizeof(buf), MSG_DONTWAIT); } } fd--; } return 0; }
$ gcc -o libhack.so -shared -fPIC hack.c $ sudo cp libhack.so /opt/cisco/anyconnect/lib/
修改/etc/init.d/vpnagentd,启动vpnagentd的地方前面添加LD_PRELOAD=/opt/cisco/anyconnect/lib/libhack.so
LD_PRELOAD=/opt/cisco/anyconnect/lib/libhack.so /opt/cisco/anyconnect/bin/vpnagentd
重新启动vpnagentd
$ sudo /etc/init.d/vpnagentd start
最后修改一下iptables
$ sudo iptables-save | grep -v DROP | iptables-restore
再修改路由表就可以生效了
$ sudo route add -net 192.168.1.0 netmask 255.255.255.0 dev eth0 $ sudo route -n
以上方法对于version 3.1.00495, 3.1.05152, 3.1.05170的Anyconnect客户端有效
如果前面说的方法无效,可以试试用gdb调试,找出回调函数的名字
gdb -p $(pidof vpnagentd) b socket c bt
参考:How to allow local LAN access while connected to Cisco VPN?
PDF:How to allow local LAN access while connected to Cisco VPN