Skip to content

Instantly share code, notes, and snippets.

@Mrnikbobjeff
Created February 26, 2021 17:48
Show Gist options
  • Save Mrnikbobjeff/7d59e88627cd2c06f2e64c8d64419fbc to your computer and use it in GitHub Desktop.
Save Mrnikbobjeff/7d59e88627cd2c06f2e64c8d64419fbc to your computer and use it in GitHub Desktop.
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Runtime.CompilerServices;
using System.Text;
using System.Text.Json;
using System.Xml;
using System.Xml.Linq;
using System.Xml.Serialization;
namespace DUMPBINPARSER
{
public class Program
{
public class KnownApis
{
public KnownApi[] Apis { get; set; }
}
public class Person
{
public string Name { get; set; }
public int Alter { get; set; }
}
[Serializable]
public class KnownApi
{
public string Dll { get; set; }
public string[] Methods { get; set; }
}
private static XDocument CreateXmlFromObjects(string rootElementName, params object[] inputs)
{
var doc = new XDocument();
using (XmlWriter writer = doc.CreateWriter())
{
writer.WriteStartElement(rootElementName);
foreach (var input in inputs)
new XmlSerializer(input.GetType()).Serialize(writer, input);
writer.WriteEndElement();
}
return doc;
}
static List<string> GetDumpbinOutput(string filepath)
{
var pi = new ProcessStartInfo(@"C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Tools\MSVC\14.27.29110\bin\Hostx86\x86\dumpbin.exe", $"/EXPORTS {filepath}");
pi.RedirectStandardOutput = true;
var newPRoc = Process.Start(pi);
List<string> lines = new List<string>();
while (!newPRoc.StandardOutput.EndOfStream)
{
string line = newPRoc.StandardOutput.ReadLine();
lines.Add(line);
}
newPRoc.WaitForExit();
return lines;
}
static void Main()
{
var files = Directory.EnumerateFiles(@"C:\Windows\System32", "*.dll").ToArray();
var dict = new Dictionary<string, HashSet<string>>();
var file = files.AsParallel().Select(ParseDumpbin).Where(x => x.methods.Any()).Select(xy => new KnownApi() { Dll = Path.GetFileName(xy.dll), Methods = xy.methods }).ToArray();
var ms = new MemoryStream();
System.Xml.Serialization.XmlSerializer x = new System.Xml.Serialization.XmlSerializer(file.First().GetType().MakeArrayType());
//var xml = CreateXmlFromObjects("KnownApi", files.Cast<Object>().ToArray());
var ct = file.SelectMany(xx => xx.Methods).Count();
x.Serialize(ms, file);
var json = JsonSerializer.Serialize<KnownApi[]>(file);
KnownApi[] knownApis = JsonSerializer.Deserialize<KnownApi[]>(json);
File.WriteAllText(@"D:\Repos\Serilized.txt", Encoding.UTF8.GetString(ms.ToArray()));
Console.ReadKey();
}
/*
var serializer = new XmlSerializer(typeof(KnownApi).MakeArrayType());
var str = GeneratorResources.ResourceManager.GetString("DllImportExactNamingGeneratorResource", CultureInfo.InvariantCulture);
var json = (serializer.Deserialize(XmlReader.Create(new StringReader(str))) as KnownApi[])!;*/
static (string dll, string[] methods) ParseDumpbin(string file)
{
var lines = (GetDumpbinOutput(file));
var dll = lines.Single(x => x.StartsWith("Dump of file "));
var indexOfDll = lines.IndexOf(dll);
dll = dll.Substring(dll.LastIndexOf("\\"));
var methods = lines
.SkipWhile(l => !l.StartsWith(" ordinal hint RVA name"))
.Skip(2)
.Where(x => x.Length > 27)
.Select(x => x.Substring(26).Trim())
.Where(x => !x.Equals("[NONAME]"))
.Select(x => x.Contains(' ') ? x.Substring(0, x.IndexOf(' ')) : x).ToArray();
var newLines = methods.ToHashSet(); //l.EndsWith("W") && newLines.Contains(l.Substring(0, l.Length - 1) + "A") && !newLines.Contains(l.Substring(0, l.Length - 1))
methods = methods.Where(l => !l.Contains("?")).ToArray();
return (dll, methods);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment