| /******************************************************************************* |
| * Copyright (c) 2004, 2008 IBM Corporation and others. |
| * All rights reserved. This program and the accompanying materials |
| * are made available under the terms of the Eclipse Public License v1.0 |
| * which accompanies this distribution, and is available at |
| * http://www.eclipse.org/legal/epl-v10.html |
| * |
| * Contributors: |
| * IBM Corporation - initial API and implementation |
| *******************************************************************************/ |
| package org.eclipse.jdt.debug.tests.sourcelookup; |
| |
| import java.io.File; |
| import java.util.concurrent.CountDownLatch; |
| import java.util.concurrent.ExecutorService; |
| import java.util.concurrent.Executors; |
| import java.util.concurrent.atomic.AtomicReference; |
| |
| import org.eclipse.core.runtime.IPath; |
| import org.eclipse.core.runtime.Path; |
| import org.eclipse.debug.core.sourcelookup.ISourceContainer; |
| import org.eclipse.debug.core.sourcelookup.ISourceLookupDirector; |
| import org.eclipse.debug.core.sourcelookup.containers.ExternalArchiveSourceContainer; |
| import org.eclipse.debug.core.sourcelookup.containers.ZipEntryStorage; |
| import org.eclipse.jdt.debug.testplugin.JavaTestPlugin; |
| import org.eclipse.jdt.debug.tests.AbstractDebugTest; |
| import org.eclipse.jdt.internal.launching.JavaSourceLookupDirector; |
| import org.eclipse.jdt.launching.JavaRuntime; |
| import org.eclipse.jdt.launching.LibraryLocation; |
| |
| /** |
| * Tests external archive source containers |
| */ |
| public class ExternalArchiveSourceContainerTests extends AbstractDebugTest { |
| |
| public ExternalArchiveSourceContainerTests(String name) { |
| super(name); |
| } |
| |
| /** |
| * Returns the JREs source archive. |
| * |
| * @return |
| * @throws Exception |
| */ |
| protected ExternalArchiveSourceContainer getContainer(boolean detect, boolean duplicates) throws Exception { |
| ISourceLookupDirector director = new JavaSourceLookupDirector(); |
| director.initializeParticipants(); |
| director.setFindDuplicates(duplicates); |
| LibraryLocation[] locations = JavaRuntime.getLibraryLocations(JavaRuntime.getDefaultVMInstall()); |
| for (int i = 0; i < locations.length; i++) { |
| LibraryLocation location = locations[i]; |
| IPath path = location.getSystemLibrarySourcePath(); |
| if (path != null && !path.isEmpty()) { |
| ExternalArchiveSourceContainer container = new ExternalArchiveSourceContainer(path.toOSString(), detect); |
| director.setSourceContainers(new ISourceContainer[]{container}); |
| return container; |
| } |
| } |
| assertTrue("Did not find JRE source archive. This failure is expected if you are running the tests with a JRE that does not contain source.", false); |
| return null; |
| } |
| |
| /** |
| * Returns the source archive at the specified path within this plug-in. |
| */ |
| protected ExternalArchiveSourceContainer getContainer(String path, boolean detect, boolean duplicates) throws Exception { |
| ISourceLookupDirector director = new JavaSourceLookupDirector(); |
| director.initializeParticipants(); |
| director.setFindDuplicates(duplicates); |
| IPath p = new Path(path); |
| File file = JavaTestPlugin.getDefault().getFileInPlugin(p); |
| assertTrue("file " + path + " does not exist", file != null && file.exists()); |
| ExternalArchiveSourceContainer container = new ExternalArchiveSourceContainer(file.getAbsolutePath(), detect); |
| director.setSourceContainers(new ISourceContainer[]{container}); |
| return container; |
| } |
| |
| /** |
| * Tests creation and restoring from a memento. |
| * |
| * @throws Exception |
| */ |
| public void testArchiveSourceContainerMemento() throws Exception { |
| ExternalArchiveSourceContainer container = getContainer(true, false); |
| assertFalse(container.isComposite()); |
| assertTrue(container.isDetectRoot()); |
| String memento = container.getType().getMemento(container); |
| ExternalArchiveSourceContainer restore = (ExternalArchiveSourceContainer) container.getType().createSourceContainer(memento); |
| assertEquals("Directory source container memento failed", container, restore); |
| assertFalse(restore.isComposite()); |
| assertTrue(restore.isDetectRoot()); |
| } |
| |
| public void testAutoDetectRootSourceLookupPositive() throws Exception { |
| ExternalArchiveSourceContainer container = getContainer(true, false); |
| Object[] objects = container.findSourceElements("java/lang/Object.java"); |
| assertEquals("Expected 1 result", 1, objects.length); |
| ZipEntryStorage storage = (ZipEntryStorage) objects[0]; |
| assertEquals("Wrong file", "Object.java", storage.getName()); |
| } |
| |
| public void testAutoDetectRootSourceLookupNegative() throws Exception { |
| ExternalArchiveSourceContainer container = getContainer(true, false); |
| Object[] objects = container.findSourceElements("java/lang/FileNotFound.java"); |
| assertEquals("Expected 0 files", 0, objects.length); |
| } |
| |
| public void testSourceLookupPositive() throws Exception { |
| ExternalArchiveSourceContainer container = getContainer(false, false); |
| Object[] objects = container.findSourceElements("java/lang/Object.java"); |
| assertEquals("Expected 1 result", 1, objects.length); |
| ZipEntryStorage storage = (ZipEntryStorage) objects[0]; |
| assertEquals("Wrong file", "Object.java", storage.getName()); |
| } |
| |
| public void testSourceLookupNegative() throws Exception { |
| ExternalArchiveSourceContainer container = getContainer(false, false); |
| Object[] objects = container.findSourceElements("java/lang/FileNotFound.java"); |
| assertEquals("Expected 0 files", 0, objects.length); |
| } |
| |
| public void testPartiallyQualifiedSourceLookupPositive() throws Exception { |
| ExternalArchiveSourceContainer container = getContainer(false, false); |
| Object[] objects = container.findSourceElements("lang/Object.java"); |
| assertEquals("Expected 1 result", 1, objects.length); |
| ZipEntryStorage storage = (ZipEntryStorage) objects[0]; |
| assertEquals("Wrong file", "Object.java", storage.getName()); |
| } |
| |
| public void testAutoDetectUnqualifiedSourceLookupPositive() throws Exception { |
| ExternalArchiveSourceContainer container = getContainer(true, false); |
| // force detection |
| Object[] objects = container.findSourceElements("java/lang/Object.java"); |
| // then search for unqualified file |
| objects = container.findSourceElements("Object.java"); |
| assertEquals("Expected 1 result", 1, objects.length); |
| ZipEntryStorage storage = (ZipEntryStorage) objects[0]; |
| assertEquals("Wrong file", "Object.java", storage.getName()); |
| } |
| |
| public void testAutoDetectMultipleRoots() throws Exception { |
| ExternalArchiveSourceContainer container = getContainer("testresources/source-test.zip", true, false); |
| // find .java file |
| Object[] objects = container.findSourceElements("one/two/Three.java"); |
| assertEquals("Expected 1 result", 1, objects.length); |
| ZipEntryStorage storage = (ZipEntryStorage) objects[0]; |
| assertEquals("Wrong file", "Three.java", storage.getName()); |
| // find .txt file |
| objects = container.findSourceElements("another/file-b.txt"); |
| storage = (ZipEntryStorage) objects[0]; |
| assertEquals("Wrong file", "file-b.txt", storage.getName()); |
| // find another .txt file |
| objects = container.findSourceElements("folder/file-c.txt"); |
| storage = (ZipEntryStorage) objects[0]; |
| assertEquals("Wrong file", "file-c.txt", storage.getName()); |
| } |
| |
| /** |
| * Test for bug 515941 (ConcurrentModificationException on container dispose) |
| */ |
| public void testDisposed() throws Exception { |
| int threads = Math.min(Runtime.getRuntime().availableProcessors(), 4); |
| ExecutorService exec = Executors.newFixedThreadPool(threads); |
| AtomicReference<Throwable> err = new AtomicReference<>(); |
| AtomicReference<ExternalArchiveSourceContainer> container = new AtomicReference<>(); |
| AtomicReference<Boolean> stop = new AtomicReference<>(Boolean.FALSE); |
| CountDownLatch latch = new CountDownLatch(1); |
| for (int i = 0; i < threads; i++) { |
| exec.submit(() -> { |
| try { |
| latch.await(); |
| while (!stop.get()) { |
| ExternalArchiveSourceContainer c = container.get(); |
| if (c != null) { |
| c.dispose(); |
| } |
| } |
| } |
| catch (Throwable e) { |
| err.set(e); |
| } |
| }); |
| } |
| latch.countDown(); |
| try { |
| for (int i = 0; i < 5_000; i++) { |
| ExternalArchiveSourceContainer cont = getContainer("testresources/source-test.zip", true, false); |
| try { |
| container.set(cont); |
| Thread.sleep(1); |
| cont.findSourceElements("one/two/Three.java"); |
| |
| } |
| finally { |
| cont.dispose(); |
| } |
| } |
| } |
| finally { |
| stop.set(true); |
| exec.shutdownNow(); |
| } |
| } |
| } |