Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorThomas Watson2016-06-02 19:29:32 +0000
committerThomas Watson2017-06-16 12:38:08 +0000
commit0965ee422528b80cd11bb690f7d94559c54c0d16 (patch)
tree19240cb97a60192fb768f3254e418f52a98963ac
parent943977005bfc2a3c04daca26822418310029133f (diff)
downloadrt.equinox.framework-0965ee422528b80cd11bb690f7d94559c54c0d16.tar.gz
rt.equinox.framework-0965ee422528b80cd11bb690f7d94559c54c0d16.tar.xz
rt.equinox.framework-0965ee422528b80cd11bb690f7d94559c54c0d16.zip
Bug 492825 - [osgi R7] Resolver specification updates for version 1.1
Add onCancel support Change-Id: I0e46d80bb47a044fa9d1087515b550fc2cf0773b Signed-off-by: Thomas Watson <tjwatson@us.ibm.com>
-rw-r--r--bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/TestModuleContainer.java3
-rw-r--r--bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/dummys/DummyContainerAdaptor.java11
-rw-r--r--bundles/org.eclipse.osgi/META-INF/MANIFEST.MF2
-rw-r--r--bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleContainerAdaptor.java11
-rw-r--r--bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleResolver.java51
-rw-r--r--bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/internal/framework/EquinoxContainerAdaptor.java5
-rwxr-xr-xbundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/Candidates.java16
-rwxr-xr-xbundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/ResolverImpl.java126
-rw-r--r--bundles/org.eclipse.osgi/osgi/src/org/osgi/service/resolver/packageinfo1
-rw-r--r--bundles/org.eclipse.osgi/pom.xml2
10 files changed, 158 insertions, 70 deletions
diff --git a/bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/TestModuleContainer.java b/bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/TestModuleContainer.java
index 96b67023b..884901693 100644
--- a/bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/TestModuleContainer.java
+++ b/bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/TestModuleContainer.java
@@ -1800,12 +1800,14 @@ public class TestModuleContainer extends AbstractTest {
}
};
ExecutorService executor = new ThreadPoolExecutor(coreThreads, maxThreads, idleTimeout, TimeUnit.SECONDS, queue, threadFactory, rejectHandler);
+ ScheduledExecutorService timeoutExecutor = new ScheduledThreadPoolExecutor(1);
Map<String, String> configuration = new HashMap<String, String>();
configuration.put(EquinoxConfiguration.PROP_RESOLVER_BATCH_TIMEOUT, "5000");
Map<String, String> debugOpts = Collections.emptyMap();
DummyContainerAdaptor adaptor = new DummyContainerAdaptor(new DummyCollisionHook(false), configuration, new DummyResolverHookFactory(), new DummyDebugOptions(debugOpts));
adaptor.setResolverExecutor(executor);
+ adaptor.setTimeoutExecutor(timeoutExecutor);
ModuleContainer container = adaptor.getContainer();
for (int i = 1; i <= 1000; i++) {
for (Map<String, String> manifest : getUsesTimeoutManifests("test" + i)) {
@@ -1818,6 +1820,7 @@ public class TestModuleContainer extends AbstractTest {
Assert.assertEquals("Wrong state of module: " + module, State.RESOLVED, module.getState());
}
executor.shutdown();
+ timeoutExecutor.shutdown();
System.gc();
System.gc();
System.gc();
diff --git a/bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/dummys/DummyContainerAdaptor.java b/bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/dummys/DummyContainerAdaptor.java
index 630b2f43e..4bf96b573 100644
--- a/bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/dummys/DummyContainerAdaptor.java
+++ b/bundles/org.eclipse.osgi.tests/src/org/eclipse/osgi/tests/container/dummys/DummyContainerAdaptor.java
@@ -13,6 +13,7 @@ package org.eclipse.osgi.tests.container.dummys;
import java.util.EnumSet;
import java.util.Map;
import java.util.concurrent.Executor;
+import java.util.concurrent.ScheduledExecutorService;
import java.util.concurrent.atomic.AtomicBoolean;
import org.eclipse.osgi.container.*;
import org.eclipse.osgi.container.Module.Settings;
@@ -31,6 +32,7 @@ public class DummyContainerAdaptor extends ModuleContainerAdaptor {
private final ResolverHookFactory resolverHookFactory;
private final DebugOptions debugOptions;
private volatile Executor resolverExecutor;
+ private volatile ScheduledExecutorService timeoutExecutor;
public DummyContainerAdaptor(ModuleCollisionHook collisionHook, Map<String, String> configuration) {
this(collisionHook, configuration, new DummyResolverHookFactory());
@@ -123,4 +125,13 @@ public class DummyContainerAdaptor extends ModuleContainerAdaptor {
return super.getResolverExecutor();
}
+ public void setTimeoutExecutor(ScheduledExecutorService timeoutExecutor) {
+ this.timeoutExecutor = timeoutExecutor;
+ }
+
+ @Override
+ public ScheduledExecutorService getScheduledExecutor() {
+ return this.timeoutExecutor;
+ }
+
}
diff --git a/bundles/org.eclipse.osgi/META-INF/MANIFEST.MF b/bundles/org.eclipse.osgi/META-INF/MANIFEST.MF
index 872adf90a..91c3be476 100644
--- a/bundles/org.eclipse.osgi/META-INF/MANIFEST.MF
+++ b/bundles/org.eclipse.osgi/META-INF/MANIFEST.MF
@@ -105,7 +105,7 @@ Bundle-Activator: org.eclipse.osgi.internal.framework.SystemBundleActivator
Bundle-Description: %systemBundle
Bundle-Copyright: %copyright
Bundle-Vendor: %eclipse.org
-Bundle-Version: 3.12.0.qualifier
+Bundle-Version: 3.13.0.qualifier
Bundle-Localization: systembundle
Bundle-DocUrl: http://www.eclipse.org
Eclipse-ExtensibleAPI: true
diff --git a/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleContainerAdaptor.java b/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleContainerAdaptor.java
index 31cce058c..117473a79 100644
--- a/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleContainerAdaptor.java
+++ b/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleContainerAdaptor.java
@@ -13,6 +13,7 @@ package org.eclipse.osgi.container;
import java.io.DataInputStream;
import java.util.EnumSet;
import java.util.concurrent.Executor;
+import java.util.concurrent.ScheduledExecutorService;
import org.eclipse.osgi.container.Module.Settings;
import org.eclipse.osgi.service.debug.DebugOptions;
import org.osgi.framework.Constants;
@@ -317,4 +318,14 @@ public abstract class ModuleContainerAdaptor {
// do nothing by default
return null;
}
+
+ /**
+ * Returns the scheduled executor that may be used by the
+ * container to schedule background tasks.
+ * @return the scheduled executor, or null if background tasks are not supported
+ * @since 3.13
+ */
+ public ScheduledExecutorService getScheduledExecutor() {
+ return null;
+ }
}
diff --git a/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleResolver.java b/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleResolver.java
index d58c142e6..9d0b7872f 100644
--- a/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleResolver.java
+++ b/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/container/ModuleResolver.java
@@ -12,8 +12,8 @@ package org.eclipse.osgi.container;
import java.security.Permission;
import java.util.*;
-import java.util.concurrent.Executor;
-import java.util.concurrent.TimeUnit;
+import java.util.concurrent.*;
+import java.util.concurrent.atomic.AtomicBoolean;
import org.apache.felix.resolver.*;
import org.eclipse.osgi.container.ModuleRequirement.DynamicModuleRequirement;
import org.eclipse.osgi.container.namespaces.EquinoxFragmentNamespace;
@@ -472,11 +472,6 @@ final class ModuleResolver {
return version instanceof Version ? (Version) version : Version.emptyVersion;
}
- static class ResolutionTimeout extends RuntimeException {
- private static final long serialVersionUID = 1L;
- // Just a marker exception to break out of extra long resolution
- }
-
class ResolveProcess extends ResolveContext implements Comparator<Capability>, FelixResolveContext, Executor {
class ResolveLogger extends Logger {
@@ -512,7 +507,6 @@ final class ModuleResolver {
@Override
public boolean isDebugEnabled() {
- checkTimeout();
return DEBUG_USES;
}
@@ -553,8 +547,7 @@ final class ModuleResolver {
private volatile boolean currentlyResolvingMandatory = false;
private final Set<Resource> transitivelyResolveFailures = new LinkedHashSet<>();
private final Set<Resource> failedToResolve = new HashSet<>();
- private final long resolveTimeout = System.currentTimeMillis() + resolverBatchTimeout;
- private volatile boolean checkTimeout = true;
+ private AtomicBoolean scheduleTimeout = new AtomicBoolean(true);
/*
* Used to generate the UNRESOLVED_PROVIDER resolution report entries.
*
@@ -849,12 +842,13 @@ final class ModuleResolver {
@Override
public Collection<Resource> findRelatedResources(Resource host) {
+ // for the container we only care about fragments for related resources
List<ModuleCapability> hostCaps = ((ModuleRevision) host).getModuleCapabilities(HostNamespace.HOST_NAMESPACE);
if (hostCaps.isEmpty()) {
return Collections.emptyList();
}
- Collection<Resource> ondemandFragments = new ArrayList<>();
+ Collection<Resource> relatedFragments = new ArrayList<>();
for (String hostBSN : getHostBSNs(hostCaps)) {
String matchFilter = "(" + EquinoxFragmentNamespace.FRAGMENT_NAMESPACE + "=" + hostBSN + ")"; //$NON-NLS-1$//$NON-NLS-2$//$NON-NLS-3$
Requirement fragmentRequirement = ModuleContainer.createRequirement(EquinoxFragmentNamespace.FRAGMENT_NAMESPACE, Collections.<String, String> singletonMap(Namespace.REQUIREMENT_FILTER_DIRECTIVE, matchFilter), Collections.<String, Object> emptyMap());
@@ -866,14 +860,14 @@ final class ModuleResolver {
ModuleRequirement hostReq = candidate.getRevision().getModuleRequirements(HostNamespace.HOST_NAMESPACE).get(0);
for (ModuleCapability hostCap : hostCaps) {
if (hostReq.matches(hostCap)) {
- ondemandFragments.add(candidate.getResource());
+ relatedFragments.add(candidate.getResource());
break;
}
}
}
}
- return ondemandFragments;
+ return relatedFragments;
}
private Collection<String> getHostBSNs(List<ModuleCapability> hostCaps) {
@@ -1037,9 +1031,13 @@ final class ModuleResolver {
}
maxUsedMemory = Math.max(maxUsedMemory, Runtime.getRuntime().freeMemory() - initialFreeMemory);
}
- } catch (ResolutionTimeout timeoutException) {
+ } catch (ResolutionException resolutionException) {
+ if (resolutionException.getCause() instanceof CancellationException) {
// revert back to single bundle resolves
resolveRevisionsIndividually(isMandatory, logger, result, toResolve, revisions);
+ } else {
+ throw resolutionException;
+ }
} catch (OutOfMemoryError memoryError) {
// revert back to single bundle resolves
resolveRevisionsIndividually(isMandatory, logger, result, toResolve, revisions);
@@ -1053,7 +1051,7 @@ final class ModuleResolver {
}
private void resolveRevisionsIndividually(boolean isMandatory, ResolveLogger logger, Map<Resource, List<Wire>> result, Collection<Resource> toResolve, Collection<ModuleRevision> revisions) throws ResolutionException {
- checkTimeout = false;
+ scheduleTimeout.set(false);
for (Resource resource : toResolve) {
if (!wirings.containsKey(resource) && !failedToResolve.contains(resource)) {
resolveRevisions(Collections.singletonList(resource), isMandatory, logger, result);
@@ -1091,9 +1089,11 @@ final class ModuleResolver {
result.put(interimResultEntry.getKey(), interimResultEntry.getValue());
}
}
- } catch (ResolutionTimeout timeoutException) {
+ } catch (ResolutionException resolutionException) {
+ if (resolutionException.getCause() instanceof CancellationException) {
applyTransitiveFailures = false;
- throw timeoutException;
+ }
+ throw resolutionException;
} catch (OutOfMemoryError memoryError) {
applyTransitiveFailures = false;
throw memoryError;
@@ -1588,14 +1588,21 @@ final class ModuleResolver {
@Override
public void execute(Runnable command) {
- checkTimeout();
adaptor.getResolverExecutor().execute(command);
}
- void checkTimeout() {
- if (checkTimeout && resolveTimeout < System.currentTimeMillis()) {
- checkTimeout = false;
- throw new ResolutionTimeout();
+ @Override
+ public void onCancel(Runnable callback) {
+ // Note that for each resolve Process we only want timeout the initial batch resolve
+ if (scheduleTimeout.compareAndSet(true, false)) {
+ ScheduledExecutorService scheduledExecutor = adaptor.getScheduledExecutor();
+ if (scheduledExecutor != null) {
+ try {
+ scheduledExecutor.schedule(callback, resolverBatchTimeout, TimeUnit.MILLISECONDS);
+ } catch (RejectedExecutionException e) {
+ // ignore may have been shutdown, it is ok we will not be able to timeout
+ }
+ }
}
}
diff --git a/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/internal/framework/EquinoxContainerAdaptor.java b/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/internal/framework/EquinoxContainerAdaptor.java
index f02e02d30..4c3e6539a 100644
--- a/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/internal/framework/EquinoxContainerAdaptor.java
+++ b/bundles/org.eclipse.osgi/container/src/org/eclipse/osgi/internal/framework/EquinoxContainerAdaptor.java
@@ -339,6 +339,11 @@ public class EquinoxContainerAdaptor extends ModuleContainerAdaptor {
return executor.getInitialized(lazyExecutorCreator);
}
+ @Override
+ public ScheduledExecutorService getScheduledExecutor() {
+ return container.getScheduledExecutor();
+ }
+
public void shutdownResolverExecutor() {
Executor current = executor.getAndClear();
if (current instanceof ExecutorService) {
diff --git a/bundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/Candidates.java b/bundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/Candidates.java
index af597d487..f2ef54f52 100755
--- a/bundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/Candidates.java
+++ b/bundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/Candidates.java
@@ -184,17 +184,15 @@ class Candidates
addCandidates(result.candidates);
result.candidates = null;
result.remaining = null;
- if (!Util.isFragment(resource))
+ Collection<Resource> relatedResources = rc.findRelatedResources(resource);
+ m_session.setRelatedResources(resource, relatedResources);
+ for (Resource relatedResource : relatedResources)
{
- Collection<Resource> ondemandFragments = rc.findRelatedResources(resource);
- for (Resource fragment : ondemandFragments)
+ if (m_session.isValidRelatedResource(relatedResource))
{
- if (m_session.isValidOnDemandResource(fragment))
- {
- // This resource is a valid on demand resource;
- // populate it now, consider it optional
- toPopulate.addFirst(fragment);
- }
+ // This resource is a valid related resource;
+ // populate it now, consider it optional
+ toPopulate.addFirst(relatedResource);
}
}
continue;
diff --git a/bundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/ResolverImpl.java b/bundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/ResolverImpl.java
index 7735df71f..09f9ec56a 100755
--- a/bundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/ResolverImpl.java
+++ b/bundles/org.eclipse.osgi/felix/src/org/apache/felix/resolver/ResolverImpl.java
@@ -53,7 +53,7 @@ public class ResolverImpl implements Resolver
// Note this class is not thread safe.
// Only use in the context of a single thread.
- static class ResolveSession
+ static class ResolveSession implements Runnable
{
// Holds the resolve context for this session
private final ResolveContext m_resolveContext;
@@ -62,9 +62,11 @@ public class ResolverImpl implements Resolver
private final Resource m_dynamicHost;
private final Requirement m_dynamicReq;
private final List<Capability> m_dynamicCandidates;
- // keeps track of valid on demand fragments that we have seen.
+ // keeps track of valid related resources that we have seen.
// a null value or TRUE indicate it is valid
- Map<Resource, Boolean> m_validOnDemandResources = new HashMap<Resource, Boolean>(0);
+ private Map<Resource, Boolean> m_validRelatedResources = new HashMap<Resource, Boolean>(0);
+ // keeps track of related resources for each resource
+ private Map<Resource, Collection<Resource>> m_relatedResources = new HashMap<Resource, Collection<Resource>>(0);
// Holds candidate permutations based on permutating "uses" chains.
// These permutations are given higher priority.
private final List<Candidates> m_usesPermutations = new LinkedList<Candidates>();
@@ -88,8 +90,19 @@ public class ResolverImpl implements Resolver
private final Set<Requirement> m_sub_mutated = new HashSet<Requirement>();
private final ConcurrentMap<String, List<String>> m_usesCache = new ConcurrentHashMap<String, List<String>>();
private ResolutionError m_currentError;
+ volatile private CancellationException m_isCancelled = null;
- ResolveSession(ResolveContext resolveContext, Executor executor, Resource dynamicHost, Requirement dynamicReq, List<Capability> dynamicCandidates)
+ static ResolveSession createSession(ResolveContext resolveContext, Executor executor, Resource dynamicHost, Requirement dynamicReq, List<Capability> dynamicCandidates)
+ {
+ ResolveSession session = new ResolveSession(resolveContext, executor, dynamicHost, dynamicReq, dynamicCandidates);
+ // call onCancel first
+ session.getContext().onCancel(session);
+ // now gather the mandatory and optional resources
+ session.initMandatoryAndOptionalResources();
+ return session;
+ }
+
+ private ResolveSession(ResolveContext resolveContext, Executor executor, Resource dynamicHost, Requirement dynamicReq, List<Capability> dynamicCandidates)
{
m_resolveContext = resolveContext;
m_executor = executor;
@@ -100,12 +113,18 @@ public class ResolverImpl implements Resolver
m_mandatoryResources = Collections.singletonList(dynamicHost);
m_optionalResources = Collections.emptyList();
} else {
- // Make copies of arguments in case we want to modify them.
- m_mandatoryResources = new ArrayList<Resource>(resolveContext.getMandatoryResources());
- m_optionalResources = new ArrayList<Resource>(resolveContext.getOptionalResources());
+ // Do not call resolve context yet, onCancel must be called first
+ m_mandatoryResources = new ArrayList<Resource>();
+ m_optionalResources = new ArrayList<Resource>();
}
}
+ private void initMandatoryAndOptionalResources() {
+ if (!isDynamic()) {
+ m_mandatoryResources.addAll(getContext().getMandatoryResources());
+ m_optionalResources.addAll(getContext().getOptionalResources());
+ }
+ }
Candidates getMultipleCardCandidates()
{
return m_multipleCardCandidates;
@@ -281,28 +300,52 @@ public class ResolverImpl implements Resolver
return m_dynamicCandidates;
}
- public boolean isValidOnDemandResource(Resource fragment) {
- Boolean valid = m_validOnDemandResources.get(fragment);
+ public boolean isValidRelatedResource(Resource resource) {
+ Boolean valid = m_validRelatedResources.get(resource);
if (valid == null)
{
- // Mark this resource as a valid on demand resource
- m_validOnDemandResources.put(fragment, Boolean.TRUE);
+ // Mark this resource as a valid related resource
+ m_validRelatedResources.put(resource, Boolean.TRUE);
valid = Boolean.TRUE;
}
return valid;
}
- public boolean invalidateOnDemandResource(Resource faultyResource) {
- Boolean valid = m_validOnDemandResources.get(faultyResource);
+ public boolean invalidateRelatedResource(Resource faultyResource) {
+ Boolean valid = m_validRelatedResources.get(faultyResource);
if (valid != null && valid)
{
- // This was an ondemand resource.
+ // This was related resource.
// Invalidate it and try again.
- m_validOnDemandResources.put(faultyResource, Boolean.FALSE);
+ m_validRelatedResources.put(faultyResource, Boolean.FALSE);
return true;
}
return false;
}
+
+ public Collection<Resource> getRelatedResources(Resource resource) {
+ Collection<Resource> related = m_relatedResources.get(resource);
+ return related == null ? Collections.<Resource> emptyList() : related;
+ }
+
+ public void setRelatedResources(Resource resource, Collection<Resource> related) {
+ m_relatedResources.put(resource, related);
+ }
+
+ @Override
+ public void run() {
+ m_isCancelled = new CancellationException();
+ }
+
+ boolean isCancelled() {
+ return m_isCancelled != null;
+ }
+
+ void checkForCancel() throws ResolutionException {
+ if (isCancelled()) {
+ throw new ResolutionException("Resolver operation has been cancelled.", m_isCancelled, null);
+ }
+ }
}
public ResolverImpl(Logger logger)
@@ -373,13 +416,12 @@ public class ResolverImpl implements Resolver
public Map<Resource, List<Wire>> resolve(ResolveContext rc, Executor executor) throws ResolutionException
{
- ResolveSession session = new ResolveSession(rc, executor, null, null, null);
+ ResolveSession session = ResolveSession.createSession(rc, executor, null, null, null);
return doResolve(session);
}
private Map<Resource, List<Wire>> doResolve(ResolveSession session) throws ResolutionException {
Map<Resource, List<Wire>> wireMap = new HashMap<Resource, List<Wire>>();
-
boolean retry;
do
{
@@ -393,6 +435,7 @@ public class ResolverImpl implements Resolver
Map<Resource, ResolutionError> faultyResources = new HashMap<Resource, ResolutionError>();
Candidates allCandidates = findValidCandidates(session, faultyResources);
+ session.checkForCancel();
// If there is a resolve exception, then determine if an
// optionally resolved resource is to blame (typically a fragment).
@@ -404,7 +447,7 @@ public class ResolverImpl implements Resolver
retry = (session.getOptionalResources().removeAll(resourceKeys));
for (Resource faultyResource : resourceKeys)
{
- if (session.invalidateOnDemandResource(faultyResource))
+ if (session.invalidateRelatedResource(faultyResource))
{
retry = true;
}
@@ -432,8 +475,7 @@ public class ResolverImpl implements Resolver
}
if (session.isDynamic() )
{
- wireMap = populateDynamicWireMap(session.getContext(),
- session.getDynamicHost(), session.getDynamicRequirement(),
+ wireMap = populateDynamicWireMap(session,
wireMap, allCandidates);
}
else
@@ -444,7 +486,7 @@ public class ResolverImpl implements Resolver
{
wireMap =
populateWireMap(
- session.getContext(), allCandidates.getWrappedHost(resource),
+ session, allCandidates.getWrappedHost(resource),
wireMap, allCandidates);
}
}
@@ -551,7 +593,7 @@ public class ResolverImpl implements Resolver
}
}
}
- while (session.getCurrentError() != null);
+ while (!session.isCancelled() && session.getCurrentError() != null);
return allCandidates;
}
@@ -579,6 +621,9 @@ public class ResolverImpl implements Resolver
rethrow = checkPackageSpaceConsistency(
session, entry.getValue(),
allCandidates, session.isDynamic(), resourcePkgMap, resultCache);
+ if (session.isCancelled()) {
+ return null;
+ }
if (rethrow != null)
{
Resource faultyResource = entry.getKey();
@@ -622,7 +667,7 @@ public class ResolverImpl implements Resolver
"Matching candidate does not provide a package name.");
}
}
- ResolveSession session = new ResolveSession(context, new DumbExecutor(), host, dynamicRequirement, matches);
+ ResolveSession session = ResolveSession.createSession(context, new DumbExecutor(), host, dynamicRequirement, matches);
return doResolve(session);
}
@@ -1456,6 +1501,9 @@ public class ResolverImpl implements Resolver
rethrow = checkPackageSpaceConsistency(
session, cap.getResource(),
allCandidates, false, resourcePkgMap, resultCache);
+ if (session.isCancelled()) {
+ return null;
+ }
if (rethrow != null)
{
// If the lower level check didn't create any permutations,
@@ -1855,11 +1903,11 @@ public class ResolverImpl implements Resolver
}
private static Map<Resource, List<Wire>> populateWireMap(
- ResolveContext rc, Resource resource,
+ ResolveSession session, Resource resource,
Map<Resource, List<Wire>> wireMap, Candidates allCandidates)
{
Resource unwrappedResource = getDeclaredResource(resource);
- if (!rc.getWirings().containsKey(unwrappedResource)
+ if (!session.getContext().getWirings().containsKey(unwrappedResource)
&& !wireMap.containsKey(unwrappedResource))
{
wireMap.put(unwrappedResource, Collections.<Wire>emptyList());
@@ -1882,7 +1930,7 @@ public class ResolverImpl implements Resolver
|| !resource.equals(cand.getResource()))
{
// Populate wires for the candidate
- populateWireMap(rc, cand.getResource(),
+ populateWireMap(session, cand.getResource(),
wireMap, allCandidates);
Resource provider;
@@ -1962,7 +2010,7 @@ public class ResolverImpl implements Resolver
// Otherwise, if the fragment isn't already resolved and
// this is the first time we are seeing it, then create
// a wire for the non-payload requirement.
- else if (!rc.getWirings().containsKey(fragment)
+ else if (!session.getContext().getWirings().containsKey(fragment)
&& !wireMap.containsKey(fragment))
{
Wire wire = createWire(req, allCandidates);
@@ -1978,6 +2026,12 @@ public class ResolverImpl implements Resolver
wireMap.put(fragment, fragmentWires);
}
}
+ // now make sure any related resources are populated
+ for (Resource related : session.getRelatedResources(unwrappedResource)) {
+ if (allCandidates.isPopulated(related)) {
+ populateWireMap(session, related, wireMap, allCandidates);
+ }
+ }
}
return wireMap;
@@ -2012,31 +2066,31 @@ public class ResolverImpl implements Resolver
}
private static Map<Resource, List<Wire>> populateDynamicWireMap(
- ResolveContext rc, Resource resource, Requirement dynReq,
- Map<Resource, List<Wire>> wireMap, Candidates allCandidates)
+ ResolveSession session, Map<Resource,
+ List<Wire>> wireMap, Candidates allCandidates)
{
- wireMap.put(resource, Collections.<Wire>emptyList());
+ wireMap.put(session.getDynamicHost(), Collections.<Wire>emptyList());
List<Wire> packageWires = new ArrayList<Wire>();
// Get the candidates for the current dynamic requirement.
// Record the dynamic candidate.
- Capability dynCand = allCandidates.getFirstCandidate(dynReq);
+ Capability dynCand = allCandidates.getFirstCandidate(session.getDynamicRequirement());
- if (!rc.getWirings().containsKey(dynCand.getResource()))
+ if (!session.getContext().getWirings().containsKey(dynCand.getResource()))
{
- populateWireMap(rc, dynCand.getResource(),
+ populateWireMap(session, dynCand.getResource(),
wireMap, allCandidates);
}
packageWires.add(
new WireImpl(
- resource,
- dynReq,
+ session.getDynamicHost(),
+ session.getDynamicRequirement(),
getDeclaredResource(dynCand.getResource()),
getDeclaredCapability(dynCand)));
- wireMap.put(resource, packageWires);
+ wireMap.put(session.getDynamicHost(), packageWires);
return wireMap;
}
diff --git a/bundles/org.eclipse.osgi/osgi/src/org/osgi/service/resolver/packageinfo b/bundles/org.eclipse.osgi/osgi/src/org/osgi/service/resolver/packageinfo
deleted file mode 100644
index 3987f9c4e..000000000
--- a/bundles/org.eclipse.osgi/osgi/src/org/osgi/service/resolver/packageinfo
+++ /dev/null
@@ -1 +0,0 @@
-version 1.1
diff --git a/bundles/org.eclipse.osgi/pom.xml b/bundles/org.eclipse.osgi/pom.xml
index 793b913e4..3fefdbb72 100644
--- a/bundles/org.eclipse.osgi/pom.xml
+++ b/bundles/org.eclipse.osgi/pom.xml
@@ -19,7 +19,7 @@
</parent>
<groupId>org.eclipse.osgi</groupId>
<artifactId>org.eclipse.osgi</artifactId>
- <version>3.12.0-SNAPSHOT</version>
+ <version>3.13.0-SNAPSHOT</version>
<packaging>eclipse-plugin</packaging>
<build>

Back to the top