Skip to main content
summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJohn Arthorne2008-02-29 21:56:22 +0000
committerJohn Arthorne2008-02-29 21:56:22 +0000
commitf5a9ed5c50e642115b3e50b5cc8734e388d01286 (patch)
tree356961e7f61ddaeadeffab1ca8e14e6c45ff128c
parent51188a46cbb5dd4819fffaf38fd66d4b6c53dd08 (diff)
downloadrt.equinox.p2-f5a9ed5c50e642115b3e50b5cc8734e388d01286.tar.gz
rt.equinox.p2-f5a9ed5c50e642115b3e50b5cc8734e388d01286.tar.xz
rt.equinox.p2-f5a9ed5c50e642115b3e50b5cc8734e388d01286.zip
Bug 220872 Many (many) attempts to read from the same invalid artifact repositoryv200803040717
-rw-r--r--bundles/org.eclipse.equinox.p2.artifact.repository/src/org/eclipse/equinox/internal/p2/artifact/repository/ArtifactRepositoryManager.java40
-rw-r--r--bundles/org.eclipse.equinox.p2.metadata.repository/src/org/eclipse/equinox/internal/p2/metadata/repository/MetadataRepositoryManager.java59
2 files changed, 91 insertions, 8 deletions
diff --git a/bundles/org.eclipse.equinox.p2.artifact.repository/src/org/eclipse/equinox/internal/p2/artifact/repository/ArtifactRepositoryManager.java b/bundles/org.eclipse.equinox.p2.artifact.repository/src/org/eclipse/equinox/internal/p2/artifact/repository/ArtifactRepositoryManager.java
index b04440cd9..22cf4ac56 100644
--- a/bundles/org.eclipse.equinox.p2.artifact.repository/src/org/eclipse/equinox/internal/p2/artifact/repository/ArtifactRepositoryManager.java
+++ b/bundles/org.eclipse.equinox.p2.artifact.repository/src/org/eclipse/equinox/internal/p2/artifact/repository/ArtifactRepositoryManager.java
@@ -60,6 +60,12 @@ public class ArtifactRepositoryManager implements IArtifactRepositoryManager {
//lock object to be held when referring to the repositories field
private final Object repositoryLock = new Object();
+ /**
+ * Cache List of repositories that are not reachable. Maintain cache
+ * for short duration because repository may become available at any time.
+ */
+ private SoftReference unavailableRepositories;
+
public ArtifactRepositoryManager() {
//initialize repositories lazily
}
@@ -281,6 +287,8 @@ public class ArtifactRepositoryManager implements IArtifactRepositoryManager {
IArtifactRepository result = getRepository(location);
if (result != null)
return result;
+ if (checkNotFound(location))
+ fail(location, ProvisionException.REPOSITORY_NOT_FOUND);
String[] suffixes = getAllSuffixes();
SubMonitor sub = SubMonitor.convert(monitor, suffixes.length * 100);
for (int i = 0; i < suffixes.length; i++) {
@@ -290,10 +298,42 @@ public class ArtifactRepositoryManager implements IArtifactRepositoryManager {
return result;
}
}
+ rememberNotFound(location);
fail(location, ProvisionException.REPOSITORY_NOT_FOUND);
return null;
}
+ /**
+ * Check if we recently attempted to load the given location and failed
+ * to find anything. Returns <code>true</code> if the repository was not
+ * found, and <code>false</code> otherwise.
+ */
+ private boolean checkNotFound(URL location) {
+ if (unavailableRepositories == null)
+ return false;
+ List badRepos = (List) unavailableRepositories.get();
+ if (badRepos == null)
+ return false;
+ return badRepos.contains(location);
+ }
+
+ /**
+ * Cache the fact that we tried to load a repository at this location and did not find anything.
+ */
+ private void rememberNotFound(URL location) {
+ List badRepos;
+ if (unavailableRepositories != null) {
+ badRepos = (List) unavailableRepositories.get();
+ if (badRepos != null) {
+ badRepos.add(location);
+ return;
+ }
+ }
+ badRepos = new ArrayList();
+ badRepos.add(location);
+ unavailableRepositories = new SoftReference(badRepos);
+ }
+
private IArtifactRepository loadRepository(URL location, String suffix, SubMonitor monitor) {
IExtension[] providers = findMatchingRepositoryExtensions(suffix);
// Loop over the candidates and return the first one that successfully loads
diff --git a/bundles/org.eclipse.equinox.p2.metadata.repository/src/org/eclipse/equinox/internal/p2/metadata/repository/MetadataRepositoryManager.java b/bundles/org.eclipse.equinox.p2.metadata.repository/src/org/eclipse/equinox/internal/p2/metadata/repository/MetadataRepositoryManager.java
index 691e9ac00..fb48d9501 100644
--- a/bundles/org.eclipse.equinox.p2.metadata.repository/src/org/eclipse/equinox/internal/p2/metadata/repository/MetadataRepositoryManager.java
+++ b/bundles/org.eclipse.equinox.p2.metadata.repository/src/org/eclipse/equinox/internal/p2/metadata/repository/MetadataRepositoryManager.java
@@ -54,9 +54,16 @@ public class MetadataRepositoryManager implements IMetadataRepositoryManager {
* obtained vai getKey(URL).
*/
private Map repositories = null;
+
//lock object to be held when referring to the repositories field
private final Object repositoryLock = new Object();
+ /**
+ * Cache List of repositories that are not reachable. Maintain cache
+ * for short duration because repository may become available at any time.
+ */
+ private SoftReference unavailableRepositories;
+
public MetadataRepositoryManager() {
//initialize repositories lazily
}
@@ -285,21 +292,57 @@ public class MetadataRepositoryManager implements IMetadataRepositoryManager {
IMetadataRepository result = getRepository(location);
if (result != null)
return result;
+ MultiStatus notFoundStatus = new MultiStatus(Activator.ID, ProvisionException.REPOSITORY_NOT_FOUND, NLS.bind(Messages.repoMan_notExists, location.toExternalForm()), null);
+ if (checkNotFound(location))
+ throw new ProvisionException(notFoundStatus);
String[] suffixes = getAllSuffixes();
SubMonitor sub = SubMonitor.convert(monitor, Messages.REPOMGR_ADDING_REPO, suffixes.length * 100);
- MultiStatus notFoundStatus = new MultiStatus(Activator.ID, ProvisionException.REPOSITORY_NOT_FOUND, NLS.bind(Messages.repoMan_notExists, location.toExternalForm()), null);
- for (int i = 0; i < suffixes.length; i++) {
- result = loadRepository(location, suffixes[i], sub.newChild(100), notFoundStatus);
- if (result != null) {
- addRepository(result);
- sub.done();
- return result;
+ try {
+ for (int i = 0; i < suffixes.length; i++) {
+ result = loadRepository(location, suffixes[i], sub.newChild(100), notFoundStatus);
+ if (result != null) {
+ addRepository(result);
+ return result;
+ }
}
+ } finally {
+ sub.done();
}
- sub.done();
+ rememberNotFound(location);
throw new ProvisionException(notFoundStatus);
}
+ /**
+ * Check if we recently attempted to load the given location and failed
+ * to find anything. Returns <code>true</code> if the repository was not
+ * found, and <code>false</code> otherwise.
+ */
+ private boolean checkNotFound(URL location) {
+ if (unavailableRepositories == null)
+ return false;
+ List badRepos = (List) unavailableRepositories.get();
+ if (badRepos == null)
+ return false;
+ return badRepos.contains(location);
+ }
+
+ /**
+ * Cache the fact that we tried to load a repository at this location and did not find anything.
+ */
+ private void rememberNotFound(URL location) {
+ List badRepos;
+ if (unavailableRepositories != null) {
+ badRepos = (List) unavailableRepositories.get();
+ if (badRepos != null) {
+ badRepos.add(location);
+ return;
+ }
+ }
+ badRepos = new ArrayList();
+ badRepos.add(location);
+ unavailableRepositories = new SoftReference(badRepos);
+ }
+
public IStatus validateRepositoryLocation(URL location, IProgressMonitor monitor) {
Assert.isNotNull(location);
IMetadataRepository result = getRepository(location);

Back to the top