mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2025-10-06 03:50:02 +02:00
GT-2229: added action to issue a goto when new function selected
GT-2229: added support for multiple programs GT-2229: Updated icons/help/screenshots for function new comparison features GT-2229: minor fixes after code review GT-2229: minor code review fix
This commit is contained in:
parent
b9531416c0
commit
cc44d0c952
10 changed files with 230 additions and 10 deletions
|
@ -377,6 +377,7 @@ src/main/help/help/topics/FunctionComparison/images/ListingCodeComparisonOptions
|
|||
src/main/help/help/topics/FunctionComparison/images/MultiFunctionComparisonWindow.png||GHIDRA||||END|
|
||||
src/main/help/help/topics/FunctionComparison/images/NavNextIcon.png||GHIDRA||||END|
|
||||
src/main/help/help/topics/FunctionComparison/images/NavPreviousIcon.png||GHIDRA||||END|
|
||||
src/main/help/help/topics/FunctionComparison/images/NavSelectedIcon.png||GHIDRA||||END|
|
||||
src/main/help/help/topics/FunctionComparison/images/RemoveFromComparisonIcon.png||GHIDRA||||END|
|
||||
src/main/help/help/topics/FunctionComparison/images/binaryData.gif||GHIDRA||||END|
|
||||
src/main/help/help/topics/FunctionComparison/images/class.png||GHIDRA||||END|
|
||||
|
|
|
@ -428,16 +428,22 @@
|
|||
sides of the comparison window.
|
||||
</p>
|
||||
|
||||
<h3><IMG src="images/RemoveFromComparisonIcon.png" border="0"> <a name="Remove_From_Comparison"></a>Remove Function From Comparison</h3>
|
||||
<h3><IMG src="images/RemoveFromComparisonIcon.png" border="0"> <a name="Remove_From_Comparison"></a> Remove Function From Comparison</h3>
|
||||
<p>Removes the function in the focused panel from the comparison. This
|
||||
will remove the function from both the source and target selection pulldowns.</p>
|
||||
|
||||
<h3><IMG src="images/NavNextIcon.png" border="0"> <a name="Navigate_Next"></a>Go To Next Function</h3>
|
||||
<h3><IMG src="images/NavNextIcon.png" border="0"> <a name="Navigate_Next"></a> Go To Next Function</h3>
|
||||
<p>Navigates to the next available function in the selection pulldown</p>
|
||||
|
||||
<h3><IMG src="images/NavPreviousIcon.png" border="0"> <a name="Navigate_Previous"></a>Go To Previous Function</h3>
|
||||
<h3><IMG src="images/NavPreviousIcon.png" border="0"> <a name="Navigate_Previous"></a> Go To Previous Function</h3>
|
||||
<p>Navigates to the previous available function in the selection pulldown</p>
|
||||
|
||||
<h3><IMG src="Icons.NAVIGATE_ON_INCOMING_EVENT_ICON" border="0"> <a name="Navigate_To_Function"></a> Navigate To Selected Function</h3>
|
||||
<p>When toggled <b>on</b>, the function comparison panels become navigable,
|
||||
meaning a mouse click on the panel or change in the function being viewed
|
||||
will result in a GoTo event being generated. This allows other panels
|
||||
(eg: the listing) to update their views accordingly.</p>
|
||||
|
||||
<p><IMG src="../../shared/note.png"> The Remove and Go To actions described
|
||||
above will operate on the comparison panel that has focus, identified by the
|
||||
pink border.</p>
|
||||
|
|
Binary file not shown.
Before Width: | Height: | Size: 97 KiB After Width: | Height: | Size: 99 KiB |
|
@ -116,6 +116,24 @@ public class MultiFunctionComparisonPanel extends FunctionComparisonPanel {
|
|||
return sourceHasFocus ? sourceFunctionsCB : targetFunctionsCB;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the source combo box
|
||||
*
|
||||
* @return the source combo box
|
||||
*/
|
||||
public JComboBox<Function> getSourceComponent() {
|
||||
return sourceFunctionsCB;
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the target combo box
|
||||
*
|
||||
* @return the target combo box
|
||||
*/
|
||||
public JComboBox<Function> getTargetComponent() {
|
||||
return targetFunctionsCB;
|
||||
}
|
||||
|
||||
/**
|
||||
* Clears out and reloads the source function list. Any selection currently
|
||||
* made on the list will be reestablished.
|
||||
|
|
|
@ -56,11 +56,13 @@ public class MultiFunctionComparisonProvider extends FunctionComparisonProvider
|
|||
DockingAction previousFunctionAction = new PreviousFunctionAction(this);
|
||||
DockingAction removeFunctionsAction = new RemoveFunctionsAction(this);
|
||||
DockingAction openFunctionTableAction = getOpenFunctionTableAction();
|
||||
DockingAction navigateToAction = new NavigateToFunctionAction(this);
|
||||
|
||||
addLocalAction(nextFunctionAction);
|
||||
addLocalAction(previousFunctionAction);
|
||||
addLocalAction(removeFunctionsAction);
|
||||
addLocalAction(openFunctionTableAction);
|
||||
addLocalAction(navigateToAction);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -0,0 +1,187 @@
|
|||
/* ###
|
||||
* IP: GHIDRA
|
||||
*
|
||||
* 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.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
package ghidra.app.plugin.core.functioncompare.actions;
|
||||
|
||||
import java.awt.event.*;
|
||||
import java.util.List;
|
||||
|
||||
import javax.swing.ImageIcon;
|
||||
|
||||
import docking.action.ToggleDockingAction;
|
||||
import docking.action.ToolBarData;
|
||||
import docking.widgets.fieldpanel.internal.FieldPanelCoordinator;
|
||||
import ghidra.app.plugin.core.functioncompare.*;
|
||||
import ghidra.app.services.GoToService;
|
||||
import ghidra.app.util.viewer.util.CodeComparisonPanel;
|
||||
import ghidra.program.model.address.Address;
|
||||
import ghidra.program.model.listing.Function;
|
||||
import ghidra.util.HTMLUtilities;
|
||||
import ghidra.util.HelpLocation;
|
||||
import resources.Icons;
|
||||
|
||||
/**
|
||||
* Toggle Action designed to be used with a {@link MultiFunctionComparisonProvider}.
|
||||
* When toggled on, a GoTo event will be issued for the function displayed in
|
||||
* the comparison panel after the following events:
|
||||
* <ul>
|
||||
* <li>focus is gained on either the left or right panels</li>
|
||||
* <li>the function displayed in a comparison panel changes</li>
|
||||
* </ul>
|
||||
* Note that the GoTo will only operate on the comparison panel that
|
||||
* <b>has focus</b>. eg: If the left panel has focus but the user changes the
|
||||
* function being viewed in the right panel, no GoTo will be issued.
|
||||
*/
|
||||
public class NavigateToFunctionAction extends ToggleDockingAction {
|
||||
|
||||
private GoToService goToService;
|
||||
|
||||
private static final ImageIcon NAV_FUNCTION_ICON = Icons.NAVIGATE_ON_INCOMING_EVENT_ICON;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param provider the function comparison provider containing this action
|
||||
*/
|
||||
public NavigateToFunctionAction(MultiFunctionComparisonProvider provider) {
|
||||
super("Navigate To Selected Function", provider.getName());
|
||||
|
||||
goToService = provider.getTool().getService(GoToService.class);
|
||||
|
||||
setEnabled(true);
|
||||
setSelected(false);
|
||||
ToolBarData newToolBarData = new ToolBarData(NAV_FUNCTION_ICON);
|
||||
setToolBarData(newToolBarData);
|
||||
setDescription(
|
||||
HTMLUtilities.toHTML("Toggle <b>On</b> means to navigate to whatever " +
|
||||
"function is selected in the comparison panel, when focus changes or" +
|
||||
"a new function is selected."));
|
||||
setHelpLocation(
|
||||
new HelpLocation(MultiFunctionComparisonPanel.HELP_TOPIC, "Navigate_To_Function"));
|
||||
|
||||
addFocusListeners(provider);
|
||||
addChangeListeners(provider);
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a listener to each of the function selection widgets in the
|
||||
* comparison provider. When a new function is selected, a GoTo event
|
||||
* is generated for the entry point of the function.
|
||||
*
|
||||
* @param provider the function comparison provider
|
||||
*/
|
||||
private void addChangeListeners(MultiFunctionComparisonProvider provider) {
|
||||
MultiFunctionComparisonPanel panel = (MultiFunctionComparisonPanel) provider.getComponent();
|
||||
|
||||
panel.getSourceComponent().addItemListener(new ItemListener() {
|
||||
@Override
|
||||
public void itemStateChanged(ItemEvent e) {
|
||||
if (e.getStateChange() != ItemEvent.SELECTED) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (panel.getFocusedComponent() != panel.getSourceComponent()) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (NavigateToFunctionAction.this.isSelected()) {
|
||||
Function f = (Function) panel.getSourceComponent().getSelectedItem();
|
||||
goToService.goTo(f.getEntryPoint(), f.getProgram());
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
panel.getTargetComponent().addItemListener(new ItemListener() {
|
||||
@Override
|
||||
public void itemStateChanged(ItemEvent e) {
|
||||
if (e.getStateChange() != ItemEvent.SELECTED) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (panel.getFocusedComponent() != panel.getTargetComponent()) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (NavigateToFunctionAction.this.isSelected()) {
|
||||
Function f = (Function) panel.getTargetComponent().getSelectedItem();
|
||||
goToService.goTo(f.getEntryPoint(), f.getProgram());
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a listener to each panel in the function comparison provider,
|
||||
* triggered when focus has been changed. If focused is gained in a panel,
|
||||
* a GoTo event is issued containing the function start address.
|
||||
*
|
||||
* @param provider the function comparison provider
|
||||
*/
|
||||
private void addFocusListeners(MultiFunctionComparisonProvider provider) {
|
||||
|
||||
FunctionComparisonPanel mainPanel = provider.getComponent();
|
||||
List<CodeComparisonPanel<? extends FieldPanelCoordinator>> panels =
|
||||
mainPanel.getComparisonPanels();
|
||||
|
||||
for (CodeComparisonPanel<? extends FieldPanelCoordinator> panel : panels) {
|
||||
|
||||
panel.getRightFieldPanel().addFocusListener(new FocusAdapter() {
|
||||
|
||||
@Override
|
||||
public void focusGained(FocusEvent e) {
|
||||
if (NavigateToFunctionAction.this.isSelected()) {
|
||||
|
||||
Address addr = null;
|
||||
|
||||
if (panel.getRightFunction() != null) {
|
||||
addr = panel.getRightFunction().getBody().getMinAddress();
|
||||
}
|
||||
else if (panel.getRightData() != null) {
|
||||
addr = panel.getRightData().getAddress();
|
||||
}
|
||||
else if (panel.getRightAddresses() != null) {
|
||||
addr = panel.getRightAddresses().getMinAddress();
|
||||
}
|
||||
|
||||
goToService.goTo(addr, panel.getRightProgram());
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
panel.getRightFieldPanel().addFocusListener(new FocusAdapter() {
|
||||
|
||||
@Override
|
||||
public void focusGained(FocusEvent e) {
|
||||
if (NavigateToFunctionAction.this.isSelected()) {
|
||||
Address addr = null;
|
||||
|
||||
if (panel.getLeftFunction() != null) {
|
||||
addr = panel.getLeftFunction().getBody().getMinAddress();
|
||||
}
|
||||
else if (panel.getLeftData() != null) {
|
||||
addr = panel.getLeftData().getAddress();
|
||||
}
|
||||
else if (panel.getLeftAddresses() != null) {
|
||||
addr = panel.getLeftAddresses().getMinAddress();
|
||||
}
|
||||
|
||||
goToService.goTo(addr, panel.getLeftProgram());
|
||||
}
|
||||
}
|
||||
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
|
@ -2713,12 +2713,12 @@ public class ListingCodeComparisonPanel
|
|||
}
|
||||
|
||||
@Override
|
||||
protected FieldPanel getLeftFieldPanel() {
|
||||
public FieldPanel getLeftFieldPanel() {
|
||||
return getLeftPanel().getFieldPanel();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected FieldPanel getRightFieldPanel() {
|
||||
public FieldPanel getRightFieldPanel() {
|
||||
return getRightPanel().getFieldPanel();
|
||||
}
|
||||
|
||||
|
|
|
@ -326,13 +326,13 @@ public abstract class CodeComparisonPanel<T extends FieldPanelCoordinator> exten
|
|||
* Gets the left field panel for this CodeComparisonPanel.
|
||||
* @return the left FieldPanel.
|
||||
*/
|
||||
protected abstract FieldPanel getLeftFieldPanel();
|
||||
public abstract FieldPanel getLeftFieldPanel();
|
||||
|
||||
/**
|
||||
* Gets the right field panel for this CodeComparisonPanel.
|
||||
* @return the right FieldPanel.
|
||||
*/
|
||||
protected abstract FieldPanel getRightFieldPanel();
|
||||
public abstract FieldPanel getRightFieldPanel();
|
||||
|
||||
/**
|
||||
* Determines if the layouts of the views are synchronized with respect to scrolling and
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
*/
|
||||
package help.screenshot;
|
||||
|
||||
import static org.junit.Assert.*;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
|
||||
import java.awt.*;
|
||||
import java.awt.geom.GeneralPath;
|
||||
|
@ -604,6 +604,12 @@ public abstract class AbstractScreenShotGenerator extends AbstractGhidraHeadedIn
|
|||
runSwing(() -> {
|
||||
ImageIcon imageIcon = ResourceManager.getImageIcon(icon);
|
||||
image = imageIcon.getImage();
|
||||
|
||||
// The image returned here must be a BufferedImage, so create one
|
||||
// if not. It may be a ToolkitImage (eg: if the icon in question
|
||||
// is retrieved from Icons.java), which would fail on a cast to
|
||||
// BufferedImage during the save operation.
|
||||
image = ImageUtils.getBufferedImage(image);
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
@ -688,12 +688,12 @@ public abstract class DecompilerCodeComparisonPanel<T extends DualDecompilerFiel
|
|||
}
|
||||
|
||||
@Override
|
||||
protected FieldPanel getLeftFieldPanel() {
|
||||
public FieldPanel getLeftFieldPanel() {
|
||||
return getLeftDecompilerPanel().getFieldPanel();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected FieldPanel getRightFieldPanel() {
|
||||
public FieldPanel getRightFieldPanel() {
|
||||
return getRightDecompilerPanel().getFieldPanel();
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue