mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2026-05-30 01:50:16 +08:00
GP-6641 - Extensions - UI Updates to show more extension details for
contained ExtensionPoints
This commit is contained in:
@@ -14,8 +14,8 @@
|
||||
into a Ghidra distribution. This allows users to create and share new plugins and scripts.
|
||||
Ghidra ships with some pre-built extensions that not installed by default.
|
||||
</P>
|
||||
<P>Ghidra Extensions can be installed and uninstalled at runtime, with the changes taking effect
|
||||
when Ghidra is restarted. The extension installation dialog can
|
||||
<P>Ghidra Extensions can be installed and uninstalled at runtime, <U>with the changes taking effect
|
||||
when Ghidra is restarted</U>. The extension installation dialog can
|
||||
be opened by selecting the <B>Install Extensions</B> option on the project <B>File</B> menu.</P>
|
||||
|
||||
<BLOCKQUOTE>
|
||||
@@ -32,11 +32,61 @@
|
||||
</BLOCKQUOTE>
|
||||
|
||||
|
||||
<BLOCKQUOTE>
|
||||
<P>Installed extensions provide new functionality to Ghidra, such as Plugins, Analyzers and
|
||||
other Extension Points. Non-plugin Extension Points will be automatically discovered and
|
||||
loaded at startup. This is <B>not</B> the case for Plugins. Plugins must be manually
|
||||
enabled inside of the tool that is being used. For example, when running the Code Browser,
|
||||
use the <A href="help/topics/Tool/Configure_Tool.htm">
|
||||
<B>File</B><IMG src="help/shared/arrow.gif" border="0"><B>Congfigure</B></A> menu to
|
||||
enable any plugins added by newly installed extensions.
|
||||
</P>
|
||||
|
||||
<BLOCKQUOTE>
|
||||
<P><IMG src="help/shared/tip.png" alt="" border="0">The easiest way to find the plugins
|
||||
for a given extension is to use the table view of all known plugins. To see all plugins
|
||||
for an extension:</P>
|
||||
<OL>
|
||||
<LI>
|
||||
Configure plugins via <B>File</B><IMG src="help/shared/arrow.gif" border="0">
|
||||
<B>Congfigure</B>
|
||||
</LI>
|
||||
<LI>
|
||||
Click the <img src="images/plugin.png" /> icon to show all plugins
|
||||
</LI>
|
||||
<LI>
|
||||
If not already visible, add the <B>Module</B> table column via the right-click
|
||||
menu of the table header. (Extensions are modules.)
|
||||
</LI>
|
||||
<LI>
|
||||
Sort on the <B>Module</B> table column
|
||||
</LI>
|
||||
<LI>
|
||||
Optionally, you can type the name of the extension into the filter to hide other modules
|
||||
</LI>
|
||||
</OL>
|
||||
</BLOCKQUOTE>
|
||||
|
||||
</BLOCKQUOTE>
|
||||
|
||||
|
||||
<H2>Dialog Components</H2>
|
||||
|
||||
<H3>Extensions Table</H3>
|
||||
|
||||
<BLOCKQUOTE>
|
||||
|
||||
<P>To install an extension, select the extension's checkbox. To unininstall, deselect the
|
||||
checkbox.</P>
|
||||
|
||||
|
||||
<BLOCKQUOTE>
|
||||
<P><IMG src="help/shared/note.png" alt="" border="0">If the checkbox is not editable,
|
||||
that means that means the extension is installed and canont be uninistalled. This can
|
||||
happen in development mode with extensions that live in source control.</P>
|
||||
</BLOCKQUOTE>
|
||||
|
||||
|
||||
<P>The list of extensions is populated when the dialog is launched. To build the list, Ghidra
|
||||
looks in several locations:</P>
|
||||
|
||||
|
||||
+2
-2
@@ -371,8 +371,8 @@
|
||||
<P class="relatedtopic">Related Topics</P>
|
||||
|
||||
<UL>
|
||||
<LI><A href="help/topics/Tool/ToolOptions_Dialog.htm#KeyBindings_Option">Key
|
||||
Bindings</A></LI>
|
||||
<LI><A href="../BundleManager/BundleManager.htm">Ghidra Bundles</A>
|
||||
<LI><A href="help/topics/Tool/ToolOptions_Dialog.htm#KeyBindings_Option">Key Bindings</A></LI>
|
||||
</UL>
|
||||
|
||||
<P> </P>
|
||||
|
||||
@@ -27,7 +27,8 @@
|
||||
<UL>
|
||||
<LI>
|
||||
<B>Version</B> - Ghidra, Operating System, and Java version information. Clicking the
|
||||
<B><I>Copy</I></B> button will copy this information to the clipboard for easy transfer into a bug report.
|
||||
<B><I>Copy</I></B> button will copy this information to the clipboard for easy transfer into
|
||||
a bug report.
|
||||
</LI>
|
||||
<LI>
|
||||
<B>Memory</B> - JVM memory usage. Clicking the <B><I>Collect Garbage</I></B> button will
|
||||
@@ -47,7 +48,11 @@
|
||||
<B>Modules</B> - A list of discovered Ghidra Modules.
|
||||
</LI>
|
||||
<LI>
|
||||
<B>Extension Points</B> - A list of discovered Ghidra Extension Points.
|
||||
<B>Extension Points</B> - A list of discovered Ghidra Extension Points.<BR><BR>
|
||||
Note: Extension Points differ from Extensions. Extension Points are classes that Ghidra
|
||||
will find at startup. Extensions are additional Ghidra Modules that can be installed
|
||||
by the user. Further, Extensions may contain Extension Points.
|
||||
<BR><BR>
|
||||
</LI>
|
||||
<LI>
|
||||
<B>Classpath</B> - The ordered classpath for the active Ghidra application.
|
||||
|
||||
+10
-2
@@ -24,6 +24,7 @@ import java.util.*;
|
||||
import org.junit.AfterClass;
|
||||
|
||||
import docking.test.AbstractDockingTest;
|
||||
import generic.jar.ResourceFile;
|
||||
import ghidra.GhidraTestApplicationLayout;
|
||||
import ghidra.app.events.ProgramLocationPluginEvent;
|
||||
import ghidra.app.events.ProgramSelectionPluginEvent;
|
||||
@@ -659,9 +660,16 @@ public abstract class AbstractGhidraHeadlessIntegrationTest extends AbstractDock
|
||||
Set<ClassFileInfo> serviceSet = extensionPointSuffixToInfoMap.get(suffix);
|
||||
assertNotNull(serviceSet);
|
||||
serviceSet.clear();
|
||||
ClassFileInfo info = new ClassFileInfo("", replacement.getClass().getName(), suffix);
|
||||
Class<? extends Object> clazz = replacement.getClass();
|
||||
ResourceFile module = Application.getModuleContainingClass(clazz);
|
||||
String modulePath = "";
|
||||
if (module != null) {
|
||||
modulePath = module.getAbsolutePath();
|
||||
}
|
||||
String name = clazz.getName();
|
||||
ClassFileInfo info = new ClassFileInfo("", name, suffix, modulePath);
|
||||
serviceSet.add(info);
|
||||
loadedCache.put(info, replacement.getClass());
|
||||
loadedCache.put(info, clazz);
|
||||
}
|
||||
|
||||
T instance = tool.getService(service);
|
||||
|
||||
+3
-3
@@ -4,9 +4,9 @@
|
||||
* Licensed 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.
|
||||
@@ -263,7 +263,7 @@ public class AnalysisOptions2Test extends AbstractGhidraHeadedIntegrationTest {
|
||||
assertNotNull(analyzerSet);
|
||||
|
||||
analyzerSet.removeIf(c -> c.name().contains("TestStubAnalyzer"));
|
||||
ClassFileInfo info = new ClassFileInfo("", analyzer.getName(), "Analyzer");
|
||||
ClassFileInfo info = new ClassFileInfo("", analyzer.getName(), "Analyzer", "");
|
||||
analyzerSet.add(info);
|
||||
loadedCache.put(info, analyzer);
|
||||
}
|
||||
|
||||
+22
-8
@@ -31,13 +31,14 @@ import ghidra.framework.Application;
|
||||
import ghidra.framework.project.tool.testplugins.TestExtensionHello2Plugin;
|
||||
import ghidra.framework.project.tool.testplugins.TestExtensionHelloPlugin;
|
||||
import ghidra.test.AbstractGhidraHeadedIntegrationTest;
|
||||
import ghidra.util.classfinder.ClassFileInfo;
|
||||
import ghidra.util.extensions.ExtensionUtils;
|
||||
import ghidra.util.xml.GenericXMLOutputter;
|
||||
import ghidra.util.xml.XmlUtilities;
|
||||
import utilities.util.FileUtilities;
|
||||
import utility.application.ApplicationLayout;
|
||||
|
||||
public class ExtensionManagerTest extends AbstractGhidraHeadedIntegrationTest {
|
||||
public class ToolExtensionStatusManagerTest extends AbstractGhidraHeadedIntegrationTest {
|
||||
|
||||
private ApplicationLayout appLayout;
|
||||
private FakeToolExtensionsEnabledState extensionsState;
|
||||
@@ -130,6 +131,7 @@ public class ExtensionManagerTest extends AbstractGhidraHeadedIntegrationTest {
|
||||
// verify user is prompted to add new plugins
|
||||
extensionManager.checkForNewExtensions();
|
||||
waitForSwing();
|
||||
waitForSwing();
|
||||
assertTrue(extensionsState.didPrompt());
|
||||
}
|
||||
|
||||
@@ -274,35 +276,47 @@ public class ExtensionManagerTest extends AbstractGhidraHeadedIntegrationTest {
|
||||
|
||||
private class FakeToolExtensionsEnabledState implements ExtensionsEnabledState {
|
||||
|
||||
private Map<String, Set<Class<?>>> extensions = new HashMap<>();
|
||||
private Set<Class<?>> installedPlugins = new HashSet<>();
|
||||
private Map<String, Set<ClassFileInfo>> extensions = new HashMap<>();
|
||||
private Set<ClassFileInfo> installedPlugins = new HashSet<>();
|
||||
private boolean didPrompt = false;
|
||||
|
||||
@Override
|
||||
public Map<String, Set<Class<?>>> getAllKnownExtensions() {
|
||||
public Map<String, Set<ClassFileInfo>> getAllKnownExtensions() {
|
||||
return extensions;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removeInstalledPlugins(Set<Class<?>> plugins) {
|
||||
public void removeInstalledPlugins(Set<ClassFileInfo> plugins) {
|
||||
plugins.removeAll(installedPlugins);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void propmtToConfigureNewPlugins(Set<Class<?>> plugins) {
|
||||
public void propmtToConfigureNewPlugins(Set<ClassFileInfo> plugins) {
|
||||
didPrompt = true;
|
||||
}
|
||||
|
||||
void addExtension(String name, Class<?>... classes) {
|
||||
void addExtension(String name, ClassFileInfo... classes) {
|
||||
extensions.put(name, Set.of(classes));
|
||||
}
|
||||
|
||||
void addExtension(String name, Class<?>... classes) {
|
||||
|
||||
for (Class<?> c : classes) {
|
||||
String className = c.getName();
|
||||
ClassFileInfo info = new ClassFileInfo("/fake/path", className, "Plugin", "");
|
||||
addExtension(name, info);
|
||||
}
|
||||
}
|
||||
|
||||
boolean didPrompt() {
|
||||
return didPrompt;
|
||||
}
|
||||
|
||||
void setInstalled(Class<TestExtensionHelloPlugin> c) {
|
||||
installedPlugins.add(c);
|
||||
|
||||
String name = c.getName();
|
||||
ClassFileInfo info = new ClassFileInfo("/fake/path", name, "Plugin", "");
|
||||
installedPlugins.add(info);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user