Hacking involves managing a lot of contextual factors at one time. Most times, the default situation works and a tool will perform beautifully for you. Sometimes though, there are things you have to check on and work around. That’s what this blog post is. I’d like to give you a list of contextual factors you should know about your Meterpreter session with pointers on how to manipulate these factors. This information will help you think on your feet and modify your situation so that you can get what you want out of your post-exploitation agent.
Which process do I live in?
Let’s start with the first contextual factor: your process. After exploitation, Meterpreter lives in the process you took control of. This process is associated with a user, it may or may not have a subset of the active users privileges, and depending on which process it is–the process could go away.. in any moment.
To learn which process your Meterpreter session lives in, use the getpid command. This will return your current process id.
To see which processes are on the system, type ps to see a listing of processes.
To change to another process, use migrate [process id] to force Meterpreter to open a handle to another process, allocate memory there, copy itself, and start a new thread of execution in that process. Somehow, Meterpreter preserves state during this migration as well. I’d like to give you a summary of how it does that, but truth is–I don’t know 🙂 The PID column of the ps output indicates the process ID. Don’t confuse this column with PPID which is the parent process ID.
Be aware of “when” you choose to migrate. If you live in a process and you’ve started pivoting, logging keystrokes, and doing other things–when you migrate, you may end up forcing Meterpreter to think it must control or interact with a non-existent resource and you may lose your session. It’s best to migrate early, before you’ve started to do anything significant. If in doubt, have Beacon on the system to give you a quick way to recover your session if something goes wrong.
What is the architecture of the system I’m on and the process I’m in?
When you attack a system and get a session, you may deliver an x86 payload, but find that you’re on an x64 system. It’s important to know the architecture of the system you’re on and the type of process you live in. If you’re in an x86 process on an x64 system, some actions that require manipulation of system data structures will fail. If you want to dump hashes or use mimikatz, you will need to make sure you live in a process that matches the native system.
How do you do this? You can pull this off with our friend migrate. Use migrate [process id] to move to another process. If you move from an x86 to an x64 process or vice versa, Meterpreter will manage this transition for you. The Arch column of ps’s output is the architecture of the process.
To determine the architecture of your current Meterpreter session and the system you’re on, use sysinfo.
What is my current desktop?
This is one that bites folks a lot. Windows has the concept of desktop sessions. Each desktop session has its own number. Most Meterpreter actions will act on the active desktop session. If you try to take a screenshot, Meterpreter will try to oblige you by getting a screenshot of the current desktop session. If your process is not associated with a desktop, then you will not get a screenshot. If your process is not associated with a desktop that’s in use, then you will not get a useful screenshot. This same logic also applies to keystrokes and other tools that allow you to capture user activity. This same logic also applies if you’re trying to execute a non-hidden program and make it show on the user’s desktop.
To see which desktop you’re in, use getpid to determine your process and look at the session column in the output of ps.
Use enumdesktops to see which desktops are available.
Use setdesktop to force your process to associate with another desktop. This command requires a few arguments provided by enumdesktops, make sure you review the help provided by setdesktop -h.
Take a look at the Session column of ps’s output to see the desktop session associated with each process.
Which token do I have?
The last item to know is your current token. In Windows, each process and thread has a token associated with it. This token states which user the thread of execution is associated with and which subset of that user’s rights the thread or process has. Knowing the token you currently have is everything. Your token is your free pass to summer fun and the ability to do things.
If you have the NT AUTHORITY\SYSTEM token, you have a token that gives you complete control of the host that you’re on. Generally, you need this token to dump hashes and perform other actions that require interrogating the system for things you want. This token is associated with the current host though. This token does not give you the right to manipulate other systems that trust the same domain controller.
If you have the token of a user on the domain, you have the rights to do things and access the resources that user can get to. For example, if there’s a share on another system that you have the rights to, you may open a command shell and interrogate it.
If you have the token of a domain administrator, then you may go to town and take over the world. You can try to copy an executable to a place another host can reach and schedule it to run on another host. This gives you the ability to get code execution on other hosts that are part of the same domain.
Knowing your current token is important. To determine the token you have, use getuid.
To steal a token from a process, use steal_token [process id]. The User column of ps’s output has the token associated with each process.
To go back to your original token when you’re ready to do so, use rev2self (revert to self).
A process listing is one place to find a token, but it’s not the only place. Windows may associate a different token with each thread and tokens persist on a system until reboot. If you want to enumerate the current system for all available tokens, use the incognito module to do so. I could write about this module here, but the Metasploit Unleashed Wiki covers it well.
The Take Away
When I’m using meterpreter, sometimes, an action will not happen as I hoped. When I find myself in this situation. I take a look at these contextual factors. If I want to spy on the user, I make sure I’m in a process associated with the right desktop session. If I want to dump hashes I make sure my meterpreter architecture matches the operating system’s architecture. If I want to perform a privileged action, I make sure I have the right token to do it.
As deceptively simple as Meterpreter is, there are a lot of contextual factors to know to get the most from it.