小弟使用了datagrampacket和datagramsocket2个类实现了基于udp协议的网络通讯,现在想让我每一个数据报的大小都在MTU值之下,大概在548字节,也就是说我发送的每一个数据包都只需要发送一次而不需要底层去拆分和组装。
现在的问题就是我所我给datagrampacket的byte数组大小的最大值取多少合适,我读了下源码,大概知道一个包包装完的大小是byte大小+4个4字节的int变量和一个InetAddress类,但是没办法确定InetAddress类的大小,所以请教下大家,有谁能确定换句话说就是,假设我有个100字节的byte数组,通过udp协议发送时,实际在网络上传输的数据包大小是多少?
现在的问题就是我所我给datagrampacket的byte数组大小的最大值取多少合适,我读了下源码,大概知道一个包包装完的大小是byte大小+4个4字节的int变量和一个InetAddress类,但是没办法确定InetAddress类的大小,所以请教下大家,有谁能确定换句话说就是,假设我有个100字节的byte数组,通过udp协议发送时,实际在网络上传输的数据包大小是多少?
解决方案 »
- java面向对象设计求素数错误求解
- JTable 的标题
- dwr高手请进----关于dwr直接调用服务端Java方法并调回调函数的问题
- 用JMF从摄象头捕获的连续图象是什么格式?
- 有专讲JDBC的经典好书吗?麻烦大家推荐一下!
- 请问有没有人在IBM Visual Age For Java 下面开发,怎么学VAJ4.0呀,有没有相关的文档?
- 在一个应用程序中我用new String(str.getBytes("ISO8859_1"),""GBK)来转换字符,运行时却报UnsupportedEncodingException: GBK错误。什么
- 怎么向别人发送电子邮件?
- Spring jdbc 动态的将参数Insert 至对应的表栏位
- 用java正则表达式(或其他简单方法)判断字符串是否含有除特定字母外的字符
- 弱弱问下 HashMap中存放元素时 有没可能hashCode相同 而equals值不同?
- ResultSet的问题
然而,然后底层的原生网络软件就少宽容了,最原始UDP实现不支持超过 8,192 byte/datagram。IPv4的理论极限datagram是65,507字节,而如果一个DatagramPacket对象带有65,507字节大小的缓存的话就可以无损接收任何可能的IPv4 datagram。许多基于UDP的协议如DNS和TFTP会使用每datagram 512字节或更少。NFS的普通使用最大数据大小是8,192字节。几乎所有的你可能碰到的UDP datagrams是8K或更少。实际上,许多操作系统并不支持超过8K数据的UDP datagrams,或截断、或分拆,或丢弃。如果一个datagram因过大而遭到网络截断或丢弃,你的java程序并不会被通知到该问题的存在(UDP毕竟是不可靠协议) 。因此,你不应该创建超过8,192字节的DatagramPacket对象。
import java.io.BufferedReader;
import java.io.InputStreamReader;/**
*
* @author chencheng
* @version 1.0.0
* @2008-8-12 上午09:16:58
*/
public class ScanMTU { private String ip; private String parameter; public static void main(String args[]) { ScanMTU mtu = new ScanMTU(); if (args == null || args.length <= 0) {
System.out.println("Please input dest ip.");
return;
} else
mtu.ip = args[0]; try {
mtu.checkIp(mtu.ip);
} catch (Exception e) {
System.err.println(e.getMessage());
return;
} System.out.println("Test Result: Maximum Transmission Unit(MTU): " + mtu.scan() + " Bytes Free."); } private int scan() {
for (int length = 1500; length > 0; length--) {
try {
Process pro = Runtime.getRuntime().exec(setCommand(ip, length));
BufferedReader buf = new BufferedReader(new InputStreamReader(pro.getInputStream())); int count = 0;
String line = null;
while ((line = buf.readLine()) != null) {
if (!line.equals("")) {
System.out.println(line);
if (count++ == 1) {
if (line.toLowerCase().indexOf("df") == -1)
return length;
break;
}
}
}
buf.close(); } catch (Exception ex) {
System.out.println(ex.getMessage());
}
}
return -1;
} private String setCommand(String ipAddress, int fragSize) {
if (checkForLinux())
parameter = "ping -M do -s " + fragSize;
else if (checkForWindows()) {
parameter = "ping -f -l " + fragSize;
}
return parameter + " " + ipAddress;
} /**
* 检测输入的IP格式是否正确
*
* @return
* @throws Exception
*/
private void checkIp(String ipAddress) throws Exception {
String regex = "[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}.[0-9]{1,3}";
if (!ipAddress.matches(regex) && !ipAddress.equalsIgnoreCase("localhost")) {
throw new Exception("Input Error!");
}
} /**
* 检查当前操作系统是否为linux
*
* @return
*/
private boolean checkForLinux() {
String os = System.getProperty("os.name");
return os != null && os.toLowerCase().startsWith("linux") ? true : false;
} /**
* 检查当前操作系统是否为windows
*
* @return
*/
private boolean checkForWindows() {
String os = System.getProperty("os.name");
return os != null && os.toLowerCase().startsWith("win") ? true : false;
}
如果网络最大的MTU值是548字节,那么我想让每一个数据包的大小都不超过548字节,但是如果我把数据包的大小设为548字节,肯定是不对的,因为DatagramPacket类和DatagramSocket类又包装了2次548字节的数据,实际流传到网络上的包肯定大于548字节,那么系统应该是拆分成2个,2个包的最大大小应该是2X548字节,效率就降低不少了,所以就想确定一个数据包的最大大小合适?