mirror of
https://gitee.com/willfree/min-vpn-client_v2.git
synced 2026-10-04 19:42:00 +08:00
对收包操作进行了去解码化的简化处理,网速又有了明显提升
This commit is contained in:
1 parent
ebfccef80d
commit
e9638f6215
5 files changed
+102
-12
No files matched your search
@@ -314,7 +314,7 @@ public class MINVpnService extends VpnService implements Handler.Callback{
|
||||
// }
|
||||
|
||||
// 灌包测试-灌IP包
|
||||
// for (int i = 0; i < 10000; i++) {
|
||||
// for (int i = 0; i < 10000*1; i++) {
|
||||
// ByteBuffer buffer=ByteBufferPool.acquire();
|
||||
// buffer.put(pay);
|
||||
// buffer.flip();
|
||||
@@ -364,7 +364,7 @@ public class MINVpnService extends VpnService implements Handler.Callback{
|
||||
|
||||
// 新
|
||||
executorService.submit(new ReceiveQuickTask(writeTunLpPackets, vpnConnectionInfo.face));
|
||||
executorService.submit(new Min2IpQuickTask(writeTunLpPackets, writeTunDataQueue));
|
||||
executorService.submit(new Min2IpQuickTask(writeTunLpPackets, writeTunDataQueue, vpnConnectionInfo.allocatedAddress));
|
||||
executorService.submit(new WriteTunTask(writeTunDataQueue, tunOutput));
|
||||
|
||||
// executorService.submit(new ReceiveTask(writeTunCPackets, vpnConnectionInfo.face));
|
||||
|
||||
@@ -12,7 +12,7 @@ import android.util.Pair;
|
||||
import com.pkusz.min_vpn_client.model.MINVpnSettingAPI;
|
||||
import com.pkusz.min_vpn_client.services.ByteBufferPool;
|
||||
import com.pkusz.min_vpn_client.utils.IPPackageUtil;
|
||||
import com.pkusz.min_vpn_client.utils.StringUtil;
|
||||
import com.pkusz.min_vpn_client.utils.StringUtilForCPacketEncoding;
|
||||
|
||||
import java.nio.ByteBuffer;
|
||||
import java.util.Arrays;
|
||||
@@ -21,7 +21,6 @@ import java.util.concurrent.atomic.AtomicInteger;
|
||||
|
||||
import component.ComponentException;
|
||||
import component.Identifier;
|
||||
import component.IdentifierComponent;
|
||||
import encoding.VlIntException;
|
||||
import packet.CPacket;
|
||||
|
||||
@@ -132,7 +131,7 @@ public class Ip2MinTask implements Runnable{
|
||||
tlvTail=new byte[7];
|
||||
System.arraycopy(genRes.getRawData(),genRes.getRawData().length-7,tlvTail,0,7);
|
||||
// 初始化随机数字字符串位置信息
|
||||
randomPos=StringUtil.findThePos(genRes.rawData);
|
||||
randomPos= StringUtilForCPacketEncoding.findThePos(genRes.rawData);
|
||||
readPos=randomPos+10;
|
||||
System.out.println("初始化 random pos: "+randomPos);
|
||||
System.out.println("初始化 head array: "+ Arrays.toString(tlvHead));
|
||||
@@ -141,7 +140,7 @@ public class Ip2MinTask implements Runnable{
|
||||
// 更新tlvHead的目的地址字段(随机字符串)&负载头部字段
|
||||
Pair<byte[],Integer> calculateRes;
|
||||
try {
|
||||
calculateRes=StringUtil.replaceRandomPos(tlvHead,randomPos,readPos,buf.length);
|
||||
calculateRes= StringUtilForCPacketEncoding.replaceRandomPos(tlvHead,randomPos,readPos,buf.length);
|
||||
} catch (VlIntException e) {
|
||||
System.out.println("tlv计算报错了: "+e.getMessage());
|
||||
return null;
|
||||
@@ -182,7 +181,7 @@ public class Ip2MinTask implements Runnable{
|
||||
// serverIdentifier = new Identifier(serverPrefix
|
||||
// +"/"+ StringUtil.getFixLenthString(10));
|
||||
serverIdentifier = new Identifier(serverPrefix
|
||||
+"/"+ StringUtil.getAll0String()); // 第一个包作为典型包,其随机字符串是全0字符串。
|
||||
+"/"+ StringUtilForCPacketEncoding.getAll0String()); // 第一个包作为典型包,其随机字符串是全0字符串。
|
||||
} catch (ComponentException e) {
|
||||
e.printStackTrace();
|
||||
System.out.println("genInterestPkt error 1: serverIdentifier init error: " + e.getMessage());
|
||||
|
||||
@@ -8,7 +8,11 @@ package com.pkusz.min_vpn_client.services.Runnables;
|
||||
*/
|
||||
|
||||
import com.pkusz.min_vpn_client.services.ByteBufferPool;
|
||||
import com.pkusz.min_vpn_client.utils.IPPackageUtil;
|
||||
import com.pkusz.min_vpn_client.utils.StringUtilForLpPacketDecoding;
|
||||
|
||||
import java.nio.ByteBuffer;
|
||||
import java.util.Arrays;
|
||||
import java.util.concurrent.ConcurrentLinkedQueue;
|
||||
import packet.LpPacket;
|
||||
|
||||
@@ -16,11 +20,14 @@ public class Min2IpQuickTask implements Runnable{
|
||||
private ConcurrentLinkedQueue<LpPacket> writeTunLpPackets;
|
||||
private ConcurrentLinkedQueue<ByteBuffer> writeTunDataQueue;
|
||||
private boolean isSM4=false; // 加密方式
|
||||
private byte[] tunAddress; // tun地址(服务器给分配的地址)
|
||||
|
||||
public Min2IpQuickTask(ConcurrentLinkedQueue<LpPacket> writeTunLpPackets,
|
||||
ConcurrentLinkedQueue<ByteBuffer> writeTunDataQueue){
|
||||
ConcurrentLinkedQueue<ByteBuffer> writeTunDataQueue,
|
||||
String tunAddress){
|
||||
this.writeTunLpPackets=writeTunLpPackets;
|
||||
this.writeTunDataQueue=writeTunDataQueue;
|
||||
this.tunAddress = IPPackageUtil.StringAddress2byteAddress(tunAddress);
|
||||
}
|
||||
|
||||
@Override
|
||||
@@ -49,8 +56,21 @@ public class Min2IpQuickTask implements Runnable{
|
||||
System.out.println("debug min2ip len: "+pendingProcessLpPacket.payload.getValue().length); // 测试
|
||||
|
||||
// 2.读取负载字段
|
||||
pendingProcessLpPacket.decodeSelf();
|
||||
byte[] rawIpDataBytes = pendingProcessLpPacket.getRawPayload();
|
||||
// pendingProcessLpPacket.decodeSelf();
|
||||
// byte[] rawIpDataBytes = pendingProcessLpPacket.getRawPayload();
|
||||
byte[] rawIpDataBytes=getRawIpData(pendingProcessLpPacket.payload.getValue(),tunAddress);
|
||||
if(rawIpDataBytes==null){
|
||||
System.out.println("你的分析代码出错了!!!");
|
||||
continue;
|
||||
}
|
||||
// todo: 分析LpPacket包结构
|
||||
System.out.println("LpPacket负载字段: "+ Arrays.toString(pendingProcessLpPacket.payload.getValue()));
|
||||
System.out.println("LpPacket负载字段len: "+ pendingProcessLpPacket.payload.getValue().length);
|
||||
// System.out.println("负载字段中的负载字段: "+ Arrays.toString(pendingProcessLpPacket.getRawPayload()));
|
||||
// System.out.println("负载字段中的负载字段len: "+ pendingProcessLpPacket.getRawPayload().length);
|
||||
System.out.println("负载字段中的负载字段(分析提取): "+ Arrays.toString(rawIpDataBytes));
|
||||
System.out.println("负载字段中的负载字段(分析提取)len: "+ rawIpDataBytes.length);
|
||||
// Thread.sleep(1000);
|
||||
// 解密
|
||||
ByteBuffer ipData= ByteBufferPool.acquire();
|
||||
if(isSM4){ //解密
|
||||
@@ -67,4 +87,22 @@ public class Min2IpQuickTask implements Runnable{
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 从LpPacket的负载字段中取出IP地址
|
||||
* @param lpPacketPayload
|
||||
* @param tunAddress
|
||||
* @return
|
||||
*/
|
||||
private byte[] getRawIpData(byte[] lpPacketPayload,byte[] tunAddress){
|
||||
int startPos = StringUtilForLpPacketDecoding.findTheStartPos(lpPacketPayload,tunAddress);
|
||||
if(startPos<0){
|
||||
return null;
|
||||
}
|
||||
int endPos=lpPacketPayload.length-7;
|
||||
int ipLen=endPos-startPos;
|
||||
byte[] ipData=new byte[ipLen];
|
||||
System.arraycopy(lpPacketPayload,startPos,ipData,0,ipLen);
|
||||
return ipData;
|
||||
}
|
||||
}
|
||||
+20
-2
@@ -1,7 +1,8 @@
|
||||
package com.pkusz.min_vpn_client.utils;
|
||||
/*
|
||||
* @Author: Wang Feng
|
||||
* @Description:脏类。方法仅供一时之需。
|
||||
* @Description:脏类。方法有局限性。
|
||||
* 用于实现CPacket的快速编码,从而快速发包。
|
||||
* @Version: 1.0.0
|
||||
* @Date: 16:15 2021/10/27
|
||||
* @Copyright: MIN-Group;国家重大科技基础设施——未来网络北大实验室;深圳市信息论与未来网络重点实验室
|
||||
@@ -21,7 +22,7 @@ import encoding.TLVException;
|
||||
import encoding.VlInt;
|
||||
import encoding.VlIntException;
|
||||
|
||||
public class StringUtil {
|
||||
public class StringUtilForCPacketEncoding {
|
||||
public static String getFixLenthString(int strLength) {
|
||||
Random rm = new Random();
|
||||
// 获得随机数
|
||||
@@ -49,6 +50,12 @@ public class StringUtil {
|
||||
//100, 11, 0, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48, 100, 2, 4, 10, 52, 12, -52, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 53, 5, 55, 3, -44, 1, 64
|
||||
// 要找的字符数组是:100, 11, 0, 48, 48, 48, 48, 48, 48, 48, 48, 48, 48
|
||||
// 分析其特点,找到连续的五个48,且前面依次是11、0,即可。假定是10个连续随机数
|
||||
|
||||
/**
|
||||
* 查找CPacket编码结构中的目的标识的变化字段(长度为10的变化字段)
|
||||
* @param targetArray
|
||||
* @return
|
||||
*/
|
||||
public static int findThePos(byte[] targetArray){
|
||||
byte[] matchArray=new byte[]{(byte)11,(byte) 0,(byte) 48};
|
||||
System.out.println("target: "+ Arrays.toString(targetArray));
|
||||
@@ -74,6 +81,17 @@ public class StringUtil {
|
||||
|
||||
// | 总包长 | 标识区 | 负载区 | TTL |
|
||||
// 注意,这里返回的数组不包括TTL区,以及负载区的真实负载
|
||||
|
||||
/**
|
||||
* 根据上一个CPacket的编码结果,对本次CPacket进行头部构造。
|
||||
* 主要涉及:1.目的标识的变化字段的替换;2.TLV中标记L的部分的修改(网络包的长度、负载字段长度、只读区的长度)
|
||||
* @param targetArray 上一个CPacket的编码结果
|
||||
* @param randomPos
|
||||
* @param readPos
|
||||
* @param payloadLen
|
||||
* @return
|
||||
* @throws VlIntException
|
||||
*/
|
||||
public static Pair<byte[], Integer> replaceRandomPos(byte[] targetArray, int randomPos, int readPos, int payloadLen)
|
||||
throws VlIntException {
|
||||
// System.out.println("ttt1");
|
||||
@@ -0,0 +1,35 @@
|
||||
package com.pkusz.min_vpn_client.utils;
|
||||
/*
|
||||
* @Author: Wang Feng
|
||||
* @Description:脏类。方法有局限性。
|
||||
* 用于实现LpPacket的快速解码,从而快速收包。
|
||||
* @Version: 1.0.0
|
||||
* @Date: 15:05 2021/10/28
|
||||
* @Copyright: MIN-Group;国家重大科技基础设施——未来网络北大实验室;深圳市信息论与未来网络重点实验室
|
||||
*/
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
public class StringUtilForLpPacketDecoding {
|
||||
/**
|
||||
* 根据tun地址,定位到收到的IP包的地址ipPos,而IP包的开始位置startPos=ipPos-12-4,
|
||||
* 从而快速将LpPacket中的负载字段(其负载实际上是一个CPacket)中实际搭载的IP包给解析出来
|
||||
* @param targetArray LpPacket.payload
|
||||
* @param matchArray tun地址,长度为4byte
|
||||
* @return ip包开始位置
|
||||
*/
|
||||
public static int findTheStartPos(byte[] targetArray,byte[] matchArray){
|
||||
System.out.println("target: "+ Arrays.toString(targetArray));
|
||||
System.out.println("match: "+ Arrays.toString(matchArray));
|
||||
for (int i = 0; i < (targetArray.length-4); i++) {
|
||||
if((targetArray[i]==matchArray[0])
|
||||
&& (targetArray[i+1]==matchArray[1])
|
||||
&& (targetArray[i+2]==matchArray[2])
|
||||
&& (targetArray[i+3]==matchArray[3])){
|
||||
System.out.println("IP地址,我中了: "+(i-16));
|
||||
return i-16;
|
||||
}
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user