Skip to content
This repository was archived by the owner on Mar 21, 2025. It is now read-only.
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
72 changes: 71 additions & 1 deletion malware-analysis/Malware-Analysis.ipynb
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,11 @@
"from MalwareSample import *\n",
"from pprint import pprint\n",
"import os.path\n",
"from time import sleep"
"from time import sleep\n",
"\n",
"import pefile\n",
"import requests\n",
"import bs4"
]
},
{
Expand Down Expand Up @@ -282,6 +286,72 @@
" print(info + \"No VT API Key. Skipping...\")"
]
},
{
"cell_type": "markdown",
"id": "782868c7",
"metadata": {},
"source": [
"## Identify PE Sample and Parse IAT\n",
"Original Code: Squiblydoo [MalAPIReader](https://github.com/Squiblydoo/MalAPIReader)"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "c5e06094",
"metadata": {},
"outputs": [],
"source": [
"# MalAPI.io currently does not have an actual API\n",
"def apiCheck(api):\n",
" APItoCheck = api\n",
" APICheck = requests.get(\"https://malapi.io/winapi/\" + APItoCheck)\n",
" APICheck.raise_for_status()\n",
" APISoup = bs4.BeautifulSoup(APICheck.text, 'html.parser')\n",
" \n",
" details = APISoup.select('.detail-container .content')\n",
" ApiInfo = details[1].getText().lstrip().rstrip()\n",
" return ApiInfo"
]
},
{
"cell_type": "code",
"execution_count": null,
"id": "4f1b4595",
"metadata": {},
"outputs": [],
"source": [
"for obj in sample_obj:\n",
" try:\n",
" # If not a valid PE file, line below should throw a PEFormatError\n",
" pe = pefile.PE(\"./dropbox/\"+obj.sample_name, fast_load=True)\n",
"\n",
" print(good + f\"{obj.sample_name} is a valid PE file. Examining...\")\n",
" pe.parse_data_directories()\n",
" for entry in pe.DIRECTORY_ENTRY_IMPORT:\n",
" for imp in entry.imports:\n",
" api = imp.name.decode(\"utf-8\") # Not necessarily an API call\n",
" try:\n",
" details = apiCheck(api)\n",
" # Replacement is necessary to allow the csv to be functional\n",
" obj.winapi_imports.append((api, details.replace(\",\",\"\"), True))\n",
" except:\n",
" if api[0] != \"_\": # Primitive way to filter out non-API strings\n",
" obj.winapi_imports.append((api, None, False))\n",
"\n",
" MalwareSample.save_imports(obj.sample_path, obj.saved_sample_name, obj.winapi_imports)\n",
"\n",
" except pefile.PEFormatError:\n",
" print(info + f\"{obj.sample_name} is not a valid PE file. Skipping...\")\n",
"\n",
" except Exception as err:\n",
" print(printError + f\"Something went wrong, skipping {obj.sample_name}. Error: {err}\")\n",
" \n",
"print(important + \"If a WINAPI was used maliciously, consider contributing information to MalAPI.io.\")\n",
"print(r\" \\\\--> \" + info + \"Note that an API will be marked as \\\"True\\\" (malicious) only if it is an exact match to MalAPI\\'s table\")\n",
" "
]
},
{
"cell_type": "markdown",
"id": "343fa9fa-4c44-445c-ab71-687f1e7d56fa",
Expand Down
18 changes: 17 additions & 1 deletion malware-analysis/MalwareSample.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ def check_dir(dir):
"""
Checks if the specified directory exists, if not, it creates it.

For use with dropbox and saved-specimens dirs, which are important ot the functionality of the notebook
For use with dropbox and saved-specimens dirs, which are important to the functionality of the notebook
"""
if not os.path.isdir(dir):
os.mkdir(dir)
Expand All @@ -49,6 +49,8 @@ def __init__(self, sample_name):
self.sample_path = ""
self.sha256sum = ""

self.winapi_imports = []

@classmethod
def create_specimen_dirs(cls, sample_name):
"""
Expand Down Expand Up @@ -106,6 +108,20 @@ def pull_strings(cls, length, saved_sample_name, sample_path):
os.system(cmd)
print(recc + "Written to outfile: " + outfile)

@classmethod
def save_imports(cls, sample_path, saved_sample_name, winapi_imports):
"""
Takes imports identified by MalAPIReader and saves them to a file: winapi_imports.csv
"""
malapi_out = "winapi_imports.csv"
outfile = saved_specimens + saved_sample_name + "/" + malapi_out
with open(outfile, "w") as f:
f.write("Import,Details,isMalicious\n")
for imp, details, is_malicious in winapi_imports:
f.write(f"{imp},{details},{is_malicious}\n")
print(recc + "Written to outfile: " + outfile)
return outfile

@classmethod
def zip_and_password_protect(cls, sample_path, saved_sample_name):
"""
Expand Down
Loading