http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/geo/HostGeoInfo.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/geo/HostGeoInfo.java 
b/core/src/main/java/org/apache/brooklyn/location/geo/HostGeoInfo.java
deleted file mode 100644
index fc88cd2..0000000
--- a/core/src/main/java/org/apache/brooklyn/location/geo/HostGeoInfo.java
+++ /dev/null
@@ -1,205 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you 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.apache.brooklyn.location.geo;
-
-import java.io.Serializable;
-import java.net.InetAddress;
-
-import javax.annotation.Nullable;
-
-import org.apache.brooklyn.api.entity.Entity;
-import org.apache.brooklyn.api.location.AddressableLocation;
-import org.apache.brooklyn.api.location.Location;
-import org.apache.brooklyn.location.core.AbstractLocation;
-import org.apache.brooklyn.location.core.LocationConfigKeys;
-import org.apache.brooklyn.util.core.flags.TypeCoercions;
-import org.apache.brooklyn.util.exceptions.Exceptions;
-import org.apache.brooklyn.util.guava.Maybe;
-import org.apache.brooklyn.util.internal.BrooklynSystemProperties;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import com.google.common.base.Objects;
-
-/**
- * Encapsulates geo-IP information for a given host.
- */
-public class HostGeoInfo implements Serializable {
-    
-    private static final long serialVersionUID = -5866759901535266181L;
-
-    public static final Logger log = 
LoggerFactory.getLogger(HostGeoInfo.class);
-
-    /** the IP address */
-    public final String address;
-    
-    public final String displayName;
-    
-    public final double latitude;
-    public final double longitude;
-    
-    private static Maybe<HostGeoLookup> cachedLookup = null;
-
-    public static HostGeoInfo create(String address, String displayName, 
double latitude, double longitude) {
-        return new HostGeoInfo(address, displayName, latitude, longitude);
-    }
-    
-    public static HostGeoInfo fromIpAddress(InetAddress address) {
-        try {
-            HostGeoLookup lookup = getDefaultLookup();
-            if (lookup!=null)
-                return lookup.getHostGeoInfo(address);
-        } catch (Exception e) {
-            if (log.isDebugEnabled())
-                log.debug("unable to look up geo DNS info for "+address, e);
-        }
-        return null;
-    }
-
-    @Nullable
-    public static HostGeoLookup getDefaultLookup() throws 
InstantiationException, IllegalAccessException, ClassNotFoundException {
-        if (cachedLookup==null) {
-            cachedLookup = Maybe.of(findHostGeoLookupImpl());
-        }                
-        return cachedLookup.get();
-    }
-    
-    public static void clearCachedLookup() {
-        cachedLookup = null;
-    }
-    
-    /** returns null if cannot be set */
-    public static HostGeoInfo fromLocation(Location l) {
-        if (l==null) return null;
-        
-        Location la = l;
-        HostGeoInfo resultFromLocation = null;
-        while (la!=null) {
-            if (la instanceof HasHostGeoInfo) {
-                resultFromLocation = ((HasHostGeoInfo)l).getHostGeoInfo();
-                if (resultFromLocation!=null) break;
-            }
-            la = la.getParent();
-        }
-        if (resultFromLocation!=null && l==la) {
-            // from the location
-            return resultFromLocation;
-        }
-        // resultFromLocation may be inherited, in which case we will copy it 
later
-        
-        InetAddress address = findIpAddress(l);
-        Object latitude = l.getConfig(LocationConfigKeys.LATITUDE);
-        Object longitude = l.getConfig(LocationConfigKeys.LONGITUDE);
-
-        if (resultFromLocation!=null && (latitude == null || longitude == 
null)) {
-            latitude = resultFromLocation.latitude;
-            longitude = resultFromLocation.longitude;            
-        }
-        if (address!=null && (latitude == null || longitude == null)) {
-            HostGeoInfo geo = fromIpAddress(address);
-            if (geo==null) return null;
-            latitude = geo.latitude;
-            longitude = geo.longitude;
-        }
-        
-        if (latitude==null || longitude==null)
-            return null;
-        
-        Exception error=null;
-        try {
-            latitude = TypeCoercions.castPrimitive(latitude, Double.class);
-            longitude = TypeCoercions.castPrimitive(longitude, Double.class);
-        } catch (Exception e) {
-            Exceptions.propagateIfFatal(e);
-            error = e;
-        }
-        if (error!=null || !(latitude instanceof Double) || !(longitude 
instanceof Double))
-            throw new IllegalArgumentException("Location "+l+" specifies 
invalid type of lat/long: " +
-                    "lat="+latitude+" (type "+(latitude==null ? null : 
latitude.getClass())+"); " +
-                    "lon="+longitude+" (type "+(longitude==null ? null : 
longitude.getClass())+")", error);
-        
-        HostGeoInfo result = new HostGeoInfo(address!=null ? 
address.getHostAddress() : null, l.getDisplayName(), (Double) latitude, 
(Double) longitude);
-        if (l instanceof AbstractLocation) {
-            ((AbstractLocation)l).setHostGeoInfo(result);
-        }
-        return result;
-    }
-    
-    private static HostGeoLookup findHostGeoLookupImpl() throws 
InstantiationException, IllegalAccessException, ClassNotFoundException {
-        String type = BrooklynSystemProperties.HOST_GEO_LOOKUP_IMPL.getValue();
-        /* utrace seems more accurate than geobytes, and it gives a report of 
how many tokens are left;
-         * but maxmind if it's installed locally is even better (does not 
require remote lookup),
-         * so use it if available */
-        if (type==null) {
-            if (MaxMind2HostGeoLookup.getDatabaseReader()!=null)
-                return new MaxMind2HostGeoLookup();
-            log.debug("Using Utrace remote for geo lookup because MaxMind2 is 
not available");
-            return new UtraceHostGeoLookup();
-        }
-        if (type.isEmpty()) return null;
-        return (HostGeoLookup) Class.forName(type).newInstance();
-    }
-
-    public static HostGeoInfo fromEntity(Entity e) {
-        for (Location l : e.getLocations()) {
-            HostGeoInfo hgi = fromLocation(l);
-            if (hgi != null)
-                return hgi;
-        }
-        return null;
-    }
-    
-    public static InetAddress findIpAddress(Location l) {
-        if (l == null)
-            return null;
-        if (l instanceof AddressableLocation)
-            return ((AddressableLocation) l).getAddress();
-        return findIpAddress(l.getParent());
-    }
-    
-    public HostGeoInfo(String address, String displayName, double latitude, 
double longitude) {
-        this.address = address;
-        this.displayName = displayName==null ? "" : displayName;
-        this.latitude = latitude;
-        this.longitude = longitude;
-    }
-
-    public String getAddress() {
-        return address;
-    }
-    
-    @Override
-    public String toString() {
-        return "HostGeoInfo["+displayName+": "+(address!=null ? address : 
"(no-address)")+" at ("+latitude+","+longitude+")]";
-    }
-    
-    @Override
-    public boolean equals(Object o) {
-        // Slight cheat: only includes the address + displayName field 
(displayName to allow overloading localhost etc)
-        return (o instanceof HostGeoInfo) && Objects.equal(address, 
((HostGeoInfo) o).address)
-                && Objects.equal(displayName, ((HostGeoInfo) o).displayName);
-    }
-    
-    @Override
-    public int hashCode() {
-        // Slight cheat: only includes the address + displayName field 
(displayName to allow overloading localhost etc)
-        return Objects.hashCode(address, displayName);
-    }
-    
-}

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/geo/HostGeoLookup.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/geo/HostGeoLookup.java 
b/core/src/main/java/org/apache/brooklyn/location/geo/HostGeoLookup.java
deleted file mode 100644
index db58276..0000000
--- a/core/src/main/java/org/apache/brooklyn/location/geo/HostGeoLookup.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you 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.apache.brooklyn.location.geo;
-
-import java.net.InetAddress;
-
-public interface HostGeoLookup {
-
-    public HostGeoInfo getHostGeoInfo(InetAddress address) throws Exception;
-    
-}

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/geo/LocalhostExternalIpLoader.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/geo/LocalhostExternalIpLoader.java
 
b/core/src/main/java/org/apache/brooklyn/location/geo/LocalhostExternalIpLoader.java
deleted file mode 100644
index 7ded0ba..0000000
--- 
a/core/src/main/java/org/apache/brooklyn/location/geo/LocalhostExternalIpLoader.java
+++ /dev/null
@@ -1,177 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you 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.apache.brooklyn.location.geo;
-
-import java.util.Collections;
-import java.util.List;
-import java.util.concurrent.Callable;
-import java.util.concurrent.CountDownLatch;
-import java.util.concurrent.atomic.AtomicBoolean;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
-
-import org.apache.brooklyn.util.core.ResourceUtils;
-import org.apache.brooklyn.util.exceptions.Exceptions;
-import org.apache.brooklyn.util.text.StringPredicates;
-import org.apache.brooklyn.util.time.Duration;
-import org.apache.brooklyn.util.time.Durations;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import com.google.common.annotations.VisibleForTesting;
-import com.google.common.base.Predicates;
-import com.google.common.base.Splitter;
-import com.google.common.collect.Iterables;
-import com.google.common.collect.Lists;
-
-public class LocalhostExternalIpLoader {
-
-    public static final Logger LOG = 
LoggerFactory.getLogger(LocalhostExternalIpLoader.class);
-
-    private static final AtomicBoolean retrievingLocalExternalIp = new 
AtomicBoolean(false);
-    private static final CountDownLatch triedLocalExternalIp = new 
CountDownLatch(1);
-    private static volatile String localExternalIp;
-
-    private static class IpLoader implements Callable<String> {
-        private static final Pattern ipPattern = Pattern.compile(
-                
"\\b((25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])\\.){3}(25[0-5]|2[0-4][0-9]|1[0-9][0-9]|[1-9]?[0-9])\\b");
-        final String url;
-
-        protected IpLoader(String url) {
-            this.url = url;
-        }
-
-        @Override
-        public String call() {
-            String response = 
ResourceUtils.create(LocalhostExternalIpLoader.class)
-                    .getResourceAsString(url).trim();
-            return postProcessResponse(response);
-        }
-
-        String postProcessResponse(String response) {
-            Matcher matcher = ipPattern.matcher(response);
-            boolean matched = matcher.find();
-            if (!matched) {
-                LOG.error("No IP address matched in output from {}: {}", url, 
response);
-                return null;
-            } else {
-                return matcher.group();
-            }
-        }
-    }
-
-    @VisibleForTesting
-    static List<String> getIpAddressWebsites() {
-        String file = new ResourceUtils(LocalhostExternalIpLoader.class)
-                
.getResourceAsString("classpath://org/apache/brooklyn/location/geo/external-ip-address-resolvers.txt");
-        Iterable<String> lines = Splitter.on('\n')
-                .omitEmptyStrings()
-                .trimResults()
-                .split(file);
-        List<String> urls = Lists.newArrayList(Iterables.filter(lines, 
Predicates.not(StringPredicates.startsWith("#"))));
-        Collections.shuffle(urls);
-        return urls;
-    }
-
-    @VisibleForTesting
-    static String getIpAddressFrom(String url) {
-        return new IpLoader(url).call();
-    }
-    
-    /** As {@link #getLocalhostIpWithin(Duration)} but returning 127.0.0.1 if 
not accessible */
-    public static String getLocalhostIpQuicklyOrDefault() {
-        String result = doLoad(Duration.seconds(2));
-        if (result==null) return "127.0.0.1";
-        return result;
-    }
-
-    /** As {@link #getLocalhostIpWithin(Duration)} but without the time limit 
cut-off, failing if the load gives an error. */
-    public static String getLocalhostIpWaiting() {
-        return getLocalhostIpWithin(null);
-    }
-
-    /**
-     * Attempts to load the public IP address of localhost, failing if the load
-     * does not complete within the given duration.
-     * @return The public IP address of localhost
-     */
-    public static String getLocalhostIpWithin(Duration timeout) {
-        String result = doLoad(timeout);
-        if (result == null) {
-            throw new IllegalStateException("Unable to retrieve external IP 
for localhost; network may be down or slow or remote service otherwise not 
responding");
-        }
-        return result;
-    }
-
-    /**
-     * Requests URLs returned by {@link #getIpAddressWebsites()} until one 
returns an IP address.
-     * The address is assumed to be the external IP address of localhost.
-     * @param blockFor The maximum duration to wait for the IP address to be 
resolved.
-     *                 An indefinite way if null.
-     * @return A string in IPv4 format, or null if no such address could be 
ascertained.
-     */
-    private static String doLoad(Duration blockFor) {
-        if (localExternalIp != null) {
-            return localExternalIp;
-        }
-
-        final List<String> candidateUrls = getIpAddressWebsites();
-        if (candidateUrls.isEmpty()) {
-            LOG.debug("No candidate URLs to use to determine external IP of 
localhost");
-            return null;
-        }
-
-        // do in private thread, otherwise blocks for 30s+ on dodgy network!
-        // (we can skip it if someone else is doing it, we have synch lock so 
we'll get notified)
-        if (retrievingLocalExternalIp.compareAndSet(false, true)) {
-            new Thread() {
-                public void run() {
-                    for (String url : candidateUrls) {
-                        try {
-                            LOG.debug("Looking up external IP of this host 
from {} in private thread {}", url, Thread.currentThread());
-                            localExternalIp = new IpLoader(url).call();
-                            LOG.debug("Finished looking up external IP of this 
host from {} in private thread, result {}", url, localExternalIp);
-                            break;
-                        } catch (Throwable t) {
-                            LOG.debug("Unable to look up external IP of this 
host from {}, probably offline {})", url, t);
-                        } finally {
-                            retrievingLocalExternalIp.set(false);
-                            triedLocalExternalIp.countDown();
-                        }
-                    }
-                }
-            }.start();
-        }
-
-        try {
-            if (blockFor!=null) {
-                Durations.await(triedLocalExternalIp, blockFor);
-            } else {
-                triedLocalExternalIp.await();
-            }
-        } catch (InterruptedException e) {
-            throw Exceptions.propagate(e);
-        }
-        if (localExternalIp == null) {
-            return null;
-        }
-        return localExternalIp;
-    }
-
-}

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/geo/MaxMind2HostGeoLookup.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/geo/MaxMind2HostGeoLookup.java
 
b/core/src/main/java/org/apache/brooklyn/location/geo/MaxMind2HostGeoLookup.java
deleted file mode 100644
index b2fc5c9..0000000
--- 
a/core/src/main/java/org/apache/brooklyn/location/geo/MaxMind2HostGeoLookup.java
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you 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.apache.brooklyn.location.geo;
-
-import java.io.File;
-import java.io.IOException;
-import java.net.InetAddress;
-import java.net.MalformedURLException;
-
-import org.apache.brooklyn.util.internal.BrooklynSystemProperties;
-import org.apache.brooklyn.util.net.Networking;
-import org.apache.brooklyn.util.text.Strings;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import com.google.common.base.Throwables;
-import com.google.common.collect.Lists;
-import com.maxmind.geoip2.DatabaseReader;
-import com.maxmind.geoip2.model.CityResponse;
-import com.maxmind.geoip2.record.Subdivision;
-
-public class MaxMind2HostGeoLookup implements HostGeoLookup {
-
-    public static final Logger log = 
LoggerFactory.getLogger(MaxMind2HostGeoLookup.class);
-    
-    static final String MAXMIND_DB_URL = 
"http://dev.maxmind.com/geoip/geoip2/geolite2/#Downloads";;
-    // TODO this should be configurable from system property or 
brooklyn.properties
-    // TODO and should use properties BrooklynServerConfig.MGMT_BASE_DIR (but 
hard to get mgmt properties here!)
-    static final String MAXMIND_DB_PATH = 
System.getProperty("user.home")+"/"+".brooklyn/"+"GeoLite2-City.mmdb";
-    
-    static boolean lookupFailed = false;
-    static DatabaseReader databaseReader = null;
-    
-    public static synchronized DatabaseReader getDatabaseReader() {
-        if (databaseReader!=null) return databaseReader;
-        try {
-            File f = new File(MAXMIND_DB_PATH);
-            databaseReader = new DatabaseReader.Builder(f).build();
-        } catch (IOException e) {
-            lookupFailed = true;
-            log.debug("MaxMind geo lookup unavailable; either download and 
unpack the latest "+
-                    "binary from "+MAXMIND_DB_URL+" into "+MAXMIND_DB_PATH+", 
"+
-                    "or specify a different HostGeoLookup implementation with 
the key "+
-                    
BrooklynSystemProperties.HOST_GEO_LOOKUP_IMPL.getPropertyName()+" (error trying 
to read: "+e+")");
-        }
-        return databaseReader;
-    }
-    
-    public HostGeoInfo getHostGeoInfo(InetAddress address) throws 
MalformedURLException, IOException {
-        if (lookupFailed) return null;
-        
-        DatabaseReader ll = getDatabaseReader();
-        if (ll==null) return null;
-        
-        InetAddress extAddress = address;
-        if (Networking.isPrivateSubnet(extAddress)) extAddress = 
InetAddress.getByName(LocalhostExternalIpLoader.getLocalhostIpQuicklyOrDefault());
-        
-        try {
-            CityResponse l = ll.city(extAddress);
-            if (l==null) {
-                if (log.isDebugEnabled()) log.debug("Geo info failed to find 
location for address {}, using {}", extAddress, ll);
-                return null;
-            }
-            
-            StringBuilder name = new StringBuilder();
-            
-            if (l.getCity()!=null && l.getCity().getName()!=null) 
name.append(l.getCity().getName());
-            
-            if (l.getSubdivisions()!=null) {
-                for (Subdivision subd: Lists.reverse(l.getSubdivisions())) {
-                    if (name.length()>0) name.append(", ");
-                    // prefer e.g. USA state codes over state names
-                    if (!Strings.isBlank(subd.getIsoCode())) 
-                        name.append(subd.getIsoCode());
-                    else
-                        name.append(subd.getName());
-                }
-            }
-            
-            if (l.getCountry()!=null) {
-                if (name.length()==0) {
-                    name.append(l.getCountry().getName());
-                } else {
-                    name.append(" ("); 
name.append(l.getCountry().getIsoCode()); name.append(")");
-                }
-            }
-
-            
-            HostGeoInfo geo = new HostGeoInfo(address.getHostName(), 
name.toString(), l.getLocation().getLatitude(), l.getLocation().getLongitude());
-            log.debug("Geo info lookup (MaxMind DB) for "+address+" returned: 
"+geo);
-            return geo;
-        } catch (Exception e) {
-            if (log.isDebugEnabled())
-                log.debug("Geo info lookup failed: "+e);
-            throw Throwables.propagate(e);
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/geo/UtraceHostGeoLookup.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/geo/UtraceHostGeoLookup.java 
b/core/src/main/java/org/apache/brooklyn/location/geo/UtraceHostGeoLookup.java
deleted file mode 100644
index 795ccb8..0000000
--- 
a/core/src/main/java/org/apache/brooklyn/location/geo/UtraceHostGeoLookup.java
+++ /dev/null
@@ -1,209 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements.  See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership.  The ASF licenses this file
- * to you 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.apache.brooklyn.location.geo;
-
-import groovy.util.Node;
-import groovy.util.NodeList;
-import groovy.util.XmlParser;
-
-import java.io.IOException;
-import java.net.InetAddress;
-import java.net.MalformedURLException;
-import java.util.concurrent.atomic.AtomicReference;
-
-import javax.annotation.Nonnull;
-import javax.annotation.Nullable;
-
-import org.apache.brooklyn.util.exceptions.Exceptions;
-import org.apache.brooklyn.util.javalang.JavaClassNames;
-import org.apache.brooklyn.util.net.Networking;
-import org.apache.brooklyn.util.time.Duration;
-import org.apache.brooklyn.util.time.Durations;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import com.google.common.base.Throwables;
-
-public class UtraceHostGeoLookup implements HostGeoLookup {
-
-
-    /*
-     * 
-http://xml.utrace.de/?query=88.198.156.18 
-(IP address or hostname)
-
-The XML result is as follows:
-
-<?xml version="1.0" encoding="iso-8869-1"?>
-<results>
-<result>
-<ip>88.198.156.18</ip>
-<host>utrace.de</host>
-<isp>Hetzner Online AG</isp>
-<org>Pagedesign GmbH</org>
-<region>Hamburg</region>
-<countrycode>DE</countrycode>
-<latitude>53.5499992371</latitude>
-<longitude>10</longitude>
-<queries>10</queries>
-</result>
-</results>
-
-Note the queries count field -- you are permitted 100 per day.
-Beyond this you get blacklisted and requests may time out, or return none.
-(This may last for several days once blacklisting, not sure how long.)
-     */
-    
-    /** after failures, subsequent retries within this time interval are 
blocked */
-    private static final Duration RETRY_INTERVAL = Duration.FIVE_MINUTES;
-    /** requests taking longer than this period are deemed to have timed out 
and failed;
-     * set reasonably low so that if we are blacklisted for making too many 
requests,
-     * the call to get geo info does not take very long */
-    private static final Duration REQUEST_TIMEOUT = Duration.seconds(3);
-    
-    public static final Logger log = 
LoggerFactory.getLogger(UtraceHostGeoLookup.class);
-    
-    public String getLookupUrlForPublicIp(String ip) {
-        return "http://xml.utrace.de/?query="+ip.trim();
-    }
-
-    /**
-     * @deprecated since 0.7.0. Use {@link LocalhostExternalIpLoader} instead.
-     */
-    @Deprecated
-    public static String getLocalhostExternalIp() {
-        return 
LocalhostExternalIpLoader.getLocalhostIpWithin(Duration.seconds(2));
-    }
-    
-    /**
-     * @deprecated since 0.7.0. Use {@link LocalhostExternalIpLoader} instead.
-     */
-    @Deprecated
-    public static String getLocalhostExternalIpImpl() {
-        return 
LocalhostExternalIpLoader.getLocalhostIpWithin(Duration.seconds(2));
-    }
-    
-    public String getLookupUrlForLocalhost() {
-        return 
getLookupUrlForPublicIp(LocalhostExternalIpLoader.getLocalhostIpQuicklyOrDefault());
-    }
-
-    /** returns URL to get properties for the given address (assuming 
localhost if address is on a subnet) */
-    public String getLookupUrlFor(InetAddress address) {
-        if (Networking.isPrivateSubnet(address)) return 
getLookupUrlForLocalhost();
-        return getLookupUrlForPublicIp(address.getHostAddress());
-    }
-    
-    private static boolean LOGGED_GEO_LOOKUP_UNAVAILABLE = false;
-    private static long LAST_FAILURE_UTC = -1;
-    
-    /** does the {@link #retrieveHostGeoInfo(InetAddress)}, but in the 
background with a default timeout */
-    public HostGeoInfo getHostGeoInfo(InetAddress address) throws 
MalformedURLException, IOException {
-        if (Duration.sinceUtc(LAST_FAILURE_UTC).compareTo(RETRY_INTERVAL) < 0) 
{
-            // wait at least 60s since a failure
-            return null;
-        }
-        return getHostGeoInfo(address, REQUEST_TIMEOUT);
-    }
-    
-    /** does a {@link #retrieveHostGeoInfo(InetAddress)} with a timeout 
(returning null, interrupting, and setting failure time) */
-    public HostGeoInfo getHostGeoInfo(final InetAddress address, Duration 
timeout) throws MalformedURLException, IOException {
-        final AtomicReference<HostGeoInfo> result = new 
AtomicReference<HostGeoInfo>();
-        Thread lt = new Thread() {
-            public void run() {
-                try {
-                    result.set(retrieveHostGeoInfo(address));
-                } catch (Exception e) {
-                    log.warn("Error computing geo info for "+address+"; 
internet issues or too many requests to (free) servers for 
"+JavaClassNames.simpleClassName(UtraceHostGeoLookup.this)+": "+e);
-                    log.debug("Detail of host geo error: "+e, e);
-                }
-            }
-        };
-        lt.start();
-
-        try {
-            Durations.join(lt, timeout);
-        } catch (InterruptedException e) {
-            throw Exceptions.propagate(e);
-        }
-        
-        if (lt.isAlive()) {
-            // interrupt and set the failure time so that subsequent attempts 
do not face this timeout
-            lt.interrupt();
-            LAST_FAILURE_UTC = System.currentTimeMillis();
-            log.debug("Geo info lookup for "+address+" timed out after 
"+timeout);
-        }
-        
-        return result.get();
-    }
-    
-    public HostGeoInfo retrieveHostGeoInfo(InetAddress address) throws 
MalformedURLException, IOException {
-        String url = getLookupUrlFor(address);
-        if (log.isDebugEnabled())
-            log.debug("Geo info lookup for "+address+" at "+url);
-        Node xml;
-        try {
-            xml = new XmlParser().parse(getLookupUrlFor(address));
-        } catch (Exception e) {
-            LAST_FAILURE_UTC = System.currentTimeMillis();
-            if (log.isDebugEnabled())
-                log.debug("Geo info lookup for "+address+" failed: "+e);
-            if (!LOGGED_GEO_LOOKUP_UNAVAILABLE) {
-                LOGGED_GEO_LOOKUP_UNAVAILABLE = true;
-                log.info("Geo info lookup unavailable (for "+address+"; cause 
"+e+")");
-            }
-            return null;
-        }
-        try {
-            String org = getXmlResultsField(xml, "org").trim();
-            if (org.isEmpty()) org = getXmlResultsField(xml, "isp").trim();
-            String region = getXmlResultsField(xml, "region").trim();
-            if (!org.isEmpty()) {
-                if (!region.isEmpty()) region = org+", "+region;
-                else region = org;
-            }
-            if (region.isEmpty()) region = getXmlResultsField(xml, 
"isp").trim();
-            if (region.isEmpty()) region = address.toString();
-            HostGeoInfo geo = new HostGeoInfo(address.getHostName(), 
-                    region+
-                    " ("+getXmlResultsField(xml, "countrycode")+")", 
-                    Double.parseDouble(""+getXmlResultsField(xml, 
"latitude")), 
-                    Double.parseDouble(""+getXmlResultsField(xml, 
"longitude")));
-            log.info("Geo info lookup for "+address+" returned: "+geo);
-            return geo;
-        } catch (Exception e) {
-            if (log.isDebugEnabled())
-                log.debug("Geo info lookup failed, for "+address+" at "+url+", 
due to "+e+"; response is "+xml);
-            throw Throwables.propagate(e);
-        }
-    }
-    
-    @Nullable
-    private static Node getFirstChild(Node xml, String field) {
-        if (xml==null) return null;
-        NodeList nl = (NodeList)xml.get(field);
-        if (nl==null || nl.isEmpty()) return null;
-        return (Node)nl.get(0);
-    }
-    @Nonnull
-    private static String getXmlResultsField(Node xml, String field) {
-        Node f1 = getFirstChild(getFirstChild(xml, "result"), field);
-        if (f1==null) return "";
-        return f1.text();
-    }
-}

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostLocationResolver.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostLocationResolver.java
 
b/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostLocationResolver.java
index 37d885d..81a05f3 100644
--- 
a/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostLocationResolver.java
+++ 
b/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostLocationResolver.java
@@ -23,8 +23,8 @@ import java.util.Map;
 import org.apache.brooklyn.api.location.Location;
 import org.apache.brooklyn.api.location.LocationRegistry;
 import org.apache.brooklyn.api.location.LocationResolver;
-import org.apache.brooklyn.location.core.AbstractLocationResolver;
-import org.apache.brooklyn.location.core.LocationConfigUtils;
+import org.apache.brooklyn.core.location.AbstractLocationResolver;
+import org.apache.brooklyn.core.location.LocationConfigUtils;
 import org.apache.brooklyn.util.core.config.ConfigBag;
 
 /**

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostMachineProvisioningLocation.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostMachineProvisioningLocation.java
 
b/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostMachineProvisioningLocation.java
index 749bc26..76325f8 100644
--- 
a/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostMachineProvisioningLocation.java
+++ 
b/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostMachineProvisioningLocation.java
@@ -36,13 +36,13 @@ import org.apache.brooklyn.config.ConfigKey;
 import org.apache.brooklyn.config.ConfigKey.HasConfigKey;
 import org.apache.brooklyn.core.config.ConfigKeys;
 import org.apache.brooklyn.core.entity.BrooklynConfigKeys;
+import org.apache.brooklyn.core.location.BasicOsDetails;
+import org.apache.brooklyn.core.location.HasSubnetHostname;
+import org.apache.brooklyn.core.location.geo.HostGeoInfo;
 import org.apache.brooklyn.core.mgmt.persist.FileBasedObjectStore;
 import org.apache.brooklyn.core.mgmt.persist.LocationWithObjectStore;
 import org.apache.brooklyn.core.mgmt.persist.PersistenceObjectStore;
 import org.apache.brooklyn.location.byon.FixedListMachineProvisioningLocation;
-import org.apache.brooklyn.location.core.BasicOsDetails;
-import org.apache.brooklyn.location.core.HasSubnetHostname;
-import org.apache.brooklyn.location.geo.HostGeoInfo;
 import org.apache.brooklyn.location.ssh.SshMachineLocation;
 import org.apache.brooklyn.util.collections.MutableMap;
 import org.apache.brooklyn.util.core.BrooklynNetworkUtils;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostPropertiesFromBrooklynProperties.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostPropertiesFromBrooklynProperties.java
 
b/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostPropertiesFromBrooklynProperties.java
index bce0c65..a695a8f 100644
--- 
a/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostPropertiesFromBrooklynProperties.java
+++ 
b/core/src/main/java/org/apache/brooklyn/location/localhost/LocalhostPropertiesFromBrooklynProperties.java
@@ -20,7 +20,7 @@ package org.apache.brooklyn.location.localhost;
 
 import java.util.Map;
 
-import 
org.apache.brooklyn.location.core.LocationPropertiesFromBrooklynProperties;
+import 
org.apache.brooklyn.core.location.LocationPropertiesFromBrooklynProperties;
 import org.apache.brooklyn.util.core.config.ConfigBag;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/multi/MultiLocation.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/multi/MultiLocation.java 
b/core/src/main/java/org/apache/brooklyn/location/multi/MultiLocation.java
new file mode 100644
index 0000000..3b0ffdf
--- /dev/null
+++ b/core/src/main/java/org/apache/brooklyn/location/multi/MultiLocation.java
@@ -0,0 +1,167 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.apache.brooklyn.location.multi;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+import static com.google.common.base.Preconditions.checkState;
+
+import java.util.Collection;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.brooklyn.api.location.Location;
+import org.apache.brooklyn.api.location.LocationSpec;
+import org.apache.brooklyn.api.location.MachineLocation;
+import org.apache.brooklyn.api.location.MachineProvisioningLocation;
+import org.apache.brooklyn.api.location.NoMachinesAvailableException;
+import org.apache.brooklyn.api.mgmt.ManagementContext;
+import org.apache.brooklyn.config.ConfigKey;
+import org.apache.brooklyn.core.config.ConfigKeys;
+import org.apache.brooklyn.core.location.AbstractLocation;
+import 
org.apache.brooklyn.core.location.cloud.AbstractAvailabilityZoneExtension;
+import org.apache.brooklyn.core.location.cloud.AvailabilityZoneExtension;
+import org.apache.brooklyn.util.collections.MutableList;
+import org.apache.brooklyn.util.collections.MutableMap;
+import org.apache.brooklyn.util.core.flags.SetFromFlag;
+import org.apache.brooklyn.util.exceptions.CompoundRuntimeException;
+import org.apache.brooklyn.util.exceptions.Exceptions;
+import org.apache.brooklyn.util.text.Strings;
+
+import com.google.common.base.Predicate;
+import com.google.common.collect.ImmutableList;
+import com.google.common.collect.Iterables;
+import com.google.common.collect.Maps;
+import com.google.common.reflect.TypeToken;
+
+/** A location which consists of multiple locations stitched together to form 
availability zones.
+ * The first location will be used by default, but if an {@link 
AvailabilityZoneExtension}-aware entity
+ * is used, it may stripe across each of the locations.  See notes at {@link 
AvailabilityZoneExtension}. */
+public class MultiLocation<T extends MachineLocation> extends AbstractLocation 
implements MachineProvisioningLocation<T> {
+
+    private static final long serialVersionUID = 7993091317970457862L;
+    
+    @SuppressWarnings("serial")
+    @SetFromFlag("subLocations")
+    public static final ConfigKey<List<MachineProvisioningLocation<?>>> 
SUB_LOCATIONS = ConfigKeys.newConfigKey(
+            new TypeToken<List<MachineProvisioningLocation<?>>>() {},
+            "subLocations", 
+            "The sub-machines that this location can delegate to");
+    
+    @Override
+    public void init() {
+        super.init();
+        List<MachineProvisioningLocation<?>> subLocs = getSubLocations();
+        checkState(subLocs.size() >= 1, "sub-locations must not be empty");
+        AvailabilityZoneExtension azExtension = new 
AvailabilityZoneExtensionImpl(getManagementContext(), subLocs);
+        addExtension(AvailabilityZoneExtension.class, azExtension);
+    }
+
+    public T obtain() throws NoMachinesAvailableException {
+        return obtain(MutableMap.of());
+    }
+    
+    /** finds (creates) and returns a {@link MachineLocation}; 
+     * this always tries the first sub-location, moving on the second and 
subsequent if the first throws {@link NoMachinesAvailableException}.
+     * (if you want striping across locations, see notes in {@link 
AvailabilityZoneExtension}.) */
+    @SuppressWarnings("unchecked")
+    @Override
+    public T obtain(Map<?, ?> flags) throws NoMachinesAvailableException {
+        List<MachineProvisioningLocation<?>> sublocsList = getSubLocations();
+        Iterator<MachineProvisioningLocation<?>> sublocs = 
sublocsList.iterator();
+        List<NoMachinesAvailableException> errors = MutableList.of();
+        while (sublocs.hasNext()) {
+            try {
+                return (T) sublocs.next().obtain(flags);
+            } catch (NoMachinesAvailableException e) {
+                errors.add(e);
+            }
+        }
+        Exception wrapped;
+        String msg;
+        if (errors.size()>1) {
+            wrapped = new CompoundRuntimeException(errors.size()+" sublocation 
exceptions, including: "+
+                Exceptions.collapseText(errors.get(0)), errors);
+            msg = Exceptions.collapseText(wrapped);
+        } else if (errors.size()==1) {
+            wrapped = errors.get(0);
+            msg = wrapped.getMessage();
+            if (Strings.isBlank(msg)) msg = wrapped.toString();
+        } else {
+            msg = "no sub-locations set for this multi-location";
+            wrapped = null;
+        }
+        throw new NoMachinesAvailableException("No machines available in any 
of the "+sublocsList.size()+" location"+Strings.s(sublocsList.size())+
+            " configured here: "+msg, wrapped);
+    }
+
+    public List<MachineProvisioningLocation<?>> getSubLocations() {
+        return getRequiredConfig(SUB_LOCATIONS);
+    }
+
+    @SuppressWarnings("unchecked")
+    @Override
+    public MachineProvisioningLocation<T> newSubLocation(Map<?, ?> newFlags) {
+        // TODO shouldn't have to copy config bag as it should be inherited 
(but currently it is not used inherited everywhere; just most places)
+        return 
getManagementContext().getLocationManager().createLocation(LocationSpec.create(getClass())
+                .parent(this)
+                .configure(config().getLocalBag().getAllConfig())  // FIXME 
Should this just be inherited?
+                .configure(newFlags));
+    }
+
+    @SuppressWarnings("unchecked")
+    @Override
+    public void release(T machine) {
+        ((MachineProvisioningLocation<T>)machine.getParent()).release(machine);
+    }
+
+    @Override
+    public Map<String, Object> getProvisioningFlags(Collection<String> tags) {
+        return Maps.<String,Object>newLinkedHashMap();
+    }
+
+    @SuppressWarnings("unchecked")
+    protected MachineProvisioningLocation<T> firstSubLoc() {
+        return (MachineProvisioningLocation<T>) 
Iterables.get(getSubLocations(), 0);
+    }
+
+    protected <K> K getRequiredConfig(ConfigKey<K> key) {
+        return checkNotNull(getConfig(key), key.getName());
+    }
+
+    public static class AvailabilityZoneExtensionImpl extends 
AbstractAvailabilityZoneExtension implements AvailabilityZoneExtension {
+
+        private final List<MachineProvisioningLocation<?>> subLocations;
+        
+        public AvailabilityZoneExtensionImpl(ManagementContext 
managementContext, List<MachineProvisioningLocation<?>> subLocations) {
+            super(managementContext);
+            this.subLocations = ImmutableList.copyOf(subLocations);
+        }
+        
+        @Override
+        protected List<Location> doGetAllSubLocations() {
+            return ImmutableList.<Location>copyOf(subLocations);
+        }
+        
+        @Override
+        protected boolean isNameMatch(Location loc, Predicate<? super String> 
namePredicate) {
+            return namePredicate.apply(loc.getDisplayName());
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/multi/MultiLocationResolver.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/multi/MultiLocationResolver.java
 
b/core/src/main/java/org/apache/brooklyn/location/multi/MultiLocationResolver.java
new file mode 100644
index 0000000..5d9dd19
--- /dev/null
+++ 
b/core/src/main/java/org/apache/brooklyn/location/multi/MultiLocationResolver.java
@@ -0,0 +1,149 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you 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.apache.brooklyn.location.multi;
+
+import static com.google.common.base.Preconditions.checkNotNull;
+
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+import org.apache.brooklyn.api.location.Location;
+import org.apache.brooklyn.api.location.LocationRegistry;
+import org.apache.brooklyn.api.location.LocationResolver;
+import org.apache.brooklyn.api.location.LocationSpec;
+import org.apache.brooklyn.api.mgmt.ManagementContext;
+import org.apache.brooklyn.core.location.BasicLocationRegistry;
+import org.apache.brooklyn.core.location.LocationConfigUtils;
+import 
org.apache.brooklyn.core.location.LocationPropertiesFromBrooklynProperties;
+import org.apache.brooklyn.core.location.Locations;
+import org.apache.brooklyn.util.collections.MutableMap;
+import org.apache.brooklyn.util.exceptions.Exceptions;
+import org.apache.brooklyn.util.text.KeyValueParser;
+import org.apache.brooklyn.util.text.StringEscapes.JavaStringEscapes;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import com.google.common.collect.Lists;
+
+public class MultiLocationResolver implements LocationResolver {
+
+    private static final Logger LOG = 
LoggerFactory.getLogger(MultiLocationResolver.class);
+
+    private static final String MULTI = "multi";
+    
+    private static final Pattern PATTERN = Pattern.compile("(" + MULTI + "|" + 
MULTI.toUpperCase() + ")" + ":" + "\\((.*)\\)$");
+    
+    private volatile ManagementContext managementContext;
+
+    @Override
+    public void init(ManagementContext managementContext) {
+        this.managementContext = checkNotNull(managementContext, 
"managementContext");
+    }
+
+    @Override
+    public Location newLocationFromString(Map locationFlags, String spec, 
LocationRegistry registry) {
+        // FIXME pass all flags into the location
+        
+        Map globalProperties = registry.getProperties();
+        Map<String,?> locationArgs;
+        if (spec.equalsIgnoreCase(MULTI)) {
+            locationArgs = MutableMap.copyOf(locationFlags);
+        } else {
+            Matcher matcher = PATTERN.matcher(spec);
+            if (!matcher.matches()) {
+                throw new IllegalArgumentException("Invalid location '" + spec 
+ "'; must specify something like multi(targets=named:foo)");
+            }
+            String args = matcher.group(2);
+            // TODO we are ignoring locationFlags after this (apart from 
named), looking only at these args
+            locationArgs = KeyValueParser.parseMap(args);
+        }
+        String namedLocation = (String) locationFlags.get("named");
+
+        Map<String, Object> filteredProperties = new 
LocationPropertiesFromBrooklynProperties().getLocationProperties(null, 
namedLocation, globalProperties);
+        MutableMap<String, Object> flags = MutableMap.<String, Object>builder()
+                .putAll(filteredProperties)
+                .putAll(locationFlags)
+                .removeAll("named")
+                .putAll(locationArgs).build();
+        
+        if (locationArgs.get("targets") == null) {
+            throw new IllegalArgumentException("target must be specified in 
single-machine spec");
+        }
+        
+        // TODO do we need to pass location flags etc into the children to 
ensure they are inherited?
+        List<Location> targets = Lists.newArrayList();
+        Object targetSpecs = locationArgs.remove("targets");
+        try {
+            if (targetSpecs instanceof String) {
+                for (String targetSpec : 
JavaStringEscapes.unwrapJsonishListIfPossible((String)targetSpecs)) {
+                    
targets.add(managementContext.getLocationRegistry().resolve(targetSpec));
+                }
+            } else if (targetSpecs instanceof Iterable) {
+                for (Object targetSpec: (Iterable<?>)targetSpecs) {
+                    if (targetSpec instanceof String) {
+                        
targets.add(managementContext.getLocationRegistry().resolve((String)targetSpec));
+                    } else {
+                        Set<?> keys = ((Map<?,?>)targetSpec).keySet();
+                        if (keys.size()!=1) 
+                            throw new IllegalArgumentException("targets 
supplied to MultiLocation must be a list of single-entry maps (got map of size 
"+keys.size()+": "+targetSpec+")");
+                        Object key = keys.iterator().next();
+                        Object flagsS = ((Map<?,?>)targetSpec).get(key);
+                        
targets.add(managementContext.getLocationRegistry().resolve((String)key, 
(Map<?,?>)flagsS));
+                    }
+                }
+            } else throw new IllegalArgumentException("targets must be 
supplied to MultiLocation, either as string spec or list of single-entry maps 
each being a location spec");
+            
+            MultiLocation result = 
managementContext.getLocationManager().createLocation(LocationSpec.create(MultiLocation.class)
+                    .configure(flags)
+                    .configure("subLocations", targets)
+                    .configure(LocationConfigUtils.finalAndOriginalSpecs(spec, 
locationFlags, globalProperties, namedLocation)));
+
+            // TODO Important workaround for 
BasicLocationRegistry.resolveForPeeking.
+            // That creates a location (from the resolver) and immediately 
unmanages it.
+            // The unmanage *must* remove all the targets created here; 
otherwise we have a leak.
+            // Adding the targets as children achieves this.
+            for (Location target : targets) {
+                target.setParent(result);
+            }
+            return result;
+
+        } catch (Exception e) {
+            // Must clean up after ourselves: don't leak sub-locations on error
+            if (LOG.isDebugEnabled()) LOG.debug("Problem resolving 
MultiLocation; cleaning up any sub-locations and rethrowing: "+e);
+            for (Location target : targets) {
+                Locations.unmanage(target);
+            }
+            throw Exceptions.propagate(e);
+        }
+    }
+
+    @Override
+    public String getPrefix() {
+        return MULTI;
+    }
+
+    @Override
+    public boolean accepts(String spec, LocationRegistry registry) {
+        return BasicLocationRegistry.isResolverPrefixForSpec(this, spec, true);
+    }
+    
+}

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/ssh/SshMachineLocation.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/ssh/SshMachineLocation.java 
b/core/src/main/java/org/apache/brooklyn/location/ssh/SshMachineLocation.java
index 8f9871f..23c3995 100644
--- 
a/core/src/main/java/org/apache/brooklyn/location/ssh/SshMachineLocation.java
+++ 
b/core/src/main/java/org/apache/brooklyn/location/ssh/SshMachineLocation.java
@@ -59,6 +59,12 @@ import org.apache.brooklyn.core.config.ConfigKeys;
 import org.apache.brooklyn.core.config.ConfigUtils;
 import org.apache.brooklyn.core.config.MapConfigKey;
 import org.apache.brooklyn.core.entity.BrooklynConfigKeys;
+import org.apache.brooklyn.core.location.AbstractLocation;
+import org.apache.brooklyn.core.location.BasicHardwareDetails;
+import org.apache.brooklyn.core.location.BasicMachineDetails;
+import org.apache.brooklyn.core.location.BasicOsDetails;
+import org.apache.brooklyn.core.location.PortRanges;
+import org.apache.brooklyn.core.location.access.PortForwardManager;
 import org.apache.brooklyn.core.mgmt.BrooklynTaskTags;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -84,12 +90,6 @@ import com.google.common.collect.Sets;
 import com.google.common.net.HostAndPort;
 import com.google.common.reflect.TypeToken;
 
-import org.apache.brooklyn.location.access.PortForwardManager;
-import org.apache.brooklyn.location.core.AbstractLocation;
-import org.apache.brooklyn.location.core.BasicHardwareDetails;
-import org.apache.brooklyn.location.core.BasicMachineDetails;
-import org.apache.brooklyn.location.core.BasicOsDetails;
-import org.apache.brooklyn.location.core.PortRanges;
 import org.apache.brooklyn.util.collections.MutableMap;
 import org.apache.brooklyn.util.core.ResourceUtils;
 import org.apache.brooklyn.util.core.config.ConfigBag;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/location/winrm/WinRmMachineLocation.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/location/winrm/WinRmMachineLocation.java
 
b/core/src/main/java/org/apache/brooklyn/location/winrm/WinRmMachineLocation.java
index fb68c77..3a7dbd5 100644
--- 
a/core/src/main/java/org/apache/brooklyn/location/winrm/WinRmMachineLocation.java
+++ 
b/core/src/main/java/org/apache/brooklyn/location/winrm/WinRmMachineLocation.java
@@ -38,6 +38,8 @@ import org.apache.brooklyn.api.location.MachineLocation;
 import org.apache.brooklyn.api.location.OsDetails;
 import org.apache.brooklyn.config.ConfigKey;
 import org.apache.brooklyn.core.config.ConfigKeys;
+import org.apache.brooklyn.core.location.AbstractLocation;
+import org.apache.brooklyn.core.location.access.PortForwardManager;
 import org.apache.commons.codec.binary.Base64;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
@@ -50,8 +52,6 @@ import com.google.common.collect.Lists;
 import com.google.common.net.HostAndPort;
 import com.google.common.reflect.TypeToken;
 
-import org.apache.brooklyn.location.access.PortForwardManager;
-import org.apache.brooklyn.location.core.AbstractLocation;
 import org.apache.brooklyn.util.exceptions.Exceptions;
 import org.apache.brooklyn.util.stream.Streams;
 import org.apache.brooklyn.util.time.Duration;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/sensor/core/PortAttributeSensorAndConfigKey.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/sensor/core/PortAttributeSensorAndConfigKey.java
 
b/core/src/main/java/org/apache/brooklyn/sensor/core/PortAttributeSensorAndConfigKey.java
index f647db3..e269966 100644
--- 
a/core/src/main/java/org/apache/brooklyn/sensor/core/PortAttributeSensorAndConfigKey.java
+++ 
b/core/src/main/java/org/apache/brooklyn/sensor/core/PortAttributeSensorAndConfigKey.java
@@ -31,7 +31,7 @@ import org.apache.brooklyn.api.sensor.Sensor;
 import org.apache.brooklyn.config.ConfigKey;
 import org.apache.brooklyn.core.entity.BrooklynConfigKeys;
 import org.apache.brooklyn.core.internal.BrooklynInitialization;
-import org.apache.brooklyn.location.core.Locations;
+import org.apache.brooklyn.core.location.Locations;
 import org.apache.brooklyn.util.core.flags.TypeCoercions;
 import org.apache.brooklyn.util.guava.Maybe;
 import org.slf4j.Logger;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/sensor/feed/ssh/SshFeed.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/sensor/feed/ssh/SshFeed.java 
b/core/src/main/java/org/apache/brooklyn/sensor/feed/ssh/SshFeed.java
index bbee7f1..6e5a485 100644
--- a/core/src/main/java/org/apache/brooklyn/sensor/feed/ssh/SshFeed.java
+++ b/core/src/main/java/org/apache/brooklyn/sensor/feed/ssh/SshFeed.java
@@ -32,10 +32,10 @@ import org.apache.brooklyn.api.entity.Entity;
 import org.apache.brooklyn.api.entity.EntityLocal;
 import org.apache.brooklyn.config.ConfigKey;
 import org.apache.brooklyn.core.config.ConfigKeys;
+import org.apache.brooklyn.core.location.Locations;
+import org.apache.brooklyn.core.location.Machines;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
-import org.apache.brooklyn.location.core.Locations;
-import org.apache.brooklyn.location.core.Machines;
 import org.apache.brooklyn.location.ssh.SshMachineLocation;
 import org.apache.brooklyn.sensor.feed.AbstractFeed;
 import org.apache.brooklyn.sensor.feed.AttributePollHandler;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/util/core/BrooklynNetworkUtils.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/util/core/BrooklynNetworkUtils.java 
b/core/src/main/java/org/apache/brooklyn/util/core/BrooklynNetworkUtils.java
index 9bd8687..0b99a88 100644
--- a/core/src/main/java/org/apache/brooklyn/util/core/BrooklynNetworkUtils.java
+++ b/core/src/main/java/org/apache/brooklyn/util/core/BrooklynNetworkUtils.java
@@ -20,8 +20,8 @@ package org.apache.brooklyn.util.core;
 
 import java.net.InetAddress;
 
+import org.apache.brooklyn.core.location.geo.LocalhostExternalIpLoader;
 import org.apache.brooklyn.core.server.BrooklynServiceAttributes;
-import org.apache.brooklyn.location.geo.LocalhostExternalIpLoader;
 import org.apache.brooklyn.util.JavaGroovyEquivalents;
 import org.apache.brooklyn.util.core.flags.TypeCoercions;
 import org.apache.brooklyn.util.net.Networking;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/main/java/org/apache/brooklyn/util/core/task/ssh/SshTasks.java
----------------------------------------------------------------------
diff --git 
a/core/src/main/java/org/apache/brooklyn/util/core/task/ssh/SshTasks.java 
b/core/src/main/java/org/apache/brooklyn/util/core/task/ssh/SshTasks.java
index 53d5e71..022b52b 100644
--- a/core/src/main/java/org/apache/brooklyn/util/core/task/ssh/SshTasks.java
+++ b/core/src/main/java/org/apache/brooklyn/util/core/task/ssh/SshTasks.java
@@ -32,11 +32,11 @@ import org.apache.brooklyn.api.mgmt.TaskQueueingContext;
 import org.apache.brooklyn.config.ConfigKey;
 import org.apache.brooklyn.core.config.ConfigKeys;
 import org.apache.brooklyn.core.config.ConfigUtils;
+import org.apache.brooklyn.core.location.AbstractLocation;
+import org.apache.brooklyn.core.location.internal.LocationInternal;
 import org.apache.brooklyn.core.mgmt.BrooklynTaskTags;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
-import org.apache.brooklyn.location.core.AbstractLocation;
-import org.apache.brooklyn.location.core.internal.LocationInternal;
 import org.apache.brooklyn.location.ssh.SshMachineLocation;
 import org.apache.brooklyn.util.core.ResourceUtils;
 import org.apache.brooklyn.util.core.config.ConfigBag;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/config/MapListAndOtherStructuredConfigKeyTest.groovy
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/config/MapListAndOtherStructuredConfigKeyTest.groovy
 
b/core/src/test/java/org/apache/brooklyn/core/config/MapListAndOtherStructuredConfigKeyTest.groovy
index 27b8d95..e57c8cb 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/config/MapListAndOtherStructuredConfigKeyTest.groovy
+++ 
b/core/src/test/java/org/apache/brooklyn/core/config/MapListAndOtherStructuredConfigKeyTest.groovy
@@ -32,7 +32,7 @@ import 
org.apache.brooklyn.core.config.SetConfigKey.SetModifications
 import org.apache.brooklyn.core.test.entity.TestApplication
 import org.apache.brooklyn.core.test.entity.TestEntity
 import org.apache.brooklyn.core.entity.Entities
-import org.apache.brooklyn.location.core.SimulatedLocation
+import org.apache.brooklyn.core.location.SimulatedLocation
 import org.apache.brooklyn.sensor.core.DependentConfiguration
 import org.apache.brooklyn.util.collections.MutableMap
 import org.apache.brooklyn.util.core.task.DeferredSupplier

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/AbstractApplicationLegacyTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/AbstractApplicationLegacyTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/AbstractApplicationLegacyTest.java
index 66b0659..3f4c38b 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/AbstractApplicationLegacyTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/AbstractApplicationLegacyTest.java
@@ -29,6 +29,7 @@ import org.apache.brooklyn.api.location.LocationSpec;
 import org.apache.brooklyn.core.entity.AbstractApplication;
 import org.apache.brooklyn.core.entity.Entities;
 import org.apache.brooklyn.core.entity.factory.ApplicationBuilder;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.BrooklynAppUnitTestSupport;
 import org.apache.brooklyn.core.test.entity.TestApplication;
 import org.apache.brooklyn.core.test.entity.TestEntity;
@@ -38,8 +39,6 @@ import org.testng.annotations.Test;
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.ImmutableMap;
 
-import org.apache.brooklyn.location.core.SimulatedLocation;
-
 /**
  * Tests the deprecated use of AbstractAppliation, where its constructor is 
called directly.
  * 

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/AbstractEntityLegacyTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/AbstractEntityLegacyTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/AbstractEntityLegacyTest.java
index c6e89cd..bb9c97e 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/AbstractEntityLegacyTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/AbstractEntityLegacyTest.java
@@ -28,6 +28,7 @@ import org.apache.brooklyn.api.entity.Entity;
 import org.apache.brooklyn.api.entity.ImplementedBy;
 import org.apache.brooklyn.core.entity.AbstractEntity;
 import org.apache.brooklyn.core.entity.Entities;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.entity.LocalManagementContextForTests;
 import org.apache.brooklyn.core.test.entity.TestApplication;
 import org.apache.brooklyn.core.test.entity.TestApplicationImpl;
@@ -35,7 +36,6 @@ import org.apache.brooklyn.util.collections.MutableMap;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 /**
  * Tests the deprecated use of AbstractAppliation, where its constructor is 
called directly.

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/EntitiesTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/EntitiesTest.java 
b/core/src/test/java/org/apache/brooklyn/core/entity/EntitiesTest.java
index 2a2cbc7..071d6d8 100644
--- a/core/src/test/java/org/apache/brooklyn/core/entity/EntitiesTest.java
+++ b/core/src/test/java/org/apache/brooklyn/core/entity/EntitiesTest.java
@@ -29,6 +29,7 @@ import org.apache.brooklyn.api.location.LocationSpec;
 import org.apache.brooklyn.core.entity.Entities;
 import org.apache.brooklyn.core.entity.EntityAndAttribute;
 import org.apache.brooklyn.core.entity.EntityInitializers;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.BrooklynAppUnitTestSupport;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.apache.brooklyn.test.Asserts;
@@ -36,7 +37,6 @@ import org.apache.brooklyn.util.collections.MutableSet;
 import org.testng.Assert;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.Iterables;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/EntitySetFromFlagTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/EntitySetFromFlagTest.java 
b/core/src/test/java/org/apache/brooklyn/core/entity/EntitySetFromFlagTest.java
index d60c290..c909893 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/EntitySetFromFlagTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/EntitySetFromFlagTest.java
@@ -25,8 +25,8 @@ import java.util.Map;
 import org.apache.brooklyn.api.entity.Entity;
 import org.apache.brooklyn.api.location.PortRange;
 import org.apache.brooklyn.core.entity.AbstractEntity;
+import org.apache.brooklyn.core.location.PortRanges;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.PortRanges;
 import org.apache.brooklyn.util.collections.MutableMap;
 import org.apache.brooklyn.util.core.flags.SetFromFlag;
 

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/EntitySpecTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/EntitySpecTest.java 
b/core/src/test/java/org/apache/brooklyn/core/entity/EntitySpecTest.java
index af9eab0..9d8cea7 100644
--- a/core/src/test/java/org/apache/brooklyn/core/entity/EntitySpecTest.java
+++ b/core/src/test/java/org/apache/brooklyn/core/entity/EntitySpecTest.java
@@ -30,6 +30,7 @@ import org.apache.brooklyn.api.sensor.EnricherSpec;
 import org.apache.brooklyn.config.ConfigKey;
 import org.apache.brooklyn.core.config.BasicConfigKey;
 import org.apache.brooklyn.core.config.ConfigKeys;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.BrooklynAppUnitTestSupport;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.apache.brooklyn.core.test.entity.TestEntityImpl;
@@ -41,7 +42,6 @@ import org.apache.brooklyn.test.Asserts;
 import org.apache.brooklyn.util.core.flags.SetFromFlag;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.collect.ImmutableSet;
 import com.google.common.collect.Iterables;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/EntitySubscriptionTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/EntitySubscriptionTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/EntitySubscriptionTest.java
index 0abb2fc..6e2bd89 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/EntitySubscriptionTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/EntitySubscriptionTest.java
@@ -24,6 +24,7 @@ import org.apache.brooklyn.api.entity.EntityLocal;
 import org.apache.brooklyn.api.entity.EntitySpec;
 import org.apache.brooklyn.api.mgmt.SubscriptionHandle;
 import org.apache.brooklyn.core.entity.Entities;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.entity.TestApplication;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.apache.brooklyn.entity.group.BasicGroup;
@@ -32,7 +33,6 @@ import org.apache.brooklyn.test.Asserts;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.Iterables;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/drivers/BasicEntityDriverManagerTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/BasicEntityDriverManagerTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/BasicEntityDriverManagerTest.java
index fd0d421..d42ccb9 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/BasicEntityDriverManagerTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/BasicEntityDriverManagerTest.java
@@ -26,10 +26,10 @@ import 
org.apache.brooklyn.core.entity.drivers.ReflectiveEntityDriverFactoryTest
 import 
org.apache.brooklyn.core.entity.drivers.ReflectiveEntityDriverFactoryTest.MyDriverDependentEntity;
 import 
org.apache.brooklyn.core.entity.drivers.ReflectiveEntityDriverFactoryTest.MySshDriver;
 import 
org.apache.brooklyn.core.entity.drivers.RegistryEntityDriverFactoryTest.MyOtherSshDriver;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 import org.apache.brooklyn.location.ssh.SshMachineLocation;
 import org.apache.brooklyn.util.collections.MutableMap;
 

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/drivers/ReflectiveEntityDriverFactoryTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/ReflectiveEntityDriverFactoryTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/ReflectiveEntityDriverFactoryTest.java
index 86a2d99..0c7dcd1 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/ReflectiveEntityDriverFactoryTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/ReflectiveEntityDriverFactoryTest.java
@@ -19,6 +19,7 @@
 package org.apache.brooklyn.core.entity.drivers;
 
 import org.apache.brooklyn.location.paas.PaasLocation;
+import org.apache.brooklyn.location.paas.TestPaasLocation;
 import org.apache.brooklyn.location.ssh.SshMachineLocation;
 import org.apache.brooklyn.util.collections.MutableMap;
 import org.apache.brooklyn.api.entity.Entity;
@@ -28,7 +29,6 @@ import org.apache.brooklyn.api.entity.drivers.EntityDriver;
 import org.apache.brooklyn.api.location.Location;
 import org.apache.brooklyn.core.entity.AbstractEntity;
 import org.apache.brooklyn.core.entity.drivers.ReflectiveEntityDriverFactory;
-import org.apache.brooklyn.core.test.location.TestPaasLocation;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/drivers/RegistryEntityDriverFactoryTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/RegistryEntityDriverFactoryTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/RegistryEntityDriverFactoryTest.java
index 97aa2d2..4f079a1 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/RegistryEntityDriverFactoryTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/RegistryEntityDriverFactoryTest.java
@@ -28,10 +28,10 @@ import org.apache.brooklyn.api.location.Location;
 import org.apache.brooklyn.core.entity.drivers.RegistryEntityDriverFactory;
 import 
org.apache.brooklyn.core.entity.drivers.ReflectiveEntityDriverFactoryTest.MyDriver;
 import 
org.apache.brooklyn.core.entity.drivers.ReflectiveEntityDriverFactoryTest.MyDriverDependentEntity;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 import org.apache.brooklyn.location.ssh.SshMachineLocation;
 import org.apache.brooklyn.util.collections.MutableMap;
 

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/BasicDownloadsRegistryTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/BasicDownloadsRegistryTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/BasicDownloadsRegistryTest.java
index 56c711d..67b1224 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/BasicDownloadsRegistryTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/BasicDownloadsRegistryTest.java
@@ -29,13 +29,13 @@ import org.apache.brooklyn.core.entity.BrooklynConfigKeys;
 import org.apache.brooklyn.core.entity.Entities;
 import org.apache.brooklyn.core.entity.factory.ApplicationBuilder;
 import org.apache.brooklyn.core.internal.BrooklynProperties;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.mgmt.internal.LocalManagementContext;
 import org.apache.brooklyn.core.test.entity.TestApplication;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.ImmutableMap;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromLocalRepoTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromLocalRepoTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromLocalRepoTest.java
index 393e539..e6d1448 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromLocalRepoTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromLocalRepoTest.java
@@ -32,13 +32,13 @@ import 
org.apache.brooklyn.core.entity.drivers.downloads.BasicDownloadRequiremen
 import 
org.apache.brooklyn.core.entity.drivers.downloads.DownloadProducerFromLocalRepo;
 import org.apache.brooklyn.core.entity.factory.ApplicationBuilder;
 import org.apache.brooklyn.core.internal.BrooklynProperties;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.mgmt.internal.LocalManagementContext;
 import org.apache.brooklyn.core.test.entity.TestApplication;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.ImmutableMap;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromPropertiesTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromPropertiesTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromPropertiesTest.java
index e3b8f1c..1398357 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromPropertiesTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadProducerFromPropertiesTest.java
@@ -33,13 +33,13 @@ import 
org.apache.brooklyn.core.entity.drivers.downloads.DownloadProducerFromLoc
 import 
org.apache.brooklyn.core.entity.drivers.downloads.DownloadProducerFromProperties;
 import org.apache.brooklyn.core.entity.factory.ApplicationBuilder;
 import org.apache.brooklyn.core.internal.BrooklynProperties;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.mgmt.internal.LocalManagementContext;
 import org.apache.brooklyn.core.test.entity.TestApplication;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.testng.annotations.AfterMethod;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.collect.ImmutableList;
 import com.google.common.collect.ImmutableMap;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadSubstitutersTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadSubstitutersTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadSubstitutersTest.java
index 0d2ea21..822a7a9 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadSubstitutersTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/drivers/downloads/DownloadSubstitutersTest.java
@@ -29,11 +29,11 @@ import org.apache.brooklyn.api.location.Location;
 import org.apache.brooklyn.core.entity.BrooklynConfigKeys;
 import 
org.apache.brooklyn.core.entity.drivers.downloads.BasicDownloadRequirement;
 import org.apache.brooklyn.core.entity.drivers.downloads.DownloadSubstituters;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.BrooklynAppUnitTestSupport;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.base.Functions;
 import com.google.common.collect.ImmutableList;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/hello/LocalEntitiesTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/hello/LocalEntitiesTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/hello/LocalEntitiesTest.java
index 0ffa550..9fef5ba 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/hello/LocalEntitiesTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/hello/LocalEntitiesTest.java
@@ -41,13 +41,13 @@ import org.apache.brooklyn.api.sensor.SensorEvent;
 import org.apache.brooklyn.api.sensor.SensorEventListener;
 import org.apache.brooklyn.core.entity.Entities;
 import org.apache.brooklyn.core.entity.EntityInternal;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.BrooklynAppUnitTestSupport;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
 import org.testng.collections.Lists;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 import org.apache.brooklyn.test.Asserts;
 import org.apache.brooklyn.util.collections.MutableMap;
 import org.apache.brooklyn.util.time.Time;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageLegacyTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageLegacyTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageLegacyTest.java
index 801b3e5..dcd40ee 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageLegacyTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageLegacyTest.java
@@ -32,10 +32,10 @@ import org.testng.annotations.Test;
 import org.apache.brooklyn.config.ConfigKey;
 import org.apache.brooklyn.core.config.ConfigKeys;
 import org.apache.brooklyn.core.entity.Entities;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.BrooklynAppUnitTestSupport;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.apache.brooklyn.core.test.entity.TestEntityImpl;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.base.Function;
 import com.google.common.base.Predicates;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageTest.java
index 5773e5e..e5b6299 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/internal/EntityConfigMapUsageTest.java
@@ -31,13 +31,13 @@ import org.apache.brooklyn.api.entity.EntitySpec;
 import org.apache.brooklyn.config.ConfigKey;
 import org.apache.brooklyn.core.config.BasicConfigKey;
 import org.apache.brooklyn.core.entity.Entities;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.BrooklynAppUnitTestSupport;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.apache.brooklyn.sensor.core.DependentConfiguration;
 import org.apache.brooklyn.util.exceptions.Exceptions;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.base.Function;
 import com.google.common.base.Predicates;

http://git-wip-us.apache.org/repos/asf/incubator-brooklyn/blob/538324e1/core/src/test/java/org/apache/brooklyn/core/entity/trait/StartableMethodsTest.java
----------------------------------------------------------------------
diff --git 
a/core/src/test/java/org/apache/brooklyn/core/entity/trait/StartableMethodsTest.java
 
b/core/src/test/java/org/apache/brooklyn/core/entity/trait/StartableMethodsTest.java
index edfaf36..131dafe 100644
--- 
a/core/src/test/java/org/apache/brooklyn/core/entity/trait/StartableMethodsTest.java
+++ 
b/core/src/test/java/org/apache/brooklyn/core/entity/trait/StartableMethodsTest.java
@@ -26,12 +26,12 @@ import org.apache.brooklyn.api.mgmt.Task;
 import org.apache.brooklyn.core.entity.Entities;
 import org.apache.brooklyn.core.entity.trait.StartableMethods;
 import 
org.apache.brooklyn.core.entity.trait.FailingEntity.RecordingEventListener;
+import org.apache.brooklyn.core.location.SimulatedLocation;
 import org.apache.brooklyn.core.test.BrooklynAppUnitTestSupport;
 import org.apache.brooklyn.core.test.entity.TestEntity;
 import org.apache.brooklyn.util.core.task.Tasks;
 import org.testng.annotations.BeforeMethod;
 import org.testng.annotations.Test;
-import org.apache.brooklyn.location.core.SimulatedLocation;
 
 import com.google.common.collect.ImmutableList;
 

Reply via email to