Raheel Khan
Raheel Khan

Reputation: 14787

Dynamic assembly created using Reflection.Emit crashes with exit code -532462766

I have been following this article to generate a dynamic assembly as follows:

var directory = new DirectoryInfo(Environment.GetFolderPath(Environment.SpecialFolder.Desktop));
var file = new FileInfo(Path.Combine(directory.FullName, @"MyDynamicAssembly.exe"));

var domain = AppDomain.CurrentDomain;
var name = new AssemblyName("Namespace.With.Dots");
var builderAssembly = domain.DefineDynamicAssembly(name, AssemblyBuilderAccess.Save, directory.FullName);
var builderModule = builderAssembly.DefineDynamicModule("Namespace.With.Dots.Temp.exe");
var builderType = builderModule.DefineType("Program", TypeAttributes.Class | TypeAttributes.Public, typeof(object));
var builderMethod = builderType.DefineMethod("Main", MethodAttributes.Private | MethodAttributes.Static, typeof(int), new Type [] { typeof(string []) });

var generator = builderMethod.GetILGenerator();
generator.Emit(OpCodes.Ldstr, "Hello, World!");
generator.Emit(OpCodes.Call, typeof(Console).GetMethod("WriteLine", new Type [] { typeof(string) }));
generator.EmitWriteLine("Hello again.");
generator.Emit(OpCodes.Ldc_I4, 0);
generator.Emit(OpCodes.Ret);

builderAssembly.SetEntryPoint(builderMethod, PEFileKinds.ConsoleApplication);
builderAssembly.Save(file.Name, PortableExecutableKinds.ILOnly, ImageFileMachine.I386);

var process = Process.Start(file.FullName); // Crashes with image below.
var result = process.WaitForExit();
var exitCode = process.ExitCode; // -532462766.

Here is what I know about the code above:

METHOD:

CRASH:

Ignore the filename on the image. It would be MyDynamicAssembly.exe per the code above. App crash info

Any pointers on what's going wrong here would be appreciated.

Upvotes: 3

Views: 949

Answers (2)

Hans Passant
Hans Passant

Reputation: 941457

You'll have a lot more tough debugging jobs ahead of you beyond this one. You basically only ever get two exit codes. -532462766 or 0xe0434352 is the infamous "CCR" exception. The CLR died trying to load the assembly and can't perform the normal exception handling logic. You of course want to make sure that your generated IL is correct by testing it in-process before you try to run it stand-alone in a separate process. You'll at least have a debugger available that way.

The other one is -532459699 or 0xe0434f4d, the normal "COM" exception. Produced when the code threw a plain .NET exception and it wasn't handled because of a lack of try/catch and no AppDomain.UnhandledException event handler. You'll have to make-do without a stack trace and can only reverse-engineer the location where the exception was thrown with the hints in this answer.

Very punishing trouble-shooting of course, you basically do not ever want to do this. At least consider loading the code in another AppDomain so you stand a chance to produce a diagnostic and recover. It can still be in another process by writing a small "host" program that creates the appdomain and loads the assembly and generates a diagnostic. Also provides you with a way to use the debugger.

Upvotes: 2

Raheel Khan
Raheel Khan

Reputation: 14787

Finally got it to work by changing the module builder cell to overload:

var builderModule = builderAssembly.DefineDynamicModule("MyDynamicAssembly", "MyDynamicAssembly.exe", false);

Upvotes: 1

Related Questions