mirror of
https://github.com/celisej567/source-engine.git
synced 2026-01-05 22:09:59 +03:00
1
This commit is contained in:
30
utils/mapsorter/Class1.cs
Normal file
30
utils/mapsorter/Class1.cs
Normal file
@@ -0,0 +1,30 @@
|
||||
using System;
|
||||
using System.Text.RegularExpressions;
|
||||
using System.Collections;
|
||||
using System.IO;
|
||||
|
||||
namespace MapSorter
|
||||
{
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Summary description for Class1.
|
||||
/// </summary>
|
||||
class Class1
|
||||
{
|
||||
/// <summary>
|
||||
/// The main entry point for the application.
|
||||
/// </summary>
|
||||
[STAThread]
|
||||
static void Main(string[] args)
|
||||
{
|
||||
if( args.Length != 1 )
|
||||
{
|
||||
Console.WriteLine("Usage: MapSorter <filename.map>");
|
||||
return;
|
||||
}
|
||||
|
||||
new MapFileLoader(args[0]).DumpReport();
|
||||
}
|
||||
}
|
||||
}
|
||||
248
utils/mapsorter/MapFileLoader.cs
Normal file
248
utils/mapsorter/MapFileLoader.cs
Normal file
@@ -0,0 +1,248 @@
|
||||
using System;
|
||||
using System.Text.RegularExpressions;
|
||||
using System.Collections;
|
||||
using System.IO;
|
||||
|
||||
namespace MapSorter
|
||||
{
|
||||
public class Element : IComparable
|
||||
{
|
||||
/// <summary>
|
||||
/// Segment this element is in.
|
||||
/// </summary>
|
||||
public int Segment;
|
||||
|
||||
/// <summary>
|
||||
/// Base or virtual file address.
|
||||
/// </summary>
|
||||
public int Address;
|
||||
|
||||
/// <summary>
|
||||
/// Adjusted relative virtual address.
|
||||
/// </summary>
|
||||
public int RVA;
|
||||
|
||||
/// <summary>
|
||||
/// Name of this element.
|
||||
/// </summary>
|
||||
public string Text;
|
||||
|
||||
/// <summary>
|
||||
/// Object file this element is located in.
|
||||
/// </summary>
|
||||
public string Obj;
|
||||
|
||||
/// <summary>
|
||||
/// Size of this element, or -1.
|
||||
/// </summary>
|
||||
public int Size = -1;
|
||||
|
||||
/// <summary>
|
||||
/// True if this is the last element in an object file.
|
||||
/// </summary>
|
||||
public bool bCrossObj = false;
|
||||
|
||||
public Element( int Segment, int Address, string Text, int RVA, string Obj )
|
||||
{
|
||||
this.Segment = Segment;
|
||||
this.Address = Address;
|
||||
this.RVA = RVA;
|
||||
this.Text = Text;
|
||||
this.Obj = Obj;
|
||||
}
|
||||
|
||||
// Comparable interface:
|
||||
int System.IComparable.CompareTo( object o )
|
||||
{
|
||||
// HACK HACK - sorts according to size if size field is non negative, otherwise sorts by segment then address
|
||||
Element other = (Element)o;
|
||||
|
||||
// Sort by size:
|
||||
if( other.Size != -1 || Size != -1 )
|
||||
{
|
||||
if( Size < other.Size )
|
||||
return -1;
|
||||
|
||||
if( Size > other.Size )
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Sizes aren't defined, sort by Segment then Address:
|
||||
if( Segment != other.Segment )
|
||||
{
|
||||
if( Segment < other.Segment )
|
||||
return -1;
|
||||
else
|
||||
return 0;
|
||||
}
|
||||
|
||||
if( Address < other.Address )
|
||||
return -1;
|
||||
else if( Address > other.Address )
|
||||
return 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
public class Module : IComparable
|
||||
{
|
||||
public string Name;
|
||||
public int Size;
|
||||
|
||||
public Module(string Name, int Size)
|
||||
{
|
||||
this.Name = Name;
|
||||
this.Size = Size;
|
||||
}
|
||||
|
||||
int System.IComparable.CompareTo( object o )
|
||||
{
|
||||
Module m = (Module)o;
|
||||
if( Size < m.Size )
|
||||
return -1;
|
||||
|
||||
if( Size > m.Size )
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// An atomic class that loads and parses a given map file.
|
||||
/// </summary>
|
||||
public class MapFileLoader
|
||||
{
|
||||
ArrayList Elements;
|
||||
ArrayList Modules;
|
||||
|
||||
/// <summary>
|
||||
/// Regular expression to break mapfile elements up:
|
||||
/// </summary>
|
||||
protected static Regex ElementRegex = new Regex(@"([0-9a-fA-F]{4})\:([0-9a-fA-F]{8})\s+([^\s]*)\s+([0-9a-fA-F]{8})\s(f\s)?(i\s)?\s+(.*\.obj)",RegexOptions.Compiled | RegexOptions.Multiline | RegexOptions.IgnoreCase );
|
||||
|
||||
|
||||
public MapFileLoader( string filename )
|
||||
{
|
||||
// Load the element data from the mapfile:
|
||||
LoadElements( new StreamReader(filename).ReadToEnd() );
|
||||
|
||||
// Compute modules and their sizes:
|
||||
ComputeModules();
|
||||
}
|
||||
|
||||
public void DumpReport()
|
||||
{
|
||||
Console.WriteLine("***** Elements by size ascending. (*) = element straddles an .obj file boundary, so the size may not be correct.");
|
||||
Console.WriteLine();
|
||||
|
||||
foreach (Element e in Elements )
|
||||
{
|
||||
if( e.Size < 1024 )
|
||||
continue;
|
||||
|
||||
if( e.bCrossObj )
|
||||
Console.Write("(*)");
|
||||
|
||||
Console.WriteLine( e.Size / 1024 + "k : " +e.Obj + " : " + e.Text );
|
||||
}
|
||||
|
||||
Console.WriteLine();
|
||||
Console.WriteLine();
|
||||
Console.WriteLine("***** Modules by size, ascending. This is estimated based on elements that don't straddle .obj boundaries.");
|
||||
Console.WriteLine();
|
||||
|
||||
foreach(Module m in Modules )
|
||||
{
|
||||
if( m.Size < 1024 )
|
||||
continue;
|
||||
|
||||
Console.WriteLine( m.Size / 1024 + "k : " + m.Name );
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
protected void LoadElements( string mapfile )
|
||||
{
|
||||
// Match each appropriate line in the map file. The summary entries at the top of each map file are NOT matched by this regex.
|
||||
MatchCollection matches = ElementRegex.Matches(mapfile);
|
||||
|
||||
|
||||
Elements = new ArrayList();
|
||||
|
||||
// Convert each match to an Element type and add them to an array list.
|
||||
foreach( Match m in matches )
|
||||
{
|
||||
|
||||
Element e = new Element(int.Parse(m.Groups[1].Value,System.Globalization.NumberStyles.AllowHexSpecifier),
|
||||
int.Parse(m.Groups[2].Value,System.Globalization.NumberStyles.AllowHexSpecifier),
|
||||
m.Groups[3].Value,
|
||||
int.Parse(m.Groups[4].Value,System.Globalization.NumberStyles.AllowHexSpecifier),
|
||||
m.Groups[7].Value);
|
||||
|
||||
Elements.Add(e);
|
||||
|
||||
}
|
||||
|
||||
// Sort the list by address:
|
||||
Elements.Sort();
|
||||
|
||||
Element previous = null;
|
||||
|
||||
// Compute estimated sizes for each element in the list:
|
||||
foreach( Element e in Elements )
|
||||
{
|
||||
if( previous != null )
|
||||
{
|
||||
if( e.Segment == previous.Segment )
|
||||
{
|
||||
previous.Size = e.Address- previous.Address;
|
||||
|
||||
// Take note of the symbols that cross object file boundaries:
|
||||
if( !previous.Obj.Equals(e.Obj) )
|
||||
{
|
||||
previous.bCrossObj = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
previous = e;
|
||||
}
|
||||
|
||||
// Sort the list by size
|
||||
Elements.Sort();
|
||||
|
||||
|
||||
}
|
||||
|
||||
protected void ComputeModules()
|
||||
{
|
||||
// Estimate the size of each object file:
|
||||
Hashtable h = new Hashtable();
|
||||
|
||||
foreach(Element e in Elements )
|
||||
{
|
||||
if( !h.ContainsKey(e.Obj) )
|
||||
h.Add(e.Obj,0);
|
||||
|
||||
if( !e.bCrossObj )
|
||||
{
|
||||
h[e.Obj] = (int)h[e.Obj] + e.Size;
|
||||
}
|
||||
}
|
||||
|
||||
Modules = new ArrayList();
|
||||
|
||||
foreach( string key in h.Keys )
|
||||
{
|
||||
Modules.Add( new Module(key, (int)h[key] ));
|
||||
}
|
||||
|
||||
Modules.Sort();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
100
utils/mapsorter/MapSorter.csproj
Normal file
100
utils/mapsorter/MapSorter.csproj
Normal file
@@ -0,0 +1,100 @@
|
||||
<VisualStudioProject>
|
||||
<CSHARP
|
||||
ProjectType = "Local"
|
||||
ProductVersion = "7.10.3077"
|
||||
SchemaVersion = "2.0"
|
||||
ProjectGuid = "{296D6B2D-4FAD-48BE-AC61-CEF53B472983}"
|
||||
>
|
||||
<Build>
|
||||
<Settings
|
||||
ApplicationIcon = ""
|
||||
AssemblyKeyContainerName = ""
|
||||
AssemblyName = "MapSorter"
|
||||
AssemblyOriginatorKeyFile = ""
|
||||
DefaultClientScript = "JScript"
|
||||
DefaultHTMLPageLayout = "Grid"
|
||||
DefaultTargetSchema = "IE50"
|
||||
DelaySign = "false"
|
||||
OutputType = "Exe"
|
||||
PreBuildEvent = ""
|
||||
PostBuildEvent = ""
|
||||
RootNamespace = "MapSorter"
|
||||
RunPostBuildEvent = "OnBuildSuccess"
|
||||
StartupObject = ""
|
||||
>
|
||||
<Config
|
||||
Name = "Debug"
|
||||
AllowUnsafeBlocks = "false"
|
||||
BaseAddress = "285212672"
|
||||
CheckForOverflowUnderflow = "false"
|
||||
ConfigurationOverrideFile = ""
|
||||
DefineConstants = "DEBUG;TRACE"
|
||||
DocumentationFile = ""
|
||||
DebugSymbols = "true"
|
||||
FileAlignment = "4096"
|
||||
IncrementalBuild = "false"
|
||||
NoStdLib = "false"
|
||||
NoWarn = ""
|
||||
Optimize = "false"
|
||||
OutputPath = "bin\Debug\"
|
||||
RegisterForComInterop = "false"
|
||||
RemoveIntegerChecks = "false"
|
||||
TreatWarningsAsErrors = "false"
|
||||
WarningLevel = "4"
|
||||
/>
|
||||
<Config
|
||||
Name = "Release"
|
||||
AllowUnsafeBlocks = "false"
|
||||
BaseAddress = "285212672"
|
||||
CheckForOverflowUnderflow = "false"
|
||||
ConfigurationOverrideFile = ""
|
||||
DefineConstants = "TRACE"
|
||||
DocumentationFile = ""
|
||||
DebugSymbols = "false"
|
||||
FileAlignment = "4096"
|
||||
IncrementalBuild = "false"
|
||||
NoStdLib = "false"
|
||||
NoWarn = ""
|
||||
Optimize = "true"
|
||||
OutputPath = "bin\Release\"
|
||||
RegisterForComInterop = "false"
|
||||
RemoveIntegerChecks = "false"
|
||||
TreatWarningsAsErrors = "false"
|
||||
WarningLevel = "4"
|
||||
/>
|
||||
</Settings>
|
||||
<References>
|
||||
<Reference
|
||||
Name = "System"
|
||||
AssemblyName = "System"
|
||||
HintPath = "..\..\..\WINDOWS\Microsoft.NET\Framework\v1.1.4322\System.dll"
|
||||
/>
|
||||
<Reference
|
||||
Name = "System.Data"
|
||||
AssemblyName = "System.Data"
|
||||
HintPath = "..\..\..\WINDOWS\Microsoft.NET\Framework\v1.1.4322\System.Data.dll"
|
||||
/>
|
||||
<Reference
|
||||
Name = "System.XML"
|
||||
AssemblyName = "System.Xml"
|
||||
HintPath = "..\..\..\WINDOWS\Microsoft.NET\Framework\v1.1.4322\System.XML.dll"
|
||||
/>
|
||||
</References>
|
||||
</Build>
|
||||
<Files>
|
||||
<Include>
|
||||
<File
|
||||
RelPath = "Class1.cs"
|
||||
SubType = "Code"
|
||||
BuildAction = "Compile"
|
||||
/>
|
||||
<File
|
||||
RelPath = "MapFileLoader.cs"
|
||||
SubType = "Code"
|
||||
BuildAction = "Compile"
|
||||
/>
|
||||
</Include>
|
||||
</Files>
|
||||
</CSHARP>
|
||||
</VisualStudioProject>
|
||||
|
||||
BIN
utils/mapsorter/MapSorter.exe
Normal file
BIN
utils/mapsorter/MapSorter.exe
Normal file
Binary file not shown.
21
utils/mapsorter/MapSorter.sln
Normal file
21
utils/mapsorter/MapSorter.sln
Normal file
@@ -0,0 +1,21 @@
|
||||
Microsoft Visual Studio Solution File, Format Version 8.00
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "MapSorter", "MapSorter.csproj", "{296D6B2D-4FAD-48BE-AC61-CEF53B472983}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
EndProjectSection
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfiguration) = preSolution
|
||||
Debug = Debug
|
||||
Release = Release
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfiguration) = postSolution
|
||||
{296D6B2D-4FAD-48BE-AC61-CEF53B472983}.Debug.ActiveCfg = Debug|.NET
|
||||
{296D6B2D-4FAD-48BE-AC61-CEF53B472983}.Debug.Build.0 = Debug|.NET
|
||||
{296D6B2D-4FAD-48BE-AC61-CEF53B472983}.Release.ActiveCfg = Release|.NET
|
||||
{296D6B2D-4FAD-48BE-AC61-CEF53B472983}.Release.Build.0 = Release|.NET
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityAddIns) = postSolution
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
Reference in New Issue
Block a user