mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2024-11-24 21:21:56 +00:00
GP-5097 - Updated the Importer to allow users to double-click a language to pick it
This commit is contained in:
parent
d09c75e4ac
commit
b7dec5e363
@ -19,8 +19,8 @@ import javax.swing.BorderFactory;
|
|||||||
|
|
||||||
import docking.DialogComponentProvider;
|
import docking.DialogComponentProvider;
|
||||||
import ghidra.framework.plugintool.PluginTool;
|
import ghidra.framework.plugintool.PluginTool;
|
||||||
import ghidra.plugin.importer.LcsSelectionListener;
|
import ghidra.plugin.importer.*;
|
||||||
import ghidra.plugin.importer.NewLanguagePanel;
|
import ghidra.plugin.importer.LcsSelectionEvent.Type;
|
||||||
import ghidra.program.model.lang.*;
|
import ghidra.program.model.lang.*;
|
||||||
import ghidra.program.util.DefaultLanguageService;
|
import ghidra.program.util.DefaultLanguageService;
|
||||||
import ghidra.util.HelpLocation;
|
import ghidra.util.HelpLocation;
|
||||||
@ -30,33 +30,14 @@ public class SetLanguageDialog extends DialogComponentProvider {
|
|||||||
|
|
||||||
private NewLanguagePanel selectLangPanel;
|
private NewLanguagePanel selectLangPanel;
|
||||||
private PluginTool tool;
|
private PluginTool tool;
|
||||||
private LanguageCompilerSpecPair currentLCSPair;
|
private LanguageCompilerSpecPair currentLcsPair;
|
||||||
|
|
||||||
private LanguageID dialogLanguageID;
|
private LanguageID dialogLanguageID;
|
||||||
private CompilerSpecID dialogCompilerSpecID;
|
private CompilerSpecID dialogCompilerSpecID;
|
||||||
|
|
||||||
LcsSelectionListener listener = e -> {
|
private LcsSelectionListener listener = e -> {
|
||||||
LanguageID langID = null;
|
languageSelected(e.getLcs());
|
||||||
CompilerSpecID compilerSpecID = null;
|
maybePressOk(e);
|
||||||
if (e != null && e.selection != null) {
|
|
||||||
langID = e.selection.languageID;
|
|
||||||
compilerSpecID = e.selection.compilerSpecID;
|
|
||||||
}
|
|
||||||
if ((currentLCSPair != null) && (langID != null) &&
|
|
||||||
(langID.equals(currentLCSPair.getLanguageID()))) {
|
|
||||||
if (compilerSpecID != null &&
|
|
||||||
compilerSpecID.equals(currentLCSPair.getCompilerSpecID())) {
|
|
||||||
setStatusText("Please select a different Language or Compiler Spec.");
|
|
||||||
setOkEnabled(false);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
setStatusText(null);
|
|
||||||
setOkEnabled(true);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
setStatusText(null);
|
|
||||||
setOkEnabled(langID != null);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -89,7 +70,7 @@ public class SetLanguageDialog extends DialogComponentProvider {
|
|||||||
*/
|
*/
|
||||||
public SetLanguageDialog(PluginTool tool, LanguageCompilerSpecPair lcsPair, String title) {
|
public SetLanguageDialog(PluginTool tool, LanguageCompilerSpecPair lcsPair, String title) {
|
||||||
super(title, true, true, true, false);
|
super(title, true, true, true, false);
|
||||||
currentLCSPair = lcsPair;
|
currentLcsPair = lcsPair;
|
||||||
this.tool = tool;
|
this.tool = tool;
|
||||||
|
|
||||||
selectLangPanel = new NewLanguagePanel();
|
selectLangPanel = new NewLanguagePanel();
|
||||||
@ -110,7 +91,40 @@ public class SetLanguageDialog extends DialogComponentProvider {
|
|||||||
setHelpLocation(new HelpLocation("LanguageProviderPlugin", "set language"));
|
setHelpLocation(new HelpLocation("LanguageProviderPlugin", "set language"));
|
||||||
selectLangPanel.setShowRecommendedCheckbox(false);
|
selectLangPanel.setShowRecommendedCheckbox(false);
|
||||||
|
|
||||||
listener.valueChanged(null); // kick to establish initial button enablement
|
languageSelected(null); // kick to establish initial button enablement
|
||||||
|
}
|
||||||
|
|
||||||
|
private void languageSelected(LanguageCompilerSpecPair lcs) {
|
||||||
|
LanguageID langId = null;
|
||||||
|
CompilerSpecID compilerSpecID = null;
|
||||||
|
if (lcs != null) {
|
||||||
|
langId = lcs.languageID;
|
||||||
|
compilerSpecID = lcs.compilerSpecID;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((currentLcsPair != null) && (langId != null) &&
|
||||||
|
(langId.equals(currentLcsPair.getLanguageID()))) {
|
||||||
|
if (compilerSpecID != null &&
|
||||||
|
compilerSpecID.equals(currentLcsPair.getCompilerSpecID())) {
|
||||||
|
setStatusText("Please select a different Language or Compiler Spec.");
|
||||||
|
setOkEnabled(false);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
setStatusText(null);
|
||||||
|
setOkEnabled(true);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
setStatusText(null);
|
||||||
|
setOkEnabled(langId != null);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void maybePressOk(LcsSelectionEvent e) {
|
||||||
|
if (e.getType() == Type.PICKED && isOKEnabled()) {
|
||||||
|
// the user picked (i.e., double-clicked) a language and it is valid, so use it
|
||||||
|
okCallback();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static LanguageCompilerSpecPair getLanguageCompilerSpecPair(String languageIdStr,
|
private static LanguageCompilerSpecPair getLanguageCompilerSpecPair(String languageIdStr,
|
||||||
|
@ -19,14 +19,14 @@ import java.awt.Component;
|
|||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
|
||||||
import javax.swing.BorderFactory;
|
import javax.swing.BorderFactory;
|
||||||
import javax.swing.SwingUtilities;
|
|
||||||
|
|
||||||
import docking.DialogComponentProvider;
|
import docking.DialogComponentProvider;
|
||||||
import ghidra.app.util.opinion.LoadSpec;
|
import ghidra.app.util.opinion.LoadSpec;
|
||||||
import ghidra.framework.plugintool.PluginTool;
|
import ghidra.framework.plugintool.PluginTool;
|
||||||
|
import ghidra.plugin.importer.LcsSelectionEvent.Type;
|
||||||
import ghidra.program.model.lang.LanguageCompilerSpecPair;
|
import ghidra.program.model.lang.LanguageCompilerSpecPair;
|
||||||
import ghidra.util.HelpLocation;
|
import ghidra.util.HelpLocation;
|
||||||
import ghidra.util.Msg;
|
import ghidra.util.Swing;
|
||||||
|
|
||||||
public class ImporterLanguageDialog extends DialogComponentProvider {
|
public class ImporterLanguageDialog extends DialogComponentProvider {
|
||||||
|
|
||||||
@ -46,25 +46,11 @@ public class ImporterLanguageDialog extends DialogComponentProvider {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public void show(Component parent) {
|
public void show(Component parent) {
|
||||||
if (SwingUtilities.isEventDispatchThread()) {
|
Swing.runIfSwingOrRunLater(() -> {
|
||||||
build();
|
build();
|
||||||
tool.showDialog(this, parent);
|
tool.showDialog(this, parent);
|
||||||
}
|
|
||||||
else {
|
|
||||||
try {
|
|
||||||
SwingUtilities.invokeAndWait(new Runnable() {
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
build();
|
|
||||||
tool.showDialog(ImporterLanguageDialog.this, parent);
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
catch (Exception e) {
|
|
||||||
Msg.error(this, e);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void build() {
|
private void build() {
|
||||||
languagePanel = new NewLanguagePanel();
|
languagePanel = new NewLanguagePanel();
|
||||||
@ -72,10 +58,11 @@ public class ImporterLanguageDialog extends DialogComponentProvider {
|
|||||||
languagePanel.setShowAllLcsPairs(false);
|
languagePanel.setShowAllLcsPairs(false);
|
||||||
languagePanel.setBorder(
|
languagePanel.setBorder(
|
||||||
BorderFactory.createTitledBorder(" Select Language and Compiler Specification "));
|
BorderFactory.createTitledBorder(" Select Language and Compiler Specification "));
|
||||||
languagePanel.addSelectionListener(new LcsSelectionListener() {
|
languagePanel.addSelectionListener(e -> {
|
||||||
@Override
|
|
||||||
public void valueChanged(LcsSelectionEvent e) {
|
|
||||||
validateFormInput();
|
validateFormInput();
|
||||||
|
|
||||||
|
if (e.getType() == Type.PICKED && isOKEnabled()) {
|
||||||
|
okCallback();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -18,14 +18,33 @@ package ghidra.plugin.importer;
|
|||||||
import ghidra.program.model.lang.LanguageCompilerSpecPair;
|
import ghidra.program.model.lang.LanguageCompilerSpecPair;
|
||||||
|
|
||||||
public class LcsSelectionEvent {
|
public class LcsSelectionEvent {
|
||||||
public final LanguageCompilerSpecPair selection;
|
|
||||||
|
|
||||||
public LcsSelectionEvent(LanguageCompilerSpecPair selection) {
|
public enum Type {
|
||||||
this.selection = selection;
|
/** A language was selected in the UI */
|
||||||
|
SELECTED,
|
||||||
|
|
||||||
|
/** A language was picked (e.g., double-clicked) in the UI */
|
||||||
|
PICKED
|
||||||
|
}
|
||||||
|
|
||||||
|
private final LanguageCompilerSpecPair lcs;
|
||||||
|
private final Type type;
|
||||||
|
|
||||||
|
public LcsSelectionEvent(LanguageCompilerSpecPair selection, Type type) {
|
||||||
|
this.lcs = selection;
|
||||||
|
this.type = type;
|
||||||
|
}
|
||||||
|
|
||||||
|
public LanguageCompilerSpecPair getLcs() {
|
||||||
|
return lcs;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Type getType() {
|
||||||
|
return type;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String toString() {
|
public String toString() {
|
||||||
return "LSE{" + selection + "}";
|
return "LSE{" + lcs + "}";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -23,10 +23,12 @@ import java.util.List;
|
|||||||
import javax.swing.*;
|
import javax.swing.*;
|
||||||
import javax.swing.border.Border;
|
import javax.swing.border.Border;
|
||||||
|
|
||||||
|
import docking.actions.KeyBindingUtils;
|
||||||
import docking.widgets.checkbox.GCheckBox;
|
import docking.widgets.checkbox.GCheckBox;
|
||||||
import docking.widgets.label.GDLabel;
|
import docking.widgets.label.GDLabel;
|
||||||
import generic.theme.GThemeDefaults.Colors.Messages;
|
import generic.theme.GThemeDefaults.Colors.Messages;
|
||||||
import generic.theme.Gui;
|
import generic.theme.Gui;
|
||||||
|
import ghidra.plugin.importer.LcsSelectionEvent.Type;
|
||||||
import ghidra.program.model.lang.*;
|
import ghidra.program.model.lang.*;
|
||||||
import ghidra.program.util.DefaultLanguageService;
|
import ghidra.program.util.DefaultLanguageService;
|
||||||
import ghidra.util.table.*;
|
import ghidra.util.table.*;
|
||||||
@ -41,12 +43,13 @@ public class NewLanguagePanel extends JPanel {
|
|||||||
private JCheckBox recommendedCheckbox;
|
private JCheckBox recommendedCheckbox;
|
||||||
private JLabel formatLabel;
|
private JLabel formatLabel;
|
||||||
|
|
||||||
private void setDescriptionLabelText(String text) {
|
private boolean isOnShowAll = true;
|
||||||
if (text == null || "".equals(text)) {
|
|
||||||
text = " ";
|
private List<LanguageCompilerSpecPair> allLcsPairsList;
|
||||||
}
|
private List<LanguageCompilerSpecPair> recommendedLcsPairsList;
|
||||||
descriptionLabel.setText(text);
|
private LanguageCompilerSpecPair recommendedLcsPair;
|
||||||
}
|
|
||||||
|
private final Set<LcsSelectionListener> listeners = new HashSet<>();
|
||||||
|
|
||||||
public NewLanguagePanel() {
|
public NewLanguagePanel() {
|
||||||
constructEverything();
|
constructEverything();
|
||||||
@ -94,7 +97,6 @@ public class NewLanguagePanel extends JPanel {
|
|||||||
@Override
|
@Override
|
||||||
public Dimension getPreferredSize() {
|
public Dimension getPreferredSize() {
|
||||||
// this makes us a bit smaller in height, as the preferred height can be excessive
|
// this makes us a bit smaller in height, as the preferred height can be excessive
|
||||||
|
|
||||||
Dimension preferredSize = super.getPreferredSize();
|
Dimension preferredSize = super.getPreferredSize();
|
||||||
if (preferredSize.width == 0) {
|
if (preferredSize.width == 0) {
|
||||||
return preferredSize; // no size yet, don't change anything
|
return preferredSize; // no size yet, don't change anything
|
||||||
@ -138,16 +140,37 @@ public class NewLanguagePanel extends JPanel {
|
|||||||
if (e.getValueIsAdjusting()) {
|
if (e.getValueIsAdjusting()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
notifyListeners();
|
notifyLanguageSelected();
|
||||||
});
|
});
|
||||||
|
|
||||||
table.addMouseListener(new MouseAdapter() {
|
table.addMouseListener(new MouseAdapter() {
|
||||||
@Override
|
@Override
|
||||||
public void mouseReleased(MouseEvent e) {
|
public void mouseReleased(MouseEvent e) {
|
||||||
if (e.getClickCount() == 2) {
|
if (e.getClickCount() == 2) {
|
||||||
// do the next action thingie
|
notfiyLanguagePicked();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Update Enter to allow the user to pick the selected language
|
||||||
|
KeyStroke enterKs = KeyBindingUtils.parseKeyStroke("Enter");
|
||||||
|
Action action = new AbstractAction("Pick Language") {
|
||||||
|
@Override
|
||||||
|
public void actionPerformed(ActionEvent e) {
|
||||||
|
notfiyLanguagePicked();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
// remove the table's enter key binding and then add our own
|
||||||
|
KeyBindingUtils.clearKeyBinding(table, enterKs);
|
||||||
|
KeyBindingUtils.registerAction(table, enterKs, action, JComponent.WHEN_FOCUSED);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void setDescriptionLabelText(String text) {
|
||||||
|
if (text == null || "".equals(text)) {
|
||||||
|
text = " ";
|
||||||
|
}
|
||||||
|
descriptionLabel.setText(text);
|
||||||
}
|
}
|
||||||
|
|
||||||
public void setFormatText(String text) {
|
public void setFormatText(String text) {
|
||||||
@ -158,8 +181,6 @@ public class NewLanguagePanel extends JPanel {
|
|||||||
recommendedCheckbox.setVisible(show);
|
recommendedCheckbox.setVisible(show);
|
||||||
}
|
}
|
||||||
|
|
||||||
private boolean isOnShowAll = true;
|
|
||||||
|
|
||||||
private boolean isAllLcsPairsTableShowing() {
|
private boolean isAllLcsPairsTableShowing() {
|
||||||
return isOnShowAll;
|
return isOnShowAll;
|
||||||
}
|
}
|
||||||
@ -174,7 +195,7 @@ public class NewLanguagePanel extends JPanel {
|
|||||||
|
|
||||||
private void setLanguages(List<LanguageCompilerSpecPair> lcsPairList) {
|
private void setLanguages(List<LanguageCompilerSpecPair> lcsPairList) {
|
||||||
tableModel.setLanguages(lcsPairList);
|
tableModel.setLanguages(lcsPairList);
|
||||||
notifyListeners();
|
notifyLanguageSelected();
|
||||||
}
|
}
|
||||||
|
|
||||||
private void switchToAllList() {
|
private void switchToAllList() {
|
||||||
@ -203,13 +224,20 @@ public class NewLanguagePanel extends JPanel {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private List<LanguageCompilerSpecPair> allLcsPairsList;
|
private void notifyLanguageSelected() {
|
||||||
private List<LanguageCompilerSpecPair> recommendedLcsPairsList;
|
LanguageCompilerSpecPair lcs = getSelectedLcsPair();
|
||||||
|
LcsSelectionEvent e = new LcsSelectionEvent(lcs, Type.SELECTED);
|
||||||
|
doNotify(e);
|
||||||
|
}
|
||||||
|
|
||||||
private LanguageCompilerSpecPair recommendedLcsPair;
|
private void notfiyLanguagePicked() {
|
||||||
|
LanguageCompilerSpecPair lcs = getSelectedLcsPair();
|
||||||
|
LcsSelectionEvent e = new LcsSelectionEvent(lcs, Type.PICKED);
|
||||||
|
doNotify(e);
|
||||||
|
}
|
||||||
|
|
||||||
private void notifyListeners() {
|
private void doNotify(LcsSelectionEvent event) {
|
||||||
LanguageCompilerSpecPair selectedLcsPair = getSelectedLcsPair();
|
LanguageCompilerSpecPair selectedLcsPair = event.getLcs();
|
||||||
if (selectedLcsPair == null) {
|
if (selectedLcsPair == null) {
|
||||||
descriptionLabel.setText(DEFAULT_DESCRIPTION_TEXT);
|
descriptionLabel.setText(DEFAULT_DESCRIPTION_TEXT);
|
||||||
}
|
}
|
||||||
@ -221,12 +249,9 @@ public class NewLanguagePanel extends JPanel {
|
|||||||
descriptionLabel.setText("<LanguageNotFound>");
|
descriptionLabel.setText("<LanguageNotFound>");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
// notifyListenersOfValidityChanged();
|
|
||||||
if (!listeners.isEmpty()) {
|
|
||||||
LcsSelectionEvent e = new LcsSelectionEvent(selectedLcsPair);
|
|
||||||
for (LcsSelectionListener listener : listeners) {
|
for (LcsSelectionListener listener : listeners) {
|
||||||
listener.valueChanged(e);
|
listener.valueChanged(event);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -314,8 +339,6 @@ public class NewLanguagePanel extends JPanel {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
private final Set<LcsSelectionListener> listeners = new HashSet<>();
|
|
||||||
|
|
||||||
public void addSelectionListener(LcsSelectionListener listener) {
|
public void addSelectionListener(LcsSelectionListener listener) {
|
||||||
listeners.add(listener);
|
listeners.add(listener);
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user