(前言:有关于traceroute(unix/linux系统) tracert(windows系统)命令详解,请自行参考百度)
转载请注明出处,谢谢 http://blog.csdn.net/memories_code/article/details/59560219
最近项目中需要添加traceroute功能,并对结果进行分析,获取到跳转到目标路由时的跳数和响应时间.把开发的过程中遇到的一些问题在此文中记录下来.
其实在android中实现traceroute功能很简单,代码量没有多少如下所示:
String traceroute = "traceroute -m 10 -w 5 www.baidu.com 32"; // 模拟traceroute命令
InputStream inputStream = null;
InputStreamReader inputStreamReader = null;
BufferedReader reader = null;
try {
Process process = Runtime.getRuntime().exec(traceroute);
inputStream = process.getInputStream();
inputStreamReader = new InputStreamReader(inputStream);
reader = new BufferedReader(inputStreamReader);
String resalut = null;
while ((resalut = reader.readLine()) != null) {
System.out.println(resalut);
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
inputStream.close();
inputStreamReader.close();
reader.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
运行结果如下图:
(注:没有运行上述代码,此图是直接在串口中执行,方便演示
此图是-m值为10,但是第八次就到达了目标路由,后两次以* * * 显示)
自己遇到的问题是:项目需要单独获取到跳转到目标路由时的跳数和 响应时间.以上图为例,就是需要单独得到 8 和 18.077 ms 这两个值.由于在执行traceroute命令时, -m的值 和host(百度网址)值是自行设定的,导致traceroute结果列表显示是多样性的,这里给几个示例图
此图是-m值为8 刚好第八次到达目标路由,第七次无信息,以 * * * 显示
此图是-m值为20 但是第八次就到达了目标路由,并且后面12次没有执行且无* * * 显示 目前楼主就发现这几种情况(下图还会补充一种),当然,无法执行命令的情况除外,欢迎各位补充!!!
刚开始的时候自己是想解析 traceroute 的目标路由,如 www.baidu.com 解析成 ip地址 再根据ip地址的前两位去和结果中的数据比对,如果有相同,则表示命令成功,并获取该行数据结果,然后解析得到自己需要的数据.但是有的Ip地址执行traceroute 成功后,响应的路由前两位和ip前两位是不一样的,这样的话,这种思路就行不通了,如下图
此路不通,那就再考虑别的方法吧.
下面就说下自己初步实现的思路(逻辑上还有待完善):首先将traceroute命令结果以行为单位添加到arraylist,然后对此list进行操作.附上完整代码:
/**
* 执行TraceRoute
*/
private void startTraceRoute() {
String host = "www.baidu.com";
int timeout = 5;
String HopCount = "30";
String dataBlockSize = "32";
LogUtil.e("TAG", "traceroute: "+host+" "+timeout+" "+HopCount+" "+dataBlockSize);
InputStream inputStream = null;
InputStreamReader inputStreamReader = null;
BufferedReader reader = null;
List list = new ArrayList();
String str = null;
try {
Process process = Runtime.getRuntime().exec("traceroute -m "+HopCount+" -w "+timeout+" "+host+" "+dataBlockSize);
inputStream = process.getInputStream();
inputStreamReader = new InputStreamReader(inputStream);
reader = new BufferedReader(inputStreamReader);
String resalut = null;
while ((resalut = reader.readLine()) != null) {
LogUtil.e("TAG", "resalut:" + resalut);
list.add(resalut); // 将数据以行为单位添加到list
}
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} finally {
try {
inputStream.close();
inputStreamReader.close();
reader.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
if (!list.isEmpty()) {
LogUtil.e("TAG", "list.size:"+list.size());
int num = Integer.parseInt(HopCount); // 得到命令下发时的跳转次数,
if (list.size()==(num+1)) {
if (!(list.get(num).contains("*"))) { //判断最后一行数据是否有*
str = list.get(num);
String[] split = str.split(" ");
LogUtil.e("TAG", "str: "+str+ " split_length_one: "+split.length);
if (split.length >= 18) { // 这里取 18 是由于以单个空格来截取 字符串
String NumberOfRouteHops = split[1].trim();
int number = Integer.parseInt(NumberOfRouteHops);
String times = split[6].trim();
float parseFloat = Float.parseFloat(times);
int time = Math.round(parseFloat);
LogUtil.e("TAG", "Response: "+number+" "+time);
}else {
LogUtil.e("TAG", "无法发现目标路由");
}
}else {
do {
str = list.get(num); //从最后一行数据向上读取
num --;
} while (str.contains("*"));
String[] split = str.split(" ");
LogUtil.e("TAG", "str: "+str+ " split_length_two: "+split.length);
if (split.length >= 18) {
for (String string : split) {
LogUtil.e("TAG", "string: "+string);
}
String NumberOfRouteHops = split[1].trim();
int number = Integer.parseInt(NumberOfRouteHops);
String times = split[6].trim();
float parseFloat = Float.parseFloat(times);
int time = Math.round(parseFloat);
LogUtil.e("TAG", "Response: "+number+" "+time);
}else {
LogUtil.e("TAG", "无法发现目标路由");
}
}
}else if (list.size()<(num+1)) {
int size = list.size();
str = list.get((size-1));
String[] split = str.split(" ");
LogUtil.e("TAG", "str: "+str+ " split_length_one: "+split.length);
int number = size-1;
String times = split[6].trim();
float parseFloat = Float.parseFloat(times);
int time = Math.round(parseFloat);
LogUtil.e("TAG", "Response: "+number+" "+time);
}else {LogUtil.e("TAG", "无法发现目标路由");
}
}else {
LogUtil.e("TAG", "traceroute命令参数有误,无法执行命令");
}
}