mirror of
https://github.com/NationalSecurityAgency/ghidra.git
synced 2025-10-04 18:29:37 +02:00
Merge remote-tracking branch 'origin/patch'
This commit is contained in:
commit
19f9d3cecf
10 changed files with 221 additions and 20 deletions
|
@ -148,4 +148,31 @@ public abstract class GhidraScriptProvider
|
||||||
return scriptName;
|
return scriptName;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the start of certification header line if this file type is
|
||||||
|
* subject to certification.
|
||||||
|
* @return start of certification header or null if not supported
|
||||||
|
*/
|
||||||
|
protected String getCertifyHeaderStart() {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the prefix for each certification header bofy line if
|
||||||
|
* this file is subject to certification
|
||||||
|
* @return certification heaber body prefix or null if not supported
|
||||||
|
*/
|
||||||
|
protected String getCertificationBodyPrefix() {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Return the end of certification header line if this file type is
|
||||||
|
* subject to certification.
|
||||||
|
* @return end of certification header or null if not supported
|
||||||
|
*/
|
||||||
|
protected String getCertifyHeaderEnd() {
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -164,6 +164,16 @@ public class JavaScriptProvider extends GhidraScriptProvider {
|
||||||
return "//";
|
return "//";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String getCertifyHeaderStart() {
|
||||||
|
return "/* ###";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String getCertifyHeaderEnd() {
|
||||||
|
return "*/";
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* Fix script name for search in script directories, such as Java package parts in the name and inner class names.
|
* Fix script name for search in script directories, such as Java package parts in the name and inner class names.
|
||||||
|
|
|
@ -20,7 +20,6 @@ import static ghidra.util.HTMLUtilities.*;
|
||||||
import java.io.*;
|
import java.io.*;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.StringTokenizer;
|
import java.util.StringTokenizer;
|
||||||
import java.util.regex.Pattern;
|
|
||||||
|
|
||||||
import javax.swing.ImageIcon;
|
import javax.swing.ImageIcon;
|
||||||
import javax.swing.KeyStroke;
|
import javax.swing.KeyStroke;
|
||||||
|
@ -47,9 +46,6 @@ public class ScriptInfo {
|
||||||
static final String AT_MENUPATH = "@menupath";
|
static final String AT_MENUPATH = "@menupath";
|
||||||
static final String AT_TOOLBAR = "@toolbar";
|
static final String AT_TOOLBAR = "@toolbar";
|
||||||
|
|
||||||
private static final Pattern DOCUMENTATION_START = Pattern.compile("/\\*");
|
|
||||||
private static final Pattern DOCUMENTATION_END = Pattern.compile("\\*/");
|
|
||||||
|
|
||||||
// omit from METADATA to avoid pre-populating in new scripts
|
// omit from METADATA to avoid pre-populating in new scripts
|
||||||
private static final String AT_IMPORTPACKAGE = "@importpackage";
|
private static final String AT_IMPORTPACKAGE = "@importpackage";
|
||||||
|
|
||||||
|
@ -186,6 +182,16 @@ public class ScriptInfo {
|
||||||
|
|
||||||
init();
|
init();
|
||||||
|
|
||||||
|
String commentPrefix = provider.getCommentCharacter();
|
||||||
|
|
||||||
|
// Note that skipping certification header presumes that the header
|
||||||
|
// is intact with an appropriate start and end
|
||||||
|
String certifyHeaderStart = provider.getCertifyHeaderStart();
|
||||||
|
String certifyHeaderEnd = provider.getCertifyHeaderEnd();
|
||||||
|
String certifyHeaderBodyPrefix = provider.getCertificationBodyPrefix();
|
||||||
|
boolean allowCertifyHeader = (certifyHeaderStart != null);
|
||||||
|
boolean skipCertifyHeader = false;
|
||||||
|
|
||||||
BufferedReader reader = null;
|
BufferedReader reader = null;
|
||||||
try {
|
try {
|
||||||
StringBuffer buffer = new StringBuffer();
|
StringBuffer buffer = new StringBuffer();
|
||||||
|
@ -197,16 +203,34 @@ public class ScriptInfo {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (DOCUMENTATION_START.matcher(line).find()) {
|
if (allowCertifyHeader) {
|
||||||
while (line != null && !DOCUMENTATION_END.matcher(line).find()) {
|
// Skip past certification header if found
|
||||||
line = reader.readLine();
|
if (skipCertifyHeader) {
|
||||||
}
|
String trimLine = line.trim();
|
||||||
|
if (trimLine.startsWith(certifyHeaderEnd)) {
|
||||||
|
allowCertifyHeader = false;
|
||||||
|
skipCertifyHeader = false;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
if (certifyHeaderBodyPrefix == null ||
|
||||||
String commentPrefix = provider.getCommentCharacter();
|
trimLine.startsWith(certifyHeaderBodyPrefix)) {
|
||||||
|
continue; // skip certification header body
|
||||||
|
}
|
||||||
|
// broken certification header - unexpected line
|
||||||
|
Msg.error(this,
|
||||||
|
"Script contains invalid certification header: " + getName());
|
||||||
|
allowCertifyHeader = false;
|
||||||
|
skipCertifyHeader = false;
|
||||||
|
}
|
||||||
|
else if (line.startsWith(certifyHeaderStart)) {
|
||||||
|
skipCertifyHeader = true;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (line.startsWith(commentPrefix)) {
|
if (line.startsWith(commentPrefix)) {
|
||||||
|
allowCertifyHeader = false;
|
||||||
|
|
||||||
line = line.substring(commentPrefix.length()).trim();
|
line = line.substring(commentPrefix.length()).trim();
|
||||||
|
|
||||||
if (line.startsWith("@")) {
|
if (line.startsWith("@")) {
|
||||||
|
|
|
@ -15,9 +15,10 @@
|
||||||
*/
|
*/
|
||||||
package ghidra.app.util.bin.format.dwarf4;
|
package ghidra.app.util.bin.format.dwarf4;
|
||||||
|
|
||||||
import java.io.IOException;
|
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
import org.apache.commons.lang3.ArrayUtils;
|
import org.apache.commons.lang3.ArrayUtils;
|
||||||
|
|
||||||
import ghidra.app.util.bin.BinaryReader;
|
import ghidra.app.util.bin.BinaryReader;
|
||||||
|
@ -884,6 +885,30 @@ public class DIEAggregate {
|
||||||
throw new IOException("Bad/unsupported DW_AT_high_pc attribute value or type");
|
throw new IOException("Bad/unsupported DW_AT_high_pc attribute value or type");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns true if the raw lowPc and highPc values are the same.
|
||||||
|
* <p>
|
||||||
|
* This indicates an empty range, in which case the caller may want to take
|
||||||
|
* special steps to avoid issues with Ghidra ranges.
|
||||||
|
* <p>
|
||||||
|
* Only seen in extremely old gcc versions. Typically the low & high
|
||||||
|
* pc values are omitted if the CU is empty.
|
||||||
|
*
|
||||||
|
* @return boolean true if the LowPC and HighPC values are present and equal
|
||||||
|
*/
|
||||||
|
public boolean isLowPCEqualHighPC() {
|
||||||
|
AttrInfo low = findAttribute(DWARFAttribute.DW_AT_low_pc);
|
||||||
|
AttrInfo high = findAttribute(DWARFAttribute.DW_AT_high_pc);
|
||||||
|
if (low != null && high != null && low.form == high.form &&
|
||||||
|
low.attr instanceof DWARFNumericAttribute &&
|
||||||
|
high.attr instanceof DWARFNumericAttribute) {
|
||||||
|
DWARFNumericAttribute lowVal = (DWARFNumericAttribute) low.attr;
|
||||||
|
DWARFNumericAttribute highVal = (DWARFNumericAttribute) high.attr;
|
||||||
|
return lowVal.getValue() == highVal.getValue();
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A simple class used by findAttribute() to return the found attribute, along with
|
* A simple class used by findAttribute() to return the found attribute, along with
|
||||||
* the DIE it was found in, and the DWARFForm type of the raw attribute.
|
* the DIE it was found in, and the DWARFForm type of the raw attribute.
|
||||||
|
|
|
@ -49,11 +49,14 @@ public class DWARFCompileUnit {
|
||||||
String comp_dir = diea.getString(DWARFAttribute.DW_AT_comp_dir, null);
|
String comp_dir = diea.getString(DWARFAttribute.DW_AT_comp_dir, null);
|
||||||
|
|
||||||
Number high_pc = null, low_pc = null, language = null, stmt_list = null;
|
Number high_pc = null, low_pc = null, language = null, stmt_list = null;
|
||||||
|
|
||||||
if (diea.hasAttribute(DWARFAttribute.DW_AT_low_pc)) {
|
if (diea.hasAttribute(DWARFAttribute.DW_AT_low_pc)) {
|
||||||
low_pc = diea.getLowPC(0);
|
low_pc = diea.getLowPC(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (diea.hasAttribute(DWARFAttribute.DW_AT_high_pc)) {
|
// if lowPC and highPC values are the same, don't read the high value
|
||||||
|
// because Ghidra can't express an empty range.
|
||||||
|
if (diea.hasAttribute(DWARFAttribute.DW_AT_high_pc) && !diea.isLowPCEqualHighPC()) {
|
||||||
high_pc = diea.getHighPC();
|
high_pc = diea.getHighPC();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -0,0 +1,54 @@
|
||||||
|
/* ###
|
||||||
|
* 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.util.bin.format.dwarf4.next;
|
||||||
|
|
||||||
|
import static ghidra.app.util.bin.format.dwarf4.encoding.DWARFAttribute.*;
|
||||||
|
import static org.junit.Assert.*;
|
||||||
|
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
|
import org.junit.Test;
|
||||||
|
|
||||||
|
import ghidra.app.util.bin.format.dwarf4.*;
|
||||||
|
import ghidra.app.util.bin.format.dwarf4.encoding.DWARFTag;
|
||||||
|
import ghidra.app.util.bin.format.dwarf4.expression.DWARFExpressionOpCodes;
|
||||||
|
import ghidra.program.model.data.IntegerDataType;
|
||||||
|
import ghidra.program.model.listing.CodeUnit;
|
||||||
|
import ghidra.program.model.listing.Data;
|
||||||
|
import ghidra.util.exception.CancelledException;
|
||||||
|
|
||||||
|
public class DWARFStaticVarImporterTest extends DWARFTestBase {
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testIntStaticVar() throws CancelledException, IOException, DWARFException {
|
||||||
|
DebugInfoEntry intDIE = addInt(cu);
|
||||||
|
new DIECreator(DWARFTag.DW_TAG_variable)
|
||||||
|
.addString(DW_AT_name, "static_var1")
|
||||||
|
.addRef(DW_AT_type, intDIE)
|
||||||
|
.addBlock(DW_AT_location, DWARFExpressionOpCodes.DW_OP_addr, 0x10, 0x4, 0, 0, 0, 0,
|
||||||
|
0, 0)
|
||||||
|
.create(cu);
|
||||||
|
|
||||||
|
importFunctions();
|
||||||
|
|
||||||
|
CodeUnit cu = program.getListing().getCodeUnitAt(addr(0x410));
|
||||||
|
assertNotNull(cu);
|
||||||
|
assertEquals("static_var1", cu.getLabel());
|
||||||
|
assertEquals(4, cu.getLength());
|
||||||
|
assertTrue(((Data) cu).getDataType() instanceof IntegerDataType);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -87,6 +87,16 @@ public class DIECreator {
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public DIECreator addBlock(int attribute, int... intBytes) {
|
||||||
|
byte[] bytes = new byte[intBytes.length];
|
||||||
|
for (int i = 0; i < bytes.length; i++) {
|
||||||
|
bytes[i] = (byte) intBytes[i];
|
||||||
|
}
|
||||||
|
attributes.put(attribute,
|
||||||
|
new AttrInfo(attribute, DWARFForm.DW_FORM_block1, new DWARFBlobAttribute(bytes)));
|
||||||
|
return this;
|
||||||
|
}
|
||||||
|
|
||||||
DWARFAbbreviation createAbbreviation(MockDWARFCompilationUnit cu) {
|
DWARFAbbreviation createAbbreviation(MockDWARFCompilationUnit cu) {
|
||||||
DWARFAttributeSpecification[] attrSpecs =
|
DWARFAttributeSpecification[] attrSpecs =
|
||||||
new DWARFAttributeSpecification[attributes.size()];
|
new DWARFAttributeSpecification[attributes.size()];
|
||||||
|
@ -121,13 +131,15 @@ public class DIECreator {
|
||||||
die.addChild(childDIE);
|
die.addChild(childDIE);
|
||||||
}
|
}
|
||||||
|
|
||||||
cu.addMockEntry(die);
|
if (parent == null) {
|
||||||
|
parent = cu.getCompileUnitDIE();
|
||||||
|
}
|
||||||
if (parent != null) {
|
if (parent != null) {
|
||||||
|
die.setParent(parent);
|
||||||
Assert.assertTrue(parent.getCompilationUnit() == cu);
|
Assert.assertTrue(parent.getCompilationUnit() == cu);
|
||||||
parent.addChild(die);
|
parent.addChild(die);
|
||||||
die.setParent(parent);
|
|
||||||
}
|
}
|
||||||
|
cu.addMockEntry(die);
|
||||||
|
|
||||||
return die;
|
return die;
|
||||||
}
|
}
|
||||||
|
|
|
@ -32,6 +32,8 @@ import ghidra.app.util.bin.format.dwarf4.next.sectionprovider.NullSectionProvide
|
||||||
import ghidra.program.database.ProgramBuilder;
|
import ghidra.program.database.ProgramBuilder;
|
||||||
import ghidra.program.database.ProgramDB;
|
import ghidra.program.database.ProgramDB;
|
||||||
import ghidra.program.database.data.DataTypeManagerDB;
|
import ghidra.program.database.data.DataTypeManagerDB;
|
||||||
|
import ghidra.program.model.address.Address;
|
||||||
|
import ghidra.program.model.address.AddressSpace;
|
||||||
import ghidra.program.model.data.CategoryPath;
|
import ghidra.program.model.data.CategoryPath;
|
||||||
import ghidra.program.model.data.DataTypeManager;
|
import ghidra.program.model.data.DataTypeManager;
|
||||||
import ghidra.test.AbstractGhidraHeadedIntegrationTest;
|
import ghidra.test.AbstractGhidraHeadedIntegrationTest;
|
||||||
|
@ -44,7 +46,10 @@ import ghidra.util.task.TaskMonitor;
|
||||||
*/
|
*/
|
||||||
public class DWARFTestBase extends AbstractGhidraHeadedIntegrationTest {
|
public class DWARFTestBase extends AbstractGhidraHeadedIntegrationTest {
|
||||||
|
|
||||||
|
protected static final long BaseAddress = 0x400;
|
||||||
|
|
||||||
protected ProgramDB program;
|
protected ProgramDB program;
|
||||||
|
protected AddressSpace space;
|
||||||
protected DataTypeManagerDB dataMgr;
|
protected DataTypeManagerDB dataMgr;
|
||||||
protected DataTypeManager builtInDTM;
|
protected DataTypeManager builtInDTM;
|
||||||
protected int transactionID;
|
protected int transactionID;
|
||||||
|
@ -62,10 +67,16 @@ public class DWARFTestBase extends AbstractGhidraHeadedIntegrationTest {
|
||||||
*/
|
*/
|
||||||
@Before
|
@Before
|
||||||
public void setUp() throws Exception {
|
public void setUp() throws Exception {
|
||||||
program = createDefaultProgram(testName.getMethodName(), ProgramBuilder._TOY, this);
|
program = createDefaultProgram(testName.getMethodName(), ProgramBuilder._X64, this);
|
||||||
|
space = program.getAddressFactory().getDefaultAddressSpace();
|
||||||
|
|
||||||
dataMgr = program.getDataTypeManager();
|
dataMgr = program.getDataTypeManager();
|
||||||
startTransaction();
|
startTransaction();
|
||||||
|
|
||||||
|
program.getMemory()
|
||||||
|
.createInitializedBlock("test", addr(BaseAddress), 500, (byte) 0, TaskMonitor.DUMMY,
|
||||||
|
false);
|
||||||
|
|
||||||
AutoAnalysisManager mgr = AutoAnalysisManager.getAnalysisManager(program);
|
AutoAnalysisManager mgr = AutoAnalysisManager.getAnalysisManager(program);
|
||||||
DataTypeManagerService dtms = mgr.getDataTypeManagerService();
|
DataTypeManagerService dtms = mgr.getDataTypeManagerService();
|
||||||
builtInDTM = dtms.getBuiltInDataTypesManager();
|
builtInDTM = dtms.getBuiltInDataTypesManager();
|
||||||
|
@ -113,6 +124,16 @@ public class DWARFTestBase extends AbstractGhidraHeadedIntegrationTest {
|
||||||
dwarfDTM.importAllDataTypes(monitor);
|
dwarfDTM.importAllDataTypes(monitor);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected void importFunctions() throws CancelledException, IOException, DWARFException {
|
||||||
|
dwarfProg.checkPreconditions(monitor);
|
||||||
|
dwarfDTM.importAllDataTypes(monitor);
|
||||||
|
|
||||||
|
DWARFImportSummary importSummary = new DWARFImportSummary();
|
||||||
|
DWARFFunctionImporter dfi =
|
||||||
|
new DWARFFunctionImporter(dwarfProg, dwarfDTM, importOptions, importSummary, monitor);
|
||||||
|
dfi.importFunctions();
|
||||||
|
}
|
||||||
|
|
||||||
protected DIEAggregate getAggregate(DebugInfoEntry die)
|
protected DIEAggregate getAggregate(DebugInfoEntry die)
|
||||||
throws CancelledException, IOException, DWARFException {
|
throws CancelledException, IOException, DWARFException {
|
||||||
dwarfProg.setCurrentCompilationUnit(die.getCompilationUnit(), monitor);
|
dwarfProg.setCurrentCompilationUnit(die.getCompilationUnit(), monitor);
|
||||||
|
@ -278,4 +299,7 @@ public class DWARFTestBase extends AbstractGhidraHeadedIntegrationTest {
|
||||||
return arrayType;
|
return arrayType;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected Address addr(long l) {
|
||||||
|
return space.getAddress(l);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,13 +18,14 @@ package ghidra.app.util.bin.format.dwarf4;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import ghidra.app.util.bin.format.dwarf4.encoding.DWARFIdentifierCase;
|
import ghidra.app.util.bin.format.dwarf4.encoding.*;
|
||||||
import ghidra.app.util.bin.format.dwarf4.next.DWARFProgram;
|
import ghidra.app.util.bin.format.dwarf4.next.DWARFProgram;
|
||||||
import ghidra.util.task.TaskMonitor;
|
import ghidra.util.task.TaskMonitor;
|
||||||
|
|
||||||
public class MockDWARFCompilationUnit extends DWARFCompilationUnit {
|
public class MockDWARFCompilationUnit extends DWARFCompilationUnit {
|
||||||
|
|
||||||
private List<DebugInfoEntry> mockEntries = new ArrayList<>();
|
private List<DebugInfoEntry> mockEntries = new ArrayList<>();
|
||||||
|
private DebugInfoEntry compUnitDIE;
|
||||||
|
|
||||||
public MockDWARFCompilationUnit(DWARFProgram dwarfProgram, long startOffset, long endOffset,
|
public MockDWARFCompilationUnit(DWARFProgram dwarfProgram, long startOffset, long endOffset,
|
||||||
long length, int format, short version, long abbreviationOffset, byte pointerSize,
|
long length, int format, short version, long abbreviationOffset, byte pointerSize,
|
||||||
|
@ -35,6 +36,9 @@ public class MockDWARFCompilationUnit extends DWARFCompilationUnit {
|
||||||
setCompileUnit(
|
setCompileUnit(
|
||||||
new DWARFCompileUnit("Mock Comp Unit", "Mock Comp Unit Producer", "Mock Comp Unit Dir",
|
new DWARFCompileUnit("Mock Comp Unit", "Mock Comp Unit Producer", "Mock Comp Unit Dir",
|
||||||
0, 0, 0, 0, DWARFIdentifierCase.DW_ID_case_insensitive, false, null));
|
0, 0, 0, 0, DWARFIdentifierCase.DW_ID_case_insensitive, false, null));
|
||||||
|
compUnitDIE = new DIECreator(DWARFTag.DW_TAG_compile_unit)
|
||||||
|
.addString(DWARFAttribute.DW_AT_name, "MockCompUnit" + compUnitNumber)
|
||||||
|
.create(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -42,6 +46,10 @@ public class MockDWARFCompilationUnit extends DWARFCompilationUnit {
|
||||||
dies.addAll(mockEntries);
|
dies.addAll(mockEntries);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public DebugInfoEntry getCompileUnitDIE() {
|
||||||
|
return compUnitDIE;
|
||||||
|
}
|
||||||
|
|
||||||
public void addMockEntry(DebugInfoEntry die) {
|
public void addMockEntry(DebugInfoEntry die) {
|
||||||
mockEntries.add(die);
|
mockEntries.add(die);
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
/* ###
|
/* ###
|
||||||
* IP: GHIDRA
|
* IP: GHIDRA
|
||||||
* REVIEWED: YES
|
|
||||||
*
|
*
|
||||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
* you may not use this file except in compliance with the License.
|
* you may not use this file except in compliance with the License.
|
||||||
|
@ -16,12 +15,12 @@
|
||||||
*/
|
*/
|
||||||
package ghidra.python;
|
package ghidra.python;
|
||||||
|
|
||||||
|
import java.io.*;
|
||||||
|
|
||||||
import generic.jar.ResourceFile;
|
import generic.jar.ResourceFile;
|
||||||
import ghidra.app.script.GhidraScript;
|
import ghidra.app.script.GhidraScript;
|
||||||
import ghidra.app.script.GhidraScriptProvider;
|
import ghidra.app.script.GhidraScriptProvider;
|
||||||
|
|
||||||
import java.io.*;
|
|
||||||
|
|
||||||
public class PythonScriptProvider extends GhidraScriptProvider {
|
public class PythonScriptProvider extends GhidraScriptProvider {
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -39,6 +38,21 @@ public class PythonScriptProvider extends GhidraScriptProvider {
|
||||||
return "#";
|
return "#";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String getCertifyHeaderStart() {
|
||||||
|
return "## ###";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String getCertifyHeaderEnd() {
|
||||||
|
return "##";
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
protected String getCertificationBodyPrefix() {
|
||||||
|
return "#";
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getDescription() {
|
public String getDescription() {
|
||||||
return "Python";
|
return "Python";
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue