.Net Assembly Spoof Attack

To be honest I am not sure about the name of such attack, but in the nutshell it is attack where the original good code is replaced by bad one with the same interface but very bad implementation - may be Trojan DLL? Anyway...

My Australia based teammate Rocky posted sometime ago coolest screencast - Assembly Hijacking. He calls it hijacking. Go see it, very cool.

The final verdict was to sign the assemblies with SNK which is almost always a good idea to do. This should definitely prevent such attack he demonstrated. To " Evaluate Whether You Need Strong Names " check on the following in referenced article:

  • You need to add your assembly to the global assembly cache.
  • You want to prevent partial trust callers.
  • You want cryptographically strong evidence for security policy evaluation. <-- this one is for our case

Lately I stumbled on another post Assembly Load Contexts Subtleties that "focus on Assembly.Load and Assembly.LoadFrom" which discusses dynamic assembly and types invocation.

I thought to myself "What role SNK plays in this case?"

None

Dynamically loaded assembly is not checked for its evidence. That means that all applications that use reflection to load assemblies dynamically are vulnerable to such attack - regardless if there is SNK in place or not.

What to do to prevent such attack when using reflection?

1. Do sign with SNK your assemblies.

2. Use Full Assembly Names When You Dynamically Load Assemblies

The code you should find there will look like this:

public static StrongName GetStrongName(Assembly assembly)
{
if(assembly == null)
throw new ArgumentNullException("assembly");

AssemblyName assemblyName = assembly.GetName();
// get the public key blob
byte[] publicKey = assemblyName.GetPublicKey();
if(publicKey == null || publicKey.Length == 0)
throw new InvalidOperationException(String.Format("{0} is not strongly named", assembly));
StrongNamePublicKeyBlob keyBlob = new StrongNamePublicKeyBlob(publicKey);

// create the StrongName
return new StrongName(keyBlob, assemblyName.Name, assemblyName.Version);
}

And here is the check itself:

//LOAD ASSEMBLY DYNAMICALLY
Assembly assembly = Assembly.LoadFrom("ReflectedDll.dll");

//GET STRONG NAME FOR THE LOADED ASSEMBLY
StrongName sn = GetStrongName(assembly);

StrongName myStrongName = null;

//GET CURRENT APPDOMAIN STRONG NAME
IEnumerator enumerator = (IEnumerator)AppDomain.CurrentDomain.Evidence.GetEnumerator();
enumerator.Reset();
while (enumerator.MoveNext())
{
if (enumerator.Current.GetType().Equals(typeof(StrongName)))
myStrongName = (StrongName)enumerator.Current;
}

if (!sn.PublicKey.Equals(myStrongName.PublicKey))
{
throw new ApplicationException("SPOOFED!!");
}

//OK, STRONG NAME IS COOL, LETS RUN IT FURTHER

 

In the world of provider design pattern (abstract factory – GoF definition) where assemblies get loaded dynamically one should pay closer attention to this.

Enjoy

Comments

  • Anonymous
    March 12, 2007
    Couldn't an attacker with sufficient access replace the assembly containing this check code as well?Or, even easier, delay sign the malicious assembly with your public key and configure the machine it's loaded on to bypass signature verification for that public key?It looks like the attacker in the screencast had full administrative access to the computer so, unless I'm missing something, it seems like the end attack would still be possible even if Logger.dll were signed.
  • Anonymous
    March 12, 2007
    Regarding the screen cast (i am happy you went to look at it!) - yes, the attacker had full access to the web site. BUT the twist here is that it was done through the vulnerability of the web site:
  1. The site was running under administrative account.
  2. The site was vulnerable to SQL Injection attack. The developer of the web site was using dynamic SQL statements
  3. xp_cmdshell was not disabled Regarding replacing the check or delay sign. I presume that attacker's goal is not to disclose himself. So if one replaces the application then it will be discovered and maliciuos code that steals data identified and moved. Using DLL spoofing like this allows attacker minimal dev effort and longer time to work under cover and steal things... Now that you know it all... - do not try it on others sites but your development one:), I mean the attack. But go for the countermeasure.
  • Anonymous
    March 15, 2007
    In my previous post, .Net Assembly Spoof Attack , I've described potential DLL hijacking/spoof attack
  • Anonymous
    April 18, 2007
    Imagine if security was cool like Silverlight .... But security is not that cool, so the biggest challenge
  • Anonymous
    May 17, 2007
    My favorite design patterns is Provider design pattern (abstract factory – GoF definition) . I like it
  • Anonymous
    May 31, 2007
    I just finished building another security workshop that covers authentication and identity technologies
  • Anonymous
    January 14, 2008
    The pattern is also called Intercepting Filter, Pipeline, AOP, and may be few more&#8230; I am confused
  • Anonymous
    January 14, 2008
    The pattern is also called Intercepting Filter, Pipeline, AOP, and may be few more&#8230; I am confused