General:

DO obfuscate or encrypt all strings and configuration data that directly relate to tool functionality. Consideration should be made to also only de-obfuscating strings in-memory at the moment the data is needed. When a previously de-obfuscated value is no longer needed, it should be wiped from memory. Rationale: String data and/or configuration data is very useful to analysts and reverse-engineers.

DO NOT decrypt or de-obfuscate all string data or configuration data immediately upon execution. Rationale: Raises the difficulty for automated dynamic analysis of the binary to find sensitive data.

DO explicitly remove sensitive data (encryption keys, raw collection data, shellcode, uploaded modules, etc) from memory as soon as the data is no longer needed in plain-text form. DO NOT RELY ON THE OPERATING SYSTEM TO DO THIS UPON TERMINATION OF EXECUTION. Rationale: Raises the difficulty for incident response and forensics review.

DO utilize a deployment-time unique key for obfuscation/de-obfuscation of sensitive strings and configuration data. Rationale: Raises the difficulty of analysis of multiple deployments of the same tool.

DO strip all debug symbol information, manifests(MSVC artifact), build paths, developer usernames from the final build of a binary. Rationale: Raises the difficulty for analysis and reverse-engineering, and removes artifacts used for attribution/origination.

DO strip all debugging output (e.g. calls to printf(), OutputDebugString(), etc) from the final build of a tool. Rationale: Raises the difficulty for analysis and reverse-engineering.

DO NOT explicitly import/call functions that is not consistent with a tool’s overt functionality (i.e. WriteProcessMemory, VirtualAlloc, CreateRemoteThread, etc – for binary that is supposed to be a notepad replacement). Rationale: Lowers potential scrutiny of binary and slightly raises the difficulty for static analysis and reverse-engineering.

DO NOT export sensitive function names; if having exports are required for the binary, utilize an ordinal or a benign function name. Rationale: Raises the difficulty for analysis and reverse-engineering.

DO NOT generate crashdump files, coredump files, “Blue” screens, Dr Watson or other dialog pop-ups and/or other artifacts in the event of a program crash. DO attempt to force a program crash during unit testing in order to properly verify this. Rationale: Avoids suspicion by the end user and system admins, and raises the difficulty for incident response and reverse-engineering.

DO NOT perform operations that will cause the target computer to be unresponsive to the user (e.g. CPU spikes, screen flashes, screen “freezing”, etc). Rationale: Avoids unwanted attention from the user or system administrator to tool’s existence and behavior.

DO make all reasonable efforts to minimize binary file size for all binaries that will be uploaded to a remote target (without the use of packers or compression). Ideal binary file sizes should be under 150KB for a fully featured tool. Rationale: Shortens overall “time on air” not only to get the tool on target, but to time to execute functionality and clean-up.