Endpoint defense evasion with custom built binaries
It’s already a common knowledge that merely rebuilding binaries could be a good way to attempt to bypass many AV solutions. Here’s a good illustration of exactly that case from our recent penetration testing engagement. Here’s the scenario:
After spending some time in client’s internal network, we spotted a machine with misconfigured JMX endpoint:

This was easily turned into RCE on the affected machine:

At the first look escalating to SYSTEM seemed straightforward, thanks to JuicyPotato tool and possessed permission set:

However during attack preparation and usual OPSEC checks it became evident that prebuilt version of JuicyPotato tool is not ready for operational usage:

So before using JuicyPotato we performed following steps:
- Changed main source code file to something else (
SoczystyKartofelin our case :)) - Removed
printfcalls printingJuicyPotatostring. - Renamed
PotatoAPIstructure to something else. - Changed all includes files to lowercase (i.e.
Windows.h->windows.h) as required byMinGWcompiler. - Built new
JuicyPotatobinary from modified sources.
For building we used Zig compiler as it is capable of cross-compiling of C/C++ code for Windows platforms (it uses MinGW for that):
$ zig c++ -target x86_64-windows-gnu -std=c++17 IStorageTrigger.cpp SoczystyKartofel.cpp LocalNegotiator.cpp -luuid -lole32 -DUNICODE -D_UNICODE -lws2_32 -lsecur32 -o juicyPotato
Alternatively following build.zig could be used for building:
const std = @import("std");
pub fn build(b: *std.build.Builder) void {
const target = b.standardTargetOptions(.{});
const mode = b.standardReleaseOptions();
const exe = b.addExecutable("<binName>", null);
exe.setTarget(target);
exe.setBuildMode(mode);
exe.linkSystemLibraryName("c");
exe.linkSystemLibraryName("c++");
exe.linkSystemLibraryName("uuid");
exe.linkSystemLibraryName("ws2_32");
exe.linkSystemLibraryName("secur32");
exe.linkSystemLibraryName("ole32");
exe.addCSourceFiles(&.{
"IStorageTrigger.cpp",
"SoczystyKartofel.cpp",
"LocalNegotiator.cpp",
}, &.{
"-std=c++17",
"-DUNICODE",
"-D_UNICODE",
});
exe.strip = true;
exe.install();
}
and starting build process would be done with following command:
$ zig build -Drelease-small=true -Dtarget=x86_64-windows-gnu
And voila, after those trivial modifications, the new AV discovery ratio for the JuicyPotato binary looked much better:


