Skip to content

Instantly share code, notes, and snippets.

@jhenly
Created June 14, 2018 21:38
Show Gist options
  • Select an option

  • Save jhenly/41c8676b6d7107c1ed9eb16230f4b450 to your computer and use it in GitHub Desktop.

Select an option

Save jhenly/41c8676b6d7107c1ed9eb16230f4b450 to your computer and use it in GitHub Desktop.
/*
* To change this license header, choose License Headers in Project Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package itcs3166_project;
/**
*
* @author Kyle1
*/
public class Router {
/*
* STATIC VARIABLES
*/
private static final int NUM_ROUTES = 4;
private static final String INTERFACE_0 = "135.46.56.0/22";
private static final String INTERFACE_1 = "135.46.60.0/22";
private static final String ROUTER_1 = "192.53.40.0/23";
private static final String ROUTER_2 = "0.0.0.0/0";
private static final class Route {
private String strIP;
private long ip; // must be long due to 2's complement and
// lack of unsigned integers in java
private int mask;
private String name;
public Route(String ip, int mask, String name) {
this.strIP = ip;
this.mask = mask;
this.name = name;
this.ip = ipStringToBinary(ip);
}
public long getIP() {
return this.ip;
}
public String getStrIP() {
return this.strIP;
}
public int getMask() {
return this.mask;
}
public String getName() {
return this.name;
}
}
/*
* STATIC METHODS
*/
private static long ipStringToBinary(String ipString) {
String[] octets = ipString.split("\\.");
long ip = 0;
for(int i = 0; i < 4; i++) {
ip = (ip << 8) + Integer.parseInt(octets[i]);
}
return ip;
}
private static String to32BitBinaryString(long ip) {
return Long.toBinaryString(1L << 32 | ip).substring(1);
}
private static long intMaskToLong(int mask) {
return ((Integer.MAX_VALUE << 1) + 1) << (32 - mask);
}
/*
* INSTANCE VARIABLES AND METHODS
*/
private Route[] routerTable;
private long binaryIP;
private Route matchedRoute;
private String ipAddress;
private String subnetMask;
private String networkAddress;
public Router() {
routerTable = new Route[NUM_ROUTES];
addRouteToTable(INTERFACE_0, "Interface 0");
addRouteToTable(INTERFACE_1, "Interface 1");
addRouteToTable(ROUTER_1, "Router 1");
addRouteToTable(ROUTER_2, "Router 2");
}
private void addRouteToTable(String addrMask, String name) {
String strIP = addrMask.split("/")[0];
int mask = Integer.parseInt(addrMask.split("/")[1]);
Route route = new Route(strIP, mask, name);
/*
* The following for loop inserts routes in order of their mask, where
* the route with the highest mask at index 0. This is analogous to the
* way the router functioned in Exercise 33 from Chapter 5.
*/
for(int i = 0; i < NUM_ROUTES; i++) {
if(routerTable[i] == null) {
routerTable[i] = route;
break;
} else {
if(route.getMask() > routerTable[i].getMask()) {
Route swap = routerTable[i];
routerTable[i] = route;
route = swap;
}
}
}
}
public String getIPAddress() {
return ipAddress;
}
private void setIPAddress(String s) {
ipAddress = s;
}
public String getSubnetMask() {
return subnetMask;
}
private void setSubnetMask(String s) {
subnetMask = s;
}
public String getBinaryIPAddress() {
return to32BitBinaryString(this.getBinaryIP());
}
public String getNetworkAddress() {
return networkAddress;
}
private void setNetworkAddress(String s) {
networkAddress = s;
}
private void setBinaryIP(long binaryIP) {
this.binaryIP = binaryIP;
}
private long getBinaryIP() {
return this.binaryIP;
}
private void setMatchedRoute(Route r) {
this.matchedRoute = r;
}
private Route getMatchedRoute() {
return this.matchedRoute;
}
public void setFields(String ip){
this.setIPAddress(ip);
this.setBinaryIP(ipStringToBinary(ip));
this.setMatchedRoute(this.calculateRoute(this.getBinaryIP()));
this.setSubnetMask(this.calculateSubnetMask(this.getMatchedRoute().getMask()));
this.setNetworkAddress(this.calculateNetworkAddress(this.getBinaryIP(), this.getMatchedRoute().getMask()));
}
private Route calculateRoute(long ip) {
Route cur = null;
// traverse the router table, beginning with the entry that has the
// highest mask, and check the bitwise AND of the masked IP with
// the current entry
// NOTE: the last entry has a mask of 0, so it will match any IP
for(int i = 0; i < NUM_ROUTES; i++) {
cur = this.routerTable[i];
if( (ip & intMaskToLong(cur.getMask())) == cur.getIP()) {
return cur;
}
}
// need a catch all return statement to make the compiler happy
return cur;
}
private String calculateSubnetMask(int mask) {
// Integer.toBinaryString(...) trims leading 0's
if (mask == 0) {
return String.format("%032d", 0);
}
/*
* Start with -1, which is 32 1's in twos complement then bit shift
* the 1's, 32 minus mask times, leaving you with the correct subnet mask.
*/
return Integer.toBinaryString(-1 << (32 - mask));
}
private String calculateNetworkAddress(long ip, int mask) {
long longBitmask = intMaskToLong(mask);
long maskedIP = longBitmask & ip;
return to32BitBinaryString(maskedIP);
}
public String checkRouting() {
return this.getMatchedRoute().getName();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment