diff --git a/core/net/src/main/java/org/onosproject/cluster/impl/ClusterManager.java b/core/net/src/main/java/org/onosproject/cluster/impl/ClusterManager.java
index 9444969..1dcff08 100644
--- a/core/net/src/main/java/org/onosproject/cluster/impl/ClusterManager.java
+++ b/core/net/src/main/java/org/onosproject/cluster/impl/ClusterManager.java
@@ -42,7 +42,6 @@
 import org.slf4j.Logger;
 
 import com.google.common.collect.Collections2;
-import com.google.common.collect.Lists;
 import com.google.common.collect.Sets;
 
 import java.util.ArrayList;
@@ -139,11 +138,7 @@
         checkNotNull(nodes, "Nodes cannot be null");
         checkArgument(!nodes.isEmpty(), "Nodes cannot be empty");
 
-        ClusterMetadata metadata = ClusterMetadata.builder()
-                                                  .withName("default")
-                                                  .withControllerNodes(nodes)
-                                                  .withPartitions(buildDefaultPartitions(nodes))
-                                                  .build();
+        ClusterMetadata metadata = new ClusterMetadata("default", nodes, buildDefaultPartitions(nodes));
         clusterMetadataAdminService.setClusterMetadata(metadata);
         try {
             log.warn("Shutting down container for cluster reconfiguration!");
@@ -175,10 +170,10 @@
         }
     }
 
-    private static Collection<Partition> buildDefaultPartitions(Collection<ControllerNode> nodes) {
+    private static Set<Partition> buildDefaultPartitions(Collection<ControllerNode> nodes) {
         List<ControllerNode> sorted = new ArrayList<>(nodes);
         Collections.sort(sorted, (o1, o2) -> o1.id().toString().compareTo(o2.id().toString()));
-        Collection<Partition> partitions = Lists.newArrayList();
+        Set<Partition> partitions = Sets.newHashSet();
         // add p0 partition
         partitions.add(new DefaultPartition(PartitionId.from(0),
                                             Sets.newHashSet(Collections2.transform(nodes, ControllerNode::id))));
diff --git a/core/net/src/main/java/org/onosproject/cluster/impl/ClusterMetadataManager.java b/core/net/src/main/java/org/onosproject/cluster/impl/ClusterMetadataManager.java
index 1bb2182..49a24db 100644
--- a/core/net/src/main/java/org/onosproject/cluster/impl/ClusterMetadataManager.java
+++ b/core/net/src/main/java/org/onosproject/cluster/impl/ClusterMetadataManager.java
@@ -21,81 +21,117 @@
 import java.net.InetAddress;
 import java.net.NetworkInterface;
 import java.net.SocketException;
+import java.net.URI;
+import java.net.URISyntaxException;
 import java.util.Collection;
 import java.util.Enumeration;
 
 import org.apache.felix.scr.annotations.Activate;
 import org.apache.felix.scr.annotations.Component;
 import org.apache.felix.scr.annotations.Deactivate;
-import org.apache.felix.scr.annotations.Reference;
-import org.apache.felix.scr.annotations.ReferenceCardinality;
 import org.apache.felix.scr.annotations.Service;
 import org.onlab.packet.IpAddress;
 import org.onosproject.cluster.ClusterMetadata;
 import org.onosproject.cluster.ClusterMetadataAdminService;
 import org.onosproject.cluster.ClusterMetadataEvent;
 import org.onosproject.cluster.ClusterMetadataEventListener;
+import org.onosproject.cluster.ClusterMetadataProvider;
+import org.onosproject.cluster.ClusterMetadataProviderRegistry;
+import org.onosproject.cluster.ClusterMetadataProviderService;
 import org.onosproject.cluster.ClusterMetadataService;
-import org.onosproject.cluster.ClusterMetadataStore;
-import org.onosproject.cluster.ClusterMetadataStoreDelegate;
 import org.onosproject.cluster.ControllerNode;
-import org.onosproject.event.AbstractListenerManager;
+import org.onosproject.cluster.NodeId;
+import org.onosproject.cluster.PartitionId;
+import org.onosproject.net.provider.AbstractListenerProviderRegistry;
+import org.onosproject.net.provider.AbstractProviderService;
 import org.onosproject.store.service.Versioned;
 import org.slf4j.Logger;
 
+import com.google.common.base.Throwables;
+
 /**
  * Implementation of ClusterMetadataService.
  */
 @Component(immediate = true)
 @Service
 public class ClusterMetadataManager
-    extends AbstractListenerManager<ClusterMetadataEvent, ClusterMetadataEventListener>
-    implements ClusterMetadataService, ClusterMetadataAdminService {
+    extends AbstractListenerProviderRegistry<ClusterMetadataEvent,
+                                             ClusterMetadataEventListener,
+                                             ClusterMetadataProvider,
+                                             ClusterMetadataProviderService>
+    implements ClusterMetadataService, ClusterMetadataAdminService, ClusterMetadataProviderRegistry {
 
     private final Logger log = getLogger(getClass());
     private ControllerNode localNode;
 
-    private ClusterMetadataStoreDelegate delegate = new InternalStoreDelegate();
-
-    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
-    protected ClusterMetadataStore store;
-
     @Activate
     public void activate() {
-        store.setDelegate(delegate);
+        // FIXME: Need to ensure all cluster metadata providers are registered before we activate
         eventDispatcher.addSink(ClusterMetadataEvent.class, listenerRegistry);
-        establishSelfIdentity();
         log.info("Started");
     }
 
     @Deactivate
     public void deactivate() {
-        store.unsetDelegate(delegate);
         eventDispatcher.removeSink(ClusterMetadataEvent.class);
         log.info("Stopped");
     }
 
     @Override
     public ClusterMetadata getClusterMetadata() {
-        return Versioned.valueOrElse(store.getClusterMetadata(), null);
+        Versioned<ClusterMetadata> metadata = getProvider().getClusterMetadata();
+        return metadata.value();
+    }
+
+
+    @Override
+    protected ClusterMetadataProviderService createProviderService(
+            ClusterMetadataProvider provider) {
+        return new InternalClusterMetadataProviderService(provider);
     }
 
     @Override
     public ControllerNode getLocalNode() {
+        if (localNode == null) {
+            establishSelfIdentity();
+        }
         return localNode;
     }
 
     @Override
     public void setClusterMetadata(ClusterMetadata metadata) {
         checkNotNull(metadata, "Cluster metadata cannot be null");
-        store.setClusterMetadata(metadata);
+        ClusterMetadataProvider primaryProvider = getPrimaryProvider();
+        if (primaryProvider == null) {
+            throw new IllegalStateException("Missing primary provider. Cannot update cluster metadata");
+        }
+        primaryProvider.setClusterMetadata(metadata);
     }
 
-    // Store delegate to re-post events emitted from the store.
-    private class InternalStoreDelegate implements ClusterMetadataStoreDelegate {
-        @Override
-        public void notify(ClusterMetadataEvent event) {
-            post(event);
+    /**
+     * Returns the provider to use for fetching cluster metadata.
+     * @return cluster metadata provider
+     */
+    private ClusterMetadataProvider getProvider() {
+        ClusterMetadataProvider primaryProvider = getPrimaryProvider();
+        if (primaryProvider != null && primaryProvider.isAvailable()) {
+            return primaryProvider;
+        }
+        log.warn("Primary cluster metadata provider not available. Using default fallback.");
+        return getProvider("default");
+    }
+
+    /**
+     * Returns the primary provider for cluster metadata.
+     * @return primary cluster metadata provider
+     */
+    private ClusterMetadataProvider getPrimaryProvider() {
+        try {
+            URI uri = new URI(System.getProperty("onos.cluster.metadata.uri", "config:///cluster.json"));
+            return getProvider(uri.getScheme());
+        } catch (URISyntaxException e) {
+            Throwables.propagate(e);
+            return null;
         }
     }
 
@@ -129,4 +165,25 @@
             throw new IllegalStateException("Cannot determine local IP", e);
         }
     }
+
+    private class InternalClusterMetadataProviderService
+            extends AbstractProviderService<ClusterMetadataProvider>
+            implements ClusterMetadataProviderService {
+
+        InternalClusterMetadataProviderService(ClusterMetadataProvider provider) {
+            super(provider);
+        }
+
+        @Override
+        public void clusterMetadataChanged(Versioned<ClusterMetadata> newMetadata) {
+            log.info("Cluster metadata changed. New metadata: {}", newMetadata);
+            post(new ClusterMetadataEvent(ClusterMetadataEvent.Type.METADATA_CHANGED, newMetadata.value()));
+        }
+
+        @Override
+        public void newActiveMemberForPartition(PartitionId partitionId, NodeId nodeId) {
+            log.info("Node {} is active member for partition {}", nodeId, partitionId);
+            // TODO: notify listeners
+        }
+    }
 }
\ No newline at end of file
diff --git a/core/net/src/main/java/org/onosproject/cluster/impl/ConfigFileBasedClusterMetadataProvider.java b/core/net/src/main/java/org/onosproject/cluster/impl/ConfigFileBasedClusterMetadataProvider.java
new file mode 100644
index 0000000..825aa0a
--- /dev/null
+++ b/core/net/src/main/java/org/onosproject/cluster/impl/ConfigFileBasedClusterMetadataProvider.java
@@ -0,0 +1,235 @@
+/*
+ * Copyright 2015-2016 Open Networking Laboratory
+ *
+ * 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 org.onosproject.cluster.impl;
+
+import static org.slf4j.LoggerFactory.getLogger;
+
+import java.io.File;
+import java.io.IOException;
+import java.util.Set;
+import java.util.concurrent.atomic.AtomicReference;
+
+import org.apache.felix.scr.annotations.Activate;
+import org.apache.felix.scr.annotations.Component;
+import org.apache.felix.scr.annotations.Deactivate;
+import org.apache.felix.scr.annotations.Reference;
+import org.apache.felix.scr.annotations.ReferenceCardinality;
+import org.onlab.packet.IpAddress;
+import org.onosproject.cluster.ClusterMetadata;
+import org.onosproject.cluster.ClusterMetadataProvider;
+import org.onosproject.cluster.ClusterMetadataProviderRegistry;
+import org.onosproject.cluster.ClusterMetadataProviderService;
+import org.onosproject.cluster.ControllerNode;
+import org.onosproject.cluster.DefaultControllerNode;
+import org.onosproject.cluster.DefaultPartition;
+import org.onosproject.cluster.NodeId;
+import org.onosproject.cluster.Partition;
+import org.onosproject.cluster.PartitionId;
+import org.onosproject.net.provider.ProviderId;
+import org.onosproject.store.service.Versioned;
+import org.slf4j.Logger;
+
+import com.fasterxml.jackson.core.JsonGenerator;
+import com.fasterxml.jackson.core.JsonParser;
+import com.fasterxml.jackson.core.JsonProcessingException;
+import com.fasterxml.jackson.databind.DeserializationContext;
+import com.fasterxml.jackson.databind.JsonDeserializer;
+import com.fasterxml.jackson.databind.JsonNode;
+import com.fasterxml.jackson.databind.JsonSerializer;
+import com.fasterxml.jackson.databind.ObjectMapper;
+import com.fasterxml.jackson.databind.SerializerProvider;
+import com.fasterxml.jackson.databind.module.SimpleModule;
+import com.google.common.base.Throwables;
+import com.google.common.collect.Sets;
+import com.google.common.io.Files;
+
+import static com.google.common.base.Preconditions.checkState;
+
+/**
+ * Provider of {@link ClusterMetadata cluster metadata} sourced from a local config file.
+ */
+@Component(immediate = true)
+public class ConfigFileBasedClusterMetadataProvider implements ClusterMetadataProvider {
+
+    private final Logger log = getLogger(getClass());
+
+    // constants for filed names (used in serialization)
+    private static final String ID = "id";
+    private static final String PORT = "port";
+    private static final String IP = "ip";
+
+    private static final File CONFIG_FILE = new File("../config/cluster.json");
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    protected ClusterMetadataProviderRegistry providerRegistry;
+
+    private static final ProviderId PROVIDER_ID = new ProviderId("config", "none");
+    private AtomicReference<Versioned<ClusterMetadata>> cachedMetadata = new AtomicReference<>();
+
+    private ObjectMapper mapper;
+    private ClusterMetadataProviderService providerService;
+
+    @Activate
+    public void activate() {
+        mapper = new ObjectMapper();
+        SimpleModule module = new SimpleModule();
+        module.addSerializer(NodeId.class, new NodeIdSerializer());
+        module.addDeserializer(NodeId.class, new NodeIdDeserializer());
+        module.addSerializer(ControllerNode.class, new ControllerNodeSerializer());
+        module.addDeserializer(ControllerNode.class, new ControllerNodeDeserializer());
+        module.addDeserializer(Partition.class, new PartitionDeserializer());
+        module.addSerializer(PartitionId.class, new PartitionIdSerializer());
+        module.addDeserializer(PartitionId.class, new PartitionIdDeserializer());
+        mapper.registerModule(module);
+        providerService = providerRegistry.register(this);
+        log.info("Started");
+    }
+
+    @Deactivate
+    public void deactivate() {
+        providerRegistry.unregister(this);
+        log.info("Stopped");
+    }
+
+    @Override
+    public ProviderId id() {
+        return PROVIDER_ID;
+    }
+
+    @Override
+    public Versioned<ClusterMetadata> getClusterMetadata() {
+        checkState(isAvailable());
+        synchronized (this) {
+            if (cachedMetadata.get() == null) {
+                loadMetadata();
+            }
+            return cachedMetadata.get();
+        }
+    }
+
+    @Override
+    public void setClusterMetadata(ClusterMetadata metadata) {
+        try {
+            Files.createParentDirs(CONFIG_FILE);
+            mapper.writeValue(CONFIG_FILE, metadata);
+            providerService.clusterMetadataChanged(new Versioned<>(metadata, CONFIG_FILE.lastModified()));
+        } catch (IOException e) {
+            Throwables.propagate(e);
+        }
+    }
+
+    @Override
+    public void addActivePartitionMember(PartitionId partitionId, NodeId nodeId) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public void removeActivePartitionMember(PartitionId partitionId, NodeId nodeId) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public Set<NodeId> getActivePartitionMembers(PartitionId partitionId) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public boolean isAvailable() {
+        return CONFIG_FILE.exists();
+    }
+
+    private void loadMetadata() {
+        ClusterMetadata metadata = null;
+        long version = 0;
+        try {
+            metadata = mapper.readValue(CONFIG_FILE, ClusterMetadata.class);
+            version = metadata.hashCode();
+        } catch (IOException e) {
+            Throwables.propagate(e);
+        }
+        cachedMetadata.set(new Versioned<>(new ClusterMetadata(PROVIDER_ID,
+                                                               metadata.getName(),
+                                                               Sets.newHashSet(metadata.getNodes()),
+                                                               Sets.newHashSet(metadata.getPartitions())),
+                                           version));
+    }
+
+    private static class PartitionDeserializer extends JsonDeserializer<Partition> {
+        @Override
+        public Partition deserialize(JsonParser jp, DeserializationContext ctxt)
+                throws IOException, JsonProcessingException {
+            return jp.readValueAs(DefaultPartition.class);
+        }
+    }
+
+    private static class PartitionIdSerializer extends JsonSerializer<PartitionId> {
+        @Override
+        public void serialize(PartitionId partitionId, JsonGenerator jgen, SerializerProvider provider)
+          throws IOException, JsonProcessingException {
+            jgen.writeNumber(partitionId.asInt());
+        }
+    }
+
+    private class PartitionIdDeserializer extends JsonDeserializer<PartitionId> {
+        @Override
+        public PartitionId deserialize(JsonParser jp, DeserializationContext ctxt)
+          throws IOException, JsonProcessingException {
+            JsonNode node = jp.getCodec().readTree(jp);
+            return new PartitionId(node.asInt());
+        }
+    }
+
+    private static class ControllerNodeSerializer extends JsonSerializer<ControllerNode> {
+        @Override
+        public void serialize(ControllerNode node, JsonGenerator jgen, SerializerProvider provider)
+          throws IOException, JsonProcessingException {
+            jgen.writeStartObject();
+            jgen.writeStringField(ID, node.id().toString());
+            jgen.writeStringField(IP, node.ip().toString());
+            jgen.writeNumberField(PORT, node.tcpPort());
+            jgen.writeEndObject();
+        }
+    }
+
+    private static class ControllerNodeDeserializer extends JsonDeserializer<ControllerNode> {
+        @Override
+        public ControllerNode deserialize(JsonParser jp, DeserializationContext ctxt)
+                throws IOException, JsonProcessingException {
+            JsonNode node = jp.getCodec().readTree(jp);
+            NodeId nodeId = new NodeId(node.get(ID).textValue());
+            IpAddress ip = IpAddress.valueOf(node.get(IP).textValue());
+            int port = node.get(PORT).asInt();
+            return new DefaultControllerNode(nodeId, ip, port);
+        }
+    }
+
+    private static class NodeIdSerializer extends JsonSerializer<NodeId> {
+        @Override
+        public void serialize(NodeId nodeId, JsonGenerator jgen, SerializerProvider provider)
+          throws IOException, JsonProcessingException {
+            jgen.writeString(nodeId.toString());
+        }
+    }
+
+    private class NodeIdDeserializer extends JsonDeserializer<NodeId> {
+        @Override
+        public NodeId deserialize(JsonParser jp, DeserializationContext ctxt)
+          throws IOException, JsonProcessingException {
+            JsonNode node = jp.getCodec().readTree(jp);
+            return new NodeId(node.asText());
+        }
+    }
+}
\ No newline at end of file
diff --git a/core/net/src/main/java/org/onosproject/cluster/impl/DefaultClusterMetadataProvider.java b/core/net/src/main/java/org/onosproject/cluster/impl/DefaultClusterMetadataProvider.java
new file mode 100644
index 0000000..7566e48
--- /dev/null
+++ b/core/net/src/main/java/org/onosproject/cluster/impl/DefaultClusterMetadataProvider.java
@@ -0,0 +1,186 @@
+/*
+ * Copyright 2015-2016 Open Networking Laboratory
+ *
+ * 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 org.onosproject.cluster.impl;
+
+import static java.net.NetworkInterface.getNetworkInterfaces;
+import static org.slf4j.LoggerFactory.getLogger;
+
+import java.net.Inet4Address;
+import java.net.InetAddress;
+import java.net.NetworkInterface;
+import java.util.Collections;
+import java.util.Set;
+import java.util.concurrent.atomic.AtomicReference;
+import java.util.function.Function;
+
+import org.apache.felix.scr.annotations.Activate;
+import org.apache.felix.scr.annotations.Component;
+import org.apache.felix.scr.annotations.Deactivate;
+import org.apache.felix.scr.annotations.Reference;
+import org.apache.felix.scr.annotations.ReferenceCardinality;
+import org.onlab.packet.IpAddress;
+import org.onosproject.cluster.ClusterMetadata;
+import org.onosproject.cluster.ClusterMetadataProvider;
+import org.onosproject.cluster.ClusterMetadataProviderRegistry;
+import org.onosproject.cluster.ControllerNode;
+import org.onosproject.cluster.DefaultControllerNode;
+import org.onosproject.cluster.DefaultPartition;
+import org.onosproject.cluster.NodeId;
+import org.onosproject.cluster.Partition;
+import org.onosproject.cluster.PartitionId;
+import org.onosproject.net.provider.ProviderId;
+import org.onosproject.store.service.Versioned;
+import org.slf4j.Logger;
+
+import com.google.common.collect.ImmutableSet;
+import com.google.common.collect.Sets;
+
+/**
+ * Provider of default {@link ClusterMetadata cluster metadata}.
+ */
+@Component(immediate = true)
+public class DefaultClusterMetadataProvider implements ClusterMetadataProvider {
+
+    private final Logger log = getLogger(getClass());
+
+    @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
+    protected ClusterMetadataProviderRegistry providerRegistry;
+
+    private static final String ONOS_IP = "ONOS_IP";
+    private static final String ONOS_INTERFACE = "ONOS_INTERFACE";
+    private static final String ONOS_ALLOW_IPV6 = "ONOS_ALLOW_IPV6";
+    private static final String DEFAULT_ONOS_INTERFACE = "eth0";
+    private static final int DEFAULT_ONOS_PORT = 9876;
+    private static final ProviderId PROVIDER_ID = new ProviderId("default", "none");
+    private AtomicReference<Versioned<ClusterMetadata>> cachedMetadata = new AtomicReference<>();
+
+    @Activate
+    public void activate() {
+        String localIp = getSiteLocalAddress();
+        ControllerNode localNode =
+                new DefaultControllerNode(new NodeId(localIp), IpAddress.valueOf(localIp), DEFAULT_ONOS_PORT);
+        // p0 partition
+        Partition basePartition = new DefaultPartition(PartitionId.from(0), Sets.newHashSet(localNode.id()));
+        // p1 partition
+        Partition extendedPartition = new DefaultPartition(PartitionId.from(1), Sets.newHashSet(localNode.id()));
+        ClusterMetadata metadata = new ClusterMetadata(PROVIDER_ID,
+                                        "default",
+                                        ImmutableSet.of(localNode),
+                                        ImmutableSet.of(basePartition, extendedPartition));
+        long version = System.currentTimeMillis();
+        cachedMetadata.set(new Versioned<>(metadata, version));
+        providerRegistry.register(this);
+        log.info("Started");
+    }
+
+    @Deactivate
+    public void deactivate() {
+        providerRegistry.unregister(this);
+        log.info("Stopped");
+    }
+
+    @Override
+    public ProviderId id() {
+        return PROVIDER_ID;
+    }
+
+    @Override
+    public Versioned<ClusterMetadata> getClusterMetadata() {
+        return cachedMetadata.get();
+    }
+
+    @Override
+    public void setClusterMetadata(ClusterMetadata metadata) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public void addActivePartitionMember(PartitionId partitionId, NodeId nodeId) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public void removeActivePartitionMember(PartitionId partitionId, NodeId nodeId) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public Set<NodeId> getActivePartitionMembers(PartitionId partitionId) {
+        throw new UnsupportedOperationException();
+    }
+
+    @Override
+    public boolean isAvailable() {
+        return true;
+    }
+
+    private static String getSiteLocalAddress() {
+
+        /*
+         * If the IP ONOS should use is set via the environment variable we will assume it is valid and should be used.
+         * Setting the IP address takes presidence over setting the interface via the environment.
+         */
+        String useOnosIp = System.getenv(ONOS_IP);
+        if (useOnosIp != null) {
+            return useOnosIp;
+        }
+
+        // Read environment variables for IP interface information or set to default
+        String useOnosInterface = System.getenv(ONOS_INTERFACE);
+        if (useOnosInterface == null) {
+            useOnosInterface = DEFAULT_ONOS_INTERFACE;
+        }
+
+        // Capture if they want to limit IP address selection to only IPv4 (default).
+        boolean allowIPv6 = (System.getenv(ONOS_ALLOW_IPV6) != null);
+
+        Function<NetworkInterface, IpAddress> ipLookup = nif -> {
+            IpAddress fallback = null;
+
+            // nif can be null if the interface name specified doesn't exist on the node's host
+            if (nif != null) {
+                for (InetAddress address : Collections.list(nif.getInetAddresses())) {
+                    if (address.isSiteLocalAddress() && (allowIPv6 || address instanceof Inet4Address)) {
+                        return IpAddress.valueOf(address);
+                    }
+                    if (fallback == null && !address.isLoopbackAddress() && !address.isMulticastAddress()
+                        && (allowIPv6 || address instanceof Inet4Address)) {
+                        fallback = IpAddress.valueOf(address);
+                    }
+                }
+            }
+            return fallback;
+        };
+        try {
+            IpAddress ip = ipLookup.apply(NetworkInterface.getByName(useOnosInterface));
+            if (ip != null) {
+                return ip.toString();
+            }
+            for (NetworkInterface nif : Collections.list(getNetworkInterfaces())) {
+                if (!nif.getName().equals(useOnosInterface)) {
+                    ip = ipLookup.apply(nif);
+                    if (ip != null) {
+                        return ip.toString();
+                    }
+                }
+            }
+        } catch (Exception e) {
+            throw new IllegalStateException("Unable to get network interfaces", e);
+        }
+
+        return IpAddress.valueOf(InetAddress.getLoopbackAddress()).toString();
+    }
+}
\ No newline at end of file
