SafeExamBrowser analysis
Date: 2025-09-10
Tags: #RE
Github repo: Jakub2555/SEBBypass
Introduction
SafeExamBrowser is a sort of Lock down Browser to perform exams on. It’s widely used in switzerland, basically every school uses it here and other countries like Indonesia. Another fact is its open source! Which is cool... but that also has a downside since it’s easy to bypass. There is one module I will cover later which isnt open source.
Initial analysis
SEB (SafeExamBrowser) is entirely written in C# so its easy to analyse. It consist of 2-3 applications SafeExamBrowser.exe, SafeExamBrowser.Client.exe and SafeExamBrowser.Service.exe. When you run SEB you run the SafeExambrowser.exe which is gonna perform some initial checks such as if currently in VM, etc... (I will cover later) after the checks the client is gonna run as a child, both processes are communicating with the service which is running in the background all the time, to perform stuff that needs admin privilages. It uses CEF for the Web Browser.
Configuration
SEB also has a configuration manager with which you can change seb settings, they arent applied for real exams you load. Exams are loaded by using a .seb file which contains the exams configurations. There are some core options such as Clipboard which can be blocked completely, isolated or allowed. Then there is how seb should start, in a new Desktop, current desktop or debug which won’t put you in fullscreen and your able to access your apps. Then theres also an application blocklist. I would say these are the main configurations that matter when you wanna write a bypass.
Features of SEB
- Verify hash of exam configuration
- Verify integrity of SEB files
- Block certain applications
- Detecting processes by windows
- Detect VMs
- Screenshot screen and allow websites (exam providers) to record screen
- Block clipboard depending on config
- Isolate the session
- Logs Keyboard and mouse input
- Prevents capture of SEB windows
- Checks for remote access
Internal workings
seb_x64.dll
This is the only module which isn’t open source. Since I think around version 3.8 its is protected with themida (seems to be only imports hidden) and completely written in C/C++. Even though it doesnt do too much it exports 4 functions: CalculateAppSignatureKey, VerifyCodeSignature, CalculateBrowserExamKey, IsVirtualMachine which are used by seb. For reversing there isn’t much to do except fixing the imports. Which can be achived using static + dynamic analysis.
These functions are used to verify if any files of SEB have been modified or the exam configuration so the .seb file has been modified. The hashes are sent and checked by the server. But there is no real need to modify the files or the exam configuration since you need to find a different way to bypass the protection cause of the screenshots and screenrecordings SEB does which would look suspicious if you would be outside of SEB or have a modified exam. There is also IsVirtualMachine which got added in 3.10.1. All of these functions seem to be hookable so if you hook them before they used you can simply spoof them.
SEB Core
Blocking applications
In SafeExamBrowser.Monitoring under Applications you can find everything about blocking applications. What we want to look at it Timer_Elapsed where the checks happen. It is itterating through all active processes, In the function GetAllRunning we can see it is using the GetProcesses function by C#. With this we can easily write a bypass, by simply hooking NtQuerySystemInformation and skipping the process we want to hide:
if (SystemInformationClass == 5 && status == 0) // 0x05 SystemProcessInformation
{
P_SYSTEM_PROCESS_INFORMATION prev =
P_SYSTEM_PROCESS_INFORMATION(SystemInformation);
P_SYSTEM_PROCESS_INFORMATION cur =
P_SYSTEM_PROCESS_INFORMATION((PUCHAR)prev + prev->NextEntryOffset);
while (prev->NextEntryOffset != NULL)
{
if (fnv1a::hash("notepad.exe") == fnv1a::hash(cur->ImageName.Buffer))
{
// Swap NextEntryOffset to the one after the process we want to hide
if (cur->NextEntryOffset == 0)
prev->NextEntryOffset = 0;
else
prev->NextEntryOffset += cur->NextEntryOffset;
cur = prev;
}
prev = cur;
cur = P_SYSTEM_PROCESS_INFORMATION((PUCHAR)cur + cur->NextEntryOffset);
}
}
Detect processes by windows
Detect VMs
In SafeExamBrowser.Monitoring under VirtualMachineDetector you can find different functions that check for VirtualDevices, Registry keys, etc. When you follow where systemInfo is assigned, you can see they are using ManagementObjectSearcher to use SQL queries to get information about the system. This can also be hooked spoofed to a component that is not blacklisted. EDIT: Since around SEB 3.10.1 They also have a VM detect module in seb_x64.dll
Prevent capture of SEB windows
This one is easy, since around SEB 3.10 they are setting the Window affinity to WDA_EXCLUDEFROMCAPTURE using SetWindowDisplayAffinity. You can simply hook this function and prevent it from being set. There are no checks if this has been applied and if there would be they would most likely be done by GetWindowDisplayAffinity which also can be hooked and spoofed.
End Word
I didnt cover every feature since the ones I covered are the most necessery ones to create a bypass. There is simply too much to cover and there are countless ways to bypass SEB. The easiest one is to allow applications run that are blacklisted. If you got interested feel free to play around with it and find creative ways to break SEB.