package org.openstack.atlas.api.validation.util.IPString;
import java.util.List;
import java.util.regex.Pattern;
import java.util.regex.Matcher;
import java.util.Random;
public class IPUtils {
private static final byte[] hexmap = "0123456789ABCDEF".getBytes();
private static final Pattern subnetPattern = Pattern.compile("^(.*)/(.*)$");
private static final String ipv4PatternStr = "^((25[0-5]|2[0-4]\\d|1\\d\\d"
+ "|[1-9]\\d|\\d)\\.){3}(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]\\d|\\d)(/(3[0-2]|[0-2][0-9]|[0-9]))?$";
private static final String ipv6PatternStr = "^\\s*((([0-9A-Fa-f]{1,4}:){7}([0-9A-Fa-f]{1,4}|:))"
+ "|(([0-9A-Fa-f]{1,4}:){6}(:[0-9A-Fa-f]{1,4}|((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)"
+ "(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3})|:))|(([0-9A-Fa-f]{1,4}:){5}(((:[0-9A-Fa-f]{1,4}){1,2})"
+ "|:((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3})|:))"
+ "|(([0-9A-Fa-f]{1,4}:){4}(((:[0-9A-Fa-f]{1,4}){1,3})|((:[0-9A-Fa-f]{1,4})?:"
+ "((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:))"
+ "|(([0-9A-Fa-f]{1,4}:){3}(((:[0-9A-Fa-f]{1,4}){1,4})|((:[0-9A-Fa-f]{1,4}){0,2}:"
+ "((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:))"
+ "|(([0-9A-Fa-f]{1,4}:){2}(((:[0-9A-Fa-f]{1,4}){1,5})|((:[0-9A-Fa-f]{1,4}){0,3}:"
+ "((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:))"
+ "|(([0-9A-Fa-f]{1,4}:){1}(((:[0-9A-Fa-f]{1,4}){1,6})|((:[0-9A-Fa-f]{1,4}){0,4}:"
+ "((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:))"
+ "|(:(((:[0-9A-Fa-f]{1,4}){1,7})|((:[0-9A-Fa-f]{1,4}){0,5}:((25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)"
+ "(\\.(25[0-5]|2[0-4]\\d|1\\d\\d|[1-9]?\\d)){3}))|:)))(%.+)?\\s*"
+ "(/([0-1][0-2][0-8]|1[0-1][0-9]|[0-9][0-9]|[0-9]))?$";
private static final Pattern ipv4Pattern = Pattern.compile(ipv4PatternStr);
private static final Pattern ipv6Pattern = Pattern.compile(ipv6PatternStr);
private static final Pattern ipvbothPattern = Pattern.compile(ipv4PatternStr + "|" + ipv6PatternStr);
private static Random rnd = new Random();
public static Integer rndInt(int lo, int hi) {
int ri = rnd.nextInt();
ri = ri < 0 ? 0 - ri : ri;
return new Integer(ri % (hi - lo + 1) + lo);
}
public static Double rndDouble(double lo, double hi) {
double d = rnd.nextDouble();
return (Double) (hi - lo) * d + lo;
}
public static Integer rndPosInt(int lo, int hi) {
int ri = rnd.nextInt();
ri = ri < 0 ? 0 - ri : ri;
return new Integer(ri % (hi - lo + 1) + lo);
}
public static String rndIp() {
String out = String.format("%s.%s.%s.%s", rndPosInt(0, 255), rndPosInt(0, 255), rndPosInt(0, 255), rndPosInt(0, 255));
return out;
}
public static Object rndChoice(List oList) {
int ri = rndPosInt(0, oList.size() - 1);
return oList.get(ri);
}
public static Object rndChoice(Object[] oArray) {
int ri = rndPosInt(0, oArray.length) - 1;
return oArray[ri];
}
public static String rndperc() {
return String.format("%s%%", rndPosInt(0, 100).toString());
}
public static final int ubyte2int(byte in) {
return (in < 0) ? (int) in + 256 : (int) in;
}
/* Strips off extra bits and negative sign */
public static final byte int2ubyte(int in) {
in = ((in < 0) ? in = 0 - in : in) % 256;
return (in > 127) ? (byte) (in - 256) : (byte) in;
}
public static boolean isValidIpv6String(String in) {
IPv6 ip = new IPv6(in);
try {
ip.getBytes();
} catch (IPStringConversionException ex) {
return false;
}
return true;
}
public static final boolean isValidIpv4Subnet(String in) {
String ip;
String subnet;
Matcher ipMatcher;
if (in == null) {
return false;
}
ipMatcher = subnetPattern.matcher(in);
int subnetint;
if (ipMatcher.find()) {
ip = ipMatcher.group(1);
subnet = ipMatcher.group(2);
try {
subnetint = Integer.parseInt(subnet);
if (subnetint < 0 || subnetint > 32 || !isValidIpv4String(ip)) {
return false;
}
return true;
} catch (NumberFormatException e) {
return false;
}
}
return false;
}
public static boolean isValidIpv6Subnet(String in) {
String ip;
String subnet;
Matcher ipMatcher;
if (in == null) {
return false;
}
ipMatcher = subnetPattern.matcher(in);
int subnetint;
if (ipMatcher.find()) {
ip = ipMatcher.group(1);
subnet = ipMatcher.group(2);
try {
subnetint = Integer.parseInt(subnet);
if (subnetint < 0 || subnetint > 128 || !isValidIpv6String(ip)) {
return false;
}
return true;
} catch (NumberFormatException e) {
return false;
}
}
return false;
}
public static boolean isValidIpv4String(String in) {
IPv4 ip = new IPv4(in);
try {
ip.getBytes();
} catch (IPStringConversionException ex) {
return false;
}
return true;
}
public static int nibble2int(byte nibble) {
int out;
switch (nibble) {
case '0':
out = 0;
break;
case '1':
out = 1;
break;
case '2':
out = 2;
break;
case '3':
out = 3;
break;
case '4':
out = 4;
break;
case '5':
out = 5;
break;
case '6':
out = 6;
break;
case '7':
out = 7;
break;
case '8':
out = 8;
break;
case '9':
out = 9;
break;
case 'a':
out = 10;
break;
case 'b':
out = 11;
break;
case 'c':
out = 12;
break;
case 'd':
out = 13;
break;
case 'e':
out = 14;
break;
case 'f':
out = 15;
break;
case 'A':
out = 10;
break;
case 'B':
out = 11;
break;
case 'C':
out = 12;
break;
case 'D':
out = 13;
break;
case 'E':
out = 14;
break;
case 'F':
out = 15;
break;
default:
out = -1;
break;
}
return out;
}
public static final byte int2nibble(int in) {
return (in < 0 || in > 15) ? (byte) -1 : hexmap[in];
}
public static String int16bit2hex(int i16) {
String out;
byte[] nibbles = new byte[4];
int i;
if (i16 < 0x0000 || i16 > 0xffff) {
return null;
}
nibbles[0] = int2nibble((i16 & 0xf000) >> 12);
nibbles[1] = int2nibble((i16 & 0x0f00) >> 8);
nibbles[2] = int2nibble((i16 & 0x00f0) >> 4);
nibbles[3] = int2nibble((i16 & 0x000f) >> 0);
out = new String(nibbles);
return out;
}
public static int hex16bit2int(String in) {
int i;
int last;
int base;
int v;
byte[] hex;
int out;
out = 0;
base = 1;
if (in == null) {
return -1;
}
hex = in.getBytes();
if (hex.length > 4) {
return -1;
}
last = hex.length - 1;
for (i = last; i >= 0; i--) {
v = nibble2int(hex[i]);
if (v == -1) {
return -1;
}
out += v * base;
base *= 16;
}
return out;
}
public static boolean IP4RegEx(String ip) {
return ipv4Pattern.matcher(ip).matches();
}
public static boolean IP6RegEx(String ip) {
return ipv6Pattern.matcher(ip).matches();
}
public static boolean IPRegEx(String ip) {
return ipvbothPattern.matcher(ip).matches();
}
}