/******************************************************************************* * Copyright (c) 2007, 2014 Wind River Systems, Inc. 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: * Wind River Systems - initial API and implementation *******************************************************************************/ package org.eclipse.tcf.internal.debug.launch; import java.io.File; import java.net.URI; import java.util.HashSet; import java.util.Map; import java.util.Set; import org.eclipse.core.filesystem.URIUtil; import org.eclipse.core.resources.IFile; import org.eclipse.core.resources.IStorage; import org.eclipse.core.resources.ResourcesPlugin; import org.eclipse.core.runtime.IPath; import org.eclipse.debug.core.model.ISourceLocator; import org.eclipse.debug.core.model.IStackFrame; import org.eclipse.debug.core.sourcelookup.AbstractSourceLookupDirector; import org.eclipse.debug.core.sourcelookup.ISourceContainerType; import org.eclipse.debug.core.sourcelookup.ISourceLookupDirector; import org.eclipse.debug.core.sourcelookup.ISourceLookupParticipant; import org.eclipse.debug.core.sourcelookup.containers.LocalFileStorage; import org.eclipse.tcf.internal.debug.model.TCFLaunch; import org.eclipse.tcf.services.ILineNumbers; import org.eclipse.tcf.services.IPathMap; import org.eclipse.tcf.util.TCFDataCache; import org.eclipse.tcf.util.TCFTask; /** * TCF source lookup director. * For TCF source lookup there is one source lookup participant. */ public class TCFSourceLookupDirector extends AbstractSourceLookupDirector { private static Set<String> fSupportedContainerTypes; static { fSupportedContainerTypes = new HashSet<String>(); // Bug 440538: // Only CDT path mapping source containers are currently supported fSupportedContainerTypes.add("org.eclipse.cdt.debug.core.containerType.mapping"); }; public static Object lookup(final TCFLaunch launch, final String ctx, Object element) { if (element instanceof ILineNumbers.CodeArea) { element = TCFSourceLookupParticipant.toFileName((ILineNumbers.CodeArea)element); } Object source_element = null; ISourceLocator locator = launch.getSourceLocator(); if (locator instanceof ISourceLookupDirector) { source_element = ((ISourceLookupDirector)locator).getSourceElement(element); } else if (element instanceof IStackFrame) { source_element = locator.getSourceElement((IStackFrame)element); } if (source_element == null && element instanceof String) { /* Try to lookup the element using target side path mapping rules */ final String str = (String)element; String key = str; if (ctx != null) key = ctx + "::" + str; Map<String,IStorage> map = launch.getTargetPathMappingCache(); synchronized (map) { if (map.containsKey(str)) return map.get(key); } IStorage storage = new TCFTask<IStorage>(launch.getChannel()) { public void run() { TCFDataCache<IPathMap.PathMapRule[]> cache = launch.getTargetPathMap(); if (cache != null) { if (!cache.validate(this)) return; IPathMap.PathMapRule[] data = cache.getData(); if (data != null) { for (IPathMap.PathMapRule r : data) { final String query = r.getContextQuery(); if (query != null && query.length() > 0 && !query.equals("*")) { if (ctx == null) continue; TCFDataCache<String[]> q_cache = launch.getContextQuery(query); if (q_cache == null) continue; if (!q_cache.validate(this)) return; String[] q_data = q_cache.getData(); if (q_data == null) continue; boolean ok = false; for (String id : q_data) { if (ctx.equals(id)) ok = true; } if (!ok) continue; } String fnm = TCFSourceLookupParticipant.toFileName(r, str); if (fnm == null) continue; File file = new File(fnm); if (file.isAbsolute() && file.exists() && file.isFile()) { done(new LocalFileStorage(file)); return; } } } } done(null); } }.getE(); if (storage != null) { /* Map to workspace resource */ IPath path = storage.getFullPath(); if (path != null) { URI uri = URIUtil.toURI(path); IFile[] arr = ResourcesPlugin.getWorkspace().getRoot().findFilesForLocationURI(uri); if (arr != null && arr.length > 0) { for (IFile resource : arr) { if (resource.isAccessible()) { storage = resource; break; } } } } } synchronized (map) { map.put(key, storage); } source_element = storage; } return source_element; } public void initializeParticipants() { addParticipants(new ISourceLookupParticipant[] { new TCFSourceLookupParticipant() }); } /* (non-Javadoc) * @see org.eclipse.debug.core.sourcelookup.ISourceLookupDirector#supportsSourceContainerType(org.eclipse.debug.core.sourcelookup.ISourceContainerType) */ @Override public boolean supportsSourceContainerType(ISourceContainerType type) { return fSupportedContainerTypes.contains(type.getId()); } }