Saturday, September 8, 2012

Cross Domain XHR

Recently I was doing a project (REST web services) where there was an interesting implementation of a defense against CSRF attacks. You would login to the application and immediately be assigned a session ID in a cookie; along with this you would also be assigned an AntiCSRF token, in another cookie. Now this immediately means that both cookies are going to be sent across to the server each time and going to be verified each time. Hence, if this had been the only defense it would be pretty useless; as the additional cookie does..nothing.

In the application though, what was happening was..the cookie 'token' was read, its value grabbed and a new custom header called X-Security-token added in the header with its value. So if on login I get a cookie: token=abcd, the next time I say...do an Edit Profile...I have a new HTTP header called X-Security-token: abcd as part of the request header.

Now my first thought was, Ha, spoofable...the attacker just needs to write a little Javascript, read the cookie (document.cookie) and then add a new custom header and send the request off.

The data was all in JSON format and I wanted a POC to show so I thought I'd just have a simple HTML file with some Jquery code which would make an XHR request by doing all the stuff I talked about above. The code seemed all okay when I tested it on localhost. As in..I set a cookie with the domain as localhost and value as 'arvind' and tried writing JQuery to pick it up and create a new header. That worked and the request DID read the cookie, append it to the header..and send a request to localhost.

The moment I changed the URL to the actual site URL, the request never even fired. I could understand it if the cookie didn't get sent but the request never fired either. More reading revealed that this was due to XHR's limitation of sending cross origin requests. It just refused to send anything at all; I couldn't even see anything in Firebug. I change the URL to localhost..immediately an XHR request gets fired. I tried removing the cookie and resending it...no luck..same behavior. Posts to localhost. Okay. Anywhere else. Browser doesn't allow sending an XHR request anywhere else. Not yet totally clear what's happening.

The other strange thing though is that there is this addon called a REST client which is installed in the same browser and seems to be able to make calls happily to multiple domains other than localhost.

So the question is..What is the difference between an HTML file hosted on a local web server..making XHR calls to abcbank.com AND a firefox addon making calls (not sure if its XHR as I did not see an X-Requested-With header) to abcbank.com? Why does the latter work?

So as a CSRF protection...it doesn't seem safe but I'm not able to get it working with XHR at least. There's some suggestions elsewhere that some versions of Flash allow this; but right now I'm not sure. I'll update this later if I stumble upon something.

Sunday, August 26, 2012

SoapUI - XML Entity Injection

So another thing that I tried out with some help from the guys I work with was this attack called XML Entity Injection. It has been around for quite a while and there are plenty of resources on it so I won't talk about it too much. Here is an OWASP reference and another link which was quite cool and explained things well.

In my previous post I described how to use SoapUI through Stunnel to test HTTPS web services. So following up on that, I was using SoapUI to test XXE attacks as well. So I followed stuff given above on the link to try and read the passwd file from the remote machine (which I'd confirmed was a Ubuntu box). To my pleasant surprise it immediately worked and the entire /etc/passwd file got displayed in the Soap response. Yay. Victory jig. And all that ;)

I was brought down to earth though when I saw an account called 'arvind' in the response. For some stupid reason, SoapUI was retrieving my own passwd file and displaying it in the response. Huh?

So I set Burp up again and set Intercept to on to see what was happening. To my surprise, the request itself already had my passwd file..and the response was just reflecting it back. So even before hitting my own client proxy SoapUI had done 'something' with my request, expanded my own entities and THEN sent it to Burp. It wasn't ever reaching the server directly. Meaning..if I used SoapUI there wasn't any way to directly test XXE...unless there was some tweak somewhere where I could turn off request parsing.

Anyway since I had Burp as well in my proxy chain before it hit the server, it didn't really matter and I could test it in Burp. Turned out that the server was not vulnerable at all. Oh well. Maybe next time it will be ;)

SoapUI to Burp - Fuzz away

I was recently testing another web service (lot of them recently) and was using SoapUI as a client to invoked the WSDL. You don't HAVE to use SoapUI; its just that it was the most popular tool out there and seemed to do its job.

So one of the main tests in a web service is to fuzz all the methods. For the new guys it just means the following:

a) Identify the method and find out what arguments it has
b) Find out what valid arguments need to be passed for the method to work
c) Fill each argument with a huge bunch of malicious data specific to SQL Inj or XSS or any other type of injection and see how the server reacts

Now you could do this manually and put in a ' , < , > , #, OR 1=1 and so on manually and see what responses you get back. That, I guarantee you is not going to be too much of fun after around 10 minutes max :). So you want to automate this process.

SoapUI has its own security scan from version 4.0 onwards and this is what a large number of people working with web services tend to use. I'm not sure what I was doing wrong, but the free version allowed me to scan just 4 specific parameters [username, password, request and one more]. It has a huge number of scans; SoapUI but if it is not going to allow to me to fuzz the parameters I want, it kinda is useless. Maybe its because I was using the free version and the Pro version supports scanning all parameters. Anyone tried that out? If not, no worries, I will ..sometime :)

So now I thought of chaining SoapUI to Burp and using Burp to do all my fuzzing instead. This turned out to be harder than I thought and frustratingly very little good help on how to do it. Note that it was a HTTPS connection; if its HTTP it is easy enough. SoapUI seems to have something called a HTTP Tunnel which I guess you have to configure with keystores and trust stores...but whatever I did I couldn't get it to work. And I couldn't find any other fuzzers which would reliably work. I am sure there might well be something...I was on a deadline though; you know how that goes.

So I pinged a few of my colleagues for help and Max helpfully suggested that I use stunnel to make the SSL connection to the server instead. That actually worked and  I could get everything working. Here is what I did and why it worked.

a) Set SoapUI proxy settings to Burp - File: Preferences: Proxy Settings. Now load up any 1 request in the SoapUI request editor and edit its Endpoint to point to http://abcbank.com:443/blah/blah instead of https://abcbank.com:443/blah/blah. So it means...if you want a response for this method go to http://abcbank.com:443. This is just to ensure that the request gets to Burp...in the first place. If you keep the endpoint as https it gives you a 'Cannot cast to HTTP' error. I think that is because the proxy setting in SoapUI is ONLY for http.

b) Start Burp

c) Open Terminal (Ubuntu) ..probably CMD on Windows although untested and start stunnel as follows: sudo stunnel -cf -d 127.0.0.1:443 -r www.abcbank.com:443

d) Go to Burp - Options - Hostname resolution. This is the one to the left of the Alerts tab and set  the hostname of the remote site to 127.0.0.1. So you should have an entry in there which is Enabled and says:
www.abcbank.com 127.0.0.1

e) Load the WSDL up in SoapUI and invoke any method. Look into Burp; you should see a request in its history. Look into stunnel; you should see some data getting written to its console [Service stunnel3 accepted connection from 127.0.0.1:50318]. Yay. Done :).

f) The request is now in Burp. Uncheck the Enabled box in the Hostname Options in Burp. Now have fun with Burp Intruder/Scanner as usual.

For the curious..what exactly happened and why did this work? Well to start off, we simply set a proxy for SoapUI, so anything from SoapUI will go to Burp. Now Burp, like any other proxy needs to forward a request it got to the destination, else it'd be useless rt? ;)

Now just like your browser resolves a hostname to try and open up a site for you, Burp needs to do that as well...but it first looks into its hostname section to see if you've hard coded something there. You have..in this case.. www.abcbank.com = 127.0.0.1. So the SoapUI request goes to 127.0.0.1.

What's the destination port when you sent it from SoapUI? 443. And we haven't changed that in Burp. Its just a different hostname..that's all. So the traffic gets sent to 127.0.0.1:443.

And what's listening on 127.0.0.1:443? Stunnel of course. And Stunnel has been configured with the -r argument to forward all its traffic to abcbank.com:443.. So stunnel, since it understands SSL..completes the HTTPS connection with abcbank.com and returns the response to Stunnel - Burp and then SoapUI as well. Very very neat :)

Oh and once you have all of SoapUI's requests in Burp, you don't need to use SoapUI any more; you can just use the awesome Burp. You also do not need Stunnel anymore..as Burp can understand HTTPS by itself. The reason we needed Stunnel was because SoapUI did not seem to directly understand SSL. I am NOT stating this as fact..because I'm not sure; but certainly, from what I searched and worked with, it isn't that easy.

I hope that helps anyone who is trying to get this setup. Again big thanks to Max, Google ;) and this post.

Thursday, August 2, 2012

ASMX Webservices - XSS

I tested a few public Web services recently. 1 of them had a front end so it was easier to visualize but that apart it was quite tough, specially as numerous methods were so complex that the developers had a tough time trying to answer some of my questions.

Now assuming that the application that consumes the web services is not in testing scope, all you have is the .asmx and the .wsdl. At times, these methods might be invokable from the browser itself, via the ASMX web interface like this. Other times invoking is restricted to the local machine alone, in which case you have to use a third party client like SoapUI or write your own using a library. I wrote mine using a library called Suds (Python). Obviously, writing the client is more work and if the arguments that need to be passed are complex, it can be quite tricky.

There are 2 ways to test for SQL Injection or XSS. In my case I could invoke the methods via the browser, so that made it easier and I could find a SQL injection.

a) You can code your custom client and fuzz through that.
b) You can simply write a very simple client, with Burp set as a proxy. You can then use Burp Intruder or its inbuilt scanner to fuzz the application.

I wasn't lucky with the XSS though. The content type of the response was text/xml. I saw a few attack vectors for XSS in xml but all of them involved closing the existing XML tag but for any of them..I'd have to break out of the existing structure. And < and > were getting encoded..to &lt and &gt. So unless I could do that, I couldn't see anything anywhere that would make this vulnerable to XSS.

And much like my Flash post earlier, the content type is text/xml. So unless I could find a way to get a browser to forcefully treat it as text/html, there wasn't going to be a way to do this.

A colleague said this - "...In terms of triggering XSS it will be harder unless you can convince the client to render it using an XSLT" coz that would convert the XML into HTML. But I wasn't sure how I'd go about this. And then I ran out of time :).

So here I am. You guys know of how this is possible?

Update: I posted to the list and had a few ideas here.

Testing a Flex application

So I have been testing quite a bit recently. A while back I ran into an application which had a Flex frontend. The Flex UI talked to a backend server which ran Flourine FX. This eventually talked to a .NET application - MSSQL Db combination. The Flex client used AMF 3.0 to talk to the server.

This whole thread by the way is just a sort of a rant on how I could NOT do things and all the things I failed at. It offers no solutions. It is however interesting if you want to know what to avoid. If that's okay..read on.

Now I knew that Burp had support for AMF for sure. And the application was browser based, so everything should have been normal. Testing for SQL Inj, XSS, Authorization bypass tend to take the most time in a test. Usually though, if you can reliably intercept and replay traffic, it is quite doable. I had no reason to think that this would be anywhere different; considering that Burp talked AMF.

a) Authorization Test

Now, this particular app had 2 types of users: user & manager. So I tried to replay a manager request as a user, but it kept failing. So I think..okay..protected. Then I took a menu which both users had access to. Replayed request. Fail. Huh? Both have access, why should it fail? Something very funny going on. Or maybe I have no clue (more likely :)). The last test I did was trap a user request and replay it as the same user, inside the same session, inside the same TAB. Surely this should work?? FAIL. Huh?

Now I'm confused. This means that something is happening ON the client itself. Sent 2 user requests to Burp Comparer. Turns out there are 3 values that change with every request. They are: ClientID, MessageID(under body) and DSId (under body and then headers). Now the ClientID and DSId didn't seem like they were too important, as in, tampering with those didn't give me an invalid request. However anytime I touched the MessageID, I was rebuffed.

So drilling down further MessageID seems to be of the structure of a 32 bit Guid. Spoofing an older valid message ID or a newer message ID or a pre-generated but not sent (Dropped request) message ID all fail. There is nothing that comes back in the response either; like an Anti CSRF token in a hidden field. So I am sure it is nothing that is stored on the server. If it isn't though, how does it recognize just THAT ONE message ID? And no... it does not seem to be all client side either. This is because I could see AMF requests being sent; dropping them also caused an error.

b) SQL Injection and XSS

At this point I hit a limitation with Burp. In a normal request (non AMF) you can add, modify and delete parameters. Right? So in AMF, while I can still modify data in individual parameters, I cannot add or delete anything through Burp.

This probably has something to do with the structure of the request. I tried Charles too, but have the same problem. Now I can sit and manually put a single quote and < > in every parameter but I'd probably die before I complete the test. Meaning...I cannot fuzz every parameter reliably using Burp. That's cause although there is repeater and intruder support to parse AMF, it doesn't detect the exact places properly...so I can choose which parameters to fuzz.

The closest I came was to carefully look at the 'Raw' request which tended to be just 1 value and fuzz just that. I got a few errors here but nothing concrete from a SQL Inj perspective. Ditto XSS. I tried deblaze, Pinta and a ton of tools which are already out there on the OWASP Flash page. None worked. It almost certainly meant I'd have to write my own client specially for FlourineFX. A custom BlazeDS client written by a colleague also failed. On this particular engagement I ran out of time.

The last thing I wanted to talk about was that the Response content type was x-amf. So all the Stack overflow and Google threads I read, talked about how this was real hard to do. I bounced this off a few guys and everyone did say...If there is no HTML content type responses...you can't get JS to execute. Which made sense.

c) CSRF

The fact that the message ID was 'unspoofable' automatically gave this Flex app protection against CSRF. No token. No nothing.

So in a nutshell, its super hard to test for SQL, XSS, CSRF and Replay traffic with existing tools. Almost certainly a custom FlourineFX client has got to be written. How and when and by whom I don't know. Maybe I'll write one some day :)

You guys have any ideas on how anything could have been done better? I saw a talk on BlackHat12 which talked about this. I'll check that out. That apart..anything?

Friday, May 11, 2012

Reverse Engineering - Android APK

There's nothing really complex about this post. In the past I've always maintained that reversing is kind of tough; and that's true if its an EXE,DLL etc. But in the case of an Android application; it really is very easy.

While all this information is already there, here is a very short blog post summarizing how you get from APK to Source. I used a Vuln app available here; but you can use anything really.

If all you want is the source, do the following:

1. Use dex2jar downloaded from here and run ./dex2jar.sh . This results in a JAR file getting created in the directory where the APK is already present. The JAR file contains all the JAVA class files; namely the Java byte code - something that you get once you compile your Java code.

2. Convert your Java byte code into actual Java code. You need something called a Java decompiler for this. You can download one called the Jd-Gui from here - http://jd.benow.ca/#jd-gui-download.Load the JAR into it and use the 'Save all sources' feature to save all the source (Java) files to your disk. Now you can review it like you would review any Java code.

Some other interesting things about APKs though:

1. An APK can be extracted to a folder. Its just a Zip file so any archiving program should do; I use the inbuilt Ubuntu GUI archiving tool. You can also use unzip, 7z, WinRar or anything you want.

2. Look at the file AndroidManifest.xml. It'll open in a Text editor but its largely binary; hence unreadable. Use Apktool to decode this XML file as well as every other XML file in the APK. You can get it from here. Run apktool against the APK. It'll run and give you all the XML files totally decoded; so you can now read them.

3. All the application code is in classes.dex. This is Android Byte code, reversible to Java Byte Code. So we first 'dedex'. Use 'dedexer' that can be found here. Run it as follows: java -jar ddx1.22.jar -d classes.dex.

Nothing in this post is original. I just wanted a place to refer to instead of Googling a million times for the syntax.

Thursday, May 10, 2012

Market app - Android 2.2

Was doing a test on an Android app (first ever ;)) and was trying to install an app which was available on Android market. As it turns out, the emulator doesn't have the app pre-installed. So I followed instructions here. That largely works except that despite following everything the app vanishes the next time around. So after more digging I came up on this thread which provided the missing piece. I'll sum it up quickly.

--- You need to edit files on the emulator which will prevent the emulator from checking if its a valid phone or not
--- You need to upload the packages for the Market app and the GoogleServicesFramework as those are not shipped
--- You can do both of the above only if you have WRITE access to the emulator's system directory.

So far everything is covered by Varun's blog. The 1 point which he hasn't made clear is that once you've pushed all your changes to build.prop, uploaded the 2 apps mentioned above and deleted SdkSetup.apk you have to sync your changes and save the temp image in which all these changes are made.

Think of it in this way..all the changes you make are temporary and made in a file /tmp/android-. The filename starts with emulator. Once you're done making your changes save this file somewhere. Shut the emulator down. Now rename the saved file to system.img and copy it into ~/.android/avd/.avd. Now boot the emulator. It should work.

I've said nothing new frankly. If you use Varun's post and the post on the XDA forums together, you will be able to do this. However I was stuck for quite a while here, so thought a few guys would benefit by me linking the two together :)

Saturday, May 5, 2012

Blogging elsewhere for a bit

I've been blogging at Infosec Institute (a little :)) and on the TeamMentor development blog (a lot) ... so that's why this isn't as updated with my experiences. Do peek at my work at II or on TeamMentor if you're interested in knowing what I am up to :)

Wednesday, April 4, 2012

Olly - Hit trace..finding code flow

Many a time we come across malware which is extremely confusing and has lots of JMP and CALL statements. It becomes very difficult to find out what exactly the malware is doing; if you use a purely manual technique..and you start seeing stars after a while. At least I did :)

So to help you understand the control flow better you can use something called a Hit Trace in Olly. Here is how you can best use a Hit Trace:-

a) Load the executable into Olly. You'll have to use 2.01; I couldn't find this in Olly 1.10.

b) Till what point in the code, do you want to understand code flow? Identify that point and set a breakpoint there using F2.

c) Once you've set the breakpoint, navigate to Trace - Run hit trace. This will automatically run the malware until the breakpoint that you had set earlier.

d) If there's some anti debug measures or the process simply exits before your breakpoint...you won't be able to see the Hit Trace at all. However, if the program is still active, you should see a little red dot to the left of each assembly instruction. This just says....'This instruction has been run at least once'.

You will notice a lot of gaps in between the 'red dot' lines. That is because those instructions were never triggered at all. You'll see this specially in cases of JMP instructions.

There's another feature called 'Run Trace' in Olly and the way to use that to identify code flow is to Log to File and then study the log.

Or lastly (as far as I know) you can set breakpoints and then use the 'Trace Over/Into and Animate over/Into) to step into and over code interactively using the '+' and '-' keys to go forward or back.

But the Hit Trace is quite neat and it offers a very nice option to identify control flow. Until next time ...bye :)

EXE dependencies - Read from PEB

I was trying to understand where executables load all their dependencies from. So for example: When I load up minesweeper (winmine.exe) there are a host of additional DLLs that are loaded up as well. That's fine as there are functions inside each of those DLLs that winmine uses. What was interesting to find out though, was how the list of those DLLs was built in the first place. Where did the OS loader look...into the process..to find out 'what else to load'?

So I loaded up winmine.exe in Olly, Dep Walker and a few other tools to get an understanding of 'what all' was loaded. Once that was done I read up a little about the PE header to understand where dependencies are accessed from. In PE terminology, these are called imports. It turned out there was a Data Directory for the Import Table. So i thought; lets read the import table; that should give me a list.

So I wrote a little bit of Python code [after learning Python from Google's Python class ;)] to read the IMPORT TABLE from the PE header. This did give me quite a few DLLs but it still did not tally with what Olly was displaying.

The next thing I did was to modify my code to be recursive. So...

--- Load EXE. Get dependent DLLs from import table.
--- Load 1st DLL from previous list. Get its dependent DLLs. Add to list.
--- Load 2nd DLL from previous list. Get its dependent DLLs. Add to list.

And so on... until all dependencies were resolved.This was doubtlessly an improvement as I was closer to what was displayed in Olly [Alt+E]. It still wasn't complete though.

Then I read some more, read how Dependency Walker works, asked on Woodmann and re-read a few sections from Xeno Kovah's Life Of Binaries class. Turns out there are somethings called Delayed Imports. These aren't loaded statically at load time; like the Import table but only when a particular function needs to be called..later on...at runtime.

So I modified the code a little to recursively get all the DELAYED IMPORTS too. This would have been enough but it gave me a huge huge list which contained much much more than what Olly ever showed me :). So obviously this wasn't efficient either and it was something else.

So as usual when I'm stuck I bug the nice guys on Woodmann and I'm rarely disappointed. This time was no exception and I was pointed in the direction of something called a PEB.

The PEB or the Process Environment Block is apparently the only "part" (very loosely used) of a process that is in User Mode. Everything else is in Kernel mode. So if you want to find out every DLL that an EXE depends upon; its best to query the PEB instead of doing all that stuff I did earlier :)

I want to quickly touch upon the structure of the PEB before I finish this post. To look at the entire structure of the PEB you can visit this link. You need to query the PEB_LDR_DATA structure to get the list of Loaded DLLs. Here is an article that I found quite useful while I was learning stuff about all this.

And lastly..here is the complete thread of my discussion on Woodmann, if at all you are interested :).

Wednesday, February 8, 2012

Links - All recent articles

I've been primarily writing for Infosec Institute these days; so there's very few updates on my blog. I could duplicate stuff here; but that's not of much use to me or anyone :). So if you're interested in what I'm writing about, do take a look here.

Wednesday, October 12, 2011

Freelancing - Infosec Institute

I recently started writing for Infosec Institute on a freelance basis. You can read all my articles here.

Sunday, September 25, 2011

Reverse Engineering - Know your tools...

I've talked quite a bit about what tools to use and when in general. While all that is correct in principle, I recently, after a lot of painful 'research' [mostly already out there somewhere] , came up with a process for myself to use the right tools at the right time. Here is a short summary of the same:

1) Do your dynamic analysis and document what you found.

2) To learn more you have to now do static analysis; don't start off with IDA Pro; it overwhelms you very quickly... specially if you are new.

3) Put the EXE through Olly or Immunity and start identifying what each function does, step by step. I'm just saying... don't be worried initially about understanding everything about the malware. If you can even confirm what you found in dynamic analysis, via static analysis and say that...I know what these 5 functions do...that's good enough for a start.

4) Now once you know what these 5 functions do, open the EXE up in IDA Pro and rename the 'known' functions from sub_4012345 to something meaningful, like sub_malware_connect_irc. Repeat for each function you know. Go back to Olly now.

5) Now take each function(known); say sub_malware_connect_irc and identify all of its system function calls.. connect() send() getcommandline() etc etc.

6) Look at MSDN and understand the arguments that are passed to each. See where these arguments are stored in the disassembly you have. Is it stored on the stack or in a variable?

7) If its in a variable go to IDA and give that variable a meaningful name. So for e.g rename something like dword_ptr_401324 to malware_irc_host-name. This will result in every single place where that variable is accessed, getting renamed to the new variable. So dword_ptr_401234 will no longer exist; it will be referred to as malware_irc_host-name. Repeat this process for all known functions and all known variables.

8) Once you have a few functions and all corresponding variables renamed, use the GroupNodes feature in IDA (Right click on any block, select GroupNodes) to collapse blocks you have already analysed. Give each block a name that you will recognize instantly, without having to look at the disassembly again. Repeat this for all blocks that you have analyzed. So this will reduce the disassembly that you have to look at, in other parts of the program you have not yet analyzed.

9) So now, to summarize, for all known functions you have renamed the functions, renamed the variables, and grouped blocks of code that you have already analyzed and named the block. This should give you a nice 'pseudo codish' flowchart in IDA for quite a few functions :)

10)  Now use the 'Functions' submenu in IDA and sort by the first column to see how many functions are pending; you can get this by seeing how many start with sub_.

11) Go to each function and see where it is called from. You can do this first in Olly 1.10 by highlighting the first line (usually PUSH EBP) of the function and looking in the middle pane on where all it is called from. Visit each of the calls in the middle pane and see where they were called .. and so on. Do this till you get to the root of the call.. see if you can now understand 'when' it was triggered.. 'What' behavior triggered it? Do the renaming and grouping as before. If you can't understand.. at least give the function a name.. some name.. like dummy_notunderstood_1, dummy_notunderstood_2 and so on. That still is better than sub 401237.

12) At the end of all of this you should have a .IDB file fully named (as much as possible) and fully grouped. Now ..only now should you start drilling down into HOW exactly each function works...the exact algorithm behind each function and so on. Repeat this for as many interesting functions that you want.

13) Once this also is done, if you WANT , try rewriting this in a high level language, at least pseudo code so you can quickly refer back to it when you want.

I guess, this is all very intuitive for most reversers who have learnt this on their own or been reversing for a long time. It took me a long time though, to reach this level and hope it is helpful to any relative newbie reading this blog post and feeling lost. I know I was one a few months ago ;).

p.s.... Make sure you back the .IDB file up ;)

Here are 2 sample screen-shots:
Sample Graph of Grouped Functions  


Renamed functions - A sample list

Thursday, September 22, 2011

Debugging threads - Olly

Recently I was debugging a piece of malware which launched numerous threads inside, after it ran. Now, after the thread spawned, I could no longer F7 or F8 my way through the malware and understand things. This was because it was the thread which was doing all the work. So somehow I needed to get into the thread.

The first thing I did was 'Right click' and then select a thread from the Threads sub menu. That though just seemed to take me to system space, which was kind of useless. I wanted to see what the Thread did in User Space.

I looked at the CreateThread API then, which was what was being used. The 3rd argument to the function was a start address for the thread. I did a Ctrl+G, went to that address in Olly and put a breakpoint there, and then restarted the program. Went on as normal till CreateThread and then F9'd to run till next breakpoint. The main thread still "hung" but I did break inside UserMode for the Thread and could debug it.. yay :)

If you want to break even before UserMode and want to track it the moment the thread is launched, you can set debugging options in Olly to break each time a new thread is started or stopped. There's simple check boxes under the Options menu. Go search :)

The last bit is when  the Thread itself exits..it just says Thread Terminated and you again cannot F7 or F8 because there is nothing left to F7 or F8 into. You need to get back to the main thread, where the CreateThread API was called. Makes sense ..rt? Main.. created a thread...I debugged thread...now I come back to main...once I finish debugging the thread.

To do so, pause the program(F12) after the thread terminates and hit Alt+F9 to return to user mode. This will bring you right to the spot after CreateThread was first called.


Hope this helps someone newish to reversing :). Have fun!!

Saturday, July 30, 2011

12.3 - Example - Static Malware Analysis(Continued)

In the last part we saw that a part of the code launches an embedded instance of IE. We also have Wireshark running so we can capture any network traffic that is sent by the malware. We also broke last time at 40B511, exiting from the thread that created IE. Lets move forward quicker now and see what else happens.

Remember that the more functions you can identify; the easier it is for you to analyze the overall purpose of the executable. There are a few CALLs that happen which just try and find out which directory a file was from or do other relatively unimportant operations from a malware perspective. We then come to a call - CALL 0040B849. On going deeper into this function you will find that its a very interesting function which logs all the operations of the malware into a file in C:\. So that now is another bit of information that we can tally with our dynamic analysis. And since its logging stuff... it also gives us some nice inputs about what the malware is doing at a specific amount of time. Open up the file soft_AOL.log in C: and see for yourself. Another key point that you'd want to know is that this function is also a very common function - look at the middle pane again in Olly just after you step into it. It has a lot of addresses from where a call was made. For e.g:
Local calls from 00401729, 00401754, 004017D8, 004019B6, 004019D8, 00401B85, 00401C5B, 00401D13, 00401D6C, 00401F3E, 00401F99, 004026F6, 0040278B, 004027C6, 00402894, 0040293D, 00402ACE, 00402B1F, 00402B69, 00402B71, 00402B7B, 00402BA5, 00402C4A, ...

At 40B56B the existence of a file c:\Windows\lgv is checked. Its not too clear why it does this at this point; maybe its confirmation that the malware is active and more stuff can be done. Keep looking at Wireshark by the way - the moment you see some data there, you know you have to stop and go back and see where the traffic came from. So lets F8 on till we come to a call at 0040b679 - CALL 004029B8. Step over this as well and then quickly look at Wireshark..its suddenly filled up with traffic. That means the previous CALL was very important. Put a breakpoint on that call and restart; when you get to the CALL step into it. Starting at 4029B8 F8 on till 402A08 where Wireshark starts filling up again. Put another breakpoint, restart and step into the CALL at 402A0B this time. And so on..you keep stepping in till you find out exactly where the call is and why Wireshark is filling up. Once you step into the CALL at 402A0B you reach the address at 0040B01A. Now look at the code below..lots of comments there and some very interesting ones. I won't talk about every single CALL, I'll never finish that way ;). Before you move on though, do step into the call at the address 40B04B - its the routine which decides the list of domains that the malware will talk to at some point. There's a small encryption algorithm in there.. do try and see how the names of those domains are generated. Notice all that text btw? "scan domain attempt" or "check inet"... all of that goes into that log file in C: . Have a look.

Go on till you reach 40B0AC where there is a JMP 40B113. This means that control flow switches to this address. F8 so the JMP happens and at the very next instruction jumps back to 40B0AE. F8 on till you reach 40B0CB and look at the EAX register on the right side. You see a weird looking site there? Yes you do :). Now that is a big piece of information..maybe maybe the malware connects there for some purpose? Go on til 40B0E2 and look at EAX again. You see something called .sys.php? Looks like a part of some URL. Things are getting interesting now..aren't they? Go on till 40B0F8. Look at Wireshark and notice that nothing has happened so far. F8 over the CALL 405086 statement and now look at Wireshark. Yesss!! Traffic seen..and its a HTTP request made to that site we saw in EAX and for the file .sys.php. Look at the response to the request though in Wireshark - its a 404 not found. The malware did not find what it was looking for. How does it respond? F8 on and you'll notice that you get to the same point where you jump back to 40B0AE and repeat this same stuff with a new site. This process continues until some site responds with a 200 OK message, saying "Yes I have that file". Put a breakpoint on 40B17B so the code just doesn't connect and complete the remaining process before you can intervene.

The code returns eventually to 402A10 and continues from there. Lots of interesting stuff but just continue on till you reach 402BA0. "Crypted Code detected".. hmmm. Something encrypted was returned when we made a request for .sys.php and the malware is decrypting it for some reason. How does this decryption work? Do not know. F8 on till you reach 402BE5. Look at the contents of the EBX register now? See a message there with a URL that looks like Internet Spam?? Right click on the EBX register and say "Follow in Dump". The whole URL is very clearly visible now!!

I think the rest is guessable. This malware connects to a huge list of random sites, finds an active on, requests a URL from it, gets an encrypted message, decrypts it and then posts it on lifestream.aol.com which is AOL's social media platform using some user ID and password. If you continue stepping through the code you will also find out the credentials that are used each time. I tried it 3 times and found 3 different passwords - I think it creates a new account, posts Spam and logs out. But hey..don't take my word for it. Try it out for yourself :)

At one point of time the Embedded IE window can be viewed completely and you can actually see malware entering credentials into it and coming back with a "Cannot Login" message.

I still have questions about some parts of this malware and could not fully understand every bit. For e.g I could not find out how the SSL connection which we talked about during dynamic analysis was established. But I'm sure its all a matter of time and thought that all of this itself is a good learning and many newbies to this field can gain something from it.

I hope you enjoyed this and you feel reversing is doable by you as well. Until next time goodbye :)