/**
 *  Copyright (C) 2010 Cloud.com, Inc.  All rights reserved.
 * 
 * This software is licensed under the GNU General Public License v3 or later.
 * 
 * It is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or any later version.
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 * 
 */

package com.cloud.test;

import java.lang.reflect.Array;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.List;
import java.util.Vector;

import com.cloud.utils.component.ComponentLocator;
import com.cloud.utils.db.DB;
import com.cloud.utils.db.Transaction;
import com.cloud.utils.net.NetUtils;


public class IPRangeConfig {
	
	public static void main(String[] args) {
		IPRangeConfig config = ComponentLocator.inject(IPRangeConfig.class);
		config.run(args);
		System.exit(0);
    }
	
	//This class is not applicable in 2.2 with the new networking model
	private String usage() {
		return "Usage: ./change_ip_range.sh [add|delete] [public zone | private pod zone] startIP endIP";
	}
	
	
	public void run(String[] args) {
		if (args.length < 2) {
            printError(usage());
        }
		
		String op = args[0];
		String type = args[1];
		
		if (type.equals("public")) {
			if (args.length != 4 && args.length != 5) {
                printError(usage());
            }
			String zone = args[2];
			String startIP = args[3];
			String endIP = null;
			if (args.length == 5) {
                endIP = args[4];
            }
			
			String result = checkErrors(type, op, null, zone, startIP, endIP);
			if (!result.equals("success")) {
                printError(result);
            }
			
			long zoneId = PodZoneConfig.getZoneId(zone);
			result = changeRange(op, "public", -1, zoneId, startIP, endIP, null);
			result.replaceAll("<br>", "/n");
			System.out.println(result);
		} else if (type.equals("private")) {
			if (args.length != 5 && args.length != 6) {
                printError(usage());
            }
			String pod = args[2];
			String zone = args[3];;
			String startIP = args[4];
			String endIP = null;
			if (args.length == 6) {
                endIP = args[5];
            }
			
			String result = checkErrors(type, op, pod, zone, startIP, endIP);
			if (!result.equals("success")) {
                printError(result);
            }
			
			long podId = PodZoneConfig.getPodId(pod, zone);
			long zoneId = PodZoneConfig.getZoneId(zone);
			result = changeRange(op, "private", podId, zoneId, startIP, endIP, null);
			result.replaceAll("<br>", "/n");
			System.out.println(result);
		} else {
			printError(usage());
		}
	}
	
	public List<String> changePublicIPRangeGUI(String op, String zone, String startIP, String endIP) {
		String result = checkErrors("public", op, null, zone, startIP, endIP);
		if (!result.equals("success")) {
            return DatabaseConfig.genReturnList("false", result);
        }
		
		long zoneId = PodZoneConfig.getZoneId(zone);
		result = changeRange(op, "public", -1, zoneId, startIP, endIP, null);
		
		return DatabaseConfig.genReturnList("true", result);
	}
	
	public List<String> changePrivateIPRangeGUI(String op, String pod, String zone, String startIP, String endIP) {
		String result = checkErrors("private", op, pod, zone, startIP, endIP);
		if (!result.equals("success")) {
            return DatabaseConfig.genReturnList("false", result);
        }
		
		long podId = PodZoneConfig.getPodId(pod, zone);
		long zoneId = PodZoneConfig.getZoneId(zone);
		result = changeRange(op, "private", podId, zoneId, startIP, endIP, null);
		
		return DatabaseConfig.genReturnList("true", result);
	}

	private String checkErrors(String type, String op, String pod, String zone, String startIP, String endIP) {
		if (!op.equals("add") && !op.equals("delete")) {
            return usage();
        }
		
		if (type.equals("public")) {
			// Check that the zone is valid
			if (!PodZoneConfig.validZone(zone)) {
                return "Please specify a valid zone.";
            }
		} else if (type.equals("private")) {
			// Check that the pod and zone are valid
			if (!PodZoneConfig.validZone(zone)) {
                return "Please specify a valid zone.";
            }
			if (!PodZoneConfig.validPod(pod, zone)) {
                return "Please specify a valid pod.";
            }
		}
		
		if (!validIP(startIP)) {
            return "Please specify a valid start IP";
        }
		
		if (!validOrBlankIP(endIP)) {
            return "Please specify a valid end IP";
        }
		
		// Check that the IPs that are being added are compatible with either the zone's public netmask, or the pod's CIDR
		if (type.equals("public")) {
			// String publicNetmask = getPublicNetmask(zone);
			// String publicGateway = getPublicGateway(zone);
			
			// if (publicNetmask == null) return "Please ensure that your zone's public net mask is specified";
			// if (!sameSubnet(startIP, endIP, publicNetmask)) return "Please ensure that your start IP and end IP are in the same subnet, as per the zone's netmask.";
			// if (!sameSubnet(startIP, publicGateway, publicNetmask)) return "Please ensure that your start IP is in the same subnet as your zone's gateway, as per the zone's netmask.";
			// if (!sameSubnet(endIP, publicGateway, publicNetmask)) return "Please ensure that your end IP is in the same subnet as your zone's gateway, as per the zone's netmask.";
		} else if (type.equals("private")) {
			String cidrAddress = getCidrAddress(pod, zone);
			long cidrSize = getCidrSize(pod, zone);

			if (!sameSubnetCIDR(startIP, endIP, cidrSize)) {
                return "Please ensure that your start IP and end IP are in the same subnet, as per the pod's CIDR size.";
            }
			if (!sameSubnetCIDR(startIP, cidrAddress, cidrSize)) {
                return "Please ensure that your start IP is in the same subnet as the pod's CIDR address.";
            }
			if (!sameSubnetCIDR(endIP, cidrAddress, cidrSize)) {
                return "Please ensure that your end IP is in the same subnet as the pod's CIDR address.";
            }
		}
		
		if (!validIPRange(startIP, endIP)) {
            return "Please specify a valid IP range.";
        }
		
		return "success";
	}
	
	private String genChangeRangeSuccessString(List<String> problemIPs, String op) {
		if (problemIPs == null) {
            return "";
        }
		
		if (problemIPs.size() == 0) {
			if (op.equals("add")) {
                return "Successfully added all IPs in the specified range.";
            } else if (op.equals("delete")) {
                return "Successfully deleted all IPs in the specified range.";
            } else {
                return "";
            }
		} else {
			String successString = "";
			if (op.equals("add")) {
                successString += "Failed to add the following IPs, because they are already in the database: <br><br>";
            } else if (op.equals("delete")) {
                successString += "Failed to delete the following IPs, because they are in use: <br><br>";
            }
			
			for (int i = 0; i < problemIPs.size(); i++) {
				successString += problemIPs.get(i);
				if (i != (problemIPs.size() - 1)) {
                    successString += ", ";
                }
			}
			
			successString += "<br><br>";
			
			if (op.equals("add")) {
                successString += "Successfully added all other IPs in the specified range.";
            } else if (op.equals("delete")) {
                successString += "Successfully deleted all other IPs in the specified range.";
            }
			
			return successString;
		}
	}
	
	private String changeRange(String op, String type, long podId, long zoneId, String startIP, String endIP, Long networkId) {
		
		// Go through all the IPs and add or delete them
		List<String> problemIPs = null;
		if (op.equals("add")) {
			problemIPs = saveIPRange(type, podId, zoneId, 1, startIP, endIP, networkId);
		} else if (op.equals("delete")) {
			problemIPs = deleteIPRange(type, podId, zoneId, 1, startIP, endIP);
		}
		
		if (problemIPs == null) {
            return null;
        } else {
            return genChangeRangeSuccessString(problemIPs, op);
        }
	}
	
	private String genSuccessString(Vector<String> problemIPs, String op) {
		if (problemIPs == null) {
            return "";
        }
		
		if (problemIPs.size() == 0) {
			if (op.equals("add")) {
                return "Successfully added all IPs in the specified range.";
            } else if (op.equals("delete")) {
                return "Successfully deleted all IPs in the specified range.";
            } else {
                return "";
            }
		} else {
			String successString = "";
			if (op.equals("add")) {
                successString += "Failed to add the following IPs, because they are already in the database: <br><br>";
            } else if (op.equals("delete")) {
                successString += "Failed to delete the following IPs, because they are in use: <br><br>";
            }
			
			for (int i = 0; i < problemIPs.size(); i++) {
				successString += problemIPs.elementAt(i);
				if (i != (problemIPs.size() - 1)) {
                    successString += ", ";
                }
			}
			
			successString += "<br><br>";
			
			if (op.equals("add")) {
                successString += "Successfully added all other IPs in the specified range.";
            } else if (op.equals("delete")) {
                successString += "Successfully deleted all other IPs in the specified range.";
            }
			
			return successString;
		}
	}
	
	public static String getCidrAddress(String pod, String zone) {
		long dcId = PodZoneConfig.getZoneId(zone);
		String selectSql = "SELECT * FROM `cloud`.`host_pod_ref` WHERE name = \"" + pod + "\" AND data_center_id = \"" + dcId + "\"";
		String errorMsg = "Could not read CIDR address for pod/zone: " + pod + "/" + zone + " from database. Please contact Cloud Support.";
		return DatabaseConfig.getDatabaseValueString(selectSql, "cidr_address", errorMsg);
	}
	
	public static long getCidrSize(String pod, String zone) {
		long dcId = PodZoneConfig.getZoneId(zone);
		String selectSql = "SELECT * FROM `cloud`.`host_pod_ref` WHERE name = \"" + pod + "\" AND data_center_id = \"" + dcId + "\"";
		String errorMsg = "Could not read CIDR address for pod/zone: " + pod + "/" + zone + " from database. Please contact Cloud Support.";
		return DatabaseConfig.getDatabaseValueLong(selectSql, "cidr_size", errorMsg);
	}

	@DB
	protected Vector<String> deleteIPRange(String type, long podId, long zoneId, long vlanDbId, String startIP, String endIP) {
    	long startIPLong = NetUtils.ip2Long(startIP);
    	long endIPLong = startIPLong;
    	if (endIP != null) {
            endIPLong = NetUtils.ip2Long(endIP);
        }
 
    	Transaction txn = Transaction.currentTxn();
    	Vector<String> problemIPs = null;
    	if (type.equals("public")) {
            problemIPs = deletePublicIPRange(txn, startIPLong, endIPLong, vlanDbId);
        } else if (type.equals("private")) {
            problemIPs = deletePrivateIPRange(txn, startIPLong, endIPLong, podId, zoneId);
        }
    	
    	return problemIPs;
    }
	
	private Vector<String> deletePublicIPRange(Transaction txn, long startIP, long endIP, long vlanDbId) {
		String deleteSql = "DELETE FROM `cloud`.`user_ip_address` WHERE public_ip_address = ? AND vlan_id = ?";
		String isPublicIPAllocatedSelectSql = "SELECT * FROM `cloud`.`user_ip_address` WHERE public_ip_address = ? AND vlan_id = ?";
		
		Vector<String> problemIPs = new Vector<String>();
		PreparedStatement stmt = null;
		PreparedStatement isAllocatedStmt = null;
		
		Connection conn = null;
		try {
			conn = txn.getConnection();
			stmt = conn.prepareStatement(deleteSql);
			isAllocatedStmt = conn.prepareStatement(isPublicIPAllocatedSelectSql);
		} catch (SQLException e) {
			return null;
		}
		
		while (startIP <= endIP) {
			if (!isPublicIPAllocated(startIP, vlanDbId, isAllocatedStmt)) {
				try {
					stmt.clearParameters();
					stmt.setLong(1, startIP);
					stmt.setLong(2, vlanDbId);
					stmt.executeUpdate();
				} catch (Exception ex) {
				}
			} else {
				problemIPs.add(NetUtils.long2Ip(startIP));
			}
			startIP += 1;
		}
			
        return problemIPs;
	}
	
	private Vector<String> deletePrivateIPRange(Transaction txn, long startIP, long endIP, long podId, long zoneId) {
		String deleteSql = "DELETE FROM `cloud`.`op_dc_ip_address_alloc` WHERE ip_address = ? AND pod_id = ? AND data_center_id = ?";
		String isPrivateIPAllocatedSelectSql = "SELECT * FROM `cloud`.`op_dc_ip_address_alloc` WHERE ip_address = ? AND data_center_id = ? AND pod_id = ?";
		
		Vector<String> problemIPs = new Vector<String>();
		PreparedStatement stmt = null;
		PreparedStatement isAllocatedStmt = null;
				
		Connection conn = null;
		try {
			conn = txn.getConnection();
			stmt = conn.prepareStatement(deleteSql);
			isAllocatedStmt = conn.prepareStatement(isPrivateIPAllocatedSelectSql);
		} catch (SQLException e) {
			System.out.println("Exception: " + e.getMessage());
			printError("Unable to start DB connection to delete private IPs. Please contact Cloud Support.");
		}
		
		while (startIP <= endIP) {
			if (!isPrivateIPAllocated(NetUtils.long2Ip(startIP), podId, zoneId, isAllocatedStmt)) {
				try {
					stmt.clearParameters();
					stmt.setString(1, NetUtils.long2Ip(startIP));
					stmt.setLong(2, podId);
					stmt.setLong(3, zoneId);
					stmt.executeUpdate();
				} catch (Exception ex) {
				}
			} else {
				problemIPs.add(NetUtils.long2Ip(startIP));
			}
        	startIP += 1;
		}

        return problemIPs;
	}
	
	private boolean isPublicIPAllocated(long ip, long vlanDbId, PreparedStatement stmt) {
		try {
        	stmt.clearParameters();
        	stmt.setLong(1, ip);
        	stmt.setLong(2, vlanDbId);
        	ResultSet rs = stmt.executeQuery();
        	if (rs.next()) {
                return (rs.getString("allocated") != null);
            } else {
                return false;
            }
        } catch (SQLException ex) {
        	System.out.println(ex.getMessage());
            return true;
        }
	}
	
	private boolean isPrivateIPAllocated(String ip, long podId, long zoneId, PreparedStatement stmt) {
		try {
			stmt.clearParameters();
        	stmt.setString(1, ip);
        	stmt.setLong(2, zoneId);
        	stmt.setLong(3, podId);
        	ResultSet rs = stmt.executeQuery();
        	if (rs.next()) {
                return (rs.getString("taken") != null);
            } else {
                return false;
            }
        } catch (SQLException ex) {
        	System.out.println(ex.getMessage());
            return true;
        }
	}
	
	@DB
	public List<String> saveIPRange(String type, long podId, long zoneId, long vlanDbId, String startIP, String endIP, Long sourceNetworkId) {
    	long startIPLong = NetUtils.ip2Long(startIP);
    	long endIPLong = startIPLong;
    	if (endIP != null) {
            endIPLong = NetUtils.ip2Long(endIP);
        }
    	
    	Transaction txn = Transaction.currentTxn();
    	List<String> problemIPs = null;
    	
    	if (type.equals("public")) {
            problemIPs = savePublicIPRange(txn, startIPLong, endIPLong, zoneId, vlanDbId, sourceNetworkId);
        } else if (type.equals("private")) {
            problemIPs = savePrivateIPRange(txn, startIPLong, endIPLong, podId, zoneId);
        }
    	
    	String[] linkLocalIps = NetUtils.getLinkLocalIPRange(10);
    	long startLinkLocalIp = NetUtils.ip2Long(linkLocalIps[0]);
    	long endLinkLocalIp = NetUtils.ip2Long(linkLocalIps[1]);
    	
    	saveLinkLocalPrivateIPRange(txn, startLinkLocalIp,  endLinkLocalIp, podId, zoneId);
    	
    	return problemIPs;
    }
    
	public Vector<String> savePublicIPRange(Transaction txn, long startIP, long endIP, long zoneId, long vlanDbId, Long sourceNetworkId) {
		String insertSql = "INSERT INTO `cloud`.`user_ip_address` (public_ip_address, data_center_id, vlan_db_id, mac_address, source_network_id) VALUES (?, ?, ?, (select mac_address from `cloud`.`data_center` where id=?), ?)";
		String updateSql = "UPDATE `cloud`.`data_center` set mac_address = mac_address+1 where id=?";
		Vector<String> problemIPs = new Vector<String>();
		PreparedStatement stmt = null;
		
		Connection conn = null;
		try {
			conn = txn.getConnection();
		} catch (SQLException e) {
			return null;
		}
        
        while (startIP <= endIP) {
            try {
    		stmt = conn.prepareStatement(insertSql);
    		stmt.setString(1, NetUtils.long2Ip(startIP));
    		stmt.setLong(2, zoneId);
    		stmt.setLong(3, vlanDbId);
    		stmt.setLong(4, zoneId);
    		stmt.setLong(5, sourceNetworkId);
    		stmt.executeUpdate();
    		stmt.close();
    		stmt = conn.prepareStatement(updateSql);
    		stmt.setLong(1, zoneId);
            stmt.executeUpdate();
            stmt.close();
            } catch (Exception ex) {
                problemIPs.add(NetUtils.long2Ip(startIP));
            }
            startIP++;
        }
        
        return problemIPs;
	}
	
	public List<String> savePrivateIPRange(Transaction txn, long startIP, long endIP, long podId, long zoneId) {
		String insertSql = "INSERT INTO `cloud`.`op_dc_ip_address_alloc` (ip_address, data_center_id, pod_id, mac_address) VALUES (?, ?, ?, (select mac_address from `cloud`.`data_center` where id=?))";
        String updateSql = "UPDATE `cloud`.`data_center` set mac_address = mac_address+1 where id=?";
		Vector<String> problemIPs = new Vector<String>();
		
        try {
            Connection conn = null;
            conn = txn.getConnection();
            while (startIP <= endIP) {
                try {
                    PreparedStatement stmt = conn.prepareStatement(insertSql);
            		stmt.setString(1, NetUtils.long2Ip(startIP));
            		stmt.setLong(2, zoneId);
            		stmt.setLong(3, podId);
            		stmt.setLong(4, zoneId);
            		stmt.executeUpdate();
            		stmt.close();
                    stmt = conn.prepareStatement(updateSql);
                    stmt.setLong(1, zoneId);
                    stmt.executeUpdate();
                    stmt.close();
                } catch (Exception e) {
                    problemIPs.add(NetUtils.long2Ip(startIP));
                }
                startIP++;
            }
        } catch (Exception ex) {
            System.out.print(ex.getMessage());
            ex.printStackTrace();
        } 
        
        return problemIPs;
	}
	
	private Vector<String> saveLinkLocalPrivateIPRange(Transaction txn, long startIP, long endIP, long podId, long zoneId) {
		String insertSql = "INSERT INTO `cloud`.`op_dc_link_local_ip_address_alloc` (ip_address, data_center_id, pod_id) VALUES (?, ?, ?)";
		Vector<String> problemIPs = new Vector<String>();
		
		Connection conn = null;
		try {
			conn = txn.getConnection();
		} catch (SQLException e) {
			System.out.println("Exception: " + e.getMessage());
			printError("Unable to start DB connection to save private IPs. Please contact Cloud Support.");
		}
		
        try {
            long start = startIP;
            PreparedStatement stmt = conn.prepareStatement(insertSql);
            while (startIP <= endIP) {
        		stmt.setString(1, NetUtils.long2Ip(startIP++));
        		stmt.setLong(2, zoneId);
        		stmt.setLong(3, podId);
        		stmt.addBatch();
            }
            int[] results = stmt.executeBatch();
            for (int i = 0; i < results.length; i += 2) {
                if (results[i] == Statement.EXECUTE_FAILED) {
                    problemIPs.add(NetUtils.long2Ip(start + (i / 2)));
                }
            }
            stmt.close();
	    } catch (Exception ex) {
        }
        
        return problemIPs;
	}
	
	public static String getPublicNetmask(String zone) {
		return DatabaseConfig.getDatabaseValueString("SELECT * FROM `cloud`.`data_center` WHERE name = \"" + zone + "\"", "netmask",
								"Unable to start DB connection to read public netmask. Please contact Cloud Support.");
	}
		
	public static String getPublicGateway(String zone) {
		return DatabaseConfig.getDatabaseValueString("SELECT * FROM `cloud`.`data_center` WHERE name = \"" + zone + "\"", "gateway",
								"Unable to start DB connection to read public gateway. Please contact Cloud Support.");
	}
	
	public static String getGuestNetworkCidr(Long zoneId)
	{
		return DatabaseConfig.getDatabaseValueString("SELECT * FROM `cloud`.`data_center` WHERE id = \"" + zoneId + "\"","guest_network_cidr",
				"Unable to start DB connection to read guest cidr network. Please contact Cloud Support.");
	}
	
//	public static String getGuestIpNetwork() {
//		return DatabaseConfig.getDatabaseValueString("SELECT * FROM `cloud`.`configuration` WHERE name = \"guest.ip.network\"", "value",
//		"Unable to start DB connection to read guest IP network. Please contact Cloud Support.");
//	}
//	
//	public static String getGuestNetmask() {
//		return DatabaseConfig.getDatabaseValueString("SELECT * FROM `cloud`.`configuration` WHERE name = \"guest.netmask\"", "value",
//		"Unable to start DB connection to read guest netmask. Please contact Cloud Support.");
//	}
	
//	public static String getGuestSubnet() {
//		String guestIpNetwork = getGuestIpNetwork();
//		String guestNetmask = getGuestNetmask();
//		
//		if (guestIpNetwork == null || guestIpNetwork.isEmpty()) printError("Please enter a valid guest IP network address.");
//		if (guestNetmask == null || guestNetmask.isEmpty()) printError("Please enter a valid guest IP network netmask");
//		
//		return NetUtils.getSubNet(guestIpNetwork, guestNetmask);
//	}

//	public static long getGuestCidrSize() {
//		String guestNetmask = getGuestNetmask();
//		return NetUtils.getCidrSize(guestNetmask);
//	}
	
	public static boolean validCIDR(final String cidr) {
		if (cidr == null || cidr.isEmpty()) {
            return false;
        }
        String[] cidrPair = cidr.split("\\/");
        if (cidrPair.length != 2) {
            return false;
        }
        String cidrAddress = cidrPair[0];
        String cidrSize = cidrPair[1];
        if (!validIP(cidrAddress)) {
            return false;
        }
        int cidrSizeNum = -1;
        
        try {
        	cidrSizeNum = Integer.parseInt(cidrSize);
        } catch (Exception e) {
        	return false;
        }
        
        if (cidrSizeNum < 1 || cidrSizeNum > 32) {
            return false;
        }
        
        return true;
	}
	
	public static boolean validOrBlankIP(final String ip) {
	    if (ip == null || ip.isEmpty()) {
            return true;
        }
	    return validIP(ip);
	}
	    
	public static boolean validIP(final String ip) {
		final String[] ipAsList = ip.split("\\.");
		
	    // The IP address must have four octets
	    if (Array.getLength(ipAsList) != 4) {
	    	return false;
	    }
	    
	    for (int i = 0; i < 4; i++) {
	    	// Each octet must be an integer
	    	final String octetString = ipAsList[i];
	    	int octet;
	    	try {
	    		octet = Integer.parseInt(octetString);
	    	} catch(final Exception e) {
	    		return false;
	   		}
	    	// Each octet must be between 0 and 255, inclusive
	    	if (octet < 0 || octet > 255) {
                return false;
            }

	    	// Each octetString must have between 1 and 3 characters
	    	if (octetString.length() < 1 || octetString.length() > 3) {
                return false;
            }
	   		
	   	}
	    
	   	// IP is good, return true
		return true;
	}
	   
    public static boolean validIPRange(String startIP, String endIP) {
    	if (endIP == null || endIP.isEmpty()) {
            return true;
        }
    	
    	long startIPLong = NetUtils.ip2Long(startIP);
    	long endIPLong =  NetUtils.ip2Long(endIP);
	   	return (startIPLong < endIPLong);
    }
    
    public static boolean sameSubnet(final String ip1, final String ip2, final String netmask) {
    	if (ip1 == null || ip1.isEmpty() || ip2 == null || ip2.isEmpty()) {
            return true;
        }
    	String subnet1 = NetUtils.getSubNet(ip1, netmask);
    	String subnet2 = NetUtils.getSubNet(ip2, netmask);
    	
    	return (subnet1.equals(subnet2));
    }
    
    public static boolean sameSubnetCIDR(final String ip1, final String ip2, final long cidrSize) {
    	if (ip1 == null || ip1.isEmpty() || ip2 == null || ip2.isEmpty()) {
            return true;
        }
    	String subnet1 = NetUtils.getCidrSubNet(ip1, cidrSize);
    	String subnet2 = NetUtils.getCidrSubNet(ip2, cidrSize);
    	
    	return (subnet1.equals(subnet2));
    }
    
	private static void printError(String message) {
		DatabaseConfig.printError(message);
	}
	
}
