Latest Entries »

In the last months I spent a lot of efforts in Thug development. During these months a few interesting features and improvements were introduced but right now I want to spend some time for taking a look at the new plugin framework introduced in the version 0.3.0. If you ever thought about extending Thug with additional features but didn’t know how to do it you should really keep on reading. Let’s start by taking a look a the code.

Taking a look at src/thug.py we can now read these lines of code

 

216 if p:
217     ThugPlugins(PRE_ANALYSIS_PLUGINS, self)()
218     p(args[0])
219     ThugPlugins(POST_ANALYSIS_PLUGINS, self)()

 

Please note that every operation done by Thug is started by line 218 but now you can see that two hooks exist in order to execute plugins in a pre and post-analysis stage. Let’s keep exploring the source code and let’s take a look at src/Plugins/ThugPlugins.py

 

34 class ThugPlugins:
35     phases = {
36                         PRE_ANALYSIS_PLUGINS : ‘ThugPluginsPre’,
37                         POST_ANALYSIS_PLUGINS : ‘ThugPluginsPost’
38                       }
39
40     def __init__(self, phase, thug):
41         self.phase = phase
42         self.thug = thug
43         self.__init_config()
44
45     def __init_config(self):
46         self.plugins = set()
47         config = ConfigParser.ConfigParser()
48
49         conf_file = os.path.join(os.path.dirname(os.path.abspath(__file__)), ‘plugins.conf’)
50         config.read(conf_file)
51
52         plugins = config.get(self.phases[self.phase], ‘plugins’)
53         for plugin in plugins.split(‘,’):
54             self.plugins.add(plugin.strip())
55
56     def __call__(self):
57         self.run()
58
59     def run(self):
60         for source in self.plugins:
61             module = __import__(source)
62             components = source.split(‘.’)
63             for component in components[1:]:
64                 module = getattr(module, component)
65
66             handler = getattr(module, “Handler”, None)
67             if handler:
68                 p = handler()
69             try:
70                 verifyObject(IPlugin, p)
71                 p.run(self.thug, log)
72             except BrokenImplementation as e:
73                 log.warning(“[%s] %s” % (source, e, ))

 

and src/Plugins/plugins.conf

 

1 [ThugPluginsPre]
2 plugins: Plugins.TestPlugin
3
4 [ThugPluginsPost]
5 plugins: Plugins.TestPlugin

 

The configuration file plugins.conf defines which plugins are to be loaded in pre and post-analysis stage (you can specify many plugins by simply comma separating them). The plugins should contain a class named Handler which should be conform to this interface

 

21 class IPlugin(zope.interface.Interface):
22     def run(thug, log):
23     “”"
24     This method is called when the plugin is invoked
25
26     Parameters:
27     @thug: Thug class main instance
28     @log: Thug root logger
29     “”"

 

If the interface is correctly implemented the `run’ method is called with two parameters: the Thug class main instance and the Thug root logger. Let’s see a really simple example of plugin

 

20 import zope.interface
21 from .IPlugin import IPlugin
22
23 class Handler:
24     zope.interface.implements(IPlugin)
25
26     def run(self, thug, log):
27         log.debug(thug)
28         log.debug(log)

 

This plugin just logs the parameters but you can do whatever you want. Do you want to pre-check if the URL domain is within a blacklist? Just do it with a pre-analysis plugin. Do you want to extract and/or correlate information from the MAEC log files? Just do it with a post-analysis plugin. Simply staten… have fun!

I’m glad to announce I publicly released a brand new low-interaction honeyclient I’m working on from a few months now. The project name is Thug and it was publicly presented during the Honeynet Project Security Workshop in Facebook HQ in Menlo Park. Please take a look at the presentation for details about Thug.

Just a few highlights about Thug:

  • DOM (almost) compliant with W3C DOM Core and HTML specifications (Level 1, 2 and partially 3) and partially compliant with W3C DOM Events and Style specifications
  • Google V8 Javascript engine wrapped through PyV8
  • Vulnerability modules (ActiveX controls, core browser functionalities, browser plugins)
  • Currently 6 IE personalities supported
  • Hybrid static/dynamic analysis
  • MITRE MAEC native logging format
  • HPFeeds and MongoDB logging

The source code is available here.

Feedback and comments welcome.

Have fun!

Forensic Challenge 8 – “Malware Reverse Engineering”

I am pleased to announce the next forensic challenge: Forensic Challenge 8 – “Malware Reverse Engineering”.

The challenge has been created by Angelo Dell’Aera and Guido Landi from the Sysenter Honeynet Project Chapter.

Submission deadline is June 15th and we will be announcing winners around the third week of July. We have a few small prizes for the top three submissions.

Have fun!

Angelo Dell’Aera
The Honeynet Project

Another challenge is ready to be tackled by forensic analysts, students, hackers and alike. This time, we present you with an attack vector that has become quite successful: malicious PDF files!

For challenge 6 of our series (provided by Mahmud Ab Rahman and Ahmad Azizan Idris from the Malaysia Honeynet Project Chapter) we present you with a pcap file that contains network traffic generated by the following scenario: An unsuspecting user opens a compromised web page, which redirects the user’s web browser to a URL of a malicious PDF file. As the PDF plug-in of the browser opens the PDF, the unpatched version of Adobe Acrobat Reader is exploited and, as a result, downloads and silently installs malware on the user’s machine.

We prepared a set of questions that requires you to dive deep into the portable document format. Submit your solution by November 30th 2010. The top three submissions will receive small prizes.

Enjoy!

Christian Seifert
Chief Communications Officer
The Honeynet Project

The first one writing about this new threat was Marco Giuliani. So, Murofet or Zeus++?

Taking a look at a couple of samples we were able to identify:

- Same API hooks
- Same encryption routine for configuration file (RC4)
- Pretty much the same configuration file format

Here you can take a look at a decrypted configuration file. It’s possible to realize that it makes use of the same block-based structure of Zeus configuration files. Just like any other Zeus it has a block with id 0x214e (at offset 0x1c) where the version of the builder used to create the bot is stored (at offset 0x2c). In our case that is 2.1.0.7.

So what about calling it just Zeus 2.1 ?

Trojan Carberp

I’m interested in infostealers and specifically in banking-trojans so I didn’t want to miss this one. Samples of Carberp are floating around at least since last spring but in late September we saw such numbers increasing.

Taking a look at how Carberp hooks API it looks like yet another Zeus “clone”. What I found interesting is how it hooks system calls. This is how a normal syscall looks like

MOV EAX,0xce // ZwResumeThread syscall id
MOV EDX,0x7FFE0300 // pointer to KiFastSystemCall
CALL DWORD PTR DS:[EDX]
RETN 0x8

And this is how the hooked syscall looks like

MOV EAX,0xce
MOV EDX,0x00152958 // pointer to fake KiFastSystemCall
CALL DWORD PTR DS:[EDX]
RETN 0x8

Instead of overwriting the first instruction(s) with a JMP/CALL to redirect the execution flow to the hook, Carberp substitutes the pointer to KiFastSystemCall. This is nothing new but it is actually enough to hide such hook from most of the “anti-rootkit” products out there (including rkunhooker).

– “it bypasses DEP and ASLR using impressive tricks and unusual methods” – Vupen

– “it uses a previously unpublished technique to bypass ASLR” – Metasploit Blog

- “exploit uses the ROP technique to bypass the ASLR and DEP” – ZDnet/Kasperky

– “it’s so scary I ran away screaming” – anonymous

Is that PDF so scary? I don’t think so.

DEP is an hardware feature that prevents execution of data, it obviously works if software sets the execution flag only on memory pages containing code.

If you VirtualAlloc all of your memory with PAGE_EXECUTE_READWRITE DEP can’t help.
If you opt-out, it can’t help.
If you disable it system-wide.. guess what.

Is “directly executing injected data” the only way to get “arbitrary code execution”? Answer is: nope.

It is possible to get “arbitrary code execution” by taking advantage of the call/return mechanism of x86. This was called ret2libc more than ten years ago and it works by injecting fake stack frames instead of code. The return addresses of those stack frames are used to jump to code already in memory that belongs to main executable or libraries. By chaining stack frames, if enough functions are present in memory, you can achieve “arbitrary code execution”.

Since windows is pretty happy to give you memory with write and execution permissions and there are even a few api to programmatically disable DEP, there’s no really need to use ret2libc to implement the entire shellcode. Instead you use it to call just a couple of functions or “pieces of functions”(gadgets) to ask for +RWX memory, copy the shellcode there, jump to it. All you need is the addresses of those functions/gadgets.

Is that a DEP bypass? nope. but it’s smart and convenient, isn’t it?
Is it something new, at least in the wild? nope.
ret2what? ret2libc, but cool guys now call it ROP.

ASLR is a software feature that randomizes memory allocations and should stop ret2libc because it makes hard to guess the location of a piece of code. It works if software does not give the attacker too much control over memory allocations.

If software does leak pointers ASLR can’t help.
If you don’t opt-in, it can’t help.

How that scary exploit works? It uses heap-spray to fill the memory with fake stack frames and ret2libc to “bypass” DEP as describe above, the addresses of functions/gadgets used to put the shellcode in an +rwx area come from a DLL that does not opt-in to ASLR.

Is that an ASLR bypass? nope, it’s sounds to me like bypassing ASLR when ASLR is disabled.

Forensic Challenge 5 – Log Mysteries is now live! This challenge takes you into the world of virtual systems and confusing log data. Figure out what happened to a virtual server using all the logs from a possibly compromised server.

Challenge 5 has been created by Raffael Marty from the Bay Area Chapter, Anton Chuvakin from the Hawaiian Chapter, and Sebastien Tricaud from the French Chapter. It is a bit more open ended than the last challenges, so I am really looking forward to some creative answers!

Submission deadline is September 30th and we will be announcing winners around October 21st. We have a few small prizes for the top three submission.

Enjoy!

I’ll tell you the truth: Export Address Table Filtering, the feature of the upcoming release of EMET, “designed to break nearly all shell code in use today”, intrigued me a bit.

Since I wasn’t able to find docs about the actual implementation, I started to think about how that could be done and I wrote a simple POC that uses VirtualProtect to flag the relevant pages of the .data section of ntdll and kernel32 with PAGE_GUARD to intercept read operations over the PEB.Ldr. A Vectored Exception Handler is then used to handle the exception and to check if the faulting address is within the code section of a module(MEMORY_BASIC_INFORMATION.Type == MEM_IMAGE). Here is the pseudo-code:

BOOL WINAPI DllMain(...)
{
    [...]
    AddVectoredExceptionHandler(1, VectoredHandler);
    VirtualProtect(PLDR,
        PAGE_SIZE,
        PAGE_READWRITE|PAGE_GUARD,
        &old_protect);
    [...]
}
LONG CALLBACK VectoredHandler(
    __in PEXCEPTION_POINTERS ExceptionInfo)
{
    [...]
    if(ExceptionInfo->ExceptionRecord->ExceptionCode ==
        STATUS_GUARD_PAGE_VIOLATION)
    {
        VirtualQueryEx(GetCurrentProcess()	,
            (LPVOID)ExceptionInfo->ExceptionRecord->ExceptionAddress,
            &lpMemInfo,
            sizeof(MEMORY_BASIC_INFORMATION)))

        if(lpMemInfo.Type != MEM_IMAGE)
            ShellcodeDetected();
    [...]

Yesterday I found this .doc. It explains pretty much everything: they use hardware breakpoints to intercept read operations and a Vectored Exception Handler to check if the faulting address belongs to a module…. pretty much the same thing, isn’t it?

Then I started to think about how EAT filtering could be bypassed, obviously there are many ways to find the address of a function without touching the EAT, but I was looking for a quick way to just fix existing shellcodes and make them working under EMET. Since EMET is going to use hardware breakpoints it will be probably faster than the PAGE_GUARD approach because while you can put a breakpoint on a single DWORD using debug registers, the granularity of VirtualProtect is PAGE_SIZE.

But hardware registers can be zeroed out, disabling the protection, by taking advantage of the Structured Exception Handling and without even using a single API. And so, I thought, you can easily add to a metasploit shellcode something like this:

START:
    call +0                  // poor's man get_pc()
    mov eax, [esp]
    add eax, HANDLER_OFFSET
    push eax               // install SEH handler
    push fs:[0]
    mov fs:[0], esp
    xor eax, eax
    mov byte [eax], 1	// oops
    [...]

HANDLER:
    xor eax, eax
    mov ebx, [esp+0xc]	// context
    add [ebx+0xb8], 3	// eip += len("mov byte [eax], 1")
    mov [ecx+0x4], EAX	// clean debug registers
    mov [ecx+0x8], EAX
    mov [ecx+0xc], EAX
    mov [ecx+0x10], EAX
    mov [ecx+0x14], EAX
    mov [ecx+0x18], EAX
    ret

right? Well, not quite really! Because this is not gonna work with SAFESEH enabled! :)

Btw, is there a way to quickly disable PAGE_GUARD using only position independent code and without touching EAT?

A new improvement in PHoneyC DOM emulation code was committed in SVN r1624. The idea is to better emulate the DOM behaviour depending on the selected browser personality. Let’s take a look at the code starting from the personalities definition in config.py.

39 UserAgents = [
40     (1,
41      "Internet Explorer 6.0 (Windows 2000)",
42      "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.0; .NET CLR 1.1.4322; .NET CLR 2.0.50727)",
43      "Mozilla",
44      "Microsoft Internet Explorer",
45      "4.0 (compatible; MSIE 6.0; Windows NT 5.0; .NET CLR 1.1.4322; .NET CLR 2.0.50727)",
46      "ie60",
47     ),
48     (2,
49      "Internet Explorer 6.1 (Windows XP)",
50      "Mozilla/4.0 (compatible; MSIE 6.1; Windows XP; .NET CLR 1.1.4322; .NET CLR 2.0.50727)",
51      "Mozilla",
52      "Microsoft Internet Explorer",
53      "4.0 (compatible; MSIE 6.1; Windows XP; .NET CLR 1.1.4322; .NET CLR 2.0.50727)",
54      "ie61",
55     ),
56     (3,
57      "Internet Explorer 7.0 (Windows XP)",
58      "Mozilla/4.0 (Windows; MSIE 7.0; Windows NT 5.1; SV1; .NET CLR 2.0.50727)",
59      "Mozilla",
60      "Microsoft Internet Explorer",
61      "4.0 (Windows; MSIE 7.0; Windows NT 5.1; SV1; .NET CLR 2.0.50727)",
62      "ie70",
63     ),
64     (4,
65      "Internet Explorer 8.0 (Windows XP)",
66      "Mozilla/4.0 (compatible; MSIE 8.0; Windows NT 5.1; Trident/4.0; (R1 1.5); .NET CLR 1.1.4322; .NET CLR 2.0.50727)",
67      "Mozilla",
68      "Microsoft Internet Explorer",
69      "4.0 (compatible; MSIE 8.0; Windows NT 5.1; Trident/4.0; (R1 1.5); .NET CLR 1.1.4322; .NET CLR 2.0.50727)",
70      "ie80",
71     ),
72 ]

It’s important to realize that each personality was added a tag (i.e. ie80). Taking a look at DOM/Window.py the following code can be seen.

229     def __init_methods(self):
230         for attr in dir(self):
231             prefix = “_Window__window_%s_” % (config.browserTag, )
232             if attr.startswith(prefix):
233                 p = attr.split(prefix)[1]
234                 self.__dict__['__cx'].add_global(p, getattr(self, attr))
235                 self.__dict__['__cx'].execute(“window.%s = %s;” % (p, p, ))

Let’s consider an example and assume the Internet Explorer 8.0 personality was selected. It’s easy to realize that the prefix would assume the value _Window__window_ie80_. A few simple wrappers were created, one per personality, to each method as shown in the following code.

340     def __window_back(self):
341         “”"
342         Returns the window to the previous item in the history.
343         Syntax
344
345         window.back()
346
347         Parameters
348
349         None.
350         “”"
351         pass
352
353     def __window_ie60_back(self):
354         self.__window_back()
355
356     def __window_ie61_back(self):
357         self.__window_back()
358
359     def __window_ie70_back(self):
360         self.__window_back()
361
362     def __window_ie80_back(self):
363         self.__window_back()
364
365     def __window_firefox_back(self):
366         self.__window_back()

This is a quite simple situation but what if you want to define addEventListener method just for Firefox personalities and attachEvent just for Internet Explorer ones? Really simple to do!

1191     def __window_attachEvent(self, sEvent, fpNotify):
1192         if dataetc.isevent(sEvent, ‘window’):
1193             self.__dict__[sEvent] = fpNotify
1194
1195     def __window_ie60_attachEvent(self, sEvent, fpNotify):
1196         self.__window_attachEvent(sEvent, fpNotify)
1197
1198     def __window_ie61_attachEvent(self, sEvent, fpNotify):
1199         self.__window_attachEvent(sEvent, fpNotify)
1200
1201     def __window_ie70_attachEvent(self, sEvent, fpNotify):
1202         self.__window_attachEvent(sEvent, fpNotify)
1203
1204     def __window_ie80_attachEvent(self, sEvent, fpNotify):
1205         self.__window_attachEvent(sEvent, fpNotify)
1206
1207
1208     def __window_detachEvent(self, sEvent, fpNotify):
1209         if sEvent in self.__dict__ and self.__dict__[sEvent] == fpNotify:
1210             del self.__dict__[sEvent]
1211
1212     def __window_ie60_detachEvent(self, sEvent, fpNotify):
1213         self.__window_detachEvent(sEvent, fpNotify)
1214
1215     def __window_ie61_detachEvent(self, sEvent, fpNotify):
1216         self.__window_detachEvent(sEvent, fpNotify)
1217
1218     def __window_ie70_detachEvent(self, sEvent, fpNotify):
1219         self.__window_detachEvent(sEvent, fpNotify)
1220
1221     def __window_ie80_detachEvent(self, sEvent, fpNotify):
1222         self.__window_detachEvent(sEvent, fpNotify)
1223
1224
1225     def __window_addEventListener(self, type, listener, useCapture = False):
1226         if dataetc.isevent(type, ‘window’):
1227             self.__dict__[type] = listener
1228
1229     def __window_firefox_addEventListener(self, type, listener, useCapture = False):
1230         self.__window_addEventListener(type, listener, useCapture = False)
1231
1232
1233     def __window_removeEventListener(self, type, listener, useCapture = False):
1234         if type in self.__dict__ and self.__dict__[type] == listener:
1235             del self.__dict__[type]
1236
1237     def __window_firefox_removeEventListener(self, type, listener, useCapture = False):
1238         self.__window_removeEventListener(type, listener, useCapture = False)

Moreover this approach could allow to insert specific code within the wrappers if needed while implementing the method functionalities in the higher level __window_<method_name> wrapper.

Bad Behavior has blocked 203 access attempts in the last 7 days.