Spaces:
Running
Running
File size: 8,988 Bytes
25a8adb c99b4e2 25a8adb c99b4e2 25a8adb c99b4e2 25a8adb c99b4e2 25a8adb c99b4e2 25a8adb c99b4e2 25a8adb c99b4e2 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 |
import streamlit as st
import os
import zipfile
import tempfile
import pefile
import shutil
from pathlib import Path
st.set_page_config(page_title="File Analyzer", page_icon="π")
st.title("File Analysis Tool")
st.markdown("""
This tool allows you to analyze various file types:
- Extract and view contents of .zip files
- Unpack .exe files to examine their contents
- View information about .dll files
""")
# No size limit
def unpack_exe(file_path, output_dir):
"""Extract information from an EXE file using pefile"""
try:
pe = pefile.PE(file_path)
# Create a basic info dictionary
info = {
"Machine": hex(pe.FILE_HEADER.Machine),
"TimeDateStamp": pe.FILE_HEADER.TimeDateStamp,
"NumberOfSections": pe.FILE_HEADER.NumberOfSections,
"Sections": []
}
# Get section information
for section in pe.sections:
section_name = section.Name.decode('utf-8', errors='ignore').strip('\x00')
info["Sections"].append({
"Name": section_name,
"VirtualAddress": hex(section.VirtualAddress),
"SizeOfRawData": section.SizeOfRawData,
"Entropy": section.get_entropy()
})
# Get imports
if hasattr(pe, 'DIRECTORY_ENTRY_IMPORT'):
info["Imports"] = []
for entry in pe.DIRECTORY_ENTRY_IMPORT:
dll_name = entry.dll.decode('utf-8', errors='ignore')
imports = []
for imp in entry.imports:
if imp.name:
imports.append(imp.name.decode('utf-8', errors='ignore'))
info["Imports"].append({
"DLL": dll_name,
"Functions": imports
})
# Extract resources if present
if hasattr(pe, 'DIRECTORY_ENTRY_RESOURCE'):
resource_dir = os.path.join(output_dir, "resources")
os.makedirs(resource_dir, exist_ok=True)
for resource_type in pe.DIRECTORY_ENTRY_RESOURCE.entries:
if hasattr(resource_type, 'directory'):
for resource_id in resource_type.directory.entries:
if hasattr(resource_id, 'directory'):
for resource_lang in resource_id.directory.entries:
data = pe.get_data(resource_lang.data.struct.OffsetToData, resource_lang.data.struct.Size)
resource_filename = f"resource_{resource_type.id}_{resource_id.id}_{resource_lang.id}"
with open(os.path.join(resource_dir, resource_filename), 'wb') as f:
f.write(data)
return info
except Exception as e:
return {"Error": str(e)}
def analyze_dll(file_path):
"""Extract information from a DLL file using pefile"""
try:
pe = pefile.PE(file_path)
# Create a basic info dictionary
info = {
"Machine": hex(pe.FILE_HEADER.Machine),
"TimeDateStamp": pe.FILE_HEADER.TimeDateStamp,
"NumberOfSections": pe.FILE_HEADER.NumberOfSections,
"Characteristics": hex(pe.FILE_HEADER.Characteristics),
"DllCharacteristics": hex(pe.OPTIONAL_HEADER.DllCharacteristics),
"Sections": []
}
# Get section information
for section in pe.sections:
section_name = section.Name.decode('utf-8', errors='ignore').strip('\x00')
info["Sections"].append({
"Name": section_name,
"VirtualAddress": hex(section.VirtualAddress),
"SizeOfRawData": section.SizeOfRawData,
"Entropy": section.get_entropy()
})
# Get exports if present
if hasattr(pe, 'DIRECTORY_ENTRY_EXPORT'):
info["Exports"] = []
for exp in pe.DIRECTORY_ENTRY_EXPORT.symbols:
if exp.name:
info["Exports"].append(exp.name.decode('utf-8', errors='ignore'))
# Get imports
if hasattr(pe, 'DIRECTORY_ENTRY_IMPORT'):
info["Imports"] = []
for entry in pe.DIRECTORY_ENTRY_IMPORT:
dll_name = entry.dll.decode('utf-8', errors='ignore')
imports = []
for imp in entry.imports:
if imp.name:
imports.append(imp.name.decode('utf-8', errors='ignore'))
info["Imports"].append({
"DLL": dll_name,
"Functions": imports
})
return info
except Exception as e:
return {"Error": str(e)}
def process_zip_file(file_path, temp_dir):
"""Process a ZIP file and extract its contents"""
try:
with zipfile.ZipFile(file_path, 'r') as zip_ref:
# Get file list before extraction
file_list = zip_ref.namelist()
# Extract to temp directory
zip_ref.extractall(temp_dir)
# Check for nested executables
nested_files = {}
for root, _, files in os.walk(temp_dir):
for file in files:
full_path = os.path.join(root, file)
rel_path = os.path.relpath(full_path, temp_dir)
if file.endswith('.exe'):
exe_output_dir = os.path.join(temp_dir, f"{file}_unpacked")
os.makedirs(exe_output_dir, exist_ok=True)
nested_files[rel_path] = {
'type': 'exe',
'info': unpack_exe(full_path, exe_output_dir)
}
elif file.endswith('.dll'):
nested_files[rel_path] = {
'type': 'dll',
'info': analyze_dll(full_path)
}
return {
'file_list': file_list,
'nested_files': nested_files
}
except Exception as e:
return {'error': str(e)}
# Main app logic
uploaded_file = st.file_uploader("Upload a file (.zip, .exe, or .dll)", type=["zip", "exe", "dll"])
if uploaded_file is not None:
# Process file without size check
with tempfile.TemporaryDirectory() as temp_dir:
# Save the uploaded file to the temporary directory
file_path = os.path.join(temp_dir, uploaded_file.name)
with open(file_path, "wb") as f:
f.write(uploaded_file.getbuffer())
st.success(f"File uploaded: {uploaded_file.name}")
# Process based on file type
if uploaded_file.name.lower().endswith('.zip'):
st.subheader("ZIP File Contents")
output_dir = os.path.join(temp_dir, "extracted")
os.makedirs(output_dir, exist_ok=True)
result = process_zip_file(file_path, output_dir)
if 'error' in result:
st.error(f"Error processing ZIP file: {result['error']}")
else:
with st.expander("ZIP Contents", expanded=True):
st.write(f"Total files: {len(result['file_list'])}")
st.json(result['file_list'])
if result['nested_files']:
st.subheader("Detected Executable Files")
for file_path, file_info in result['nested_files'].items():
with st.expander(f"{file_path} ({file_info['type'].upper()})"):
st.json(file_info['info'])
elif uploaded_file.name.lower().endswith('.exe'):
st.subheader("EXE File Analysis")
output_dir = os.path.join(temp_dir, "exe_unpacked")
os.makedirs(output_dir, exist_ok=True)
try:
exe_info = unpack_exe(file_path, output_dir)
st.json(exe_info)
# Check if resources were extracted
resource_dir = os.path.join(output_dir, "resources")
if os.path.exists(resource_dir) and os.listdir(resource_dir):
st.subheader("Extracted Resources")
for resource_file in os.listdir(resource_dir):
st.text(f"Resource: {resource_file}")
except Exception as e:
st.error(f"Error analyzing EXE file: {str(e)}")
elif uploaded_file.name.lower().endswith('.dll'):
st.subheader("DLL File Information")
try:
dll_info = analyze_dll(file_path)
st.json(dll_info)
except Exception as e:
st.error(f"Error analyzing DLL file: {str(e)}") |