Offensive Development with C++ and C#: Getting Started with Win32 API and practical examples
RedTeam C++ Maldev Malware Dev Offensive Development Offensive Security Win32 API MessageBox CreateToolhelp32Snapshot
We introduce the basics of Win32 API and some implementations, crucial for those interested in offensive security. We will explore fundamental concepts, necessary tools, and provide practical examples using the MessageBox
function
Learning Objectives
- Understand what the Windows API is, its use cases, and how it interacts with the OS subsystems
- Learn how to implement the Windows API in C++ to pop a message or list all processes.
What is Windows API?
Programs often need to access or modify Windows subsystems or hardware but are restricted to maintain machine stability. To solve this problem, Microsoft released the Win32 API. The Win32 API is a set of functions and procedures that abstract many tasks performed daily to interface between user-mode applications and the kernel on the Windows OS.
For example, the Win32API function called WriteProcessMemory
writes data into a specific region of the memory’s process.
There is mainly two set of functions, user mode functions and kernel functions. The first set has limited acces and sometimes Hooked/monitor by Antivirus or EDR.
Below is a visual representation of how a user application can use API calls to modify kernel components.

User Mode vs. Kernel Mode
Understanding the difference between user mode and kernel mode is essential when working with the Windows API:
- User Mode: applications have limited access to system resources and hardware. This mode provides a controlled environment where most applications run, preventing them from performing operations that could harm the system or other applications.
- Kernel Mode: code has unrestricted access to all system resources, including hardware. This mode is where the core of the operating system runs, along with device drivers and other low-level components. Operations requiring direct interaction with hardware or critical system components are executed in kernel mode.
To resume:
User mode | Kernel mode |
---|---|
No direct hardware access | Direct hardware access |
Access to “owned/virtual” memory locations | Access to entire physical memory |
Development environment
Why C++ & C#?
C++ and C# are powerful languages for system programming and application development.
C++ is widely used for its efficiency and ability to directly manipulate hardware resources, making it an excellent choice for low-level programming and offensive security tasks.
C#, on the other hand, offers a higher level of abstraction and ease of use. C# is a Object Oriented language that is based on the .NET Framework.
Understandably, it does not provide the hiding capabilities of C++. But it has other aspects like in memory execution and with the increase in tools that use C# we have also seen some cool tactics that can be utilized to bypass detection and defenses.
We will use both languages depending on the example to demonstrate their respective strengths.
Environment
- Microsoft Visual Studio: A comprehensive development environment for C++ and other languages.
- Windows 11: The latest version of Windows OS, which includes all necessary tools and updates for modern API development.
Practical Example I: Creating a MessageBox
One of the simplest Windows API functions is MessageBox
, which displays a dialog box containing a message. This function is part of the User32 library in the Win32 API.
The Microsoft Docs provide this C++ definition : link: https://learn.microsoft.com/fr-fr/windows/win32/api/winuser/nf-winuser-messageboxa
int MessageBoxA(
[in, optional] HWND hWnd,
[in, optional] LPCTSTR lpText,
[in, optional] LPCTSTR lpCaption,
[in] UINT uType
);
MessageBoxA
is the ASCII implementation of the function.
Here’s a basic example of implementation in C++:
#include <windows.h>
int main() {
MessageBoxA(NULL, "Hello, Windows API! by R3dLevy", "Hello", MB_OK);
return 0;
}
This code will display a message box with the text “Hello, Windows API!” and an “OK” button.

Breaking down the code
#include <windows.h>
: This includes the Windows API functions.MessageBoxA
function parameters:NULL
: Handle to the owner window (no owner in this case)."Hello, Windows API! by R3dLevy"
: The message to display."Hello"
: The title of the message box.MB_OK
: Indicates that the message box will contain an OK button.
Practical Example II: Process Enumeration
To dive deeper, let’s look at more API calls for process enumeration. This is particularly useful in offensive security for understanding and interacting with processes running on a system. We will use 3 functions for this example :
CreateToolhelp32Snapshot
: Takes a snapshot of the specified processes, heaps, modules, and threads used by the processes.
HANDLE CreateToolhelp32Snapshot(
[in] DWORD dwFlags,
[in] DWORD th32ProcessID
);
Module32First
: Retrieves information about the first module associated with a processModule32Next
: Retrieves information about the next module associated with a process or thread.
Here is a brief overview:
#include <windows.h>
#include <tlhelp32.h>
#include <iostream>
void ListProcesses() {
HANDLE hProcessSnap;
PROCESSENTRY32 pe32;
hProcessSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
if (hProcessSnap == INVALID_HANDLE_VALUE) {
std::cerr << "CreateToolhelp32Snapshot failed." << std::endl;
return;
}
pe32.dwSize = sizeof(PROCESSENTRY32);
if (!Process32First(hProcessSnap, &pe32)) {
CloseHandle(hProcessSnap);
std::cerr << "Process32First failed." << std::endl;
return;
}
do {
std::wcout << L"Process name: " << pe32.szExeFile << L"\nProcess ID: " << pe32.th32ProcessID << std::endl;
} while (Process32Next(hProcessSnap, &pe32));
CloseHandle(hProcessSnap);
}
int main() {
ListProcesses();
return 0;
}
Listing all process in the debug terminal of visual studio:

Breaking down the code
CreateToolhelp32Snapshot
: Takes a snapshot of the processes, heaps, modules, or threads.- Parameters:
TH32CS_SNAPPROCESS
: Includes all processes in the snapshot.0
: Takes a snapshot of all processes in the system.
Process32First
andProcess32Next
: Used to iterate over the list of processes in the snapshot. For more informations : https://learn.microsoft.com/en-us/windows/win32/api/tlhelp32/nf-tlhelp32-createtoolhelp32snapshot
Conclusion
This post covered the basics of Windows API, including user mode and kernel mode distinctions, and provided examples of using the MessageBox
function and enumerating processes with CreateToolhelp32Snapshot
.
Future posts will delve deeper into more advanced topics such as memory management and process manipulation. Specifically, the next post will focus on process injection.
All the examples can be found on my github repos : https://github.com/R3dLevy/TheOffensiveDevelopmentProject
References
- Win32 Architecture
- For more detailed information on Windows API calls, you can refer to this resource (Sensei’s Forensics).
- Tryhackme WindowsAPI Room