Log in

View Full Version : .NET assembly problems


crassy
January 22nd, 2003, 14:36
Hi all!

I've got an add-in for VS.NET that I'm trying to fix...

The app itself is written in C# and is easily decompileable.
It uses 512-bit RSA for the serial. As I couldn't find any way to
get the private key I patched the target dll with a new public key that I generated.

Now to the problem:
As soon as I change a byte in the dll it fails to load giving me "Strong name validation failed" error. After looking around a bit I found that the problem probably is that .net assemblies can be signed so that they won't be played with. The utility for signing is called sn and is included in VS.NET.

I've found a site that seems to have some info on this but unfortunately it's in some strange language (Jewish?).
The URL is http://www.twoguru.com/playground/cs_tutorial/other/assembly3.htm .

Anyway, I've tried skipping strong name verification (sn -Vr x.dll), generating a new key pair and signing with it (sn -k and sn -R), but came nowhere...

If you want to test this I attach a test dll where i recreated the problem. Just set a reference to it and do
Code:
Console.WriteLine(TestLib1.Class1.STR);
. It prints "Haj Haj". Now change this message at offset 68Eh in the dll and rerun. Voila!

I'm really in need of ideas here.. IMO we'll see this kind of protections more and more now that .net is on the rise.

Thanks!

crassy
January 22nd, 2003, 15:43
Here is the attachment

disavowed
January 22nd, 2003, 19:53
short solution:
patch StrongNameSignatureVerificationEx from mscoree.dll to always return 1

long solution:
reverse the hashing in StrongNameSignatureVerification from mscorsn.dll
i've attached a little program below (with asm source) so that you can easily step through this function with a debugger

disavowed
January 22nd, 2003, 20:46
the attachment

crassy
January 23rd, 2003, 02:43
Thanks for replying!

Patching the dll doesn't seem to be an elegant way to solve this, so I'm getting to work on reversing the hashing algo asap (if it's reversible that is ). I'll post my findings here when I'm done.

cyberheg
January 23rd, 2003, 03:22
Please read and try this:

http://www.msdn.microsoft.com/msdnmag/issues/02/03/PE2/default.aspx

Here is a PE article which mentions the .NET header, IMAGE_COR20_HEADER structure, (in the section named .NET header) which pointed to by the IMAGE_DIRECTORY_ENTRY_COM_DESCRIPTOR in the data directory.

If you look at figure 10 you'll see the IMAGE_COR20_HEADER structure it has a bit in the DWORD named Flags which is named STRONGNAMESIGNED. From what I understand if this is disabled then strong name hashes aren't used anymore.

Since I don't have a target myself I'd like you to see if it's possible to modify this and make it work.

I was studying this thing recently since I tried to make a simple "pe packer" for .NET exe's. The problem was then that no matter what I did it kept showing a MessageBox with an error like "_CorExeMain execution failed". Maybe one of you know if it's possible to turn on some debugging or extended error logging to see what goes on when a file loads to get a clue why such errors happen.

// CyberHeg

disavowed
January 23rd, 2003, 11:15
lord pe's pe editor allows you to view this table:

Directories -> COM

however, the only flag in the dll we've been working with is COMIMAGE_FLAGS_ILONLY. STRONGNAMESIGNED is not there
(so changing that bit wouldn't help)

zacdac
January 24th, 2003, 20:00
G'day..

Attached is a patched testlib1 dll to demonstrate that it is possible to patch .net assemblies.

There are several methods that may be used to patch the assemblies, however you have to be aware of several gotchas as well.

Zac

crassy
January 25th, 2003, 05:31
Hmm... So you flipped a byte at 22Ch from 80h to 00h... Would you please explain why?

disavowed
January 25th, 2003, 11:10
interesting.. he changed the length of the StrongNameSignature from 80h to 0. i guess if the framework sees that the signature length is 0, it assumes it doesn't exist, and thus doesn't check it. nice work, zacdac

zacdac
January 25th, 2003, 17:07
Howdy..

@disavowed - correct. I think it maybe a bug with the .Net framework.

Couple of gotcha's..

a) This method will only work with win form applications, not with asp.net applications.
b) Only strong name assemblies may be stored in the GAC, so patched assemblies may not. Note if an assembly is stored in the GAC, it will take precedence over a local copy.
c) The offset of the size of the strong name signature in not constant.

Another method to allow patching of .net assemblies is to modify the strong name attribute. This however changes the assembly manifest information and requires that existing applications be recompiled. This method works for asp.net assemblies.

A third method (in theory) is to replace the public hash stored within the assembly. Note that only the last 80 bytes of the hash are stored. Keep in mind that the purpose of strong named assembly is to allow unique identification via digital signatures and is not an attempt at protection.

@crassy - if you need some help reversing your target, drop me a pm.

Zac

crassy
January 27th, 2003, 13:02
Thanks for your help everyone. I patched the length of signature in the target and it works perfectly!

Quote:
Originally posted by zacdac
A third method (in theory) is to replace the public hash stored within the assembly. Note that only the last 80 bytes of the hash are stored. Keep in mind that the purpose of strong named assembly is to allow unique identification via digital signatures and is not an attempt at protection.
Zac


Hmm, now thats interesting... Have you seen any docs on how this hash is calculated?

zacdac
January 27th, 2003, 16:25
Not really... There are some concept docs on msdn

hxxp://msdn.microsoft.com/msdnmag/issues/01/03/buildapps2/default.aspx

But nothing detailed enough.

Zac

R3v3nG3
August 11th, 2004, 10:47
Quote:
[Originally Posted by zacdac]

Couple of gotcha's..

a) This method will only work with win form applications, not with asp.net applications.

...

Another method to allow patching of .net assemblies is to modify the strong name attribute. This however changes the assembly manifest information and requires that existing applications be recompiled. This method works for asp.net assemblies.

...
Zac


Hi all!
I'm "working" with an asp.net assembly. I tried to resign the assembly with a new keypair but during execution the assembly doesn't pass the validation.
Anyone con help me?
Thanks!
R3v3nG3

omega_red
August 11th, 2004, 12:11
If the app relies only on .NET framework's strong name checking (it doesn't perform internal checking about existence of its public key), you can just remove the public key from it. See following links for details:

board.anticrack.de/viewtopic.php?p=24882#24882

Disassembling/modifying/reassembling is a very good approach most of the time, only code obfuscation may cause some trouble. Even if the app checks for existence of public key (using Reflection for example), you can just remove/modify this code and recompile

R3v3nG3
August 12th, 2004, 07:38
It works!
Thank you omega-red!
Bye,
R3v3nG3

SiNTAX
August 12th, 2004, 10:06
If I'm not mistaken, Mono has strong name support.. so you will find the source code of the SN & GAC parts in there... might be useful..

hxxp://www.mono-project.com/about/index.html