mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2026-06-01 23:30:08 +08:00
Merge remote-tracking branch 'origin/GP-2244_ghizard_developer_mode_only_place_labels_within_function_namespaces__has_problems_with_labels_becoming_primary--SQUASHED'
This commit is contained in:
+62
-17
@@ -15,6 +15,8 @@
|
|||||||
*/
|
*/
|
||||||
package ghidra.app.util.pdb.pdbapplicator;
|
package ghidra.app.util.pdb.pdbapplicator;
|
||||||
|
|
||||||
|
import java.util.regex.Matcher;
|
||||||
|
|
||||||
import ghidra.app.util.NamespaceUtils;
|
import ghidra.app.util.NamespaceUtils;
|
||||||
import ghidra.app.util.bin.format.pdb2.pdbreader.PdbException;
|
import ghidra.app.util.bin.format.pdb2.pdbreader.PdbException;
|
||||||
import ghidra.app.util.bin.format.pdb2.pdbreader.symbol.AbstractLabelMsSymbol;
|
import ghidra.app.util.bin.format.pdb2.pdbreader.symbol.AbstractLabelMsSymbol;
|
||||||
@@ -22,8 +24,6 @@ import ghidra.app.util.bin.format.pdb2.pdbreader.symbol.AbstractMsSymbol;
|
|||||||
import ghidra.app.util.pdb.pdbapplicator.SymbolGroup.AbstractMsSymbolIterator;
|
import ghidra.app.util.pdb.pdbapplicator.SymbolGroup.AbstractMsSymbolIterator;
|
||||||
import ghidra.program.model.address.Address;
|
import ghidra.program.model.address.Address;
|
||||||
import ghidra.program.model.listing.Function;
|
import ghidra.program.model.listing.Function;
|
||||||
import ghidra.program.model.listing.FunctionManager;
|
|
||||||
import ghidra.program.model.symbol.Namespace;
|
|
||||||
import ghidra.util.exception.AssertException;
|
import ghidra.util.exception.AssertException;
|
||||||
import ghidra.util.exception.CancelledException;
|
import ghidra.util.exception.CancelledException;
|
||||||
|
|
||||||
@@ -38,7 +38,6 @@ public class LabelSymbolApplier extends MsSymbolApplier {
|
|||||||
* Constructor
|
* Constructor
|
||||||
* @param applicator the {@link DefaultPdbApplicator} for which we are working.
|
* @param applicator the {@link DefaultPdbApplicator} for which we are working.
|
||||||
* @param iter the Iterator containing the symbol sequence being processed
|
* @param iter the Iterator containing the symbol sequence being processed
|
||||||
* @throws CancelledException upon user cancellation
|
|
||||||
*/
|
*/
|
||||||
public LabelSymbolApplier(DefaultPdbApplicator applicator, AbstractMsSymbolIterator iter) {
|
public LabelSymbolApplier(DefaultPdbApplicator applicator, AbstractMsSymbolIterator iter) {
|
||||||
super(applicator, iter);
|
super(applicator, iter);
|
||||||
@@ -52,28 +51,74 @@ public class LabelSymbolApplier extends MsSymbolApplier {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
void apply() throws PdbException, CancelledException {
|
void apply() throws PdbException, CancelledException {
|
||||||
if (!applicator.getPdbApplicatorOptions().applyInstructionLabels()) {
|
String label = getLabel();
|
||||||
|
if (label == null) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// Place compiler generated symbols (e.g., $LN9) within containing function when possible
|
|
||||||
String name = symbol.getName();
|
|
||||||
Address symbolAddress = applicator.getAddress(symbol);
|
Address symbolAddress = applicator.getAddress(symbol);
|
||||||
if (applicator.isInvalidAddress(symbolAddress, name)) {
|
if (applicator.isInvalidAddress(symbolAddress, label)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
FunctionManager functionManager = applicator.getProgram().getFunctionManager();
|
applicator.createSymbol(symbolAddress, label, false);
|
||||||
// TODO: What do we do with labels such as this?... "__catch$?test_eh1@@YAHXZ$7"
|
|
||||||
if (name.startsWith("$") && !name.contains(Namespace.DELIMITER)) {
|
|
||||||
Function f = functionManager.getFunctionContaining(symbolAddress);
|
|
||||||
if (f != null && !f.getName().equals(name)) {
|
|
||||||
name = NamespaceUtils.getNamespaceQualifiedName(f, name, true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
applicator.createSymbol(symbolAddress, name, false);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
void applyTo(MsSymbolApplier applyToApplier) {
|
void applyTo(MsSymbolApplier applyToApplier) {
|
||||||
// Do nothing
|
String label = getLabel();
|
||||||
|
if (label == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Address symbolAddress = applicator.getAddress(symbol);
|
||||||
|
if (applicator.isInvalidAddress(symbolAddress, label)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (applyToApplier instanceof FunctionSymbolApplier functionSymbolApplier) {
|
||||||
|
Function f = functionSymbolApplier.getFunction();
|
||||||
|
if (f != null && !f.getName().equals(label)) {
|
||||||
|
label = NamespaceUtils.getNamespaceQualifiedName(f, label, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// No longer doing this, but instead letting namespace come from GPROC sequence... that way,
|
||||||
|
// labels will pertain to functions even if landing inside other function address range.
|
||||||
|
// Keeping code here (commented out), replaced by above code, until we get other issues
|
||||||
|
// figured out.
|
||||||
|
// FunctionManager functionManager = applicator.getProgram().getFunctionManager();
|
||||||
|
// // TODO: What do we do with labels such as this?... "__catch$?test_eh1@@YAHXZ$7"
|
||||||
|
// if (!label.contains(Namespace.DELIMITER)) {
|
||||||
|
// Function f = functionManager.getFunctionContaining(symbolAddress);
|
||||||
|
// if (f != null && !f.getName().equals(label)) {
|
||||||
|
// label = NamespaceUtils.getNamespaceQualifiedName(f, label, true);
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
// TODO: Before we turn on label applications.... we probably need to change order on
|
||||||
|
// how function symbols are applied. Perhaps we need to apply all GPROC symbols before
|
||||||
|
// we apply their internals (frames, local vars, labels, blocks) because some labels (here)
|
||||||
|
// are getting applied and becoming primary (because some have addresses that are located
|
||||||
|
// outside of the the address range of their GPROC, and will prevent another GPROC at the
|
||||||
|
// same address as the label from becoming primary (e.g., $LN7 of cn3 at a750).
|
||||||
|
applicator.createSymbol(symbolAddress, label, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns label to apply or null if label excluded
|
||||||
|
* @return label to process or null
|
||||||
|
*/
|
||||||
|
private String getLabel() {
|
||||||
|
if (!applicator.getPdbApplicatorOptions().applyInstructionLabels()) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
// Place compiler generated symbols (e.g., $LN9) within containing function when possible
|
||||||
|
String label = symbol.getName();
|
||||||
|
Matcher m =
|
||||||
|
applicator.getPdbApplicatorOptions().excludeInstructionLabelsPattern().matcher(label);
|
||||||
|
if (m.find()) {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
return label;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+92
-1
@@ -15,9 +15,14 @@
|
|||||||
*/
|
*/
|
||||||
package ghidra.app.util.pdb.pdbapplicator;
|
package ghidra.app.util.pdb.pdbapplicator;
|
||||||
|
|
||||||
|
import java.util.regex.Pattern;
|
||||||
|
import java.util.regex.PatternSyntaxException;
|
||||||
|
|
||||||
import ghidra.app.util.bin.format.pdb2.pdbreader.AbstractPdb;
|
import ghidra.app.util.bin.format.pdb2.pdbreader.AbstractPdb;
|
||||||
import ghidra.framework.options.Options;
|
import ghidra.framework.options.Options;
|
||||||
import ghidra.util.HelpLocation;
|
import ghidra.util.HelpLocation;
|
||||||
|
import ghidra.util.Msg;
|
||||||
|
import ghidra.util.exception.AssertException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Options used while using a {@link DefaultPdbApplicator} to apply a PDB ({@link AbstractPdb}) to a
|
* Options used while using a {@link DefaultPdbApplicator} to apply a PDB ({@link AbstractPdb}) to a
|
||||||
@@ -51,6 +56,29 @@ public class PdbApplicatorOptions {
|
|||||||
"If checked, labels associated with instructions will be applied.";
|
"If checked, labels associated with instructions will be applied.";
|
||||||
private static final boolean DEFAULT_APPLY_INSTRUCTION_LABELS = false;
|
private static final boolean DEFAULT_APPLY_INSTRUCTION_LABELS = false;
|
||||||
private boolean applyInstructionLabels;
|
private boolean applyInstructionLabels;
|
||||||
|
// If the above option is enabled, allowing instruction labels to be applied, this
|
||||||
|
// edit box provides a filter to prevent any labels matching this pattern from being
|
||||||
|
// applied to the program.
|
||||||
|
private static final String OPTION_NAME_EXCLUDE_INSTRUCTION_LABELS =
|
||||||
|
"Exclude Instruction Labels";
|
||||||
|
private static final String OPTION_DESCRIPTION_EXCLUDE_INSTRUCTION_LABELS =
|
||||||
|
"Regular expression describing instruction labels to be excluded when \"" +
|
||||||
|
OPTION_NAME_APPLY_INSTRUCTION_LABELS + "\" is enabled.";
|
||||||
|
private static final String DEFAULT_EXCLUDE_INSTRUCTION_LABELS = "$a"; // "$a" will never match
|
||||||
|
private Pattern DEFAULT_EXCLUDE_INSTRUCTION_LABELS_PATTERN;
|
||||||
|
{
|
||||||
|
try {
|
||||||
|
DEFAULT_EXCLUDE_INSTRUCTION_LABELS_PATTERN =
|
||||||
|
Pattern.compile(DEFAULT_EXCLUDE_INSTRUCTION_LABELS);
|
||||||
|
}
|
||||||
|
catch (PatternSyntaxException e) {
|
||||||
|
throw new AssertException(
|
||||||
|
"Programming error: invalid default exclude labels pattern");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private String excludeInstructionLabels;
|
||||||
|
private Pattern excludeInstructionLabelsPattern;
|
||||||
|
|
||||||
// Attempt to map address using existing mangled symbols.
|
// Attempt to map address using existing mangled symbols.
|
||||||
private static final String OPTION_NAME_ADDRESS_REMAP = "Address Remap Using Existing Symbols";
|
private static final String OPTION_NAME_ADDRESS_REMAP = "Address Remap Using Existing Symbols";
|
||||||
@@ -169,6 +197,14 @@ public class PdbApplicatorOptions {
|
|||||||
options.registerOption(OPTION_NAME_APPLY_INSTRUCTION_LABELS, applyInstructionLabels,
|
options.registerOption(OPTION_NAME_APPLY_INSTRUCTION_LABELS, applyInstructionLabels,
|
||||||
help, OPTION_DESCRIPTION_APPLY_INSTRUCTION_LABELS);
|
help, OPTION_DESCRIPTION_APPLY_INSTRUCTION_LABELS);
|
||||||
|
|
||||||
|
// If the above option is enabled, allowing instruction labels to be applied, this
|
||||||
|
// edit box provides a filter to prevent any labels matching this pattern from being
|
||||||
|
// applied to the program.
|
||||||
|
options.registerOption(OPTION_NAME_EXCLUDE_INSTRUCTION_LABELS, excludeInstructionLabels,
|
||||||
|
help, OPTION_DESCRIPTION_EXCLUDE_INSTRUCTION_LABELS);
|
||||||
|
validatePattern(options);
|
||||||
|
// Can we disable this one above based upon the one above it? Do it with custom editor.
|
||||||
|
|
||||||
// The remap capability is not completely implemented... do not turn on.
|
// The remap capability is not completely implemented... do not turn on.
|
||||||
options.registerOption(OPTION_NAME_ADDRESS_REMAP,
|
options.registerOption(OPTION_NAME_ADDRESS_REMAP,
|
||||||
remapAddressUsingExistingPublicMangledSymbols, help,
|
remapAddressUsingExistingPublicMangledSymbols, help,
|
||||||
@@ -206,10 +242,17 @@ public class PdbApplicatorOptions {
|
|||||||
applyCodeScopeBlockComments = options.getBoolean(
|
applyCodeScopeBlockComments = options.getBoolean(
|
||||||
OPTION_NAME_APPLY_CODE_SCOPE_BLOCK_COMMENTS, applyCodeScopeBlockComments);
|
OPTION_NAME_APPLY_CODE_SCOPE_BLOCK_COMMENTS, applyCodeScopeBlockComments);
|
||||||
|
|
||||||
// Mechanism to apply instruction labels is not yet implemented-> does nothing
|
// Mechanism to apply instruction labels
|
||||||
applyInstructionLabels =
|
applyInstructionLabels =
|
||||||
options.getBoolean(OPTION_NAME_APPLY_INSTRUCTION_LABELS, applyInstructionLabels);
|
options.getBoolean(OPTION_NAME_APPLY_INSTRUCTION_LABELS, applyInstructionLabels);
|
||||||
|
|
||||||
|
// If the above option is enabled, allowing instruction labels to be applied, this
|
||||||
|
// edit box provides a filter to prevent any labels matching this pattern from being
|
||||||
|
// applied to the program
|
||||||
|
excludeInstructionLabels =
|
||||||
|
options.getString(OPTION_NAME_EXCLUDE_INSTRUCTION_LABELS, excludeInstructionLabels);
|
||||||
|
validatePattern(options);
|
||||||
|
|
||||||
remapAddressUsingExistingPublicMangledSymbols = options.getBoolean(
|
remapAddressUsingExistingPublicMangledSymbols = options.getBoolean(
|
||||||
OPTION_NAME_ADDRESS_REMAP, remapAddressUsingExistingPublicMangledSymbols);
|
OPTION_NAME_ADDRESS_REMAP, remapAddressUsingExistingPublicMangledSymbols);
|
||||||
|
|
||||||
@@ -223,12 +266,32 @@ public class PdbApplicatorOptions {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// The following code cannot remain in a final solution... The options editor does
|
||||||
|
// not get an updated String written to it. Ultimately, there is no way to validate
|
||||||
|
// this value other than have a custom options editor, which is the direction we
|
||||||
|
// already believe we need to take for purposes of appropriately grouping options
|
||||||
|
// (other than in an alphabetical order).
|
||||||
|
private void validatePattern(Options options) {
|
||||||
|
try {
|
||||||
|
excludeInstructionLabelsPattern = Pattern.compile(excludeInstructionLabels);
|
||||||
|
}
|
||||||
|
catch (PatternSyntaxException e) {
|
||||||
|
Msg.error(this, "Invalid " + OPTION_NAME_EXCLUDE_INSTRUCTION_LABELS + " value: " +
|
||||||
|
excludeInstructionLabels + "\n Resetting to default value.");
|
||||||
|
excludeInstructionLabels = DEFAULT_EXCLUDE_INSTRUCTION_LABELS;
|
||||||
|
excludeInstructionLabelsPattern = DEFAULT_EXCLUDE_INSTRUCTION_LABELS_PATTERN;
|
||||||
|
options.restoreDefaultValue(OPTION_NAME_EXCLUDE_INSTRUCTION_LABELS);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the options to their default values
|
* Set the options to their default values
|
||||||
*/
|
*/
|
||||||
public void setDefaults() {
|
public void setDefaults() {
|
||||||
applyCodeScopeBlockComments = DEFAULT_APPLY_CODE_SCOPE_BLOCK_COMMENTS;
|
applyCodeScopeBlockComments = DEFAULT_APPLY_CODE_SCOPE_BLOCK_COMMENTS;
|
||||||
applyInstructionLabels = DEFAULT_APPLY_INSTRUCTION_LABELS;
|
applyInstructionLabels = DEFAULT_APPLY_INSTRUCTION_LABELS;
|
||||||
|
excludeInstructionLabels = DEFAULT_EXCLUDE_INSTRUCTION_LABELS;
|
||||||
|
excludeInstructionLabelsPattern = DEFAULT_EXCLUDE_INSTRUCTION_LABELS_PATTERN;
|
||||||
control = DEFAULT_CONTROL;
|
control = DEFAULT_CONTROL;
|
||||||
remapAddressUsingExistingPublicMangledSymbols =
|
remapAddressUsingExistingPublicMangledSymbols =
|
||||||
DEFAULT_REMAP_ADDRESSES_USING_EXISTING_SYMBOLS;
|
DEFAULT_REMAP_ADDRESSES_USING_EXISTING_SYMBOLS;
|
||||||
@@ -269,6 +332,34 @@ public class PdbApplicatorOptions {
|
|||||||
return applyInstructionLabels;
|
return applyInstructionLabels;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// If the above option is enabled, allowing instruction labels to be applied, this
|
||||||
|
// edit box provides a filter to prevent any labels matching this pattern from being
|
||||||
|
// applied to the program
|
||||||
|
/**
|
||||||
|
* Set regular expression string describing labels to exclude from application.
|
||||||
|
* @param excludeInstructionLabels regular expression describing instruction labels to exclude
|
||||||
|
*/
|
||||||
|
public void setApplyInstructionLabels(String excludeInstructionLabels) {
|
||||||
|
this.excludeInstructionLabels = excludeInstructionLabels;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the string containing the regular expression describing instruction labels being
|
||||||
|
* excluded from application. Applicable when {@code applyInstructionLabels} is enabled
|
||||||
|
* @return the regular expression String
|
||||||
|
*/
|
||||||
|
public String excludeInstructionLabels() {
|
||||||
|
return excludeInstructionLabels;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the Regex Pattern for the Exclude Instruction Labels field.
|
||||||
|
* @return the Pattern.
|
||||||
|
*/
|
||||||
|
public Pattern excludeInstructionLabelsPattern() {
|
||||||
|
return excludeInstructionLabelsPattern;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set processing control for PdbApplicator
|
* Set processing control for PdbApplicator
|
||||||
* @param control the processing control
|
* @param control the processing control
|
||||||
|
|||||||
Reference in New Issue
Block a user