/*
 * Copyright (C) 2011 Citrix Systems, Inc.  All rights reserved.
 * 
 * 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 com.cloud.bridge.util;

import java.net.InetAddress;
import java.net.NetworkInterface;
import java.net.SocketException;
import java.net.UnknownHostException;
import java.util.ArrayList;
import java.util.Formatter;
import java.util.List;

import org.apache.log4j.Logger;

/**
 * @author Kelven Yang
 */
public class NetHelper {
    protected final static Logger logger = Logger.getLogger(NetHelper.class);

	public static String getHostName() {
        try {
            InetAddress localAddr = InetAddress.getLocalHost();
            if(localAddr != null) {
        		return localAddr.getHostName();
            }
        } catch(UnknownHostException e) {
        	logger.warn("UnknownHostException when trying to get host name. ", e);
        }
        return "localhost";
	}
    
    public static InetAddress[] getAllLocalInetAddresses() {
    	List<InetAddress> addrList = new ArrayList<InetAddress>();
    	try {
	    	for(NetworkInterface ifc : IteratorHelper.enumerationAsIterable(NetworkInterface.getNetworkInterfaces())) {
	    		if(ifc.isUp() && !ifc.isVirtual()) {
		    		for(InetAddress addr : IteratorHelper.enumerationAsIterable(ifc.getInetAddresses())) {
		    			addrList.add(addr);
		    		}
	    		}
	    	}
    	} catch (SocketException e) {
        	logger.warn("SocketException in getAllLocalInetAddresses().", e);
    	}
    	
    	InetAddress[] addrs = new InetAddress[addrList.size()];
    	if(addrList.size() > 0)
    		System.arraycopy(addrList.toArray(), 0, addrs, 0, addrList.size());
    	return addrs;
    }
    
    public static InetAddress getFirstNonLoopbackLocalInetAddress() {
    	InetAddress[] addrs = getAllLocalInetAddresses();
    	if(addrs != null) {
    		for(InetAddress addr : addrs) {
    			if(logger.isInfoEnabled())
    				logger.info("Check local InetAddress : " + addr.toString() + ", total count :" + addrs.length);
    			
    			if(!addr.isLoopbackAddress())
    				return addr;
    		}
    	}
    	
		logger.warn("Unable to determine a non-loopback address, local inet address count :" + addrs.length);
    	return null;
    }
    
    public static String getMacAddress(InetAddress address) {
    	StringBuffer sb = new StringBuffer();
    	Formatter formatter = new Formatter(sb);
    	try {
    		NetworkInterface ni = NetworkInterface.getByInetAddress(address);
    		byte[] mac = ni.getHardwareAddress();
	
			for (int i = 0; i < mac.length; i++) {
				formatter.format("%02X%s", mac[i], (i < mac.length - 1) ? ":" : "");
			}
		} catch (SocketException e) {
			logger.error("SocketException when trying to retrieve MAC address", e);
		}
		return sb.toString();
    }
}
