Skip to content
Merged
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
9 changes: 9 additions & 0 deletions analyzer/windows/modules/packages/python.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@
# This file is part of Cuckoo Sandbox - http://www.cuckoosandbox.org
# See the file 'docs/LICENSE' for copying permission.

import os

from lib.common.abstracts import Package
from lib.common.common import check_file_extension
from lib.common.constants import OPT_ARGUMENTS
Expand All @@ -24,6 +26,13 @@ def start(self, path):
except CuckooPackageError:
python = self.get_path_glob("py.exe")

# Set PYTHONHOME to help Python locate its standard library during initialization.
# Python may fail to load the 'encodings' module, resulting in:
# "ModuleNotFoundError: No module named 'encodings'"
# Might break if your Python is in VENV
python_home = os.path.dirname(python)
os.environ["PYTHONHOME"] = python_home

arguments = self.options.get(OPT_ARGUMENTS, "")

path = check_file_extension(path, ".py")
Expand Down
44 changes: 39 additions & 5 deletions modules/auxiliary/AzSniffer.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,10 +19,7 @@
HAVE_AZURE = True
except ImportError:
HAVE_AZURE = False
print("Missing machinery-required libraries.")
print(
"poetry run python -m pip install azure-identity msrest msrestazure azure-mgmt-compute azure-mgmt-network azure-mgmt-storage azure-storage-blob"
)
print("Missing machinery-required libraries.Run: poetry install --extras azure")

from lib.cuckoo.common.abstracts import Auxiliary
from lib.cuckoo.common.config import Config
Expand Down Expand Up @@ -72,13 +69,33 @@ def start(self):
self.create_packet_capture(custom_filters)

def create_packet_capture(self, custom_filters):
# Determine the target resource ID for packet capture (standalone VM or specific VMSS instance)
target = None
if hasattr(self, "machine") and self.machine and hasattr(self.machine, "label") and self.machine.label:
parts = self.machine.label.rsplit("_", 1)
if len(parts) == 2 and parts[1].isdigit() and self.vmss_name:
instance_id = parts[1]
target = f"/subscriptions/{self.subscription_id}/resourceGroups/{self.resource_group}/providers/Microsoft.Compute/virtualMachineScaleSets/{self.vmss_name}/virtualMachines/{instance_id}"
else:
# Standalone VM target fallback
target = f"/subscriptions/{self.subscription_id}/resourceGroups/{self.resource_group}/providers/Microsoft.Compute/virtualMachines/{self.machine.label}"

# Ultimate fallback to VMSS if target is still None
if not target and self.vmss_name:
target = f"/subscriptions/{self.subscription_id}/resourceGroups/{self.resource_group}/providers/Microsoft.Compute/virtualMachineScaleSets/{self.vmss_name}"

if not target:
raise ValueError("No target VM or VMSS could be determined for AzSniffer")

log.debug("AzSniffer targeting resource ID: %s", target)

storage_location = PacketCaptureStorageLocation(
storage_id=f"/subscriptions/{self.subscription_id}/resourceGroups/{self.resource_group}/providers/Microsoft.Storage/storageAccounts/{self.storage_account}",
storage_path=f"https://{self.storage_account}.blob.core.windows.net/network-watcher-logs/{self.capture_name}.cap",
)

packet_capture = PacketCapture(
target=f"/subscriptions/{self.subscription_id}/resourceGroups/{self.resource_group}/providers/Microsoft.Compute/virtualMachineScaleSets/{self.vmss_name}",
target=target,
storage_location=storage_location,
time_limit_in_seconds=18000,
total_bytes_per_session=1073741824,
Expand Down Expand Up @@ -146,6 +163,23 @@ def download_packet_capture(self):

blob_client = self.blob_service_client.get_blob_client(container=container_name, blob=blob_name)

# Check if the blob exists. If not (e.g. due to Azure-appended subfolders or timestamps),
# list blobs in the container to find any match for our capture name.
if not blob_client.exists():
log.info("Blob %s not found directly. Searching container %s for blobs matching %s", blob_name, container_name, self.capture_name)
container_client = self.blob_service_client.get_container_client(container_name)
matched_blob_name = None
for blob in container_client.list_blobs():
if (self.capture_name in blob.name or f"_{self.task.id}" in blob.name) and blob.name.endswith(".cap"):
matched_blob_name = blob.name
break

if matched_blob_name:
log.info("Found matching blob: %s", matched_blob_name)
blob_client = self.blob_service_client.get_blob_client(container=container_name, blob=matched_blob_name)
else:
log.error("No matching blob found in container %s containing %s", container_name, self.capture_name)

self._download_to_file(blob_client, primary_output_file)
log.info("Downloaded packet capture for task %s to %s", str(self.task.id), primary_output_file)
self.convert_cap_to_pcap(primary_output_file)
Expand Down
Loading
Loading