Project Description
CLIFileRW is a .NET library specifically designed to read and rewrite .NET binaries. The library. develped for the CodeBricks research project, has been developed with the uttermost performance in mind: it interacts with .NET reflection only under explicit request so large code bases can be analyzed using it. The library implements the full .NET binary format as specified by CLI standards.

Example

The best way to explain is through examples. This is an example of usage of the library: we use CLR reflection to quickly find a method, and from the method we obtain the ILCursor which is the cursor that allows enumerating the IL instructions. Using analisys already available within the library we track method calls inside the method body and retrieve information about the instructions that originates input argument for each call.

MethodTableCursor cur = CLIFileReader.FindMethod(typeof(GenericsUnitTest).GetMethod("ExpressionInput"));

CLIFile.MethodBody cb = cur.MethodBody;

LocalsVarSig locals = cb.LocalsSignature;
CLIType[] vars = locals.GetVariables().ToArray<CLIType>();
CLIType[] args = cur.GetMethodSignature().GetParameters(cur.FindCLIType()).ToArray<CLIType>();

ILCursor ilc = cb.ILInstructions;
ilc.TrackStack(args, vars, cb.MaxStack);
while (ilc.Next())
{
  ILInstruction instr = ilc.Instr;
  object o = instr.ResolveParameter(f);
  if (ilc.IsCall)
  {
    Target[] cargs = ilc.CallLoadArguments();
    MethodDesc m = (MethodDesc)o;
    Debug.WriteLine(string.Format("{0} to {1} at offset {2:X4}", ilc.Instr.op, m.Name, ilc.Position));
    for (int i = 0; i < cargs.Length; i++)
      Debug.WriteLine(string.Format("\tPar {0} at offset {1:X4}", i, cargs[i].Position));
  }
}

Few words

If you are still interested in the project may be it is worth spending few minutes reading about the design of the library and its features. The library has been implemented to provide the fastest possible access to .NET assemblies without having to use reflection (unless you need it). At the core of the library there is the MapView library which exposes memory mapped files to .NET applications through checked pointers which hide all the details of unsafe code in a small and handy library useful in itself. The CLIFileRW library is built using memory mapping to avoid unnecessary memory allocation, data is accessed directly on the disk and CLI metadata tables are exposed as a set of tables using indexers. The ILCursor class is responsible for reading method bodies, and it is conceived as a linear cursor into a stream of IL instructions. The cursor provides a number of facilities that can be requested such as
  • track targets of branch instructions
  • abstract interpretation of stack of operands
  • resolution of parameters into a representation of types which is not based on reflection (so that you can read an assembly without loading it)
  • bridge to and from reflection to easily interoperate with runtime types
  • cursor state saving to perform backtracking during code analisys

The library impelements the CLR 2 file format (the most recent) as specified in ECMA CLI standard. At the moment is only able to read the file format, though we are working to implement a very efficient assembly rewriter for supporting meta-programming on the IL.
Part of this work has been explicitly supported by CLR team from 2001 until 2005 by introducing changes into reflection in .NET CLR 2 and the support for lightweight runtime code generation.

Last edited Sep 14, 2008 at 4:41 PM by cisterni, version 3