/*
* Copyright 2011 Future Systems
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.krakenapps.linux.api;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.Inet4Address;
import java.net.InetAddress;
import java.util.ArrayList;
import java.util.List;
import org.krakenapps.linux.api.RoutingEntry.Flag;
public class RoutingTable {
public static List<RoutingEntry> getRoutingEntries() throws IOException {
List<RoutingEntry> entries = new ArrayList<RoutingEntry>();
java.lang.Process p = null;
BufferedReader br = null;
try {
String line = null;
p = Runtime.getRuntime().exec("route -een");
br = new BufferedReader(new InputStreamReader(p.getInputStream()));
br.readLine(); // ignore header line
br.readLine(); // ignore column name line
while ((line = br.readLine()) != null) {
String[] tokens = line.split("[\t| ]+");
if (tokens.length == 8) {
InetAddress destination = (!tokens[0].equals("default")) ? InetAddress.getByName(tokens[0]) : null;
InetAddress gateway = (!tokens[1].equals("*")) ? InetAddress.getByName(tokens[1]) : null;
InetAddress genmask = InetAddress.getByName(tokens[2]);
Flag flags = new RoutingEntry.Flag(tokens[3]);
int metric = Integer.parseInt(tokens[4]);
int ref = Integer.parseInt(tokens[5]);
int use = Integer.parseInt(tokens[6]);
String iface = tokens[7];
entries.add(new RoutingEntry(destination, gateway, genmask, flags, metric, ref, use, iface, null, null, null));
} else if (tokens.length == 11) {
InetAddress destination = (!tokens[0].equals("default")) ? InetAddress.getByName(tokens[0]) : null;
InetAddress gateway = (!tokens[1].equals("*")) ? InetAddress.getByName(tokens[1]) : null;
InetAddress genmask = InetAddress.getByName(tokens[2]);
Flag flags = new RoutingEntry.Flag(tokens[3]);
int metric = Integer.parseInt(tokens[4]);
int ref = Integer.parseInt(tokens[5]);
int use = Integer.parseInt(tokens[6]);
String iface = tokens[7];
int mss = Integer.parseInt(tokens[8]);
int window = Integer.parseInt(tokens[9]);
int irtt = Integer.parseInt(tokens[10]);
entries.add(new RoutingEntry(destination, gateway, genmask, flags, metric, ref, use, iface, mss, window, irtt));
}
}
} finally {
if (p != null)
p.destroy();
if (br != null)
br.close();
}
return entries;
}
public static List<RoutingEntryV6> getIpv6RoutingEntries() throws IOException {
List<RoutingEntryV6> entries = new ArrayList<RoutingEntryV6>();
java.lang.Process p = null;
BufferedReader br = null;
try {
String line = null;
p = Runtime.getRuntime().exec("route -A inet6");
br = new BufferedReader(new InputStreamReader(p.getInputStream()));
br.readLine();
br.readLine();
while ((line = br.readLine()) != null) {
String[] tokens = line.split("[\t| ]+");
if (tokens.length != 7)
continue;
String destination = tokens[0];
int mask = 0;
int pos = 0;
if ((pos = tokens[0].indexOf("/")) != -1) {
destination = destination.substring(0, pos);
mask = Integer.parseInt(tokens[0].substring(pos + 1));
}
String nextHop = (!tokens[1].equals("*")) ? tokens[1] : null;
Flag flags = new RoutingEntry.Flag(tokens[2]);
int metric = Integer.parseInt(tokens[3]);
int ref = Integer.parseInt(tokens[4]);
int use = Integer.parseInt(tokens[5]);
String iface = tokens[6];
entries.add(new RoutingEntryV6(destination, nextHop, mask, flags, metric, ref, use, iface));
}
} finally {
if (p != null)
p.destroy();
if (br != null)
br.close();
}
return entries;
}
public static String addRoutingEntries(RoutingEntry entry, boolean isHost) {
String cmd = "route add";
cmd += (isHost ? " -host " : " -net ") + entry.getDestination().getHostAddress();
if (entry.getGenmask() != null)
cmd += " netmask " + entry.getGenmask().getHostAddress();
if (entry.getGateway() != null)
cmd += " gw " + entry.getGateway().getHostAddress();
if (entry.getMetric() != null)
cmd += " metric " + entry.getMetric();
if (entry.getFlags() != null) {
if (entry.getFlags().isReject())
cmd += " reject";
if (entry.getFlags().isModified())
cmd += " mod";
if (entry.getFlags().isDynamically())
cmd += " dyn";
if (entry.getFlags().isReinstate())
cmd += " reinstate";
}
if (entry.getIface() != null)
cmd += " dev " + entry.getIface();
if (entry.getMss() != null)
cmd += " mss " + entry.getMss();
if (entry.getWindow() != null)
cmd += " window " + entry.getWindow();
if (entry.getIrtt() != null)
cmd += " irtt " + entry.getIrtt();
return Util.run(cmd);
}
public static String deleteRoutingEntries(RoutingEntry entry, boolean isHost) {
String cmd = "route del";
cmd += (isHost ? " -host " : " -net ") + entry.getDestination().getHostAddress();
if (entry.getGenmask() != null)
cmd += " netmask " + entry.getGenmask().getHostAddress();
if (entry.getGateway() != null)
cmd += " gw " + entry.getGateway().getHostAddress();
if (entry.getMetric() != null)
cmd += " metric " + entry.getMetric();
if (entry.getIface() != null)
cmd += " dev " + entry.getIface();
return Util.run(cmd);
}
public static RoutingEntry findRoute(InetAddress ip) throws IOException {
int target = toInt((Inet4Address) ip);
for (RoutingEntry entry : RoutingTable.getRoutingEntries()) {
int dst = toInt((Inet4Address) entry.getDestination());
int mask = toInt((Inet4Address) entry.getGenmask());
if (dst == (target & mask))
return entry;
}
return null;
}
private static int toInt(Inet4Address addr) {
byte[] b = addr.getAddress();
int l = 0;
for (int i = 0; i < 4; i++) {
l <<= 8;
l |= b[i] & 0xff;
}
return l;
}
}