package re3lib; import java.io.File; import java.io.PrintWriter; import java.util.ArrayList; import java.util.HashSet; import java.util.Iterator; import java.util.List; import ghidra.app.script.GhidraScript; import ghidra.program.model.data.CategoryPath; import ghidra.program.model.data.Composite; import ghidra.program.model.data.DataType; import ghidra.program.model.data.EnumDataType; import ghidra.program.model.data.ProgramBasedDataTypeManager; import ghidra.program.model.data.Structure; import ghidra.program.model.data.TypeDef; import ghidra.program.model.data.TypedefDataType; import ghidra.program.model.listing.Program; public class TypeDumper { Program currentProgram; GhidraScript script; public TypeDumper(GhidraScript script) { this.script = script; currentProgram = script.getCurrentProgram(); RecompileConfig.INSTANCE = new RecompileConfig(script); } public void run() throws Exception { ProgramBasedDataTypeManager dtm = currentProgram.getDataTypeManager(); HashSet typeBlacklist = Utils.loadSimpleBlacklist(RecompileConfig.INSTANCE.typeBlacklistPath); HashSet categoryPathBlacklist = Utils .loadSimpleBlacklist(RecompileConfig.INSTANCE.categoryPathBlacklistPath); if (typeBlacklist == null) { script.println("Building struct blacklist from existing data types"); typeBlacklist = new HashSet<>(); Iterator it = dtm.getAllDataTypes(); while (it.hasNext()) { DataType dt = it.next(); if (dt instanceof Structure || dt instanceof TypedefDataType) { typeBlacklist.add(dt.getDisplayName()); } } Utils.saveStructBlacklist(typeBlacklist, RecompileConfig.INSTANCE.typeBlacklistPath); } List filteredTypes = new ArrayList<>(); // Iterator compIt = dtm.getAllDataTypes(); // while (compIt.hasNext()) { // DataType comp = compIt.next(); // // script.println("Found: " + comp.getDisplayName() + " - " + // // comp.getClass().getSimpleName()); // if (comp instanceof TypeDef) { // if (comp.getDisplayName().startsWith("FIL_")) { // script.println("Found: " + comp.getDisplayName() + " - " + comp.getName() + " // - " + comp.getClass().getSimpleName()); // } // } // // if (comp.getName() == "FIL_tdstConcatFile") { // // // script.println("Found: " + dt.getDisplayName() + " - " + // // // dt.getClass().getSimpleName()); // // throw new Exception("Found: " + comp.getDisplayName() + " - " + // comp.getClass().getSimpleName()); // // } // } Iterator it = dtm.getAllDataTypes(); while (it.hasNext()) { DataType dt = it.next(); if (typeBlacklist.contains(dt.getDisplayName())) continue; CategoryPath catPath = dt.getCategoryPath(); if (catPath.getPathElements().length > 0 && categoryPathBlacklist.contains(catPath.getPathElements()[0])) continue; // script.println("Type: " + dt.getDisplayName() + " - CatPath: " + dt.getCategoryPath()); // if (dt.getName().equals("ImageBaseOffset32")) // throw new Exception("Found: " + dt.getDisplayName() + " - " + catPath.getPathElements()[0] + " - " + dt.getClass().getSimpleName()); if (dt instanceof Structure || dt instanceof TypeDef || dt instanceof EnumDataType) { // script.println("Adding: " + dt.getDisplayName() + " - " + // dt.getClass().getSimpleName()); filteredTypes.add(dt); } } try (PrintWriter writer = new PrintWriter(new File(RecompileConfig.INSTANCE.outputDir, "gh_types.h"), "UTF-8")) { Utils.headerGuardPre(writer, "STRUCTS"); writer.println("// AUTO-GENERATED FILE "); writer.println("#include "); DataTypeWriter dtw = new DataTypeWriter(dtm, writer); dtw.blacklistedTypes = typeBlacklist; dtw.write(filteredTypes, script.getMonitor()); Utils.headerGuardPost(writer, "STRUCTS"); } } }