Updated winpe_menus.py

This commit is contained in:
2Shirt 2018-12-27 20:15:02 -07:00
parent ec0341027e
commit c3ca58879c
Signed by: 2Shirt
GPG key ID: 152FAC923B0E132C

View file

@ -6,466 +6,468 @@ from functions.windows_setup import *
# STATIC VARIABLES # STATIC VARIABLES
FAST_COPY_PE_ARGS = [ FAST_COPY_PE_ARGS = [
'/cmd=noexist_only', '/cmd=noexist_only',
'/utf8', '/utf8',
'/skip_empty_dir', '/skip_empty_dir',
'/linkdest', '/linkdest',
'/no_ui', '/no_ui',
'/auto_close', '/auto_close',
'/exclude={}'.format(';'.join(FAST_COPY_EXCLUDES)), '/exclude={}'.format(';'.join(FAST_COPY_EXCLUDES)),
] ]
PE_TOOLS = { PE_TOOLS = {
'BlueScreenView': { 'BlueScreenView': {
'Path': r'BlueScreenView\BlueScreenView.exe', 'Path': r'BlueScreenView\BlueScreenView.exe',
}, },
'FastCopy': { 'FastCopy': {
'Path': r'FastCopy\FastCopy.exe', 'Path': r'FastCopy\FastCopy.exe',
'Args': FAST_COPY_PE_ARGS, 'Args': FAST_COPY_PE_ARGS,
}, },
'HWiNFO': { 'HWiNFO': {
'Path': r'HWiNFO\HWiNFO.exe', 'Path': r'HWiNFO\HWiNFO.exe',
}, },
'NT Password Editor': { 'NT Password Editor': {
'Path': r'NT Password Editor\ntpwedit.exe', 'Path': r'NT Password Editor\ntpwedit.exe',
}, },
'Notepad++': { 'Notepad++': {
'Path': r'NotepadPlusPlus\NotepadPlusPlus.exe', 'Path': r'NotepadPlusPlus\NotepadPlusPlus.exe',
}, },
'PhotoRec': { 'PhotoRec': {
'Path': r'TestDisk\photorec_win.exe', 'Path': r'TestDisk\photorec_win.exe',
'Args': ['-new_console:n'], 'Args': ['-new_console:n'],
}, },
'Prime95': { 'Prime95': {
'Path': r'Prime95\prime95.exe', 'Path': r'Prime95\prime95.exe',
}, },
'ProduKey': { 'ProduKey': {
'Path': r'ProduKey\ProduKey.exe', 'Path': r'ProduKey\ProduKey.exe',
}, },
'Q-Dir': { 'Q-Dir': {
'Path': r'Q-Dir\Q-Dir.exe', 'Path': r'Q-Dir\Q-Dir.exe',
}, },
'TestDisk': { 'TestDisk': {
'Path': r'TestDisk\testdisk_win.exe', 'Path': r'TestDisk\testdisk_win.exe',
'Args': ['-new_console:n'], 'Args': ['-new_console:n'],
}, },
} }
def check_pe_tools(): def check_pe_tools():
"""Fix tool paths for WinPE layout.""" """Fix tool paths for WinPE layout."""
for k in PE_TOOLS.keys(): for k in PE_TOOLS.keys():
PE_TOOLS[k]['Path'] = r'{}\{}'.format( PE_TOOLS[k]['Path'] = r'{}\{}'.format(
global_vars['BinDir'], PE_TOOLS[k]['Path']) global_vars['BinDir'], PE_TOOLS[k]['Path'])
global_vars['Tools']['wimlib-imagex'] = re.sub( global_vars['Tools']['wimlib-imagex'] = re.sub(
r'\\x(32|64)', r'\\x(32|64)',
r'', r'',
global_vars['Tools']['wimlib-imagex'], global_vars['Tools']['wimlib-imagex'],
re.IGNORECASE) re.IGNORECASE)
def menu_backup(): def menu_backup():
"""Take backup images of partition(s) in the WIM format.""" """Take backup images of partition(s) in the WIM format."""
errors = False errors = False
other_results = { other_results = {
'Error': { 'Error': {
'CalledProcessError': 'Unknown Error', 'CalledProcessError': 'Unknown Error',
'PathNotFoundError': 'Missing', 'PathNotFoundError': 'Missing',
}, },
'Warning': { 'Warning': {
'GenericAbort': 'Skipped', 'GenericAbort': 'Skipped',
'GenericRepair': 'Repaired', 'GenericRepair': 'Repaired',
}} }}
set_title('{}: Backup Menu'.format(KIT_NAME_FULL)) set_title('{}: Backup Menu'.format(KIT_NAME_FULL))
# Set backup prefix # Set backup prefix
clear_screen() clear_screen()
print_standard('{}\n'.format(global_vars['Title'])) print_standard('{}\n'.format(global_vars['Title']))
ticket_number = get_ticket_number() ticket_number = get_ticket_number()
if ENABLED_TICKET_NUMBERS: if ENABLED_TICKET_NUMBERS:
backup_prefix = ticket_number backup_prefix = ticket_number
else:
backup_prefix = get_simple_string(prompt='Enter backup name prefix')
backup_prefix = backup_prefix.replace(' ', '_')
# Assign drive letters
try_and_print(
message = 'Assigning letters...',
function = assign_volume_letters,
other_results = other_results)
# Mount backup shares
mount_backup_shares(read_write=True)
# Select destination
destination = select_backup_destination(auto_select=False)
# Scan disks
result = try_and_print(
message = 'Getting disk info...',
function = scan_disks,
other_results = other_results)
if result['CS']:
disks = result['Out']
else:
print_error('ERROR: No disks found.')
raise GenericAbort
# Select disk to backup
disk = select_disk('For which disk are we creating backups?', disks)
if not disk:
raise GenericAbort
# "Prep" disk
prep_disk_for_backup(destination, disk, backup_prefix)
# Display details for backup task
clear_screen()
print_info('Create Backup - Details:\n')
if ENABLED_TICKET_NUMBERS:
show_data(message='Ticket:', data=ticket_number)
show_data(
message = 'Source:',
data = '[{}] ({}) {} {}'.format(
disk.get('Table', ''),
disk.get('Type', ''),
disk.get('Name', 'Unknown'),
disk.get('Size', ''),
),
)
show_data(
message = 'Destination:',
data = destination.get('Display Name', destination['Name']),
)
for par in disk['Partitions']:
message = 'Partition {}:'.format(par['Number'])
data = par['Display String']
if par['Number'] in disk['Bad Partitions']:
show_data(message=message, data=data, width=30, warning=True)
if 'Error' in par:
show_data(message='', data=par['Error'], error=True)
elif par['Image Exists']:
show_data(message=message, data=data, width=30, info=True)
else: else:
backup_prefix = get_simple_string(prompt='Enter backup name prefix') show_data(message=message, data=data, width=30)
backup_prefix = backup_prefix.replace(' ', '_') print_standard(disk['Backup Warnings'])
# Assign drive letters # Ask to proceed
try_and_print( if (not ask('Proceed with backup?')):
message = 'Assigning letters...', raise GenericAbort
function = assign_volume_letters,
other_results = other_results)
# Mount backup shares # Backup partition(s)
mount_backup_shares(read_write=True) print_info('\n\nStarting task.\n')
for par in disk['Partitions']:
# Select destination
destination = select_backup_destination(auto_select=False)
# Scan disks
result = try_and_print( result = try_and_print(
message = 'Getting disk info...', message = 'Partition {} Backup...'.format(par['Number']),
function = scan_disks, function = backup_partition,
other_results = other_results) other_results = other_results,
if result['CS']: disk = disk,
disks = result['Out'] par = par)
else: if not result['CS'] and not isinstance(result['Error'], GenericAbort):
print_error('ERROR: No disks found.') errors = True
raise GenericAbort par['Error'] = result['Error']
# Select disk to backup # Verify backup(s)
disk = select_disk('For which disk are we creating backups?', disks) if disk['Valid Partitions']:
if not disk: print_info('\n\nVerifying backup images(s)\n')
raise GenericAbort
# "Prep" disk
prep_disk_for_backup(destination, disk, backup_prefix)
# Display details for backup task
clear_screen()
print_info('Create Backup - Details:\n')
if ENABLED_TICKET_NUMBERS:
show_data(message='Ticket:', data=ticket_number)
show_data(
message = 'Source:',
data = '[{}] ({}) {} {}'.format(
disk.get('Table', ''),
disk.get('Type', ''),
disk.get('Name', 'Unknown'),
disk.get('Size', ''),
),
)
show_data(
message = 'Destination:',
data = destination.get('Display Name', destination['Name']),
)
for par in disk['Partitions']: for par in disk['Partitions']:
message = 'Partition {}:'.format(par['Number']) if par['Number'] in disk['Bad Partitions']:
data = par['Display String'] continue # Skip verification
if par['Number'] in disk['Bad Partitions']: result = try_and_print(
show_data(message=message, data=data, width=30, warning=True) message = 'Partition {} Image...'.format(par['Number']),
if 'Error' in par: function = verify_wim_backup,
show_data(message='', data=par['Error'], error=True) other_results = other_results,
elif par['Image Exists']: partition = par)
show_data(message=message, data=data, width=30, info=True) if not result['CS']:
else: errors = True
show_data(message=message, data=data, width=30) par['Error'] = result['Error']
print_standard(disk['Backup Warnings'])
# Ask to proceed # Print summary
if (not ask('Proceed with backup?')): if errors:
raise GenericAbort print_warning('\nErrors were encountered and are detailed below.')
for par in [p for p in disk['Partitions'] if 'Error' in p]:
# Backup partition(s) print_standard(' Partition {} Error:'.format(par['Number']))
print_info('\n\nStarting task.\n') if hasattr(par['Error'], 'stderr'):
for par in disk['Partitions']:
result = try_and_print(
message = 'Partition {} Backup...'.format(par['Number']),
function = backup_partition,
other_results = other_results,
disk = disk,
par = par)
if not result['CS'] and not isinstance(result['Error'], GenericAbort):
errors = True
par['Error'] = result['Error']
# Verify backup(s)
if disk['Valid Partitions']:
print_info('\n\nVerifying backup images(s)\n')
for par in disk['Partitions']:
if par['Number'] in disk['Bad Partitions']:
continue # Skip verification
result = try_and_print(
message = 'Partition {} Image...'.format(par['Number']),
function = verify_wim_backup,
other_results = other_results,
partition = par)
if not result['CS']:
errors = True
par['Error'] = result['Error']
# Print summary
if errors:
print_warning('\nErrors were encountered and are detailed below.')
for par in [p for p in disk['Partitions'] if 'Error' in p]:
print_standard(' Partition {} Error:'.format(par['Number']))
if hasattr(par['Error'], 'stderr'):
try:
par['Error'] = par['Error'].stderr.decode()
except:
# Deal with badly formatted error message
pass
try:
par['Error'] = par['Error'].splitlines()
par['Error'] = [line.strip() for line in par['Error']]
par['Error'] = [line for line in par['Error'] if line]
for line in par['Error']:
print_error('\t{}'.format(line))
except:
print_error('\t{}'.format(par['Error']))
else:
print_success('\nNo errors were encountered during imaging.')
if 'LogFile' in global_vars and ask('\nReview log?'):
cmd = [
global_vars['Tools']['NotepadPlusPlus'],
global_vars['LogFile']]
try: try:
popen_program(cmd) par['Error'] = par['Error'].stderr.decode()
except Exception: except:
print_error('ERROR: Failed to open log.') # Deal with badly formatted error message
sleep(30) pass
pause('\nPress Enter to return to main menu... ') try:
par['Error'] = par['Error'].splitlines()
par['Error'] = [line.strip() for line in par['Error']]
par['Error'] = [line for line in par['Error'] if line]
for line in par['Error']:
print_error('\t{}'.format(line))
except:
print_error('\t{}'.format(par['Error']))
else:
print_success('\nNo errors were encountered during imaging.')
if 'LogFile' in global_vars and ask('\nReview log?'):
cmd = [
global_vars['Tools']['NotepadPlusPlus'],
global_vars['LogFile']]
try:
popen_program(cmd)
except Exception:
print_error('ERROR: Failed to open log.')
sleep(30)
pause('\nPress Enter to return to main menu... ')
def menu_root(): def menu_root():
"""Main WinPE menu.""" """Main WinPE menu."""
check_pe_tools() check_pe_tools()
menus = [ menus = [
{'Name': 'Create Backups', 'Menu': menu_backup}, {'Name': 'Create Backups', 'Menu': menu_backup},
{'Name': 'Setup Windows', 'Menu': menu_setup}, {'Name': 'Setup Windows', 'Menu': menu_setup},
{'Name': 'Misc Tools', 'Menu': menu_tools}, {'Name': 'Misc Tools', 'Menu': menu_tools},
] ]
actions = [ actions = [
{'Name': 'Command Prompt', 'Letter': 'C'}, {'Name': 'Command Prompt', 'Letter': 'C'},
{'Name': 'Reboot', 'Letter': 'R'}, {'Name': 'Reboot', 'Letter': 'R'},
{'Name': 'Shutdown', 'Letter': 'S'}, {'Name': 'Shutdown', 'Letter': 'S'},
] ]
# Main loop # Main loop
while True: while True:
set_title(KIT_NAME_FULL) set_title(KIT_NAME_FULL)
selection = menu_select( selection = menu_select(
title = 'Main Menu', title = 'Main Menu',
main_entries = menus, main_entries = menus,
action_entries = actions, action_entries = actions,
secret_exit = True) secret_exit = True)
if (selection.isnumeric()): if (selection.isnumeric()):
try: try:
menus[int(selection)-1]['Menu']() menus[int(selection)-1]['Menu']()
except GenericAbort: except GenericAbort:
print_warning('\nAborted\n') print_warning('\nAborted\n')
pause('Press Enter to return to main menu... ') pause('Press Enter to return to main menu... ')
elif (selection == 'C'): elif (selection == 'C'):
run_program(['cmd', '-new_console:n'], check=False) run_program(['cmd', '-new_console:n'], check=False)
elif (selection == 'R'): elif (selection == 'R'):
run_program(['wpeutil', 'reboot']) run_program(['wpeutil', 'reboot'])
elif (selection == 'S'): elif (selection == 'S'):
run_program(['wpeutil', 'shutdown']) run_program(['wpeutil', 'shutdown'])
else: else:
sys.exit() sys.exit()
def menu_setup(): def menu_setup():
"""Format a disk (MBR/GPT), apply a Windows image, and setup boot files.""" """Format a disk (MBR/GPT), apply a Windows image, and setup boot files."""
errors = False errors = False
other_results = { other_results = {
'Error': { 'Error': {
'CalledProcessError': 'Unknown Error', 'CalledProcessError': 'Unknown Error',
'PathNotFoundError': 'Missing', 'PathNotFoundError': 'Missing',
}, },
'Warning': { 'Warning': {
'GenericAbort': 'Skipped', 'GenericAbort': 'Skipped',
'GenericRepair': 'Repaired', 'GenericRepair': 'Repaired',
}} }}
set_title('{}: Setup Menu'.format(KIT_NAME_FULL)) set_title('{}: Setup Menu'.format(KIT_NAME_FULL))
# Set ticket ID # Set ticket ID
clear_screen() clear_screen()
print_standard('{}\n'.format(global_vars['Title'])) print_standard('{}\n'.format(global_vars['Title']))
ticket_number = get_ticket_number() ticket_number = get_ticket_number()
# Select the version of Windows to apply # Select the version of Windows to apply
windows_version = select_windows_version() windows_version = select_windows_version()
# Find Windows image # Find Windows image
# NOTE: Reassign volume letters to ensure all devices are scanned # NOTE: Reassign volume letters to ensure all devices are scanned
try_and_print( try_and_print(
message = 'Assigning volume letters...', message = 'Assigning volume letters...',
function = assign_volume_letters, function = assign_volume_letters,
other_results = other_results) other_results = other_results)
windows_image = find_windows_image(windows_version) windows_image = find_windows_image(windows_version)
# Scan disks # Scan disks
result = try_and_print( result = try_and_print(
message = 'Getting disk info...', message = 'Getting disk info...',
function = scan_disks, function = scan_disks,
other_results = other_results) other_results = other_results)
if result['CS']: if result['CS']:
disks = result['Out'] disks = result['Out']
else: else:
print_error('ERROR: No disks found.') print_error('ERROR: No disks found.')
raise GenericAbort raise GenericAbort
# Select disk to use as the OS disk # Select disk to use as the OS disk
dest_disk = select_disk('To which disk are we installing Windows?', disks) dest_disk = select_disk('To which disk are we installing Windows?', disks)
if not dest_disk: if not dest_disk:
raise GenericAbort raise GenericAbort
# "Prep" disk # "Prep" disk
prep_disk_for_formatting(dest_disk) prep_disk_for_formatting(dest_disk)
# Display details for setup task # Display details for setup task
clear_screen() clear_screen()
print_info('Setup Windows - Details:\n') print_info('Setup Windows - Details:\n')
if ENABLED_TICKET_NUMBERS: if ENABLED_TICKET_NUMBERS:
show_data(message='Ticket:', data=ticket_number) show_data(message='Ticket:', data=ticket_number)
show_data(message='Installing:', data=windows_version['Name']) show_data(message='Installing:', data=windows_version['Name'])
show_data(
message = 'Boot Method:',
data = 'UEFI (GPT)' if dest_disk['Use GPT'] else 'Legacy (MBR)')
show_data(message='Using Image:', data=windows_image['Path'])
show_data(
message = 'ERASING:',
data = '[{}] ({}) {} {}\n'.format(
dest_disk.get('Table', ''),
dest_disk.get('Type', ''),
dest_disk.get('Name', 'Unknown'),
dest_disk.get('Size', ''),
),
warning = True)
for par in dest_disk['Partitions']:
show_data( show_data(
message = 'Boot Method:', message = 'Partition {}:'.format(par['Number']),
data = 'UEFI (GPT)' if dest_disk['Use GPT'] else 'Legacy (MBR)') data = par['Display String'],
show_data(message='Using Image:', data=windows_image['Path']) warning = True)
show_data( print_warning(dest_disk['Format Warnings'])
message = 'ERASING:',
data = '[{}] ({}) {} {}\n'.format(
dest_disk.get('Table', ''),
dest_disk.get('Type', ''),
dest_disk.get('Name', 'Unknown'),
dest_disk.get('Size', ''),
),
warning = True)
for par in dest_disk['Partitions']:
show_data(
message = 'Partition {}:'.format(par['Number']),
data = par['Display String'],
warning = True)
print_warning(dest_disk['Format Warnings'])
if (not ask('Is this correct?')): if (not ask('Is this correct?')):
raise GenericAbort raise GenericAbort
# Safety check # Safety check
print_standard('\nSAFETY CHECK') print_standard('\nSAFETY CHECK')
print_warning('All data will be DELETED from the ' print_warning('All data will be DELETED from the '
'disk and partition(s) listed above.') 'disk and partition(s) listed above.')
print_warning('This is irreversible and will lead ' print_warning('This is irreversible and will lead '
'to {CLEAR}{RED}DATA LOSS.'.format(**COLORS)) 'to {CLEAR}{RED}DATA LOSS.'.format(**COLORS))
if (not ask('Asking again to confirm, is this correct?')): if (not ask('Asking again to confirm, is this correct?')):
raise GenericAbort raise GenericAbort
# Remove volume letters so S, T, & W can be used below # Remove volume letters so S, T, & W can be used below
try_and_print( try_and_print(
message = 'Removing volume letters...', message = 'Removing volume letters...',
function = remove_volume_letters, function = remove_volume_letters,
other_results = other_results, other_results = other_results,
keep=windows_image['Letter']) keep=windows_image['Letter'])
# Assign new letter for local source if necessary # Assign new letter for local source if necessary
if windows_image['Local'] and windows_image['Letter'] in ['S', 'T', 'W']: if windows_image['Local'] and windows_image['Letter'] in ['S', 'T', 'W']:
new_letter = try_and_print( new_letter = try_and_print(
message = 'Reassigning source volume letter...', message = 'Reassigning source volume letter...',
function = reassign_volume_letter, function = reassign_volume_letter,
other_results = other_results, other_results = other_results,
letter=windows_image['Letter']) letter=windows_image['Letter'])
windows_image['Path'] = '{}{}'.format( windows_image['Path'] = '{}{}'.format(
new_letter, windows_image['Path'][1:]) new_letter, windows_image['Path'][1:])
windows_image['Letter'] = new_letter windows_image['Letter'] = new_letter
# Format and partition disk # Format and partition disk
result = try_and_print( result = try_and_print(
message = 'Formatting disk...', message = 'Formatting disk...',
function = format_disk, function = format_disk,
other_results = other_results, other_results = other_results,
disk = dest_disk, disk = dest_disk,
use_gpt = dest_disk['Use GPT']) use_gpt = dest_disk['Use GPT'])
if not result['CS']: if not result['CS']:
# We need to crash as the disk is in an unknown state # We need to crash as the disk is in an unknown state
print_error('ERROR: Failed to format disk.') print_error('ERROR: Failed to format disk.')
raise GenericAbort raise GenericAbort
# Apply Image # Apply Image
result = try_and_print( result = try_and_print(
message = 'Applying image...', message = 'Applying image...',
function = setup_windows, function = setup_windows,
other_results = other_results, other_results = other_results,
windows_image = windows_image, windows_image = windows_image,
windows_version = windows_version) windows_version = windows_version)
if not result['CS']: if not result['CS']:
# We need to crash as the disk is in an unknown state # We need to crash as the disk is in an unknown state
print_error('ERROR: Failed to apply image.') print_error('ERROR: Failed to apply image.')
raise GenericAbort raise GenericAbort
# Create Boot files # Create Boot files
try_and_print( try_and_print(
message = 'Updating boot files...', message = 'Updating boot files...',
function = update_boot_partition, function = update_boot_partition,
other_results = other_results) other_results = other_results)
# Setup WinRE # Setup WinRE
try_and_print( try_and_print(
message = 'Updating recovery tools...', message = 'Updating recovery tools...',
function = setup_windows_re, function = setup_windows_re,
other_results = other_results, other_results = other_results,
windows_version = windows_version) windows_version = windows_version)
# Copy WinPE log(s) # Copy WinPE log(s)
source = r'{}\Logs'.format(global_vars['ClientDir']) source = r'{}\Logs'.format(global_vars['ClientDir'])
dest = r'W:\{}\Logs\WinPE'.format(KIT_NAME_SHORT) dest = r'W:\{}\Logs\WinPE'.format(KIT_NAME_SHORT)
shutil.copytree(source, dest) shutil.copytree(source, dest)
# Print summary # Print summary
print_standard('\nDone.') print_standard('\nDone.')
if 'LogFile' in global_vars and ask('\nReview log?'): if 'LogFile' in global_vars and ask('\nReview log?'):
cmd = [ cmd = [
global_vars['Tools']['NotepadPlusPlus'], global_vars['Tools']['NotepadPlusPlus'],
global_vars['LogFile']] global_vars['LogFile']]
try: try:
popen_program(cmd) popen_program(cmd)
except Exception: except Exception:
print_error('ERROR: Failed to open log.') print_error('ERROR: Failed to open log.')
sleep(30) sleep(30)
pause('\nPress Enter to return to main menu... ') pause('\nPress Enter to return to main menu... ')
def menu_tools(): def menu_tools():
"""Tool launcher menu.""" """Tool launcher menu."""
tools = [{'Name': k} for k in sorted(PE_TOOLS.keys())] tools = [{'Name': k} for k in sorted(PE_TOOLS.keys())]
actions = [{'Name': 'Main Menu', 'Letter': 'M'},] actions = [{'Name': 'Main Menu', 'Letter': 'M'},]
set_title(KIT_NAME_FULL) set_title(KIT_NAME_FULL)
# Menu loop # Menu loop
while True: while True:
selection = menu_select( selection = menu_select(
title = 'Tools Menu', title = 'Tools Menu',
main_entries = tools, main_entries = tools,
action_entries = actions) action_entries = actions)
if (selection.isnumeric()): if (selection.isnumeric()):
name = tools[int(selection)-1]['Name'] name = tools[int(selection)-1]['Name']
cmd = [PE_TOOLS[name]['Path']] + PE_TOOLS[name].get('Args', []) cmd = [PE_TOOLS[name]['Path']] + PE_TOOLS[name].get('Args', [])
if name == 'Blue Screen View': if name == 'Blue Screen View':
# Select path to scan # Select path to scan
minidump_path = select_minidump_path() minidump_path = select_minidump_path()
if minidump_path: if minidump_path:
cmd.extend(['/MiniDumpFolder', minidump_path]) cmd.extend(['/MiniDumpFolder', minidump_path])
try: try:
popen_program(cmd) popen_program(cmd)
except Exception: except Exception:
print_error('Failed to run {}'.format(name)) print_error('Failed to run {}'.format(name))
sleep(2) sleep(2)
pause() pause()
elif (selection == 'M'): elif (selection == 'M'):
break break
def select_minidump_path(): def select_minidump_path():
"""Select BSOD minidump path from a menu.""" """Select BSOD minidump path from a menu."""
dumps = [] dumps = []
# Assign volume letters first # Assign volume letters first
assign_volume_letters() assign_volume_letters()
# Search for minidumps # Search for minidumps
set_thread_error_mode(silent=True) # Prevents "No disk" popups set_thread_error_mode(silent=True) # Prevents "No disk" popups
for d in psutil.disk_partitions(): for d in psutil.disk_partitions():
if global_vars['Env']['SYSTEMDRIVE'].upper() in d.mountpoint: if global_vars['Env']['SYSTEMDRIVE'].upper() in d.mountpoint:
# Skip RAMDisk # Skip RAMDisk
continue continue
if os.path.exists(r'{}Windows\MiniDump'.format(d.mountpoint)): if os.path.exists(r'{}Windows\MiniDump'.format(d.mountpoint)):
dumps.append({'Name': r'{}Windows\MiniDump'.format(d.mountpoint)}) dumps.append({'Name': r'{}Windows\MiniDump'.format(d.mountpoint)})
set_thread_error_mode(silent=False) # Return to normal set_thread_error_mode(silent=False) # Return to normal
# Check results before showing menu # Check results before showing menu
if len(dumps) == 0: if len(dumps) == 0:
print_error('ERROR: No BSoD / MiniDump paths found') print_error('ERROR: No BSoD / MiniDump paths found')
sleep(2) sleep(2)
return None return None
# Menu # Menu
selection = menu_select( selection = menu_select(
title = 'Which BSoD / MiniDump path are we scanning?', title = 'Which BSoD / MiniDump path are we scanning?',
main_entries = dumps) main_entries = dumps)
return dumps[int(selection) - 1]['Name'] return dumps[int(selection) - 1]['Name']
if __name__ == '__main__': if __name__ == '__main__':
print("This file is not meant to be called directly.") print("This file is not meant to be called directly.")
# vim: sts=2 sw=2 ts=2