Edit: This post originally incorrectly stated that JScript is used by both ASP and ASP.NET. This is not the case, as ASP.NET has its own engine called JScript .NET. The text below has been edited to reflect this.

A while ago, during an application assessment, I came across something I had never seen before. As I googled for more information, and also asked around on Twitter, I realized that what I had found appeared to be unknown to a lot of people. Since then several people has asked me to provide some sort of write-up, and this is a (very) brief attempt of that. As the assessment was performed under a non-disclosure agreement, no information about the application in question will be provided, and all code examples are generic (although the bug itself is not).

The thing

While auditing the code of an ASP application, I came across a file called something like XMLparser.asp wich had the following header.

<%@ CodePage=10001 Language=JavaScript %>

This confused me a bit as I had never heard of ASP having a server-side JavaScript engine, but it was quite clear that the file in question contained JavaScript and nothing else. I did some quick searching online and found that the JavaScript engine used by ASP is called JScript (ASP.NET has its own called JScript .NET) and is also used by Internet Explorer up until version 9.0. At this point, I was very interested as to where this could lead and proceeded to reading the code. I soon came across a block of code that looked something like this:

var my_string = "";

var my_list_length = someList.length;



(...)



for (var i = 0; i < my_list_length; i++)

{

type = someList[i].attributes.getNamedItem("type").text;

if (sType == "xml")

{

my_string += "'" + someList[i].childNodes.nextNode.xml + "',";

}

else if (sType == "string")

{

my_string += "'" + someList[i].text + "',";

}

(...)





It didn’t take too long, especially considering the name of the file, to figure out that this was an XML parser going through an XML document, picking out values and adding them to the my_string variable. What made it really interesting though was what came a little bit further down.

XMLresponse = eval(my_string);

I started tracking backwards from this function to see if there was any way to get my input to be parsed and added to the my_string variable, and I soon found it.

Verifying the issue

My first action was to see if I could get a payload through and have it executed. Verifying server-side JavaScript injection is not as straight forward as the client-side equivalent, as you cannot just go with alert(1) for obvious reasons. After a little bit of thinking, I figured out how to inject a simple time delay just to prove that it was actually possible to exploit it. However, I still had no idea what could be achieved with this bug as I had no information about the capabilities of the JScript engine.

Search and destroy

At this point I decided to do some googling and also to ask Twitter if anyone who followed me had encountered this before. Surprisingly enough, very few seemed to even be aware that this functionality existed in ASP, and even fewer had any useful information about it. Searching some more online, I found some basic info about mixing VBScript with server-side JavaScript, but not much about how or even if it was possible to access the underlying system in any way.

And then, I found this site. Using the information from the site, I realized that by invoking an ActiveXObject in JScript, it was possible to execute plain VBScript. At this point, Remote Code Execution was inevitable and it did not take me many minutes to produce the following Proof of Concept payload which worked like a charm (encoding and escape characters removed for brevity).

(function(){var ws = new ActiveXObject("WScript.Shell" );ws.Run("ping my.ip.addr.ess");}())

Summary

Although the bug in itself is not really that interesting (don’t use eval() if you don’t have to), the realization that ASP and ASP.NET has a server-side JavaScript engine that can invoke system functionality took me and a few other people by surprise. Some take-aways for me:

ASP and ASP.NET has the ability to execute server-side JavaScript using the JScript (or JScript .NET) engine. This appears to have been unknown to many, including myself.



By invoking an ActiveX object in JScript, it is possible to create VBScript objects such as WScript.Shell and Scripting.FileSystemObject.

Exploitation of this may be via eval() as in this example, but also via stored XSS, and potentially also reflected XSS in the right (or wrong) circumstances.

As ASP.NET runs compiled code, dynamically injecting JavaScript will not work, with the exception of when eval() is used*

*I found this information on a Microsoft website that I cannot find right now.

Edit: ASP.NET uses JScript .NET, more info here.

It should be noted that I am not an expert in ASP, ASP.NET, or VBScript, so please feel free to point out any errors or additions that should be in this text.