1/**
2 *
3 */
4package javax.jmdns.impl;
5
6import java.lang.reflect.Method;
7import java.net.InetAddress;
8import java.net.NetworkInterface;
9import java.net.SocketException;
10import java.util.Enumeration;
11import java.util.HashSet;
12import java.util.Set;
13import java.util.logging.Level;
14import java.util.logging.Logger;
15
16import javax.jmdns.NetworkTopologyDiscovery;
17
18/**
19 * This class implements NetworkTopologyDiscovery.
20 *
21 * @author Pierre Frisch
22 */
23public class NetworkTopologyDiscoveryImpl implements NetworkTopologyDiscovery {
24    private final static Logger logger = Logger.getLogger(NetworkTopologyDiscoveryImpl.class.getName());
25
26    private final Method        _isUp;
27
28    private final Method        _supportsMulticast;
29
30    /**
31     *
32     */
33    public NetworkTopologyDiscoveryImpl() {
34        super();
35        Method isUp;
36        try {
37            isUp = NetworkInterface.class.getMethod("isUp", (Class<?>[]) null);
38        } catch (Exception exception) {
39            // We do not want to throw anything if the method does not exist.
40            isUp = null;
41        }
42        _isUp = isUp;
43        Method supportsMulticast;
44        try {
45            supportsMulticast = NetworkInterface.class.getMethod("supportsMulticast", (Class<?>[]) null);
46        } catch (Exception exception) {
47            // We do not want to throw anything if the method does not exist.
48            supportsMulticast = null;
49        }
50        _supportsMulticast = supportsMulticast;
51    }
52
53    /*
54     * (non-Javadoc)
55     * @see javax.jmdns.JmmDNS.NetworkTopologyDiscovery#getInetAddresses()
56     */
57    @Override
58    public InetAddress[] getInetAddresses() {
59        Set<InetAddress> result = new HashSet<InetAddress>();
60        try {
61
62            for (Enumeration<NetworkInterface> nifs = NetworkInterface.getNetworkInterfaces(); nifs.hasMoreElements();) {
63                NetworkInterface nif = nifs.nextElement();
64                for (Enumeration<InetAddress> iaenum = nif.getInetAddresses(); iaenum.hasMoreElements();) {
65                    InetAddress interfaceAddress = iaenum.nextElement();
66                    if (logger.isLoggable(Level.FINEST)) {
67                        logger.finest("Found NetworkInterface/InetAddress: " + nif + " -- " + interfaceAddress);
68                    }
69                    if (this.useInetAddress(nif, interfaceAddress)) {
70                        result.add(interfaceAddress);
71                    }
72                }
73            }
74        } catch (SocketException se) {
75            logger.warning("Error while fetching network interfaces addresses: " + se);
76        }
77        return result.toArray(new InetAddress[result.size()]);
78    }
79
80    /*
81     * (non-Javadoc)
82     * @see javax.jmdns.JmmDNS.NetworkTopologyDiscovery#useInetAddress(java.net.NetworkInterface, java.net.InetAddress)
83     */
84    @Override
85    public boolean useInetAddress(NetworkInterface networkInterface, InetAddress interfaceAddress) {
86        try {
87            if (_isUp != null) {
88                try {
89                    if (!((Boolean) _isUp.invoke(networkInterface, (Object[]) null)).booleanValue()) {
90                        return false;
91                    }
92                } catch (Exception exception) {
93                    // We should hide that exception.
94                }
95            }
96            if (_supportsMulticast != null) {
97                try {
98                    if (!((Boolean) _supportsMulticast.invoke(networkInterface, (Object[]) null)).booleanValue()) {
99                        return false;
100                    }
101                } catch (Exception exception) {
102                    // We should hide that exception.
103                }
104            }
105            if (interfaceAddress.isLoopbackAddress()) {
106                return false;
107            }
108            return true;
109        } catch (Exception exception) {
110            return false;
111        }
112    }
113
114    /*
115     * (non-Javadoc)
116     * @see javax.jmdns.NetworkTopologyDiscovery#lockInetAddress(java.net.InetAddress)
117     */
118    @Override
119    public void lockInetAddress(InetAddress interfaceAddress) {
120        // Default implementation does nothing.
121    }
122
123    /*
124     * (non-Javadoc)
125     * @see javax.jmdns.NetworkTopologyDiscovery#unlockInetAddress(java.net.InetAddress)
126     */
127    @Override
128    public void unlockInetAddress(InetAddress interfaceAddress) {
129        // Default implementation does nothing.
130    }
131
132}
133