diff --git a/.bin/Scripts/Launch.cmd b/.bin/Scripts/Launch.cmd index d178a26f..8725613b 100644 --- a/.bin/Scripts/Launch.cmd +++ b/.bin/Scripts/Launch.cmd @@ -20,6 +20,7 @@ call :DeQuote L_TYPE :SetVariables set "ARCHIVE_PASS=Abracadabra" set "OFFICE_SERVER=10.0.0.10" +set "QUICKBOOKS_SERVER=10.0.0.10" rem Set ARCH to 32 as a gross assumption and check for x86_64 status set ARCH=32 if /i "%PROCESSOR_ARCHITECTURE%" == "AMD64" set "ARCH=64" @@ -59,13 +60,14 @@ if not defined IN_CONEMU ( :CheckLaunchType rem Jump to the selected launch type or show usage -if /i "%L_TYPE%" == "Console" (goto LaunchConsole) -if /i "%L_TYPE%" == "Folder" (goto LaunchFolder) -if /i "%L_TYPE%" == "Office" (goto LaunchOfficeSetup) -if /i "%L_TYPE%" == "Program" (goto LaunchProgram) -if /i "%L_TYPE%" == "PSScript" (goto LaunchPSScript) -if /i "%L_TYPE%" == "PyScript" (goto LaunchPyScript) -if /i "%L_TYPE%" == "PywScript" (goto LaunchPywScript) +if /i "%L_TYPE%" == "Console" (goto LaunchConsole) +if /i "%L_TYPE%" == "Folder" (goto LaunchFolder) +if /i "%L_TYPE%" == "Office" (goto LaunchOfficeSetup) +if /i "%L_TYPE%" == "QuickBooks" (goto LaunchQuickBooksSetup) +if /i "%L_TYPE%" == "Program" (goto LaunchProgram) +if /i "%L_TYPE%" == "PSScript" (goto LaunchPSScript) +if /i "%L_TYPE%" == "PyScript" (goto LaunchPyScript) +if /i "%L_TYPE%" == "PywScript" (goto LaunchPywScript) goto Usage :LaunchConsole @@ -141,6 +143,33 @@ if "%_odt%" == "True" ( ) goto Exit +:LaunchQuickBooksSetup +rem set args and copy setup files to system +rem NOTE: init_client_dir.cmd sets %client_dir% and creates %SystemDrive%\WK\QuickBooks folder +call "%bin%\Scripts\init_client_dir.cmd" /QuickBooks +echo Copying setup file(s) for %L_ITEM%... +rem copy setup files from QUICKBOOKS_SERVER +set "fastcopy_args=/cmd=diff /no_ui /auto_close" +set "product=%L_PATH%\%L_ITEM%" +set "product_name=%L_ITEM%" +call :GetBasename product_name || goto ErrorBasename +set "source=\\%QUICKBOOKS_SERVER%\QuickBooks\!product!" +set "dest=%client_dir%\QuickBooks" +rem Verify source +if not exist "!source!" (goto ErrorQuickBooksSourceNotFound) +rem Copy setup file(s) to system +start "" /wait "%FASTCOPY%" !fastcopy_args! "!source!" /to="!dest!\" +rem Run setup +if exist "!dest!\!product_name!\Setup.exe" ( + pushd "!dest!\!product_name!" + start "" "!dest!\!product_name!\Setup.exe" || goto ErrorUnknown + popd +) else ( + rem QuickBooks source not supported by this script + goto ErrorQuickBooksUnsupported +) +goto Exit + :LaunchProgram rem Test L_PATH and set %_path% call :TestPath || goto ErrorProgramNotFound @@ -222,14 +251,15 @@ goto Exit :Usage echo. echo.Usage (via defined variables): -echo. L_TYPE L_PATH L_ITEM L_ARGS -echo. Console Working Dir Program Args [L_CHECK] [L_ELEV] [L_NCMD] [L_WAIT] -echo. Folder Folder '.' [L_CHECK] [L_NCMD] -echo. Office Year Product [L_CHECK] [L_NCMD] -echo. Program Working Dir Program Args [L_CHECK] [L_ELEV] [L_NCMD] [L_WAIT] -echo. PSScript Scripts Script [L_CHECK] [L_ELEV] [L_NCMD] -echo. PyScript Scripts Script [L_CHECK] [L_ELEV] [L_NCMD] -echo. PywScript Scripts Script [L_CHECK] [L_ELEV] [L_NCMD] +echo. L_TYPE L_PATH L_ITEM L_ARGS +echo. Console Working Dir Program Args [L_CHECK] [L_ELEV] [L_NCMD] [L_WAIT] +echo. Folder Folder '.' [L_CHECK] [L_NCMD] +echo. Office Year Product [L_CHECK] [L_NCMD] +echo. QuickBooks Year Product [L_CHECK] [L_NCMD] +echo. Program Working Dir Program Args [L_CHECK] [L_ELEV] [L_NCMD] [L_WAIT] +echo. PSScript Scripts Script [L_CHECK] [L_ELEV] [L_NCMD] +echo. PyScript Scripts Script [L_CHECK] [L_ELEV] [L_NCMD] +echo. PywScript Scripts Script [L_CHECK] [L_ELEV] [L_NCMD] echo. echo. NOTE: PywScript uses Python's window instead of %CON% echo. @@ -322,6 +352,18 @@ echo ERROR: Office version not supported by this script. start "" "explorer.exe" "%client_dir%\Office" goto Abort +:ErrorQuickBooksSourceNotFound +echo. +echo ERROR: QuickBooks source "%L_ITEM%" not found. +goto Abort + +:ErrorQuickBooksUnsupported +rem Source is not an executable nor is a folder with a setup.exe file inside. Open explorer to local setup file(s) instead. +echo. +echo ERROR: QuickBooks version not supported by this script. +start "" "explorer.exe" "%client_dir%\QuickBooks" +goto Abort + :ErrorProgramNotFound echo. echo ERROR: Program "%prog%" not found. diff --git a/.bin/Scripts/_Update Kit.cmd b/.bin/Scripts/_Update Kit.cmd index 812ae960..8d9c8c1c 100644 --- a/.bin/Scripts/_Update Kit.cmd +++ b/.bin/Scripts/_Update Kit.cmd @@ -30,7 +30,7 @@ call :FindBin :: Set L_NCMD to True to stay in the native console window :: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted set L_TYPE=PyScript -set L_PATH=Script +set L_PATH=Scripts set L_ITEM=update_kit.py set L_ARGS= set L_7ZIP= diff --git a/.bin/Scripts/activate.py b/.bin/Scripts/activate.py index 30988acb..f77609eb 100644 --- a/.bin/Scripts/activate.py +++ b/.bin/Scripts/activate.py @@ -9,13 +9,8 @@ import subprocess os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: Windows Activation Tool') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) -vars_wk['ProduKey'] = '{BinDir}\\ProduKey\\ProduKey.exe'.format(**vars_wk) -vars_wk['SevenZip'] = '{BinDir}\\7-Zip\\7za.exe'.format(**vars_wk) -if vars_wk['Arch'] == 64: - vars_wk['SevenZip'] = vars_wk['SevenZip'].replace('7za.exe', '7za64.exe') - vars_wk['ProduKey'] = vars_wk['ProduKey'].replace('ProduKey.exe', 'ProduKey64.exe') +init_global_vars() +set_global_vars() def abort(): print_warning('Aborted.') @@ -23,35 +18,35 @@ def abort(): def activate_with_bios(): """Attempt to activate Windows with a key stored in the BIOS.""" - extract_item('ProduKey', vars_wk, silent=True) + extract_item('ProduKey', silent=True) _args = [ '/nosavereg', - '/scomma', '{TmpDir}\\keys.csv'.format(**vars_wk), + '/scomma', '{TmpDir}\\keys.csv'.format(**global_vars), '/WindowsKeys', '1', '/OfficeKeys', '0', '/IEKeys', '0', '/SQLKeys', '0', '/ExchangeKeys', '0'] try: - run_program(vars_wk['ProduKey'], _args, pipe=False) + run_program(global_vars['Tools']['ProduKey'], _args, pipe=False) except subprocess.CalledProcessError: print_error('ERROR: Failed to extract BIOS key') abort() else: - with open ('{TmpDir}\\keys.csv'.format(**vars_wk), newline='') as key_file: + with open ('{TmpDir}\\keys.csv'.format(**global_vars), newline='') as key_file: key_reader = csv.reader(key_file) _key_found = False for key in key_reader: if 'BIOS' in key[0] and re.match(r'^\w{5}-\w{5}-\w{5}-\w{5}-\w{5}$', key[2]): _key_found = True print_standard('BIOS key found, installing...') - run_program('cscript {SYSTEMROOT}\\System32\\slmgr.vbs /ipk {pkey} //nologo'.format(**vars_wk['Env'], pkey=key[2]), check=False, shell=True) + run_program('cscript {SYSTEMROOT}\\System32\\slmgr.vbs /ipk {pkey} //nologo'.format(**global_vars['Env'], pkey=key[2]), check=False, shell=True) sleep(15) print_standard('Attempting activation...') - run_program('cscript {SYSTEMROOT}\\System32\\slmgr.vbs /ato //nologo'.format(**vars_wk['Env']), check=False, shell=True) + run_program('cscript {SYSTEMROOT}\\System32\\slmgr.vbs /ato //nologo'.format(**global_vars['Env']), check=False, shell=True) sleep(15) # Open system properties for user verification - subprocess.Popen(['control', 'system']) + popen_program(['control', 'system']) break if not _key_found: print_error('ERROR: BIOS not key found.') @@ -59,25 +54,21 @@ def activate_with_bios(): def activate_with_hive(): """Scan any transferred software hives for Windows keys and attempt activation.""" - extract_item('ProduKey', vars_wk, silent=True) - -def exit_script(): - pause("Press Enter to exit...") - quit() + extract_item('ProduKey', silent=True) def is_activated(): """Updates activation status, checks if activated, and returns a bool.""" - _out = run_program('cscript /nologo {SYSTEMROOT}\\System32\\slmgr.vbs /xpr'.format(**vars_wk['Env'])) + _out = run_program('cscript /nologo {SYSTEMROOT}\\System32\\slmgr.vbs /xpr'.format(**global_vars['Env'])) _out = _out.stdout.decode().splitlines() _out = [l for l in _out if re.match(r'^\s', l)] if len(_out) > 0: - vars_wk['Activation'] = re.sub(r'^\s+', '', _out[0]) + global_vars['OS']['Activation'] = re.sub(r'^\s+', '', _out[0]) else: - vars_wk['Activation'] = 'Activation status unknown' - return 'The machine is permanently activated.' in vars_wk['Activation'] + global_vars['OS']['Activation'] = 'Activation status unknown' + return 'The machine is permanently activated.' in global_vars['OS']['Activation'] if __name__ == '__main__': - stay_awake(vars_wk) + stay_awake() # Bail early if already activated if is_activated(): print_info('This system is already activated') @@ -88,7 +79,7 @@ if __name__ == '__main__': {'Name': 'Activate with BIOS key', 'Function': activate_with_bios}, {'Name': 'Activate with transferred SW hive', 'Function': activate_with_hive, 'Disabled': True}, ] - if not re.match(r'^(8|10)$', vars_wk['Version']): + if not re.match(r'^(8|10)$', global_vars['OS']['Version']): activation_methods[0]['Disabled'] = True actions = [ {'Name': 'Quit', 'Letter': 'Q'}, @@ -104,7 +95,7 @@ if __name__ == '__main__': elif selection == 'Q': exit_script() - # Quit + # Done print_success('Done.') - kill_process('caffeine.exe') - exit_script() \ No newline at end of file + pause("Press Enter to exit...") + exit_script() diff --git a/.bin/Scripts/check_disk.py b/.bin/Scripts/check_disk.py index 9b461945..8c125c56 100644 --- a/.bin/Scripts/check_disk.py +++ b/.bin/Scripts/check_disk.py @@ -1,37 +1,33 @@ # Wizard Kit: Check Disk Tool import os -import subprocess # Init os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: Check Disk Tool') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) +init_global_vars() +set_global_vars(LogFile='{LogDir}\\Check Disk.log'.format(**global_vars)) def abort(): - print_warning('Aborted.', vars_wk['LogFile']) + print_warning('Aborted.', global_vars['LogFile']) exit_script() -def exit_script(): - pause("Press Enter to exit...") - quit() - if __name__ == '__main__': - stay_awake(vars_wk) - print_info('* Running CHKDSK (read-only) on {SYSTEMDRIVE}'.format(**vars_wk['Env'])) - # Run scan (read-only) - try: - if vars_wk['Version'] in ['8', '10']: - run_program('chkdsk {SYSTEMDRIVE} /scan /pref'.format(**vars_wk['Env']), pipe=False) - else: - # Windows 7 and older - run_program('chkdsk {SYSTEMDRIVE}'.format(**vars_wk['Env']), pipe=False) - except subprocess.CalledProcessError: - print_error('ERROR: CHKDSK encountered a problem. Please review any messages above.') - abort() + stay_awake() + other_results = { + 'Error': { + 'CalledProcessError': 'Unknown Error', + }, + 'Warning': { + 'GenericRepair': 'Repaired', + 'UnsupportedOSError': 'Unsupported OS', + }} + os.system('cls') + print_info('Check Disk Tool') + try_and_print(message='CHKDSK ({SYSTEMDRIVE})...'.format(**global_vars['Env']), function=run_chkdsk, cs='CS', ns='NS', other_results=other_results) + # Done print_success('Done.') - kill_process('caffeine.exe') + pause("Press Enter to exit...") exit_script() diff --git a/.bin/Scripts/check_disk_fix.py b/.bin/Scripts/check_disk_fix.py index 1817dfd8..fad6724a 100644 --- a/.bin/Scripts/check_disk_fix.py +++ b/.bin/Scripts/check_disk_fix.py @@ -1,43 +1,37 @@ -# Wizard Kit: Check Disk Tool +# Wizard Kit: Check Disk (Fix) Tool import os -import subprocess # Init os.chdir(os.path.dirname(os.path.realpath(__file__))) -os.system('title Wizard Kit: Check Disk Tool') +os.system('title Wizard Kit: Check Disk (Fix) Tool') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) +init_global_vars() +set_global_vars(LogFile='{LogDir}\\Check Disk (Fix).log'.format(**global_vars)) def abort(): - print_warning('Aborted.', vars_wk['LogFile']) + print_warning('Aborted.', global_vars['LogFile']) exit_script() -def exit_script(): - pause("Press Enter to reboot...") - run_program('shutdown -r -t 3', check=False) - quit() - if __name__ == '__main__': - stay_awake(vars_wk) - print_info('* Running CHKDSK (repairs) on {SYSTEMDRIVE}'.format(**vars_wk['Env'])) - # Run scan (and attempt to repair errors) - try: - if vars_wk['Version'] in ['8', '10']: - try: - run_program('chkdsk {SYSTEMDRIVE} /sdcleanup /spotfix'.format(**vars_wk['Env']), pipe=False) - except subprocess.CalledProcessError: - print_error('ERROR: CHKDSK is still reporting problems.') - if ask('Run full offline scan?'): - run_program('chkdsk {SYSTEMDRIVE} /offlinescanandfix'.format(**vars_wk['Env']), pipe=False) - else: - # Windows 7 and older - run_program('chkdsk {SYSTEMDRIVE} /F'.format(**vars_wk['Env']), pipe=False) - except subprocess.CalledProcessError: - print_error('ERROR: CHKDSK encountered a problem. Please review any messages above.') - abort() + stay_awake() + other_results = { + 'Error': { + 'CalledProcessError': 'Unknown Error', + }, + 'Warning': { + 'GenericRepair': 'Repaired', + 'UnsupportedOSError': 'Unsupported OS', + }} + offline_scan = True + os.system('cls') + print_info('Check Disk Tool') + _spotfix = try_and_print(message='CHKDSK Spotfix ({SYSTEMDRIVE})...'.format(**global_vars['Env']), function=run_chkdsk_spotfix, cs='CS', ns='NS', other_results=other_results) + if global_vars['OS']['Version'] in ['8', '10'] and not _spotfix['CS']: + offline_scan = ask('Run full offline scan?') + try_and_print(message='CHKDSK Offline ({SYSTEMDRIVE})...'.format(**global_vars['Env']), function=run_chkdsk_offline, cs='Scheduled', ns='Error', other_results=other_results) + # Done print_success('Done.') - kill_process('caffeine.exe') - exit_script() + pause("Press Enter to exit...") + exit_script() \ No newline at end of file diff --git a/.bin/Scripts/compress_bin.cmd b/.bin/Scripts/compress_bin.cmd index affd2362..ed697a8b 100644 --- a/.bin/Scripts/compress_bin.cmd +++ b/.bin/Scripts/compress_bin.cmd @@ -1,12 +1,27 @@ @echo off -setlocal +setlocal enabledelayedexpansion pushd "%~dp0" +rem Prep +mkdir _out\_Drivers +set "out=%cd%\_out" + +rem _Drivers +pushd _Drivers +for %%f in (*) do ( + set "file=%%f" + "%programfiles%\7-Zip\7z.exe" a -t7z -mx=9 -myx=9 -ms=on -mhe -pAbracadabra "%out%\_Drivers\!file:~0,-4!.7z" "%%f" +) +popd + +rem Rest for /d %%d in (*) do ( - pushd "%%d" - "%programfiles%\7-Zip\7z.exe" a -t7z -mx=9 -myx=9 -ms=on -mhe -pAbracadabra "..\%%d.7z" * - popd + if not "%%d" == "_out" ( + pushd "%%d" + "%programfiles%\7-Zip\7z.exe" a -t7z -mx=9 -myx=9 -ms=on -mhe -pAbracadabra "%out%\%%d.7z" * + popd + ) ) popd diff --git a/.bin/Scripts/dism.py b/.bin/Scripts/dism.py index 15d75e9e..a1ceb7fa 100644 --- a/.bin/Scripts/dism.py +++ b/.bin/Scripts/dism.py @@ -1,96 +1,45 @@ # Wizard Kit: DISM wrapper import os -import subprocess # Init os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: DISM helper Tool') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) -os.makedirs('{LogDir}'.format(**vars_wk), exist_ok=True) -vars_wk['LogFile'] = '{LogDir}\\dism_helper.log'.format(**vars_wk) +init_global_vars() +set_global_vars(LogFile='{LogDir}\\DISM helper tool.log'.format(**global_vars)) def abort(): - print_warning('Aborted.', vars_wk['LogFile']) + print_warning('Aborted.') exit_script() -def exit_script(): - pause("Press Enter to exit...") - quit() - -def check_health(): - _args = [ - '/Online', - '/Cleanup-Image', - '/CheckHealth', - '/LogPath:{LogDir}\\DISM_CheckHealth.log'.format(**vars_wk)] - try: - _result = run_program('dism', _args).stdout.decode() - except subprocess.CalledProcessError: - print_error('ERROR: failed to run DISM health check', vars_wk['LogFile']) - _result = ['Unknown'] - else: - # Check result - if re.search(r'No component store corruption detected', _result, re.IGNORECASE): - return True - else: - for line in _result: - line = ' ' + line - print_warning(line, vars_wk['LogFile']) - print_error('ERROR: DISM encountered errors, please review details above', vars_wk['LogFile']) - return False - -def restore_health(): - _args = [ - '/Online', - '/Cleanup-Image', - '/RestoreHealth', - '/LogPath:{LogDir}\\DISM_RestoreHealth.log'.format(**vars_wk), - '-new_console:n', - '-new_console:s33V'] - run_program('dism', _args, pipe=False, check=False) - wait_for_process('dism') - -def scan_health(): - _args = [ - '/Online', - '/Cleanup-Image', - '/ScanHealth', - '/LogPath:{LogDir}\\DISM_ScanHealth.log'.format(**vars_wk), - '-new_console:n', - '-new_console:s33V'] - run_program('dism', _args, pipe=False, check=False) - wait_for_process('dism') - if __name__ == '__main__': - stay_awake(vars_wk) - if vars_wk['Version'] in ['8', '10']: - options = [ - {'Name': 'Check Health', 'Command': 'Check'}, - {'Name': 'Restore Health', 'Command': 'Restore'}] - actions = [{'Name': 'Quit', 'Letter': 'Q'}] - selection = menu_select('Please select action to perform', options, actions) - run_program('cls', check=False, pipe=False, shell=True) - if selection == 'Q': - abort() - elif options[int(selection)-1]['Command'] == 'Check': - print_info('Scanning for component store corruption...', vars_wk['LogFile']) - scan_health() - if check_health(): - print_success('No component store corruption detected.', vars_wk['LogFile']) - elif options[int(selection)-1]['Command'] == 'Restore': - print_info('Scanning for, and attempting to repair, component store corruption...', vars_wk['LogFile']) - restore_health() - if check_health(): - print_success('No component store corruption detected.', vars_wk['LogFile']) - else: - abort() + stay_awake() + other_results = { + 'Error': { + 'CalledProcessError': 'Unknown Error', + }, + 'Warning': { + 'GenericRepair': 'Repaired', + 'UnsupportedOSError': 'Unsupported OS', + }} + options = [ + {'Name': 'Check Health', 'Command': 'Check'}, + {'Name': 'Restore Health', 'Command': 'Restore'}] + actions = [{'Name': 'Quit', 'Letter': 'Q'}] + selection = menu_select('Please select action to perform', options, actions) + os.system('cls') + print_info('DISM helper tool') + if selection == 'Q': + abort() + elif options[int(selection)-1]['Command'] == 'Check': + try_and_print(message='DISM ScanHealth...', function=run_dism_scan_health, cs='No corruption', ns='Corruption detected', other_results=other_results) + elif options[int(selection)-1]['Command'] == 'Restore': + try_and_print(message='DISM RestoreHealth...', function=run_dism_restore_health, cs='No corruption', ns='Corruption detected', other_results=other_results) else: - # Windows 7 and older - print_error('ERROR: This tool is not intended for {ProductName}.'.format(**vars_wk), vars_wk['LogFile']) + abort() - print_success('Done.', vars_wk['LogFile']) - kill_process('caffeine.exe') + # Done + print_success('Done.') + pause("Press Enter to exit...") exit_script() diff --git a/.bin/Scripts/functions.py b/.bin/Scripts/functions.py index e7dee7e2..2c8db109 100644 --- a/.bin/Scripts/functions.py +++ b/.bin/Scripts/functions.py @@ -6,9 +6,13 @@ import psutil import re import shutil import subprocess +import sys import time +import traceback import winreg +from subprocess import CalledProcessError + # STATIC VARIABLES ARCHIVE_PASSWORD='Abracadabra' COLORS = { @@ -16,7 +20,8 @@ COLORS = { 'RED': '\033[31m', 'GREEN': '\033[32m', 'YELLOW': '\033[33m', - 'BLUE': '\033[34m'} + 'BLUE': '\033[34m' +} BACKUP_SERVERS = [ { 'IP': '10.0.0.10', 'Mounted': False, @@ -35,6 +40,7 @@ BACKUP_SERVERS = [ ] CLIENT_INFO_SERVER = { 'IP': '10.0.0.10', + 'RegEntry': r'0x10001,0xcc674aebbd889f5fd553564adcf3cab550791eca12542033d52134db893c95aabb6b318a4621d8116f6838d873edfe9db4509e1dfc9177ee7484808a62cbc42b913387f694fd67e81950f85198acf721c5767b54db7b864d69cce65e12c78c87d0fb4fc54996609c9b9274b1de7bae2f95000c9ca8d7e3f9b3f2cdb21cd578adf9ba98d10400a8203bb1a879a4cd2fad99baeb12738b9b4b99fec821f881acb62598a43c059f74af287bc8dceeb4821317aa44e2e0ee66d346927a654c702854a71a2eaed6a53f6be9360c7049974a2597a548361da42ac982ae55f993700a8b1fc9f3b4458314fbd41f239de0a29716cdcefbbb2c8d02b4c2effa4163cfeac9', 'Share': '/srv/ClientInfo', 'User': 'wkdiag', } @@ -70,9 +76,118 @@ EXTRA_FOLDERS = [ 'OneDrive', 'SkyDrive', ] +TOOLS = { + # NOTE: The brace variables will be expanded at runtime + 'AIDA64': { + '32': '{BinDir}\\AIDA64\\aida64.exe'}, + 'AutoRuns': { + '32': '{BinDir}\\SysinternalsSuite\\autoruns.exe', + '64': '{BinDir}\\SysinternalsSuite\\autoruns64.exe'}, + 'BleachBit': { + '32': '{BinDir}\\BleachBit\\bleachbit_console.exe'}, + 'Caffeine': { + '32': '{BinDir}\\caffeine\\caffeine.exe'}, + 'Du': { + '32': '{BinDir}\\SysinternalsSuite\\du.exe', + '64': '{BinDir}\\SysinternalsSuite\\du64.exe'}, + 'ERUNT': { + '32': '{BinDir}\\erunt\\ERUNT.EXE'}, + 'Everything': { + '32': '{BinDir}\\Everything\\Everything.exe', + '64': '{BinDir}\\Everything\\Everything64.exe'}, + 'FastCopy': { + '32': '{BinDir}\\FastCopy\\FastCopy.exe', + '64': '{BinDir}\\FastCopy\\FastCopy64.exe'}, + 'HitmanPro': { + '32': '{BinDir}\\HitmanPro\\HitmanPro.exe', + '64': '{BinDir}\\HitmanPro\\HitmanPro64.exe'}, + 'HWiNFO': { + '32': '{BinDir}\\HWiNFO\\HWiNFO.exe', + '64': '{BinDir}\\HWiNFO\\HWiNFO64.exe'}, + 'KVRT': { + '32': '{BinDir}\\KVRT\\KVRT.exe'}, + 'NotepadPlusPlus': { + '32': '{BinDir}\\notepadplusplus\\notepadplusplus.exe'}, + 'ProduKey': { + '32': '{BinDir}\\ProduKey\\ProduKey.exe', + '64': '{BinDir}\\ProduKey\\ProduKey64.exe'}, + 'PuTTY-PSFTP': { + '32': '{BinDir}\\PuTTY\\PSFTP.EXE'}, + 'RKill': { + '32': '{BinDir}\\RKill\\RKill.exe'}, + 'SevenZip': { + '32': '{BinDir}\\7-Zip\\7za.exe', + '64': '{BinDir}\\7-Zip\\7za64.exe'}, + 'TDSSKiller': { + '32': '{BinDir}\\TDSSKiller\\TDSSKiller.exe'}, + 'wimlib-imagex': { + '32': '{BinDir}\\wimlib\\x32\\wimlib-imagex.exe', + '64': '{BinDir}\\wimlib\\x64\\wimlib-imagex.exe'}, + 'XMPlay': { + '32': '{BinDir}\\XMPlay\\xmplay.exe'}, +} +# Browsers +DEFAULT_HOMEPAGE = 'https://www.google.com/' +REGEX_CHROMIUM_ITEMS = re.compile(r'^(Bookmarks|Cookies|Favicons|Google Profile|History|Login Data|Top Sites|TransportSecurity|Visited Links|Web Data).*', re.IGNORECASE) +REGEX_FIREFOX = re.compile(r'^(bookmarkbackups|(cookies|formhistory|places).sqlite|key3.db|logins.json|persdict.dat)$', re.IGNORECASE) +REGEX_OFFICE = re.compile(r'(Microsoft (Office\s+(365|Enterprise|Home|Pro(\s|fessional)|Single|Small|Standard|Starter|Ultimate|system)|Works[-\s\d]+\d)|(Libre|Open|Star)\s*Office|WordPerfect|Gnumeric|Abiword)', re.IGNORECASE) +# Registry +REGEX_REGISTRY_DIRS = re.compile(r'^(config$|RegBack$|System32$|Transfer|Win)', re.IGNORECASE) +REGEX_SOFTWARE_HIVE = re.compile(r'^Software$', re.IGNORECASE) +# Data 1 +REGEX_EXCL_ITEMS = re.compile(r'^(\.(AppleDB|AppleDesktop|AppleDouble|com\.apple\.timemachine\.supported|dbfseventsd|DocumentRevisions-V100.*|DS_Store|fseventsd|PKInstallSandboxManager|Spotlight.*|SymAV.*|symSchedScanLockxz|TemporaryItems|Trash.*|vol|VolumeIcon\.icns)|desktop\.(ini|.*DB|.*DF)|(hiberfil|pagefile)\.sys|lost\+found|Network\.*Trash\.*Folder|Recycle[dr]|System\.*Volume\.*Information|Temporary\.*Items|Thumbs\.db)$', flags=re.IGNORECASE) +REGEX_EXCL_ROOT_ITEMS = re.compile(r'^\\(boot(mgr|nxt)$|(eula|globdata|install|vc_?red)|.*.sys$|System Volume Information|RECYCLER|\$Recycle\.bin|\$?Win(dows(.old|\.~BT|)$|RE_)|\$GetCurrent|PerfLogs|Program Files|.*\.(esd|swm|wim|dd|map|dmg|image)$|SYSTEM.SAV|Windows10Upgrade)', flags=re.IGNORECASE) +REGEX_INCL_ROOT_ITEMS = re.compile(r'^\\(AdwCleaner|(My\s*|)(Doc(uments?( and Settings|)|s?)|Downloads|WK(-?Info|-?Transfer|)|Media|Music|Pic(ture|)s?|Vid(eo|)s?)|(ProgramData|Recovery|Temp.*|Users)$|.*\.(log|txt|rtf|qb\w*|avi|m4a|m4v|mp4|mkv|jpg|png|tiff?)$)', flags=re.IGNORECASE) +EXTRA_INCL_WIM_ITEMS = [ + 'AdwCleaner\\*log', + 'AdwCleaner\\*txt', + '\\Windows.old*\\Doc*', + '\\Windows.old*\\Download*', + '\\Windows.old*\\WK*', + '\\Windows.old*\\Media*', + '\\Windows.old*\\Music*', + '\\Windows.old*\\Pic*', + '\\Windows.old*\\ProgramData', + '\\Windows.old*\\Recovery', + '\\Windows.old*\\Temp*', + '\\Windows.old*\\Users', + '\\Windows.old*\\Vid*', + '\\Windows.old*\\Windows\\System32\\OEM', + '\\Windows.old*\\Windows\\System32\\config', + '\\Windows\\System32\\OEM', + '\\Windows\\System32\\config'] +FAST_COPY_ARGS = [ + '/cmd=noexist_only', + '/logfile={LogFile}'.format(**global_vars), + '/utf8', + '/skip_empty_dir', + '/linkdest', + '/no_ui', + '/auto_close', + r'/exclude=\*.esd;\*.swm;\*.wim;\*.dd;\*.dd.tgz;\*.dd.txz;\*.map;\*.dmg;\*.image;$RECYCLE.BIN;$Recycle.Bin;.AppleDB;.AppleDesktop;.AppleDouble;.com.apple.timemachine.supported;.dbfseventsd;.DocumentRevisions-V100*;.DS_Store;.fseventsd;.PKInstallSandboxManager;.Spotlight*;.SymAV*;.symSchedScanLockxz;.TemporaryItems;.Trash*;.vol;.VolumeIcon.icns;desktop.ini;Desktop?DB;Desktop?DF;hiberfil.sys;lost+found;Network?Trash?Folder;pagefile.sys;Recycled;RECYCLER;System?Volume?Information;Temporary?Items;Thumbs.db'] +global_vars = {} + +# Error Classes +class BinNotFoundError(Exception): + pass + +class GenericError(Exception): + pass + +class GenericRepair(Exception): + pass + +class NotInstalledError(Exception): + pass + +class NoProfilesError(Exception): + pass + +class UnsupportedOSError(Exception): + pass # General functions -def ask(prompt='Kotaero!', log_file=None): +def ask(prompt='Kotaero!'): """Prompt the user with a Y/N question, log answer, and return a bool.""" answer = None prompt = prompt + ' [Y/N]: ' @@ -82,29 +197,12 @@ def ask(prompt='Kotaero!', log_file=None): answer = True elif re.search(r'^n(o|ope|)$', tmp): answer = False - if log_file is not None: - with open(log_file, 'a') as f: - if answer: - f.write('{prompt}Yes\n'.format(prompt=prompt)) - else: - f.write('{prompt}No\n'.format(prompt=prompt)) + _message = '{prompt}{answer_text}'.format( + prompt = prompt, + answer_text = 'Yes' if answer else 'No') + print_log(message=_message) return answer -def assign_volume_letters(): - """Assign a drive letter for all attached volumes.""" - with open(diskpart_script, 'w') as script: - script.write('list volume\n') - process_return = run_program('diskpart /s {script}'.format(script=diskpart_script)) - with open(diskpart_script, 'w') as script: - for tmp in re.findall(r'Volume (\d+)\s+([A-Za-z]?)\s+', process_return.stdout.decode()): - if tmp[1] == '': - script.write('select volume {number}\n'.format(number=tmp[0])) - script.write('assign\n') - try: - run_program('diskpart /s {script}'.format(script=diskpart_script)) - except: - pass - def convert_to_bytes(size): """Convert human-readable size str to bytes and return an int.""" size = str(size) @@ -125,130 +223,1196 @@ def convert_to_bytes(size): return size -def extract_item(item=None, vars_wk=None, filter='', silent=False): +def exit_script(): + # Remove dirs (if empty) + for dir in ['BackupDir', 'LogDir', 'TmpDir']: + try: + dir = global_vars[dir] + os.rmdir(dir) + except: + pass + + # Open Log (if it exists) + _log = global_vars.get('LogFile', '') + if os.path.exists(_log): + try: + extract_item('NotepadPlusPlus', silent=True) + popen_program([global_vars['Tools']['NotepadPlusPlus'], global_vars['LogFile']]) + except: + print_error('ERROR: Failed to extract Notepad++ and open log.') + + # Kill Caffeine if still running + kill_process('caffeine.exe') + + # Exit + quit() + +def extract_item(item=None, filter='', silent=False): """Extract item from .cbin into .bin.""" - if item is None or vars_wk is None: + if item is None: raise Exception - vars_wk['SevenZip'] = '{BinDir}\\7-Zip\\7za.exe'.format(**vars_wk) - if vars_wk['Arch'] == 64: - vars_wk['SevenZip'] = vars_wk['SevenZip'].replace('7za.exe', '7za64.exe') - _cmd = '{SevenZip} x -aos -bso0 -bse0 -p{ArchivePassword} -o"{BinDir}\\{item}" "{CBinDir}\\{item}.7z" {filter}'.format(item=item, filter=filter, **vars_wk) + _cmd = [ + global_vars['Tools']['SevenZip'], 'x', '-aos', '-bso0', '-bse0', + '-p{ArchivePassword}'.format(**global_vars), + '-o"{BinDir}\\{item}"'.format(item=item, **global_vars), + '"{CBinDir}\\{item}.7z"'.format(item=item, **global_vars), + filter] if not silent: print_standard('Extracting "{item}"...'.format(item=item)) try: run_program(_cmd, shell=True) except subprocess.CalledProcessError: - print_warning('WARNING: Errors encountered while exctracting data', log_file=vars_wk['LogFile']) + print_warning('WARNING: Errors encountered while exctracting data') -def find_windows_image(filename=None): - """Search for an image file on local and network drives and return a dict.""" - image = {} +def get_ticket_number(): + """Get TicketNumber from user and save it in the info folder.""" + global_vars['TicketNumber'] = None + while global_vars['TicketNumber'] is None: + _ticket = input('Enter ticket number: ') + if re.match(r'^([0-9]+([-_]?\w+|))$', _ticket): + global_vars['TicketNumber'] = _ticket + with open('{LogDir}\\TicketNumber'.format(**global_vars), 'w') as f: + f.write(_ticket) +def human_readable_size(size, decimals=0): + """Convert size in bytes to a human-readable format and return a str.""" + # Prep string formatting + width = 3+decimals + if decimals > 0: + width += 1 + human_format = '>{width}.{decimals}f'.format(width=width, decimals=decimals) + tmp = '' + + # Convert size to int + try: + size = int(size) + except ValueError: + size = convert_to_bytes(size) + + # Verify we have a valid size + if size <= 0: + return '{size:>{width}} b'.format(size='???', width=width) + + # Format string + if size >= 1099511627776: + size /= 1099511627776 + tmp = '{size:{human_format}} Tb'.format(size=size, human_format=human_format) + elif size >= 1073741824: + size /= 1073741824 + tmp = '{size:{human_format}} Gb'.format(size=size, human_format=human_format) + elif size >= 1048576: + size /= 1048576 + tmp = '{size:{human_format}} Mb'.format(size=size, human_format=human_format) + elif size >= 1024: + size /= 1024 + tmp = '{size:{human_format}} Kb'.format(size=size, human_format=human_format) + else: + tmp = '{size:{human_format}} b'.format(size=size, human_format=human_format) + + # Return + return tmp + +def major_exception(): + """Display traceback and exit""" + print_error('Major exception') + print_warning(' Please let The Wizard know and he\'ll look into it (Please include the details below).') + print(traceback.print_exc()) + sleep(30) + pause("Press Enter to exit...") + quit() + +def menu_select(title='~ Untitled Menu ~', main_entries=[], action_entries=[], prompt='Please make a selection', secret_exit=False): + """Display options in a menu for user and return selected option as a str.""" # Bail early - if filename is None: - raise Exception('Filename not specified.') + if (len(main_entries) + len(action_entries) == 0): + raise Exception("MenuError: No items given") - # Search local source - process_return = run_program('mountvol') - for tmp in re.findall(r'.*([A-Za-z]):\\', process_return.stdout.decode()): - for ext in ['esd', 'wim', 'swm']: - if os.path.isfile('{drive}:\\images\\{filename}.{ext}'.format(drive=tmp[0], ext=ext, filename=filename)): - image['Ext'] = ext - image['File'] = '{drive}:\\images\\{filename}'.format(drive=tmp[0], filename=filename) - image['Glob'] = '--ref="{File}*.swm"'.format(**image) if ext == 'swm' else '' - image['Source'] = tmp[0] - break + # Build menu + menu_splash = '{title}\n\n'.format(title=title) + valid_answers = [] + if (secret_exit): + valid_answers.append('Q') - # Check for network source (if necessary) - if not any(image): - if not WINDOWS_SERVER['Mounted']: - mount_windows_share() - for ext in ['esd', 'wim', 'swm']: - if os.path.isfile('\\\\{IP}\\{Share}\\images\\{filename}.{ext}'.format(ext=ext, filename=filename, **WINDOWS_SERVER)): - image['Ext'] = ext - image['File'] = '\\\\{IP}\\{Share}\\images\\{filename}'.format(filename=filename, **WINDOWS_SERVER) - image['Glob'] = '--ref="{File}*.swm"'.format(**image) if ext == 'swm' else '' - image['Source'] = None - break + # Add main entries + if (len(main_entries) > 0): + for i in range(len(main_entries)): + entry = main_entries[i] + # Add Spacer + if ('CRLF' in entry): + menu_splash += '\n' + if ('Disabled' in entry): + menu_splash += '{YELLOW}{number:>{mwidth}}: {name} (DISABLED){CLEAR}\n'.format(number=i+1, mwidth=len(str(len(main_entries))), name=entry.get('Display Name', entry['Name']), **COLORS) + else: + valid_answers.append(str(i+1)) + menu_splash += '{number:>{mwidth}}: {name}\n'.format(number=i+1, mwidth=len(str(len(main_entries))), name=entry.get('Display Name', entry['Name'])) + menu_splash += '\n' + + # Add action entries + if (len(action_entries) > 0): + for entry in action_entries: + # Add Spacer + if ('CRLF' in entry): + menu_splash += '\n' + valid_answers.append(entry['Letter']) + menu_splash += '{letter:>{mwidth}}: {name}\n'.format(letter=entry['Letter'].upper(), mwidth=len(str(len(action_entries))), name=entry['Name']) + menu_splash += '\n' + + answer = '' + + while (answer.upper() not in valid_answers): + os.system('cls') + print(menu_splash) + answer = input('{prompt}: '.format(prompt=prompt)) + + return answer.upper() + +def non_clobber_rename(full_path): + """Append suffix to path, if necessary, to avoid clobbering path""" + new_path = full_path + _i = 1; + while os.path.exists(new_path): + new_path = '{path}_{i}'.format(i=_i, path=full_path) + _i += 1 - # Display image to be used (if any) and return - if any(image): - print_info('Using image: {File}.{Ext}'.format(**image)) - return image + return new_path -def format_gpt(disk=None, windows_family=None): - """Format disk for use as a Windows OS drive using the GPT (UEFI) layout.""" +def pause(prompt='Press Enter to continue... '): + """Simple pause implementation.""" + input(prompt) - # Bail early - if disk is None: - raise Exception('No disk provided.') - if windows_family is None: - raise Exception('No Windows family provided.') +def popen_program(cmd=None, pipe=False, minimized=False, shell=False): + """Run program and return a subprocess.Popen object.""" + if cmd is None: + raise Exception('No program passed.') + + startupinfo=None + if minimized: + startupinfo = subprocess.STARTUPINFO() + startupinfo.dwFlags = subprocess.STARTF_USESHOWWINDOW + startupinfo.wShowWindow = 6 + + if pipe: + popen_obj = subprocess.Popen(_cmd, shell=shell, startupinfo=None, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + else: + popen_obj = subprocess.Popen(_cmd, shell=shell, startupinfo=None) + + return popen_obj - # Format drive - print_info('Drive will use a GPT (UEFI) layout.') - with open(diskpart_script, 'w') as script: - # Partition table - script.write('select disk {number}\n'.format(number=disk['Number'])) - script.write('clean\n') - script.write('convert gpt\n') +def print_error(message='Generic error', end='\n', timestamp=True, **kwargs): + """Prints message to screen in RED.""" + print('{RED}{message}{CLEAR}'.format(message=message, **COLORS), end=end, **kwargs) + print_log(message, end, timestamp) - # Windows RE tools partitions (Windows 8+) - if re.search(r'^(8|10)', windows_family): - script.write('create partition primary size=300\n') - script.write('format quick fs=ntfs label="Windows RE tools"\n') - script.write('assign letter="T"\n') - script.write('set id="de94bba4-06d1-4d40-a16a-bfd50179d6ac"\n') - script.write('gpt attributes=0x8000000000000001\n') +def print_info(message='Generic info', end='\n', timestamp=True, **kwargs): + """Prints message to screen in BLUE.""" + print('{BLUE}{message}{CLEAR}'.format(message=message, **COLORS), end=end, **kwargs) + print_log(message, end, timestamp) - # System partition - script.write('create partition efi size=260\n') # NOTE: Allows for Advanced Format 4K drives - script.write('format quick fs=fat32 label="System"\n') - script.write('assign letter="S"\n') +def print_warning(message='Generic warning', end='\n', timestamp=True, **kwargs): + """Prints message to screen in YELLOW.""" + print('{YELLOW}{message}{CLEAR}'.format(message=message, **COLORS), end=end, **kwargs) + print_log(message, end, timestamp) - # Microsoft Reserved (MSR) partition - script.write('create partition msr size=128\n') +def print_standard(message='Generic info', end='\n', timestamp=True, **kwargs): + """Prints message to screen.""" + print('{message}'.format(message=message, **COLORS), end=end, **kwargs) + print_log(message, end, timestamp) - # Windows partition - script.write('create partition primary\n') - script.write('format quick fs=ntfs label="Windows"\n') - script.write('assign letter="W"\n') +def print_success(message='Generic success', end='\n', timestamp=True, **kwargs): + """Prints message to screen in GREEN.""" + print('{GREEN}{message}{CLEAR}'.format(message=message, **COLORS), end=end, **kwargs) + print_log(message, end, timestamp) - # Run script - print(' Formatting drive...') - run_program('diskpart /s {script}'.format(script=diskpart_script)) - time.sleep(2) +def print_log(message='', end='\n', timestamp=True): + if 'LogFile' in global_vars and global_vars['LogFile'] is not None: + with open(global_vars['LogFile'], 'a') as f: + for line in message.splitlines(): + f.write('{timestamp}{line}{end}'.format( + timestamp = time.strftime("%Y-%m-%d %H%M%z: ") if timestamp else '', + line = line, + end = end)) -def format_mbr(disk=None): - """Format disk for use as a Windows OS drive using the MBR (legacy) layout.""" +def run_program(cmd=None, args=[], check=True, pipe=True, shell=False): + """Run program and return a subprocess.CompletedProcess object.""" + if cmd is None: + raise Exception('No program passed.') + + _cmd = cmd + if len(args) > 0: + _cmd = [cmd] + args + if shell: + _cmd = ' '.join(_cmd) + + if pipe: + process_return = subprocess.run(_cmd, check=check, shell=shell, stdout=subprocess.PIPE, stderr=subprocess.PIPE) + else: + process_return = subprocess.run(_cmd, check=check, shell=shell) - # Bail early - if disk is None: - raise Exception('No disk provided.') + return process_return - # Format drive - print_info('Drive will use a MBR (legacy) layout.') - with open(diskpart_script, 'w') as script: - # Partition table - script.write('select disk {number}\n'.format(number=disk['Number'])) - script.write('clean\n') +def set_global_vars(**kwargs): + global_vars.update(kwargs) - # System partition - script.write('create partition primary size=100\n') - script.write('format fs=ntfs quick label="System Reserved"\n') - script.write('active\n') - script.write('assign letter=s\n') +def sleep(seconds=2): + time.sleep(seconds) - # Windows partition - script.write('create partition primary\n') - script.write('format fs=ntfs quick label="Windows"\n') - script.write('assign letter=w\n') +def stay_awake(): + """Prevent the system from sleeping or hibernating.""" + # Bail if caffeine is already running + for proc in psutil.process_iter(): + if proc.name() == 'caffeine.exe': + return + # Extract and run + extract_item('caffeine', silent=True) + try: + popen_program(global_vars['Tools']['Caffeine']) + except: + print_error('ERROR: No caffeine available; please set the power setting to High Performace.') - # Run script - print(' Formatting drive...') - run_program('diskpart /s {script}'.format(script=diskpart_script)) - time.sleep(2) +def try_and_print(function=None, message='Trying...', cs='CS', ns='NS', other_results={}, + catch_all=True, indent=8, width=32, print_return=False, silent_function=True, *args, **kwargs): + """Run function, print if successful or not, and return dict. + + other_results is in the form of {'Warning': {'ExceptionClassName': 'Result Message'}, 'Error': {'ExceptionClassName': 'Result Message'}} + The the ExceptionClassNames will be additionally excepted conditions and the result string will be printed in the correct color. + catch_all=False will result in unspecified exceptions being re-raised.""" + if function is None: + raise Exception + err = '' + wrn_exceptions = other_results.get('Warning', {}).keys() + wrn_exceptions = tuple(getattr(sys.modules[__name__], e) for e in wrn_exceptions) + err_exceptions = other_results.get('Error', {}).keys() + err_exceptions = tuple(getattr(sys.modules[__name__], e) for e in err_exceptions) + wrn_results = other_results.get('Warning', {}) + err_results = other_results.get('Error', {}) + + # Run function and catch errors + print_standard('{indent}{message:<{width}}'.format(indent=' '*indent, message=message, width=width), end='', flush=True) + try: + out = function(*args, **kwargs) + if print_return: + print_standard(out[0], timestamp=False) + for item in out[1:]: + print_standard('{indent}{item}'.format(indent=' '*(indent+width), item=item)) + elif silent_function: + print_success(cs, timestamp=False) + except wrn_exceptions as e: + _result = wrn_results.get(e.__class__.__name__, 'Warning') + print_warning(_result, timestamp=False) + err = e + except err_exceptions as e: + _result = err_results.get(e.__class__.__name__, 'Error') + print_error(_result, timestamp=False) + err = e + except: + print_error(ns, timestamp=False) + err = traceback.format_exc() + + # Return or raise? + if bool(err) and not catch_all: + raise + else: + return {'CS': not bool(err), 'Error': err} +def upload_data(path=None, file=None): + """Add CLIENT_INFO_SERVER to authorized connections and upload file.""" + extract_item('PuTTY', filter='WK.ppk psftp.exe', silent=True) + + # Authorize connection to the server + winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\SimonTatham\PuTTY\SshHostKeys') + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\SimonTatham\PuTTY\SshHostKeys', access=winreg.KEY_WRITE) as _key: + winreg.SetValueEx(_key, 'rsa2@22:{IP}'.format(**CLIENT_INFO_SERVER), 0, winreg.REG_SZ, CLIENT_INFO_SERVER['RegEntry']) + + # Write batch file + with open('{TmpDir}\\psftp.batch'.format(**global_vars), 'w', encoding='ascii') as f: + f.write('lcd "{path}"\n'.format(path=path)) + f.write('cd "{Share}"\n'.format(**CLIENT_INFO_SERVER)) + f.write('mkdir {TicketNumber}\n'.format(**global_vars)) + f.write('cd {TicketNumber}\n'.format(**global_vars)) + f.write('put "{file}"\n'.format(file=file)) + + # Upload Info + _cmd = [ + global_vars['Tools']['PuTTY-PSFTP'], + '-noagent', + '-i', '{BinDir}\\PuTTY\\WK.ppk'.format(**global_vars), + '{User}@{IP}'.format(**CLIENT_INFO_SERVER), + '-b', '{TmpDir}\\psftp.batch'.format(**global_vars)] + run_program(_cmd) + +def wait_for_process(name=None): + """Wait for process by name.""" + if name is None: + raise Exception + _still_running = True + while _still_running: + sleep(1) + _still_running = False + for proc in psutil.process_iter(): + if re.search(r'^{name}'.format(name=name), proc.name(), re.IGNORECASE): + _still_running = True + sleep(1) + +def kill_process(name=None): + """Kill any running caffeine.exe processes.""" + if name is None: + raise Exception + for proc in psutil.process_iter(): + if proc.name() == name: + proc.kill() + +# global_vars functions +def init_global_vars(): + """Sets global variables based on system info.""" + print_info('Initializing') + try: + try_and_print(message='Checking .bin...', function=find_bin, catch_all=False, cs='Done', ns='Error') + try_and_print(message='Checking environment...', function=set_common_vars, catch_all=False, cs='Done', ns='Error') + try_and_print(message='Checking OS...', function=check_os, catch_all=False, cs='Done', ns='Error') + try_and_print(message='Checking tools...', function=check_tools, catch_all=False, cs='Done', ns='Error') + try_and_print(message='Creating folders...', function=make_tmp_dirs, catch_all=False, cs='Done', ns='Error') + try_and_print(message='Clearing collisions...', function=clean_env_vars, catch_all=False, cs='Done', ns='Error') + except: + major_exception() + +def check_os(): + _vars_os = {} + # Query registry + _reg_path = winreg.OpenKey(winreg.HKEY_LOCAL_MACHINE, 'SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion') + for key in ['CSDVersion', 'CurrentBuild', 'CurrentBuildNumber', 'CurrentVersion', 'ProductName']: + try: + _vars_os[key] = winreg.QueryValueEx(_reg_path, key)[0] + if key in ['CurrentBuild', 'CurrentBuildNumber']: + _vars_os[key] = int(_vars_os[key]) + except ValueError: + # Couldn't convert Build to int so this should return interesting results... + _vars_os[key] = 0 + except: + _vars_os[key] = 'Unknown' + + # Determine OS bit depth + _vars_os['Arch'] = 32 + if 'PROGRAMFILES(X86)' in global_vars['Env']: + _vars_os['Arch'] = 64 + + # Determine OS Name + _vars_os['Name'] = '{ProductName} {CSDVersion}'.format(**_vars_os) + if _vars_os['CurrentBuild'] == 9600: + _vars_os['Name'] += ' Update' + if _vars_os['CurrentBuild'] == 10240: + _vars_os['Name'] += ' Release 1507 "Threshold 1"' + if _vars_os['CurrentBuild'] == 10586: + _vars_os['Name'] += ' Release 1511 "Threshold 2"' + if _vars_os['CurrentBuild'] == 14393: + _vars_os['Name'] += ' Release 1607 "Redstone 1" / "Anniversary Update"' + _vars_os['Name'] = _vars_os['Name'].replace('Service Pack ', 'SP') + _vars_os['Name'] = _vars_os['Name'].replace('Unknown Release', 'Release') + _vars_os['Name'] = re.sub(r'\s+', ' ', _vars_os['Name']) + # == vista == + # 6.0.6000 + # 6.0.6001 + # 6.0.6002 + # ==== 7 ==== + # 6.1.7600 + # 6.1.7601 + # 6.1.7602 + # ==== 8 ==== + # 6.2.9200 + # === 8.1 === + # 6.3.9200 + # === 8.1u == + # 6.3.9600 + # === 10 v1507 "Threshold 1" == + # 6.3.10240 + # === 10 v1511 "Threshold 2" == + # 6.3.10586 + # === 10 v1607 "Anniversary Update" "Redstone 1" == + # 6.3.14393 + # === 10 v???? "Redstone 2" == + # 6.3.????? + + # Determine OS version + _os_name = '{Name} x{Arch}'.format(**_vars_os) + if _vars_os['CurrentVersion'] == '6.0': + _vars_os['Version'] = 'Vista' + _os_name = _os_name + ' (very outdated)' + elif _vars_os['CurrentVersion'] == '6.1': + _vars_os['Version'] = '7' + if _vars_os['CSDVersion'] == 'Service Pack 1': + _os_name = _os_name + ' (outdated)' + else: + _os_name = _os_name + ' (very outdated)' + elif _vars_os['CurrentVersion'] == '6.2': + _vars_os['Version'] = '8' + _os_name = _os_name + ' (very outdated)' + elif _vars_os['CurrentVersion'] == '6.3': + if int(_vars_os['CurrentBuildNumber']) <= 9600: + _vars_os['Version'] = '8' + elif int(_vars_os['CurrentBuildNumber']) >= 10240: + _vars_os['Version'] = '10' + if _vars_os['CurrentBuild'] == 9200: + _os_name = _os_name + ' (very outdated)' + elif _vars_os['CurrentBuild'] == 9600: + _os_name = _os_name + ' (outdated)' + elif _vars_os['CurrentBuild'] == 10240: + _os_name = _os_name + ' (very outdated)' + elif _vars_os['CurrentBuild'] == 10586: + _os_name = _os_name + ' (outdated)' + elif _vars_os['CurrentBuild'] == 14393: + pass # Current Win10 + else: + _os_name = _os_name + ' (unrecognized)' + _vars_os['DisplayName'] = _os_name + + # Determine bootup type + _vars_os['SafeMode'] = False + if 'SAFEBOOT_OPTION' in global_vars['Env']: + _vars_os['SafeMode'] = True + + # Determine activation status + if _vars_os['SafeMode']: + _vars_os['Activation'] = 'Activation status unavailable in safe mode' + else: + _out = run_program('cscript /nologo {SYSTEMROOT}\\System32\\slmgr.vbs /xpr'.format(**global_vars['Env'])) + _out = _out.stdout.decode().splitlines() + _out = [l for l in _out if re.match(r'^\s', l)] + if len(_out) > 0: + _vars_os['Activation'] = re.sub(r'^\s+', '', _out[0]) + else: + _vars_os['Activation'] = 'Activation status unknown' + + global_vars['OS'] = _vars_os + +def check_tools(): + # Add tools to dict + if global_vars['OS'].get('Arch', 32) == 64: + global_vars['Tools'] = {k: v.get('64', v.get('32')) for (k, v) in TOOLS.items()} + else: + global_vars['Tools'] = {k: v.get('32') for (k, v) in TOOLS.items()} + + # Fix paths + global_vars['Tools'] = {k: v.format(**global_vars) for (k, v) in global_vars['Tools'].items()} + +def clean_env_vars(): + # This fixes an issue where both global_vars and global_vars['Env'] are expanded at the same time + for key in global_vars.keys(): + global_vars['Env'].pop(key, None) + +def find_bin(): + _wd = os.getcwd() + _base = None + while _base is None: + if os.path.exists('.bin'): + _base = os.getcwd() + break + if re.fullmatch(r'\w:\\', os.getcwd()): + break + os.chdir('..') + os.chdir(_wd) + if _base is None: + raise BinNotFoundError + global_vars['BaseDir'] = _base + +def set_common_vars(): + global_vars['Date'] = time.strftime("%Y-%m-%d") + global_vars['Date-Time'] = time.strftime("%Y-%m-%d_%H%M_%z") + global_vars['Env'] = os.environ.copy() + + global_vars['ArchivePassword'] = ARCHIVE_PASSWORD + global_vars['BinDir'] = '{BaseDir}\\.bin'.format(**global_vars) + global_vars['CBinDir'] = '{BaseDir}\\.cbin'.format(**global_vars) + global_vars['ClientDir'] = '{SYSTEMDRIVE}\\WK'.format(**global_vars['Env']) + global_vars['BackupDir'] = '{ClientDir}\\Backups\\{Date}'.format(**global_vars) + global_vars['LogDir'] = '{ClientDir}\\Info\\{Date}'.format(**global_vars) + global_vars['QuarantineDir'] = '{ClientDir}\\Quarantine'.format(**global_vars) + global_vars['TmpDir'] = '{BinDir}\\tmp'.format(**global_vars) + +def make_tmp_dirs(): + os.makedirs(global_vars['BackupDir'], exist_ok=True) + os.makedirs(global_vars['LogDir'], exist_ok=True) + os.makedirs(global_vars['TmpDir'], exist_ok=True) + +# Browsers +def backup_browsers(): + functions = [ + backup_chromium, + backup_chrome, + backup_chrome_canary, + backup_firefox, + backup_internet_explorer, + backup_opera, + backup_opera_beta, + backup_opera_dev] + errors = False + for function in functions: + try: + function() + except NoProfilesError: + pass + except: + errors = True + if errors: + raise GenericError + +def backup_chromium(): + """Create backup of Chromium in the BackupDir.""" + if os.path.exists('{LOCALAPPDATA}\\Chromium\\User Data'.format(**global_vars['Env'])): + cmd = [ + global_vars['Tools']['SevenZip'], 'a', '-aoa', '-bso0', '-bse0', '-mx=1', + '{BackupDir}\\Browsers ({USERNAME})\\Chromium.7z'.format(**global_vars, **global_vars['Env']), + '{LOCALAPPDATA}\\Chromium\\User Data'.format(**global_vars['Env'])] + run_program(cmd, check=False) + else: + raise NoProfilesError + +def backup_chrome(): + """Create backup of Google Chrome in the BackupDir.""" + if os.path.exists('{LOCALAPPDATA}\\Google\\Chrome\\User Data'.format(**global_vars['Env'])): + cmd = [ + global_vars['Tools']['SevenZip'], 'a', '-aoa', '-bso0', '-bse0', '-mx=1', + '{BackupDir}\\Browsers ({USERNAME})\\Google Chrome.7z'.format(**global_vars, **global_vars['Env']), + '{LOCALAPPDATA}\\Google\\Chrome\\User Data'.format(**global_vars['Env'])] + run_program(cmd, check=False) + else: + raise NoProfilesError + +def backup_chrome_canary(): + """Create backup of Google Chrome Canary in the BackupDir.""" + if os.path.exists('{LOCALAPPDATA}\\Google\\Chrome SxS\\User Data'.format(**global_vars['Env'])): + cmd = [ + global_vars['Tools']['SevenZip'], 'a', '-aoa', '-bso0', '-bse0', '-mx=1', + '{BackupDir}\\Browsers ({USERNAME})\\Google Chrome Canary.7z'.format(**global_vars, **global_vars['Env']), + '{LOCALAPPDATA}\\Google\\Chrome SxS\\User Data'.format(**global_vars['Env'])] + run_program(cmd, check=False) + else: + raise NoProfilesError + +def backup_internet_explorer(): + """Create backup of Internet Explorer in the BackupDir.""" + run_program('reg export "hkcu\\Software\\Microsoft\\Internet Explorer" "{TmpDir}\\Internet Explorer (HKCU).reg" /y'.format(**global_vars), check=False) + run_program('reg export "hklm\\Software\\Microsoft\\Internet Explorer" "{TmpDir}\\Internet Explorer (HKLM).reg" /y'.format(**global_vars), check=False) + cmd = [ + global_vars['Tools']['SevenZip'], 'a', '-aoa', '-bso0', '-bse0', '-mx=1', + '{BackupDir}\\Browsers ({USERNAME})\\Internet Explorer.7z'.format(**global_vars, **global_vars['Env']), + '{TmpDir}\\Internet*.reg'.format(**global_vars), + '{USERPROFILE}\\Favorites'.format(**global_vars['Env'])] + run_program(cmd, check=False) + +def backup_firefox(): + """Create backup of Mozilla Firefox in the BackupDir.""" + if os.path.exists('{APPDATA}\\Mozilla\\Firefox'.format(**global_vars['Env'])): + cmd = [ + global_vars['Tools']['SevenZip'], 'a', '-aoa', '-bso0', '-bse0', '-mx=1', + '{BackupDir}\\Browsers ({USERNAME})\\Mozilla Firefox.7z'.format(**global_vars, **global_vars['Env']), + '{APPDATA}\\Mozilla\\Firefox\\Profile*'.format(**global_vars['Env'])] + run_program(cmd, check=False) + else: + raise NoProfilesError + +def backup_opera(): + """Create backup of Opera Chromium in the BackupDir.""" + if os.path.exists('{APPDATA}\\Opera Software\\Opera Stable'.format(**global_vars['Env'])): + cmd = [ + global_vars['Tools']['SevenZip'], 'a', '-aoa', '-bso0', '-bse0', '-mx=1', + '{BackupDir}\\Browsers ({USERNAME})\\Opera.7z'.format(**global_vars, **global_vars['Env']), + '{APPDATA}\\Opera Software\\Opera Stable'.format(**global_vars['Env'])] + run_program(cmd, check=False) + else: + raise NoProfilesError + +def backup_opera_beta(): + """Create backup of Opera Chromium Beta in the BackupDir.""" + if os.path.exists('{APPDATA}\\Opera Software\\Opera Next'.format(**global_vars['Env'])): + cmd = [ + global_vars['Tools']['SevenZip'], 'a', '-aoa', '-bso0', '-bse0', '-mx=1', + '{BackupDir}\\Browsers ({USERNAME})\\Opera Beta.7z'.format(**global_vars, **global_vars['Env']), + '{APPDATA}\\Opera Software\\Opera Next'.format(**global_vars['Env'])] + run_program(cmd, check=False) + else: + raise NoProfilesError + +def backup_opera_dev(): + """Create backup of Opera Chromium Developer in the BackupDir.""" + if os.path.exists('{APPDATA}\\Opera Software\\Opera Developer'.format(**global_vars['Env'])): + cmd = [ + global_vars['Tools']['SevenZip'], 'a', '-aoa', '-bso0', '-bse0', '-mx=1', + '{BackupDir}\\Browsers ({USERNAME})\\Opera Dev.7z'.format(**global_vars, **global_vars['Env']), + '{APPDATA}\\Opera Software\\Opera Developer'.format(**global_vars['Env'])] + run_program(cmd, check=False) + else: + raise NoProfilesError + +def clean_chromium_profile(profile): + """Renames profile folder as backup and then recreates the folder with only the essential files.""" + if profile is None: + raise Exception + # print_info(' Resetting profile: {name}'.format(name=profile.name)) + backup_path = '{path}_{Date}.bak'.format(path=profile.path, **global_vars) + backup_path = non_clobber_rename(backup_path) + shutil.move(profile.path, backup_path) + os.makedirs(profile.path, exist_ok=True) + + # Restore essential files from backup_path + for entry in os.scandir(backup_path): + if REGEX_CHROMIUM_ITEMS.search(entry.name): + shutil.copy(entry.path, '{path}\\{name}'.format(path=profile.path, name=entry.name)) + +def clean_internet_explorer(): + """Uses the built-in function to reset IE and sets the homepage.""" + kill_process('iexplore.exe') + run_program('rundll32.exe', ['inetcpl.cpl,ResetIEtoDefaults'], check=False) + key = r'Software\Microsoft\Internet Explorer\Main' + + # Set homepage + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, key, access=winreg.KEY_WRITE) as _key: + winreg.SetValueEx(_key, 'Start Page', 0, winreg.REG_SZ, DEFAULT_HOMEPAGE) + try: + winreg.DeleteValue(_key, 'Secondary Start Pages') + except FileNotFoundError: + pass + +def clean_firefox_profile(profile): + """Renames profile folder as backup and then recreates the folder with only the essential files.""" + if profile is None: + raise Exception + # print_info(' Resetting profile: {name}'.format(name=profile.name)) + backup_path = '{path}_{Date}.bak'.format(path=profile.path, **global_vars) + backup_path = non_clobber_rename(backup_path) + shutil.move(profile.path, backup_path) + homepages = [] + os.makedirs(profile.path, exist_ok=True) + + # Restore essential files from backup_path + for entry in os.scandir(backup_path): + if REGEX_FIREFOX.search(entry.name): + if entry.is_dir(): + shutil.copytree(entry.path, '{path}\\{name}'.format(path=profile.path, name=entry.name)) + else: + shutil.copy(entry.path, '{path}\\{name}'.format(path=profile.path, name=entry.name)) + + # Set profile defaults + with open('{path}\\prefs.js'.format(path=profile.path), 'a', encoding='ascii') as f: + f.write('user_pref("browser.search.geoSpecificDefaults", false);\n') + + # Set search to Google + f.write('user_pref("browser.search.defaultenginename", "Google");\n') + f.write('user_pref("browser.search.defaultenginename.US", "Google");\n') + + # Set homepage + f.write('user_pref("browser.startup.homepage", "{homepage}");\n'.format(homepage=DEFAULT_HOMEPAGE)) + +def config_internet_explorer(): + ie_exe = get_iexplorer_exe() + run_program(ie_exe, ['https://www.microsoft.com/en-us/iegallery'], check=False) + +def config_google_chrome(): + chrome_exe = get_chrome_exe() + if chrome_exe is None: + raise NotInstalledError + + # Check for system exensions + _ublock_origin = None + _ublock_extra = None + try: + _ublock_origin = winreg.QueryValue(winreg.HKEY_LOCAL_MACHINE, r'Software\Wow6432Node\Google\Chrome\Extensions\cjpalhdlnbpafiamejdnhcphjbkeiagm') + except FileNotFoundError: + pass + try: + _ublock_extra = winreg.QueryValue(winreg.HKEY_LOCAL_MACHINE, r'Software\Wow6432Node\Google\Chrome\Extensions\pgdnlhfefecpicbbihgmbmffkjpaplco') + except FileNotFoundError: + pass + + # Open Chrome + _args = [ + 'https://chrome.google.com/webstore/detail/ublock-origin/cjpalhdlnbpafiamejdnhcphjbkeiagm?hl=en', + 'https://chrome.google.com/webstore/detail/ublock-origin-extra/pgdnlhfefecpicbbihgmbmffkjpaplco?hl=en'] + if _ublock_origin is None and _ublock_extra is None: + run_program(chrome_exe, _args, check=False) + elif _ublock_origin is None: + run_program(chrome_exe, [_args[0]], check=False) + elif _ublock_extra is None: + run_program(chrome_exe, [_args[1]], check=False) + else: + run_program(chrome_exe, ['chrome://extensions'], check=False) + +def config_google_chrome_canary(): + chrome_canary_exe = get_chrome_canary_exe() + if chrome_canary_exe is None: + raise NotInstalledError + _args = [ + 'https://chrome.google.com/webstore/detail/ublock-origin/cjpalhdlnbpafiamejdnhcphjbkeiagm?hl=en', + 'https://chrome.google.com/webstore/detail/ublock-origin-extra/pgdnlhfefecpicbbihgmbmffkjpaplco?hl=en'] + run_program(chrome_canary_exe, _args, check=False) + +def config_mozilla_firefox(): + firefox_exe = get_firefox_exe() + if firefox_exe is None: + raise NotInstalledError + + # Check for system extension(s) + _ublock_origin = '{PROGRAMFILES}\\Mozilla Firefox\\distribution\\extensions\\uBlock0@raymondhill.net'.format(**global_vars['Env']) + if 'PROGRAMFILES(X86)' in global_vars['Env']: + _ublock_origin = '{PROGRAMFILES(X86)}\\Mozilla Firefox\\distribution\\extensions\\uBlock0@raymondhill.net'.format(**global_vars['Env']) + + # Open Firefox + if os.path.exists(_ublock_origin): + run_program(firefox_exe, ['about:addons'], check=False) + else: + run_program(firefox_exe, ['https://addons.mozilla.org/en-us/firefox/addon/ublock-origin/'], check=False) + +def config_mozilla_firefox_dev(): + firefox_dev_exe = get_firefox_dev_exe() + if firefox_dev_exe is None: + raise NotInstalledError + run_program(firefox_dev_exe, ['https://addons.mozilla.org/en-us/firefox/addon/ublock-origin/'], check=False) + +def config_opera(): + opera_exe = get_opera_exe() + if opera_exe is None: + raise NotInstalledError + run_program(opera_exe, ['https://addons.opera.com/en/extensions/details/ublock/?display=en'], check=False) + +def config_opera_beta(): + opera_beta_exe = get_opera_beta_exe() + if opera_beta_exe is None: + raise NotInstalledError + run_program(opera_beta_exe, ['https://addons.opera.com/en/extensions/details/ublock/?display=en'], check=False) + +def config_opera_dev(): + opera_dev_exe = get_opera_dev_exe() + if opera_dev_exe is None: + raise NotInstalledError + run_program(opera_dev_exe, ['https://addons.opera.com/en/extensions/details/ublock/?display=en'], check=False) + +def create_firefox_default_profiles(): + """Create new default profile for Mozilla Firefox for both stable and dev releases.""" + firefox_exe = get_firefox_exe() + firefox_dev_exe = get_firefox_dev_exe() + profiles_ini_path = '{APPDATA}\\Mozilla\\Firefox\\profiles.ini'.format(**global_vars['Env']) + + # Rename profiles.ini + if os.path.exists(profiles_ini_path): + backup_path = '{path}_{Date}.bak'.format(path=profiles_ini_path, **global_vars) + backup_path = non_clobber_rename(backup_path) + shutil.move(profiles_ini_path, backup_path) + + # Create profile(s) + if firefox_exe is not None: + run_program(firefox_exe, ['-createprofile', 'default'], check=False) + if firefox_dev_exe is not None: + run_program(firefox_dev_exe, ['-createprofile'], check=False) + +def get_chrome_exe(): + """Check for conflicting Chrome installations and return chrome.exe path as str.""" + install_multi = '{PROGRAMFILES}\\Google\\Chrome\\Application\\chrome.exe'.format(**global_vars['Env']) + if 'PROGRAMFILES(X86)' in global_vars['Env']: + install_multi = '{PROGRAMFILES(X86)}\\Google\\Chrome\\Application\\chrome.exe'.format(**global_vars['Env']) + install_single = '{LOCALAPPDATA}\\Google\\Chrome\\Application\\chrome.exe'.format(**global_vars['Env']) + if os.path.exists(install_multi): + if os.path.exists(install_single): + print_log(' WARNING: Single-user and multi-user installations present.') + print_log(' It is recommended to move to only having the multi-user installation.') + return install_multi + elif os.path.exists(install_single): + return install_single + else: + return None + +def get_chrome_profiles(): + """Find any existing Chrome profiles and return as a list of os.DirEntry objects.""" + profiles = [] + try: + for entry in os.scandir('{LOCALAPPDATA}\\Google\\Chrome\\User Data'.format(**global_vars['Env'])): + if entry.is_dir() and re.search(r'^(Default|Profile)', entry.name, re.IGNORECASE): + profiles.append(entry) + profiles = [p for p in profiles if not re.search(r'\.(wk|)bak.*', p.name, re.IGNORECASE)] + except: + pass + + return profiles + +def get_chrome_canary_exe(): + """Check for Google Chrome Canary installation and return chrome.exe path as str.""" + prog_exe = '{LOCALAPPDATA}\\Google\\Chrome SxS\\Application\\chrome.exe'.format(**global_vars['Env']) + if os.path.exists(prog_exe): + return prog_exe + else: + return None + +def get_chrome_canary_profiles(): + """Find any existing Chrome profiles and return as a list of os.DirEntry objects.""" + profiles = [] + try: + for entry in os.scandir('{LOCALAPPDATA}\\Google\\Chrome SxS\\User Data'.format(**global_vars['Env'])): + if entry.is_dir() and re.search(r'^(Default|Profile)', entry.name, re.IGNORECASE): + profiles.append(entry) + profiles = [p for p in profiles if not re.search(r'\.(wk|)bak.*', p.name, re.IGNORECASE)] + except: + pass + + return profiles + +def get_iexplorer_exe(): + """Find and return iexplorer.exe path as str.""" + ie_exe = '{PROGRAMFILES}\\Internet Explorer\\iexplore.exe'.format(**global_vars['Env']) + if 'PROGRAMFILES(X86)' in global_vars['Env']: + ie_exe = '{PROGRAMFILES(X86)}\\Internet Explorer\\iexplore.exe'.format(**global_vars['Env']) + return ie_exe + +def get_firefox_exe(): + """Check for Mozilla Firefox installation and return firefox.exe path as str.""" + prog_exe = '{PROGRAMFILES}\\Mozilla Firefox\\firefox.exe'.format(**global_vars['Env']) + if 'PROGRAMFILES(X86)' in global_vars['Env']: + prog_exe = '{PROGRAMFILES(X86)}\\Mozilla Firefox\\firefox.exe'.format(**global_vars['Env']) + if os.path.exists(prog_exe): + return prog_exe + else: + return None + +def get_firefox_dev_exe(): + """Check for Mozilla Firefox Developer Edition installation and return firefox.exe path as str.""" + prog_exe = '{PROGRAMFILES}\\Firefox Developer Edition\\firefox.exe'.format(**global_vars['Env']) + if 'PROGRAMFILES(X86)' in global_vars['Env']: + prog_exe = '{PROGRAMFILES(X86)}\\Firefox Developer Edition\\firefox.exe'.format(**global_vars['Env']) + if os.path.exists(prog_exe): + return prog_exe + else: + return None + +def get_firefox_profiles(): + """Find any existing Chrome profiles and return as a list of os.DirEntry objects.""" + profiles = [] + try: + for entry in os.scandir('{APPDATA}\\Mozilla\\Firefox\\Profiles'.format(**global_vars['Env'])): + if entry.is_dir(): + profiles.append(entry) + profiles = [p for p in profiles if not re.search(r'\.(wk|)bak.*', p.name, re.IGNORECASE)] + except: + pass + + return profiles + +def get_opera_exe(): + """Check for Opera installation and return launcher.exe path as str.""" + prog_exe = '{PROGRAMFILES}\\Opera\\launcher.exe'.format(**global_vars['Env']) + if 'PROGRAMFILES(X86)' in global_vars['Env']: + prog_exe = '{PROGRAMFILES(X86)}\\Opera\\launcher.exe'.format(**global_vars['Env']) + if os.path.exists(prog_exe): + return prog_exe + else: + return None + +def get_opera_beta_exe(): + """Check for Opera Beta installation and return launcher.exe path as str.""" + prog_exe = '{PROGRAMFILES}\\Opera beta\\launcher.exe'.format(**global_vars['Env']) + # Installs as 64-bit on a 64-bit OS so PROGRAMFILES should always be correct + + if os.path.exists(prog_exe): + return prog_exe + else: + return None + +def get_opera_dev_exe(): + """Check for Opera Beta installation and return launcher.exe path as str.""" + prog_exe = '{PROGRAMFILES}\\Opera developer\\launcher.exe'.format(**global_vars['Env']) + # Installs as 64-bit on a 64-bit OS so PROGRAMFILES should always be correct + + if os.path.exists(prog_exe): + return prog_exe + else: + return None + +def get_opera_profile(): + """Find an existing Opera profile and return as a length-1 list of os.DirEntry objects.""" + profiles = [] + try: + for entry in os.scandir('{APPDATA}\\Opera Software'.format(**global_vars['Env'])): + if entry.is_dir() and entry.name == 'Opera Stable': + return [entry] + except: + pass + + return profiles + +def get_opera_beta_profile(): + """Find an existing Opera Beta profile and return as a length-1 list of os.DirEntry objects.""" + profiles = [] + try: + for entry in os.scandir('{APPDATA}\\Opera Software'.format(**global_vars['Env'])): + if entry.is_dir() and entry.name == 'Opera Next': + return [entry] + except: + pass + + return profiles + +def get_opera_dev_profile(): + """Find an existing Opera Dev profile and return as a length-1 list of os.DirEntry objects.""" + profiles = [] + try: + for entry in os.scandir('{APPDATA}\\Opera Software'.format(**global_vars['Env'])): + if entry.is_dir() and entry.name == 'Opera Developer': + return [entry] + except: + pass + + return profiles + +def list_homepages(indent=8, width=32): + """List current homepages for reference.""" + print_standard('{indent}{browser:<{width}}'.format(indent=' '*indent, width=width, browser='Google Chrome...'), end='', flush=True) + print_warning('Currently not possible', timestamp=False) + + # Firefox + profiles = get_firefox_profiles() + if len(profiles) > 0: + print_standard('{indent}{browser:<{width}}'.format(indent=' '*indent, width=width, browser='Mozilla Firefox...')) + + for profile in profiles: + try: + with open('{path}\\prefs.js'.format(path=profile.path), 'r') as f: + _search = re.search(r'browser\.startup\.homepage", "([^"]*)"', f.read(), re.IGNORECASE) + if _search: + homepages = _search.group(1).split('|') + except FileNotFoundError: + homepages = [] + + for page in homepages: + print_standard('{indent}{name:<{width}}{page}'.format(indent=' '*(indent+4), width=width-4, name=profile.name, page=page)) + + # IE + key = r'Software\Microsoft\Internet Explorer\Main' + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, key) as _key: + homepage = winreg.QueryValueEx(_key, 'Start Page')[0] + try: + secondary_homepages = winreg.QueryValueEx(_key, 'Secondary Start Pages')[0] + except FileNotFoundError: + secondary_homepages = [] + print_standard('{indent}{browser:<{width}}{page}'.format(indent=' '*indent, width=width, browser='Internet Explorer...', page=homepage)) + for page in secondary_homepages: + print_standard('{indent}{page}'.format(indent=' '*(indent+width), page=page)) + +def reset_google_chrome(): + kill_process('chrome.exe') + chrome_exe = get_chrome_exe() + profiles = get_chrome_profiles() + if len(profiles) == 0: + raise NoProfilesError + + for profile in profiles: + clean_chromium_profile(profile) + +def reset_google_chrome_canary(): + kill_process('chrome.exe') + chrome_canary_exe = get_chrome_canary_exe() + profiles = get_chrome_canary_profiles() + if len(profiles) == 0: + raise NoProfilesError + + for profile in profiles: + clean_chromium_profile(profile) + +def reset_mozilla_firefox(): + kill_process('firefox.exe') + profiles = get_firefox_profiles() + + if len(profiles) == 0: + create_firefox_default_profiles() + kill_process('firefox.exe') + raise NoProfilesError + else: + for profile in profiles: + clean_firefox_profile(profile) + +def reset_opera(): + kill_process('opera.exe') + opera_exe = get_opera_exe() + profiles = get_opera_profile() + if len(profiles) == 0: + raise NoProfilesError + + # Reset browser (Opera only supports one profile) + clean_chromium_profile(profiles[0]) + +def reset_opera_beta(): + kill_process('opera.exe') + opera_beta_exe = get_opera_beta_exe() + profiles = get_opera_beta_profile() + if len(profiles) == 0: + raise NoProfilesError + + # Reset browser (Opera only supports one profile) + clean_chromium_profile(profiles[0]) + +def reset_opera_dev(): + kill_process('opera.exe') + opera_dev_exe = get_opera_dev_exe() + profiles = get_opera_dev_profile() + if len(profiles) == 0: + raise NoProfilesError + + # Reset browser (Opera only supports one profile) + clean_chromium_profile(profiles[0]) + +def set_chrome_as_default(): + chrome_exe = get_chrome_exe() + if chrome_exe is None: + raise NotInstalledError + run_program(chrome_exe, ['--make-default-browser'], check=False) + if global_vars['OS']['Version'] in ['10']: + popen_program('ms-settings:defaultapps') + +# Cleanup +def cleanup_adwcleaner(): + _path = '{SYSTEMDRIVE}\\AdwCleaner'.format(**global_vars['Env']) + if os.path.exists(_path): + os.makedirs('{ClientDir}\\Info'.format(**global_vars), exist_ok=True) + for entry in os.scandir(_path): + if entry.is_file() and re.search(r'*.(log|txt)', entry.name): + _name = re.sub(r'^(.*)\.', '\1_{Date-Time}'.format(**global_vars), entry.name, re.IGNORECASE) + _name = '{ClientDir}\\Info\\{name}'.format(name=_name, **global_vars) + shutil.move(entry.path, non_clobber_rename(_name)) + elif entry.name == 'Quarantine': + os.makedirs(global_vars['QuarantineDir'], exist_ok=True) + _name = '{QuarantineDir}\\AdwCleaner_{Date-Time}'.format(**global_vars) + shutil.move(entry.path, non_clobber_rename(_name)) + shutil.rmtree(_path) + +def cleanup_desktop(): + #~#TODO (Pseudo-code) + #~#for d in drives: + #~# for user in os.scandir('{drive}\\Users'.format(drive=d)): + #~# if os.path.exists('{drive}\\Users\\{user}\\Desktop'.format(drive=d, user=user)): + #~# for entry in os.scandir('{drive}\\Users\\{user}\\Desktop'.format(drive=d, user=user)): + #~# # JRT, RKill, Shortcut cleaner + #~# if re.search(r'^((JRT|RKill).*|sc-cleaner)', entry.name, re.IGNORECASE): + #~# shutil.move(entry.path, '{ClientDir}\\Info\\{name}'.format(name=entry.name, **global_vars)) + os.makedirs('{ClientDir}\\Info'.format(**global_vars), exist_ok=True) + if os.path.exists('{USERPROFILE}\\Desktop'.format(**global_vars['Env'])): + for entry in os.scandir('{USERPROFILE}\\Desktop'.format(**global_vars['Env'])): + # JRT, RKill, Shortcut cleaner + if re.search(r'^((JRT|RKill).*|sc-cleaner)', entry.name, re.IGNORECASE): + _name = re.sub(r'^(.*)\.', '\1_{Date-Time}'.format(**global_vars), entry.name, re.IGNORECASE) + _name = '{ClientDir}\\Info\\{name}'.format(name=_name, **global_vars) + shutil.move(entry.path, non_clobber_rename(_name)) + run_program('rmdir "{path}"'.format(path='{ClientDir}\\Info'.format(**global_vars)), check=False, shell=True) + +def uninstall_eset(): + if 'PROGRAMFILES(X86)' in global_vars['Env']: + _path = '{PROGRAMFILES(X86)}\\ESET'.format(**global_vars['Env']) + else: + _path = '{PROGRAMFILES}\\ESET'.format(**global_vars['Env']) + if os.path.exists('{path}\\ESET Online Scanner'.format(path=_path)): + run_program('"{path}\\ESET Online Scanner\\OnlineScannerUninstaller.exe" -s'.format(path=_path)) + shutil.rmtree('{path}\\ESET Online Scanner'.format(path=_path)) + run_program('rmdir "{path}"'.format(path=_path), check=False) + +def uninstall_mbam(): + # if 'PROGRAMFILES(X86)' in global_vars['Env']: + # _path = '{PROGRAMFILES(X86)}\\Malwarebytes Anti-Malware'.format(**global_vars['Env']) + # else: + # _path = '{PROGRAMFILES}\\Malwarebytes Anti-Malware'.format(**global_vars['Env']) + # if os.path.exists('{path}'.format(path=_path)): + # print_warning('* Malwarebytes Anti-Malware installed.') + # if ask(' Uninstall?'): + # try: + # run_program('"{path}\\unins000.exe" /SILENT'.format(path=_path)) + # run_program('rmdir "{path}"'.format(path=_path), check=False) + # except: + # print_error('ERROR: Failed to uninstall Malwarebytes Anti-Malware.') + pass + +def uninstall_sas(): + # It is always in programfiles (not x86) ?? + _path = '{PROGRAMFILES}\\SUPERAntiSpyware'.format(**global_vars['Env']) + if os.path.exists(_path): + run_program('{path}\\Uninstall.exe'.format(path=_path)) + run_program('rmdir "{path}"'.format(path=_path), check=False) + +# Config +def config_classicstart(): + _classicstart = '{PROGRAMFILES}\\Classic Shell\\ClassicStartMenu.exe'.format(**global_vars['Env']) + _skin = '{PROGRAMFILES}\\Classic Shell\\Skins\\Metro-Win10-Black.skin7'.format(**global_vars['Env']) + extract_item('ClassicStart', silent=True) + + # Stop Classic Start + run_program(_classicstart, ['-exit'], check=False) + + # Configure + winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\IvoSoft\ClassicShell\Settings') + winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\IvoSoft\ClassicStartMenu\MRU') + winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\IvoSoft\ClassicStartMenu\Settings') + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\IvoSoft\ClassicStartMenu', access=winreg.KEY_WRITE) as _key: + winreg.SetValueEx(_key, 'ShowedStyle2', 0, winreg.REG_DWORD, 1) + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\IvoSoft\ClassicStartMenu\Settings', access=winreg.KEY_WRITE) as _key: + winreg.SetValueEx(_key, 'MenuStyle', 0, winreg.REG_SZ, 'Win7') + winreg.SetValueEx(_key, 'RecentPrograms', 0, winreg.REG_SZ, 'Recent') + winreg.SetValueEx(_key, 'SkipMetro', 0, winreg.REG_DWORD, 1) + + # Enable Win10 theme if on Win10 + if global_vars['OS']['Version'] == '10' and os.path.exists(_skin): + winreg.SetValueEx(_key, 'SkinW7', 0, winreg.REG_SZ, 'Metro-Win10-Black') + + # Pin Google Chrome to Start Menu (Classic) + _source = '{BinDir}\\ClassicStart\\Google Chrome.lnk'.format(**global_vars) + _dest_path = '{APPDATA}\\ClassicShell\\Pinned'.format(**global_vars['Env']) + _dest = '{dest_path}\\Google Chrome.lnk'.format(dest_path=_dest_path) + try: + os.makedirs(_dest_path, exist_ok=True) + shutil.copy(_source, _dest) + except: + pass # Meh, it's fine without + + # (Re)start Classic Start + run_program(_classicstart, ['-exit'], check=False) + sleep(1) + kill_process('ClassicStartMenu.exe') + run_program(_classicstart, check=False) + +def config_explorer(): + pass + +def update_clock(): + # Set Timezone and sync clock + run_program('tzutil /s "Pacific Standard Time"', check=False) + run_program('net stop w32ime', check=False) + run_program('w32tm /config /syncfromflags:manual /manualpeerlist:"us.pool.ntp.org time.nist.gov time.windows.com"', check=False) + run_program('net start w32ime', check=False) + run_program('w32tm /resync /nowait', check=False) + +# Data Transfers +def cleanup_transfer(): + """Fix permissions and walk through transfer folder (from the bottom) and remove extraneous items.""" + run_program('attrib -a -h -r -s "{TransferDir}"'.format(**global_vars), check=False) + if os.path.exists(global_vars['TransferDir']): + for root, dirs, files in os.walk(global_vars['TransferDir'], topdown=False): + for name in dirs: + # Remove empty directories and junction points + try: + os.rmdir(os.path.join(root, name)) + except OSError: + pass + for name in files: + # Remove files based on exclusion regex + if REGEX_EXCL_ITEMS.search(name): + try: + os.remove(os.path.join(root, name)) + except OSError: + pass + +def is_valid_wim_image(item): + _valid = item.is_file() and re.search(r'\.wim$', item.name, flags=re.IGNORECASE) + if _valid: + try: + _cmd = [global_vars['Tools']['wimlib-imagex'], 'info', '{image}'.format(image=item.path)] + run_program(_cmd) + except subprocess.CalledProcessError: + _valid = False + print_log('WARNING: Image "{image}" damaged.'.format(image=item.name)) + sleep(2) + return _valid + +# Disks, Partitions, and Volumes def get_attached_disk_info(): """Get details about the attached disks and return a list of dicts.""" disks = [] @@ -347,49 +1511,403 @@ def get_attached_disk_info(): # Done return disks -def get_free_space_info(): - """Get free space info for all fixed volumes and return a list of lists.""" - drives = run_program('fsutil fsinfo drives', check=False) - drives = drives.stdout.decode() - drives = drives.replace('Drives: ', '').replace('\\', '').split() - _return = [] - for drive in sorted(drives): - _out = run_program('fsutil fsinfo drivetype {drive}'.format(drive=drive)) - _drive_type = _out.stdout.decode() - if re.search(r'Fixed Drive', _drive_type, re.IGNORECASE): +def mount_backup_shares(): + """Mount the backup shares unless labeled as already mounted.""" + for server in BACKUP_SERVERS: + # Blindly skip if we mounted earlier + if server['Mounted']: + continue + else: try: - _out = run_program('fsutil volume diskfree {drive}'.format(drive=drive)) - _out = _out.stdout.decode().splitlines() - _free = int(re.sub(r'.*:\s+(.*)', r'\1', _out[0])) - _total = int(re.sub(r'.*:\s+(.*)', r'\1', _out[1])) - _str = '{percent:>6.2f}% Free ({free} / {total})'.format( - percent = _free/_total, - free = human_readable_size(_free, 2), - total = human_readable_size(_total, 2)) - _return.append([drive, _str]) - except subprocess.CalledProcessError: - pass - return _return + # Test connection + ping_test(server['IP']) -def get_user_data_size_info(vars_wk=None): + # Mount + run_program('net use \\\\{IP}\\{Share} /user:{User} {Pass}'.format(**server)) + print_info('Mounted {Name}'.format(**server)) + server['Mounted'] = True + except subprocess.CalledProcessError: + print_error('Failed to mount \\\\{Name}\\{Share}, {IP} unreachable.'.format(**server)) + sleep(1) + except: + print_warning('Failed to mount \\\\{Name}\\{Share} ({IP})'.format(**server)) + sleep(1) + +def select_backup(ticket): + """Find any backups for the ticket stored on one of the BACKUP_SERVERS. Returns path as a os.DirEntry.""" + _backups = [] + mount_backup_shares() + for server in BACKUP_SERVERS: + if server['Mounted']: + for d in os.scandir('\\\\{IP}\\{Share}'.format(**server)): + if d.is_dir() and re.match('^{}'.format(ticket), d.name): + _backups.append({'Name': '{s_name}: {backup}'.format(s_name=server['Name'], backup=d.name), 'Dir': d}) + actions = [{'Name': 'Quit', 'Letter': 'Q'}] + + # Select backup path + if len(_backups) > 0: + selection = menu_select('Which backup are we using?', _backups, actions) + if selection == 'Q': + return None + else: + return _backups[int(selection)-1]['Dir'] + else: + print_error('No backups found for ticket: {ticket}.'.format(ticket=ticket)) + return None + +def umount_backup_shares(): + """Unnount the backup shares regardless of current status.""" + for server in BACKUP_SERVERS: + try: + # Umount + run_program('net use \\\\{IP}\\{Share} /delete'.format(**server)) + print_info('Umounted {Name}'.format(**server)) + server['Mounted'] = False + except: + print_error('Failed to umount \\\\{Name}\\{Share}.'.format(**server)) + sleep(1) + +# Installations +def install_classicstart_skin(): + extract_item('ClassicStart', silent=True) + _source = '{BinDir}\\ClassicStart\\Metro-Win10-Black.skin7'.format(**global_vars) + _dest_path = '{PROGRAMFILES}\\Classic Shell\\Skins'.format(**global_vars['Env']) + _dest = '{dest_path}\\Metro-Win10-Black.skin7'.format(dest_path=_dest_path) + os.makedirs(_dest_path, exist_ok=True) + shutil.copy(_source, _dest) + +# Network +def check_connection(): + while True: + result = try_and_print(message='Ping test...', function=ping_test, cs='OK') + if result['CS']: + break + else: + if not ask('ERROR: System appears offline, try again?'): + abort() + +def ping_test(addr='google.com'): + """Attempt to ping addr and if unsuccessful either retry or abort.""" + _cmd = ['ping', '-n', '2', addr] + run_program(_cmd) + +# OSR / VR +def run_autoruns(): + """Run AutoRuns in the background with VirusTotal checks enabled.""" + extract_item('SysinternalsSuite', filter='autoruns*', silent=True) + winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns') + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns', access=winreg.KEY_WRITE) as _key: + winreg.SetValueEx(_key, 'checkvirustotal', 0, winreg.REG_DWORD, 1) + winreg.SetValueEx(_key, 'EulaAccepted', 0, winreg.REG_DWORD, 1) + winreg.SetValueEx(_key, 'shownomicrosoft', 0, winreg.REG_DWORD, 1) + winreg.SetValueEx(_key, 'shownowindows', 0, winreg.REG_DWORD, 1) + winreg.SetValueEx(_key, 'showonlyvirustotal', 0, winreg.REG_DWORD, 1) + winreg.SetValueEx(_key, 'submitvirustotal', 0, winreg.REG_DWORD, 0) + winreg.SetValueEx(_key, 'verifysignatures', 0, winreg.REG_DWORD, 1) + winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\SigCheck') + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\SigCheck', access=winreg.KEY_WRITE) as _key: + winreg.SetValueEx(_key, 'EulaAccepted', 0, winreg.REG_DWORD, 1) + winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\Streams') + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\Streams', access=winreg.KEY_WRITE) as _key: + winreg.SetValueEx(_key, 'EulaAccepted', 0, winreg.REG_DWORD, 1) + winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\VirusTotal') + with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\VirusTotal', access=winreg.KEY_WRITE) as _key: + winreg.SetValueEx(_key, 'VirusTotalTermsAccepted', 0, winreg.REG_DWORD, 1) + popen_program(global_vars['Tools']['AutoRuns'], minimized=True) + +def run_chkdsk(): + """Run CHKDSK in a "split window" and report errors.""" + if global_vars['OS']['Version'] in ['8', '10']: + _cmd = [ + 'chkdsk', + '{SYSTEMDRIVE}'.format(**global_vars['Env']), + '/scan', '/perf'] + else: + _cmd = [ + 'chkdsk', + '{SYSTEMDRIVE}'.format(**global_vars['Env'])] + _out = run_program(_cmd, check=False) + # retcode == 0: no issues + # retcode == 1: fixed issues (also happens when chkdsk.exe is killed?) + # retcode == 2: issues + if int(_out.returncode) > 0: + # print_error(' ERROR: CHKDSK encountered errors') + raise GenericError + + # Save stderr + with open('{LogDir}\\CHKDSK.err'.format(**global_vars), 'a') as f: + for line in _out.stderr.decode().splitlines(): + f.write(line.strip() + '\n') + # Save stdout + with open('{LogDir}\\CHKDSK.log'.format(**global_vars), 'a') as f: + for line in _out.stdout.decode().splitlines(): + f.write(line.strip() + '\n') + +def run_chkdsk_offline(): + """Set filesystem 'dirty bit' to force a chkdsk during next boot.""" + _cmd = [ + 'fsutil', 'dirty', 'set', + '{SYSTEMDRIVE}'.format(**global_vars['Env'])] + _out = run_program(_cmd, check=False) + if int(_out.returncode) > 0: + raise GenericError + +def run_chkdsk_spotfix(): + """Run CHKDSK in a "split window" and report errors.""" + if global_vars['OS']['Version'] in ['8', '10']: + _cmd = [ + 'chkdsk', + '{SYSTEMDRIVE}'.format(**global_vars['Env']), + '/scan', '/perf'] + else: + raise UnsupportedOSError + _out = run_program(_cmd, check=False) + # retcode == 0: no issues + # retcode == 1: fixed issues (also happens when chkdsk.exe is killed?) + # retcode == 2: issues + if int(_out.returncode) > 0: + # print_error(' ERROR: CHKDSK encountered errors') + raise GenericError + + # Save stderr + with open('{LogDir}\\CHKDSK_Spotfix.err'.format(**global_vars), 'a') as f: + for line in _out.stderr.decode().splitlines(): + f.write(line.strip() + '\n') + # Save stdout + with open('{LogDir}\\CHKDSK_Spotfix.log'.format(**global_vars), 'a') as f: + for line in _out.stdout.decode().splitlines(): + f.write(line.strip() + '\n') + +def run_dism_restore_health(): + """Run DISM /ScanHealth, then /CheckHealth, and then report errors.""" + if global_vars['OS']['Version'] in ['8', '10']: + # Scan Health + _cmd = [ + 'DISM', '/Online', '/Cleanup-Image', '/RestoreHealth', + '/LogPath:"{LogDir}\\DISM_RestoreHealth.log"'.format(**global_vars), + '-new_console:n', '-new_console:s33V'] + run_program(_cmd, pipe=False, check=False, shell=True) + wait_for_process('dism') + # Now check health + _cmd = [ + 'DISM', '/Online', '/Cleanup-Image', '/CheckHealth', + '/LogPath:"{LogDir}\\DISM_CheckHealth.log"'.format(**global_vars)] + _result = run_program(_cmd, shell=True).stdout.decode() + # Check result + if re.search(r'No component store corruption detected', _result, re.IGNORECASE): + pass + else: + raise GenericError + else: + raise UnsupportedOSError + +def run_dism_scan_health(): + """Run DISM /ScanHealth, then /CheckHealth, and then report errors.""" + if global_vars['OS']['Version'] in ['8', '10']: + # Scan Health + _cmd = [ + 'DISM', '/Online', '/Cleanup-Image', '/ScanHealth', + '/LogPath:"{LogDir}\\DISM_ScanHealth.log"'.format(**global_vars), + '-new_console:n', '-new_console:s33V'] + run_program(_cmd, pipe=False, check=False, shell=True) + wait_for_process('dism') + # Now check health + _cmd = [ + 'DISM', '/Online', '/Cleanup-Image', '/CheckHealth', + '/LogPath:"{LogDir}\\DISM_CheckHealth.log"'.format(**global_vars)] + _result = run_program(_cmd, shell=True).stdout.decode() + # Check result + if re.search(r'No component store corruption detected', _result, re.IGNORECASE): + pass + else: + raise GenericError + else: + raise UnsupportedOSError + +def run_hitmanpro(): + """Run HitmanPro in the background.""" + extract_item('HitmanPro', silent=True) + _cmd = [ + global_vars['Tools']['HitmanPro'], + '/quiet', '/noinstall', '/noupload', + '/log={LogDir}\\hitman.xml'.format(**global_vars)] + popen_program(_cmd) + +def run_kvrt(): + """Run KVRT.""" + extract_item('KVRT', silent=True) + os.makedirs(global_vars['QuarantineDir'], exist_ok=True) + _cmd = [ + global_vars['Tools']['KVRT'], + '-accepteula', '-dontcryptsupportinfo', '-fixednames', + '-d', global_vars['QuarantineDir'], + '-processlevel', '3'] + run_program(_cmd, pipe=False) + +def run_process_killer(): + """Kill most running processes skipping those in the whitelist.txt.""" + # borrowed from TronScript (reddit.com/r/TronScript) and credit to /u/cuddlychops06 + _prev_dir = os.getcwd() + extract_item('ProcessKiller', silent=True) + os.chdir('{BinDir}\\ProcessKiller'.format(**global_vars)) + run_program(['ProcessKiller.exe', '/silent'], check=False) + os.chdir(_prev_dir) + +def run_rkill(): + """Run RKill and cleanup afterwards.""" + extract_item('RKill', silent=True) + _cmd = [ + global_vars['Tools']['RKill'], + '-l', '{LogDir}\\RKill.log'.format(**global_vars), + '-new_console:n', '-new_console:s33V'] + run_program(_cmd, check=False) + wait_for_process('RKill') + kill_process('notepad.exe') + + # RKill cleanup + if os.path.exists('{USERPROFILE}\\Desktop'.format(**global_vars['Env'])): + for item in os.scandir('{USERPROFILE}\\Desktop'.format(**global_vars['Env'])): + if re.search(r'^RKill', item.name, re.IGNORECASE): + _name = re.sub(r'^(.*)\.', '\1_{Date-Time}'.format(**global_vars), item.name, re.IGNORECASE) + _name = '{ClientDir}\\Info\\{name}'.format(name=_name, **global_vars) + shutil.move(item.path, non_clobber_rename(_name)) + +def run_sfc_scan(): + """Run SFC in a "split window" and report errors.""" + _cmd = [ + '{SYSTEMROOT}\\System32\\sfc.exe'.format(**global_vars['Env']), + '/scannow'] + _out = run_program(_cmd, check=False) + # Save stderr + with open('{LogDir}\\SFC.err'.format(**global_vars), 'a') as f: + for line in _out.stderr.decode().splitlines(): + f.write(line.strip() + '\n') + # Save stdout + with open('{LogDir}\\SFC.log'.format(**global_vars), 'a') as f: + for line in _out.stdout.decode().splitlines(): + f.write(line.strip() + '\n') + # Report result + if re.findall(r'did\s+not\s+find\s+any\s+integrity\s+violations', _out.stdout.decode()): + pass + elif re.findall(r'successfully\s+repaired\s+them', _out.stdout.decode()): + raise GenericRepair + else: + raise GenericError + +def run_tdsskiller(): + """Run TDSSKiller.""" + extract_item('TDSSKiller', silent=True) + os.makedirs('{QuarantineDir}\\TDSSKiller'.format(**global_vars), exist_ok=True) + _cmd = [ + global_vars['Tools']['TDSSKiller'], + '-l', '{LogDir}\\TDSSKiller.log'.format(**global_vars), + '-qpath', '{QuarantineDir}\\TDSSKiller'.format(**global_vars), + '-accepteula', '-accepteulaksn', + '-dcexact', '-tdlfs'] + run_program(_cmd, pipe=False) + +# System Info +def backup_file_list(): + """Export current file listing for the system.""" + extract_item('Everything', silent=True) + _cmd = [ + global_vars['Tools']['Everything'], + '-nodb', + '-create-filelist', + '{LogDir}\\File List.txt'.format(**global_vars), + '{SYSTEMDRIVE}'.format(**global_vars['Env'])] + run_program(_cmd) + +def backup_power_plans(): + """Export current power plans.""" + os.makedirs('{BackupDir}\\Power Plans'.format(**global_vars), exist_ok=True) + _plans = run_program('powercfg /L') + _plans = _plans.stdout.decode().splitlines() + _plans = [p for p in _plans if re.search(r'^Power Scheme', p)] + for p in _plans: + _guid = re.sub(r'Power Scheme GUID:\s+([0-9a-f\-]+).*', r'\1', p) + _name = re.sub(r'Power Scheme GUID:\s+[0-9a-f\-]+\s+\(([^\)]+)\).*', r'\1', p) + # print(' {name} ({guid})'.format(guid=_guid, name=_name)) + _out = '{BackupDir}\\Power Plans\\{name}.pow'.format(name=_name, **global_vars) + if not os.path.exists(_out): + _cmd = ['powercfg', '-export', _out, _guid] + run_program(_cmd, check=False) + +def backup_registry(): + extract_item('erunt', silent=True) + _args = [ + '{LogDir}\\Registry'.format(**global_vars), + 'sysreg', + 'curuser', + 'otherusers', + '/noprogresswindow'] + run_program(global_vars['Tools']['ERUNT'], _args) + +def compress_info(): + path = '{ClientDir}'.format(**global_vars) + file = 'Info_{Date-Time}.7z'.format(**global_vars) + _cmd = [ + global_vars['Tools']['SevenZip'], + 'a', '-t7z', '-mx=9', '-bso0', '-bse0', + '{path}\\{file}'.format(path=path, file=file), + '{ClientDir}\\Info'.format(**global_vars)] + run_program(_cmd) + +def find_software_hives(): + """Search for transferred SW hives and return a list.""" + hives = [] + search_paths = [global_vars['ClientDir']] + + while len(search_paths) > 0: + for item in os.scandir(search_paths.pop(0)): + if item.is_dir() and REGEX_REGISTRY_DIRS.search(item.name): + search_paths.append(item.path) + if item.is_file() and REGEX_SOFTWARE_HIVE.search(item.name): + hives.append(item.path) + + return hives + +def get_installed_office(): + programs = [] + with open ('{LogDir}\\Installed Program List (AIDA64).txt'.format(**global_vars), 'r') as f: + for line in sorted(f.readlines()): + if REGEX_OFFICE.search(line): + programs.append(line[4:82].strip()) + + if len(programs) == 0: + programs = ['No programs found'] + return programs + +def get_product_keys(): + keys = [] + + with open ('{LogDir}\\Product Keys (ProduKey).txt'.format(**global_vars), 'r') as f: + for line in f.readlines(): + if re.search(r'^Product Name', line): + line = re.sub(r'^Product Name\s+:\s+(.*)', r'\1', line.strip()) + keys.append(line) + + if len(keys) == 0: + keys = ['No product keys found'] + return keys + +def get_user_data_size_info(all_users=True, indent=8, width=32): """Get size of user folders for all users and return a dict of dicts.""" - if vars_wk is None: - raise Exception users = {} TMP_HIVE_PATH = 'HKU\\wk_tmp' # Extract and configure du - extract_item('SysinternalsSuite', vars_wk, filter='du*', silent=True) - du = '{BinDir}\\SysinternalsSuite\\du.exe'.format(**vars_wk) - if vars_wk['Arch'] == 64: - du = du.replace('.exe', '64.exe') + extract_item('SysinternalsSuite', filter='du*', silent=True) winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\Du') with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\Du', access=winreg.KEY_WRITE) as _key: winreg.SetValueEx(_key, 'EulaAccepted', 0, winreg.REG_DWORD, 1) try: # Get SIDs - out = run_program('wmic useraccount get sid') + if all_users: + out = run_program('wmic useraccount get sid') + else: + out = run_program('wmic useraccount where name="{USERNAME}" get sid'.format(**global_vars['Env'])) sids = out.stdout.decode().splitlines() sids = [s.strip() for s in sids if re.search(r'-1\d+$', s.strip())] @@ -414,12 +1932,17 @@ def get_user_data_size_info(vars_wk=None): with winreg.OpenKey(winreg.HKEY_LOCAL_MACHINE, key) as _key: users[u]['ProfileImagePath'] = winreg.QueryValueEx(_key, 'ProfileImagePath')[0] try: - out = run_program(du, ['-nobanner', '-q', users[u]['ProfileImagePath']]) + out = run_program(global_vars['Tools']['Du'], ['-nobanner', '-q', users[u]['ProfileImagePath']]) size = out.stdout.decode().splitlines()[4] size = re.sub(r'Size:\s+([\d,]+)\sbytes$', r'\1', size) size = size.replace(',', '') size = human_readable_size(size) - size_str = '{folder:<20} {size:>10} ({path})'.format(folder='Profile', size=size, path=users[u]['ProfileImagePath']) + size_str = '{indent}{folder:<{width}}{size:>6} ({path})'.format( + indent = ' ' * indent, + width = width, + folder = 'Profile', + size = size, + path = users[u]['ProfileImagePath']) users[u]['ProfileSize'] = size_str except subprocess.CalledProcessError: # Failed to get folder size @@ -451,12 +1974,17 @@ def get_user_data_size_info(vars_wk=None): folder_path = winreg.QueryValueEx(_key, value)[0] try: # Finally calculate folder size - out = run_program(du, ['-nobanner', '-q', folder_path]) + out = run_program(global_vars['Tools']['Du'], ['-nobanner', '-q', folder_path]) size = out.stdout.decode().splitlines()[4] size = re.sub(r'Size:\s+([\d,]+)\sbytes$', r'\1', size) size = size.replace(',', '') size = human_readable_size(size) - str = '{folder:<20} {size:>10} ({path})'.format(folder=folder, size=size, path=folder_path) + str = '{indent}{folder:<{width}}{size:>6} ({path})'.format( + indent = ' ' * indent, + width = width, + folder = folder, + size = size, + path = folder_path) users[u]['Shell Folders'][folder] = str except subprocess.CalledProcessError: # Failed to get folder size @@ -475,12 +2003,17 @@ def get_user_data_size_info(vars_wk=None): folder_path = '{ProfileImagePath}\\{folder}'.format(folder=folder, **users[u]) if os.path.exists(folder_path): try: - out = run_program(du, ['-nobanner', '-q', folder_path]) + out = run_program(global_vars['Tools']['Du'], ['-nobanner', '-q', folder_path]) size = out.stdout.decode().splitlines()[4] size = re.sub(r'Size:\s+([\d,]+)\sbytes$', r'\1', size) size = size.replace(',', '') size = human_readable_size(size) - str = '{folder:<20} {size:>10} ({path})'.format(folder=folder, size=size, path=folder_path) + str = '{indent}{folder:<{width}}{size:>6} ({path})'.format( + indent = ' ' * indent, + width = width, + folder = folder, + size = size, + path = folder_path) users[u]['Shell Folders'][folder] = str except subprocess.CalledProcessError: # Failed to get folder size @@ -491,12 +2024,17 @@ def get_user_data_size_info(vars_wk=None): folder_path = '{ProfileImagePath}\\{folder}'.format(folder=folder, **users[u]) if os.path.exists(folder_path): try: - out = run_program(du, ['-nobanner', '-q', folder_path]) + out = run_program(global_vars['Tools']['Du'], ['-nobanner', '-q', folder_path]) size = size.stdout.decode().splitlines()[4] size = re.sub(r'Size:\s+([\d,]+)\sbytes$', r'\1', size) size = size.replace(',', '') size = human_readable_size(size) - str = '{folder:<20} {size:>10} ({path})'.format(folder=folder, size=size, path=folder_path) + str = '{indent}{folder:<{width}}{size:>6} ({path})'.format( + indent = ' ' * indent, + width = width, + folder = folder, + size = size, + path = folder_path) users[u]['Extra Folders'][folder] = str except subprocess.CalledProcessError: # Failed to get folder size @@ -516,584 +2054,172 @@ def get_user_data_size_info(vars_wk=None): # Done return users -def human_readable_size(size, decimals=0): - """Convert size in bytes to a human-readable format and return a str.""" - # Prep string formatting - width = 3+decimals - if decimals > 0: - width += 1 - human_format = '>{width}.{decimals}f'.format(width=width, decimals=decimals) - tmp = '' +def run_aida64(): + extract_item('AIDA64', silent=True) + # All system info + if not os.path.exists('{LogDir}\\System Information (AIDA64).html'.format(**global_vars)): + _cmd = [ + global_vars['Tools']['AIDA64'], + '/R', '{LogDir}\\System Information (AIDA64).html'.format(**global_vars), + '/CUSTOM', '{BinDir}\\AIDA64\\full.rpf'.format(**global_vars), + '/HTML', '/SILENT', '/SAFEST'] + run_program(_cmd, check=False) + + # Installed Programs + if not os.path.exists('{LogDir}\\Installed Program List (AIDA64).txt'.format(**global_vars)): + _cmd = [ + global_vars['Tools']['AIDA64'], + '/R', '{LogDir}\\Installed Program List (AIDA64).txt'.format(**global_vars), + '/CUSTOM', '{BinDir}\\AIDA64\\installed_programs.rpf'.format(**global_vars), + '/TEXT', '/SILENT', '/SAFEST'] + run_program(_cmd, check=False) + + # Product Keys + if not os.path.exists('{LogDir}\\Product Keys (AIDA64).txt'.format(**global_vars)): + _cmd = [ + global_vars['Tools']['AIDA64'], + '/R', '{LogDir}\\Product Keys (AIDA64).txt'.format(**global_vars), + '/CUSTOM', '{BinDir}\\AIDA64\\licenses.rpf'.format(**global_vars), + '/TEXT', '/SILENT', '/SAFEST'] + run_program(_cmd, check=False) - # Convert size to int - try: - size = int(size) - except ValueError: - size = convert_to_bytes(size) +def run_bleachbit(): + if not os.path.exists('{LogDir}\\BleachBit.log'.format(**global_vars)): + extract_item('BleachBit', silent=True) + _cmd = [global_vars['Tools']['BleachBit'], '--preview', '--preset'] + _out = run_program(_cmd, check=False) + # Save stderr + if len(_out.stderr.decode().splitlines()) > 0: + with open('{LogDir}\\BleachBit.err'.format(**global_vars), 'a') as f: + for line in _out.stderr.decode().splitlines(): + f.write(line.strip() + '\n') + # Save stdout + with open('{LogDir}\\BleachBit.log'.format(**global_vars), 'a') as f: + for line in _out.stdout.decode().splitlines(): + f.write(line.strip() + '\n') - # Verify we have a valid size - if size <= 0: - return '{size:>{width}} b'.format(size='???', width=width) +def run_hwinfo_sensors(): + _path = '{BinDir}\\HWiNFO'.format(**global_vars) + for bit in [32, 64]: + # Configure + _source = '{path}\\general.ini'.format(path=_path) + _dest = '{path}\\HWiNFO{bit}.ini'.format(bit=bit, path=_path) + shutil.copy(_source, _dest) + with open(_dest, 'a') as f: + f.write('SensorsOnly=1\n') + f.write('SummaryOnly=0\n') + popen_program(global_vars['Tools']['HWiNFO']) - # Format string - if size >= 1099511627776: - size /= 1099511627776 - tmp = '{size:{human_format}} Tb'.format(size=size, human_format=human_format) - elif size >= 1073741824: - size /= 1073741824 - tmp = '{size:{human_format}} Gb'.format(size=size, human_format=human_format) - elif size >= 1048576: - size /= 1048576 - tmp = '{size:{human_format}} Mb'.format(size=size, human_format=human_format) - elif size >= 1024: - size /= 1024 - tmp = '{size:{human_format}} Kb'.format(size=size, human_format=human_format) - else: - tmp = '{size:{human_format}} b'.format(size=size, human_format=human_format) - - # Return - return tmp - -def menu_select(title='~ Untitled Menu ~', main_entries=[], action_entries=[], prompt='Please make a selection', secret_exit=False): - """Display options in a menu for user and return selected option as a str.""" - # Bail early - if (len(main_entries) + len(action_entries) == 0): - raise Exception("MenuError: No items given") - - # Build menu - menu_splash = '{title}\n\n'.format(title=title) - valid_answers = [] - if (secret_exit): - valid_answers.append('Q') - - # Add main entries - if (len(main_entries) > 0): - for i in range(len(main_entries)): - entry = main_entries[i] - # Add Spacer - if ('CRLF' in entry): - menu_splash += '\n' - if ('Disabled' in entry): - menu_splash += '{YELLOW}{number:>{mwidth}}: {name} (DISABLED){CLEAR}\n'.format(number=i+1, mwidth=len(str(len(main_entries))), name=entry.get('Display Name', entry['Name']), **COLORS) - else: - valid_answers.append(str(i+1)) - menu_splash += '{number:>{mwidth}}: {name}\n'.format(number=i+1, mwidth=len(str(len(main_entries))), name=entry.get('Display Name', entry['Name'])) - menu_splash += '\n' - - # Add action entries - if (len(action_entries) > 0): - for entry in action_entries: - # Add Spacer - if ('CRLF' in entry): - menu_splash += '\n' - valid_answers.append(entry['Letter']) - menu_splash += '{letter:>{mwidth}}: {name}\n'.format(letter=entry['Letter'].upper(), mwidth=len(str(len(action_entries))), name=entry['Name']) - menu_splash += '\n' - - answer = '' - - while (answer.upper() not in valid_answers): - os.system('cls') - print(menu_splash) - answer = input('{prompt}: '.format(prompt=prompt)) - - return answer.upper() - -def mount_backup_shares(): - """Mount the backup shares unless labeled as already mounted.""" - for server in BACKUP_SERVERS: - # Blindly skip if we mounted earlier - if server['Mounted']: - continue - else: +def run_produkey(): + extract_item('ProduKey', silent=True) + if not os.path.exists('{LogDir}\\Product Keys (ProduKey).txt'.format(**global_vars)): + # Clear current configuration + for config in ['ProduKey.cfg', 'ProduKey64.cfg']: try: - # Test connection - run_program('ping -w 800 -n 2 {IP}'.format(**server)) - - # Mount - run_program('net use \\\\{IP}\\{Share} /user:{User} {Pass}'.format(**server)) - print_info('Mounted {Name}'.format(**server)) - server['Mounted'] = True - except subprocess.CalledProcessError: - print_error('Failed to mount \\\\{Name}\\{Share}, {IP} unreachable.'.format(**server)) - time.sleep(1) + if os.path.exists('{BinDir}\\ProduKey\\{config}'.format(config=config, **global_vars)): + os.remove('{BinDir}\\ProduKey\\{config}'.format(config=config, **global_vars)) except: - print_warning('Failed to mount \\\\{Name}\\{Share} ({IP})'.format(**server)) - time.sleep(1) + pass + _cmd = [ + global_vars['Tools']['ProduKey'], '/nosavereg', + '/stext', '{LogDir}\\Product Keys (ProduKey).txt'.format(**global_vars)] + run_program(_cmd, check=False) -def mount_windows_share(): - """Mount the Windows images share unless labeled as already mounted.""" - # Blindly skip if we mounted earlier - if WINDOWS_SERVER['Mounted']: - return None - else: - try: - # Test connection - run_program('ping -w 800 -n 2 {IP}'.format(**WINDOWS_SERVER)) - # Mount - run_program('net use \\\\{IP}\\{Share} /user:{User} {Pass}'.format(**WINDOWS_SERVER)) - print_info('Mounted {Name}'.format(**WINDOWS_SERVER)) - WINDOWS_SERVER['Mounted'] = True - except subprocess.CalledProcessError: - print_error('Failed to mount \\\\{Name}\\{Share}, {IP} unreachable.'.format(**WINDOWS_SERVER)) - time.sleep(1) - except: - print_warning('Failed to mount \\\\{Name}\\{Share}'.format(**WINDOWS_SERVER)) - time.sleep(1) +def run_xmplay(): + extract_item('XMPlay', silent=True) + popen_program([global_vars['Tools']['XMPlay'], '{BinDir}\\XMPlay\\music.7z'.format(**global_vars)]) -def pause(prompt='Press Enter to continue... '): - """Simple pause implementation.""" - input(prompt) - -def print_error(message='Generic error', log_file=None, **kwargs): - """Prints message to screen in RED and writes it to log_file if provided.""" - print('{RED}{message}{CLEAR}'.format(message=message, **COLORS, **kwargs)) - if log_file is not None: - with open(log_file, 'a') as f: - f.write(message + '\n') - -def print_info(message='Generic info', log_file=None, **kwargs): - """Prints message to screen in BLUE and writes it to log_file if provided.""" - print('{BLUE}{message}{CLEAR}'.format(message=message, **COLORS, **kwargs)) - if log_file is not None: - with open(log_file, 'a') as f: - f.write(message + '\n') - -def print_warning(message='Generic warning', log_file=None, **kwargs): - """Prints message to screen in YELLOW and writes it to log_file if provided.""" - print('{YELLOW}{message}{CLEAR}'.format(message=message, **COLORS, **kwargs)) - if log_file is not None: - with open(log_file, 'a') as f: - f.write(message + '\n') - -def print_standard(message='Generic info', log_file=None, **kwargs): - """Prints message to screen and writes it to log_file if provided.""" - print('{message}'.format(message=message, **COLORS, **kwargs)) - if log_file is not None: - with open(log_file, 'a') as f: - f.write(message + '\n') - -def print_success(message='Generic success', log_file=None, **kwargs): - """Prints message to screen in GREEN and writes it to log_file if provided.""" - print('{GREEN}{message}{CLEAR}'.format(message=message, **COLORS, **kwargs)) - if log_file is not None: - with open(log_file, 'a') as f: - f.write(message + '\n') - -def remove_volume_letters(keep=None): - """Remove the assigned drive letter for all attached volumes.""" - with open(diskpart_script, 'w') as script: - script.write('list volume\n') - process_return = run_program('diskpart /s {script}'.format(script=diskpart_script)) - with open(diskpart_script, 'w') as script: - for tmp in re.findall(r'Volume (\d+)\s+([A-Za-z]?)\s+', process_return.stdout.decode()): - if tmp[1] != '' and tmp[1] != keep: - script.write('select volume {number}\n'.format(number=tmp[0])) - script.write('remove\n') +def show_disk_usage(disk=None): + if disk is None: + raise Exception + print_standard(disk.device.replace('\\', ' '), end='', flush=True, timestamp=False) try: - run_program('diskpart /s {script}'.format(script=diskpart_script)) + usage = psutil.disk_usage(disk.device) + display_string = '{percent:>5.2f}% Free ({free} / {total})'.format( + percent = 100 - usage.percent, + free = human_readable_size(usage.free, 2), + total = human_readable_size(usage.total, 2)) + if usage.percent > 85: + print_error(display_string, timestamp=False) + elif usage.percent > 75: + print_warning(display_string, timestamp=False) + else: + print_standard(display_string, timestamp=False) except: - pass + print_warning('Unknown', timestamp=False) -def run_program(cmd=None, args=[], check=True, pipe=True, shell=False): - """Run program and return a subprocess.CompletedProcess instance.""" - if cmd is None: - raise Exception('No program passed.') - - _cmd = cmd - if len(args) > 0: - _cmd = [cmd] + args - - if pipe: - process_return = subprocess.run(_cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE, check=check, shell=shell) - else: - process_return = subprocess.run(_cmd, check=check, shell=shell) - - return process_return - -def select_backup(ticket): - """Find any backups for the ticket stored on one of the BACKUP_SERVERS. Returns path as a os.DirEntry.""" - _backups = [] - mount_backup_shares() - for server in BACKUP_SERVERS: - if server['Mounted']: - for d in os.scandir('\\\\{IP}\\{Share}'.format(**server)): - if d.is_dir() and re.match('^{}'.format(ticket), d.name): - _backups.append({'Name': '{s_name}: {backup}'.format(s_name=server['Name'], backup=d.name), 'Dir': d}) - actions = [{'Name': 'Quit', 'Letter': 'Q'}] - - # Select backup path - if len(_backups) > 0: - selection = menu_select('Which backup are we using?', _backups, actions) - if selection == 'Q': - return None - else: - return _backups[int(selection)-1]['Dir'] - else: - print_error('No backups found for ticket: {ticket}.'.format(ticket=ticket)) - return None - -def select_destination(): - """Select backup destination and return a dict.""" - # Build menu - dests = [] - for server in BACKUP_SERVERS: - if server['Mounted']: - dests.append(server) - actions = [ - {'Name': 'Main Menu', 'Letter': 'M'}, - ] - - # Size check - for dest in dests: - if 'IP' in dest: - dest['Usage'] = shutil.disk_usage('\\\\{IP}\\{Share}'.format(**dest)) - else: - dest['Usage'] = shutil.disk_usage('{Letter}:\\'.format(**dest)) - dest['Free Space'] = human_readable_size(dest['Usage'].free) - dest['Display Name'] = '{Name} ({Free Space} available)'.format(**dest) - - # Show menu or bail - if len(dests) > 0: - selection = menu_select('Where are we backing up to?', dests, actions) - if selection == 'M': - return None - else: - return dests[int(selection)-1] - else: - print_warning('No backup destinations found.') - return None - -def select_disk(prompt='Which disk?'): - """Select a disk from the attached disks and return the disk number as an int.""" - disks = get_attached_disk_info() - - # Build menu - disk_options = [] - for disk in disks: - display_name = '{Size}\t[{Table}] ({Type}) {Name}'.format(**disk) - if len(disk['Partitions']) > 0: - pwidth=len(str(len(disk['Partitions']))) - for par in disk['Partitions']: - # Show unsupported partition(s) in RED - par_skip = False - if 'Letter' not in par or re.search(r'(RAW|Unknown)', par['FileSystem']): - par_skip = True - if par_skip: - display_name += COLORS['YELLOW'] - - # Main text - display_name += '\n\t\t\tPartition {Number:>{pwidth}}: {Size} ({FileSystem})'.format(pwidth=pwidth, **par) - if par['Name'] != '': - display_name += '\t"{Name}"'.format(**par) - - # Clear color (if set above) - if par_skip: - display_name += COLORS['CLEAR'] - else: - display_name += '{YELLOW}\n\t\t\tNo partitions found.{CLEAR}'.format(**COLORS) - disk_options.append({'Name': display_name, 'Disk': disk}) - actions = [ - {'Name': 'Main Menu', 'Letter': 'M'}, - ] - - # Menu loop - selection = menu_select(prompt, disk_options, actions) - - if (selection.isnumeric()): - return disk_options[int(selection)-1]['Disk'] - elif (selection == 'M'): - # -1 here means cancel - return -1 - -def select_minidump_path(): - """Have the user select from all found MiniDump locations and return a dict.""" - dumps = [] - - # Assign volume letters first - assign_volume_letters() - - # Search for minidumps - tmp = run_program('mountvol') - tmp = [d for d in re.findall(r'.*([A-Za-z]):\\', tmp.stdout.decode())] - # Remove RAMDisk letter - if 'X' in tmp: - tmp.remove('X') - for drive in tmp: - if os.path.exists('{drive}:\\Windows\\MiniDump'.format(drive=drive)): - dumps.append({'Name': '{drive}:\\Windows\\MiniDump'.format(drive=drive)}) - - # Check results before showing menu - if len(dumps) == 0: - print_error(' No BSoD / MiniDump paths found') - time.sleep(2) - return None - - # Menu - selection = menu_select('Which BSoD / MiniDump path are we scanning?', dumps, []) - return dumps[int(selection) - 1]['Name'] - -def select_windows_version(): - """Select Windows version and return a dict.""" - versions = [ - {'Name': 'Windows 7 Home Basic', - 'ImageFile': 'Win7', - 'ImageName': 'Windows 7 HOMEBASIC', - 'Family': '7'}, - {'Name': 'Windows 7 Home Premium', - 'ImageFile': 'Win7', - 'ImageName': 'Windows 7 HOMEPREMIUM', - 'Family': '7'}, - {'Name': 'Windows 7 Professional', - 'ImageFile': 'Win7', - 'ImageName': 'Windows 7 PROFESSIONAL', - 'Family': '7'}, - {'Name': 'Windows 7 Ultimate', - 'ImageFile': 'Win7', - 'ImageName': 'Windows 7 ULTIMATE', - 'Family': '7'}, - - {'Name': 'Windows 8.1', - 'ImageFile': 'Win8', - 'ImageName': 'Windows 8.1', - 'Family': '8', - 'CRLF': True}, - {'Name': 'Windows 8.1 Pro', - 'ImageFile': 'Win8', - 'ImageName': 'Windows 8.1 Pro', - 'Family': '8'}, - - {'Name': 'Windows 10 Home', - 'ImageFile': 'Win10', - 'ImageName': 'Windows 10 Home', - 'Family': '10', - 'CRLF': True}, - {'Name': 'Windows 10 Pro', - 'ImageFile': 'Win10', - 'ImageName': 'Windows 10 Pro', - 'Family': '10'}, - ] - actions = [ - {'Name': 'Main Menu', 'Letter': 'M'}, - ] - - # Menu loop - selection = menu_select('Which version of Windows are we installing?', versions, actions) - - if selection.isnumeric(): - return versions[int(selection)-1] - elif selection == 'M': - return None - -def sleep(seconds=2): - time.sleep(seconds) - -def stay_awake(vars_wk=None): - """Prevent the system from sleeping or hibernating.""" - if vars_wk is None: - raise Exception - # Bail if caffeine is already running - for proc in psutil.process_iter(): - if proc.name() == 'caffeine.exe': - return - # Extract and run - extract_item('caffeine', vars_wk, silent=True) - try: - subprocess.Popen('"{BinDir}\\caffeine\\caffeine.exe"'.format(**vars_wk)) - except: - print_error('ERROR: No caffeine available; please set the power setting to High Performace.') - -def upload_data(path=None, file=None, vars_wk=None): - """Add CLIENT_INFO_SERVER to authorized connections and upload file.""" - # Bail early - if path is None or file is None or vars_wk is None: - raise Exception - - extract_item('PuTTY', vars_wk, filter='WK.ppk psftp.exe', silent=True) - - # Authorize connection to the server - winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\SimonTatham\PuTTY\SshHostKeys') - with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\SimonTatham\PuTTY\SshHostKeys', access=winreg.KEY_WRITE) as _key: - winreg.SetValueEx(_key, 'rsa2@22:10.0.0.10', 0, winreg.REG_SZ, r'0x10001,0xf60757b7656263622b3c17b2ec1a9bd74c555fe927b5e571928007cf944a98113db2434a33c782e8b51447ceb7cd0b30475f0d988ef23af75a5b48eaa8edad478489b314837fd5134a8059084ae6bafdb4a3eb759afad7474027c81773dc233ea4c4e46f6f5b32a58672b0e541613ac6eb231715fd5ffc28f237b66ef9ed18deff232e83acc1ecdf10794d11344ac68035d48d0bcc0c83f76b1fe9d5d16bb46d9906ce4e0214ba03cec411b2801a238e891e3eedc7ed4b41a81f0e228c0a4b7efedad8c10b982d01098628f8c4e3166e0b3a19fef11dc8600ceedbd19d6844d5e9c7147b4f64ec58b04dd9fb571a0909d2847894fbf9694415eb89df0a2b6fb1') - - # Write batch file - with open('{TmpDir}\\psftp.batch'.format(**vars_wk), 'w', encoding='ascii') as f: - f.write('lcd "{path}"\n'.format(path=path)) - f.write('cd "{Share}"\n'.format(**CLIENT_INFO_SERVER)) - f.write('mkdir {ProduKey}'.format(**vars_wk)) - f.write('cd {ProduKey}'.format(**vars_wk)) - f.write('put "{file}"\n'.format(file=file)) - - # Upload Info - _cmd = [ - '{BinDir}\\PuTTY\\PSFTP.EXE'.format(**vars_wk), - '-noagent', - '-i', '{BinDir}\\PuTTY\WK.ppk'.format(**vars_wk), - '{User}@{IP}'.format(**CLIENT_INFO_SERVER), - '-b', '{TmpDir}\\psftp.batch'.format(**vars_wk)] - run_program(_cmd) - -def wait_for_process(name=None): - """Wait for process by name.""" - if name is None: - raise Exception - _still_running = True - while _still_running: - sleep(1) - _still_running = False - for proc in psutil.process_iter(): - if re.search(r'^{name}'.format(name=name), proc.name(), re.IGNORECASE): - _still_running = True - sleep(1) - -def kill_process(name=None): - """Kill any running caffeine.exe processes.""" - if name is None: - raise Exception - for proc in psutil.process_iter(): - if proc.name() == name: - proc.kill() - -def umount_backup_shares(): - """Unnount the backup shares regardless of current status.""" - for server in BACKUP_SERVERS: +def show_free_space(): + """Show free space info for all fixed disks.""" + message = 'Free Space:' + for disk in psutil.disk_partitions(): try: - # Umount - run_program('net use \\\\{IP}\\{Share} /delete'.format(**server)) - print_info('Umounted {Name}'.format(**server)) - server['Mounted'] = False + if 'fixed' in disk.opts: + try_and_print(disk=disk, message=message, function=show_disk_usage, ns='Unknown', silent_function=False) + message = '' except: - print_error('Failed to umount \\\\{Name}\\{Share}.'.format(**server)) - time.sleep(1) + pass -# Init functions -def init_vars_wk(): - """Sets common variables and returns a dict.""" - print('Initializing...') - # Find base path - _wd = os.getcwd() - _base = None - while _base is None: - if os.path.exists('.bin'): - _base = os.getcwd() - break - if re.fullmatch(r'\w:\\', os.getcwd()): - break - os.chdir('..') - os.chdir(_wd) - if _base is None: - print_error('".bin" not found.') - pause('Press any key to exit...') - quit() - - # Set vars - _vars = { - 'BaseDir': _base, - 'Date': time.strftime("%Y-%m-%d"), - 'Date-Time': time.strftime("%Y-%m-%d_%H%M_%z"), - 'Env': os.environ.copy() - } - _vars['ArchivePassword'] = ARCHIVE_PASSWORD - _vars['BinDir'] = '{BaseDir}\\.bin'.format(**_vars) - _vars['CBinDir'] = '{BaseDir}\\.cbin'.format(**_vars) - _vars['ClientDir'] = '{SYSTEMDRIVE}\\WK'.format(**_vars['Env']) - _vars['LogDir'] = '{ClientDir}\\Info\\{Date}'.format(**_vars) - _vars['TmpDir'] = '{BinDir}\\tmp'.format(**_vars) - os.makedirs(_vars['TmpDir'], exist_ok=True) - - return _vars - -def init_vars_os(): - """Sets variables relating to the installed OS and returns a dict.""" - print('Checking OS...') - _vars_os = {} - _env = os.environ.copy() - - # Query registry - _reg_path = winreg.OpenKey(winreg.HKEY_LOCAL_MACHINE, 'SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion') - for key in ['CSDVersion', 'CurrentBuild', 'CurrentBuildNumber', 'CurrentVersion', 'ProductName']: - try: - _vars_os[key] = winreg.QueryValueEx(_reg_path, key)[0] - if key in ['CurrentBuild', 'CurrentBuildNumber']: - _vars_os[key] = int(_vars_os[key]) - except ValueError: - # Couldn't convert Build to int so this should return interesting results... - _vars_os[key] = 0 - except: - _vars_os[key] = 'Unknown' - - # Determine Windows version - if _vars_os['CurrentVersion'] == '6.0': - _vars_os['Version'] = 'Vista' - elif _vars_os['CurrentVersion'] == '6.1': - _vars_os['Version'] = '7' - elif _vars_os['CurrentVersion'] == '6.2': - _vars_os['Version'] = '8' - elif _vars_os['CurrentVersion'] == '6.3': - if int(_vars_os['CurrentBuildNumber']) <= 9600: - _vars_os['Version'] = '8' - elif int(_vars_os['CurrentBuildNumber']) >= 10240: - _vars_os['Version'] = '10' - - # Determine OS bit depth - _vars_os['Arch'] = 32 - if 'PROGRAMFILES(X86)' in _env: - _vars_os['Arch'] = 64 - - # Determine OS Name - _vars_os['Name'] = '{ProductName} {CSDVersion}'.format(**_vars_os) - if _vars_os['CurrentBuild'] == 9600: - _vars_os['Name'] += ' Update' - if _vars_os['CurrentBuild'] == 10240: - _vars_os['Name'] += ' Release 1507 "Threshold 1"' - if _vars_os['CurrentBuild'] == 10586: - _vars_os['Name'] += ' Release 1511 "Threshold 2"' - if _vars_os['CurrentBuild'] == 14393: - _vars_os['Name'] += ' Release 1607 "Redstone 1" / "Anniversary Update"' - _vars_os['Name'] = _vars_os['Name'].replace('Service Pack ', 'SP') - _vars_os['Name'] = _vars_os['Name'].replace('Unknown Release', 'Release') - _vars_os['Name'] = re.sub(r'\s+', ' ', _vars_os['Name']) - # == vista == - # 6.0.6000 - # 6.0.6001 - # 6.0.6002 - # ==== 7 ==== - # 6.1.7600 - # 6.1.7601 - # 6.1.7602 - # ==== 8 ==== - # 6.2.9200 - # === 8.1 === - # 6.3.9200 - # === 8.1u == - # 6.3.9600 - # === 10 v1507 "Threshold 1" == - # 6.3.10240 - # === 10 v1511 "Threshold 2" == - # 6.3.10586 - # === 10 v1607 "Anniversary Update" "Redstone 1" == - # 6.3.14393 - # === 10 v???? "Redstone 2" == - # 6.3.????? - - # Determine bootup type - _vars_os['SafeMode'] = False - if 'SAFEBOOT_OPTION' in _env: - _vars_os['SafeMode'] = True - - # Determine activation status - if _vars_os['SafeMode']: - _vars_os['Activation'] = 'Activation status unavailable in safe mode' +def show_installed_ram(): + mem = psutil.virtual_memory() + if mem.total > 8053063680: + # > 7.5 Gb so 8Gb or greater + print_standard(human_readable_size(mem.total).strip()) + elif mem.total > 3758096384: + # > 3.5 Gb so 4Gb or greater + print_warning(human_readable_size(mem.total).strip()) else: - _out = run_program('cscript /nologo {SYSTEMROOT}\\System32\\slmgr.vbs /xpr'.format(**_env)) - _out = _out.stdout.decode().splitlines() - _out = [l for l in _out if re.match(r'^\s', l)] - if len(_out) > 0: - _vars_os['Activation'] = re.sub(r'^\s+', '', _out[0]) + print_error(human_readable_size(mem.total).strip()) + +def show_os_activation(): + act_str = global_vars['OS']['Activation'] + if re.search(r'permanent', act_str, re.IGNORECASE): + print_standard(act_str, timestamp=False) + elif re.search(r'unavailable', act_str, re.IGNORECASE): + print_warning(act_str, timestamp=False) + else: + print_error(act_str, timestamp=False) + +def show_os_name(): + os_name = global_vars['OS']['DisplayName'] + if global_vars['OS']['Arch'] == 32: + # Show all 32-bit installs as an error message + print_error(os_name, timestamp=False) + else: + if re.search(r'(unrecognized|very outdated)', os_name, re.IGNORECASE): + print_error(os_name, timestamp=False) + elif re.search(r'outdated', os_name, re.IGNORECASE): + print_warning(os_name, timestamp=False) else: - _vars_os['Activation'] = 'Activation status unknown' - - return _vars_os + print_standard(os_name, timestamp=False) + +def show_temp_files_size(): + # Temp file size + size = None + with open('{LogDir}\\BleachBit.log'.format(**global_vars), 'r') as f: + for line in f.readlines(): + if re.search(r'^disk space to be recovered:', line, re.IGNORECASE): + size = re.sub(r'.*: ', '', line.strip()) + size = re.sub(r'(\w)iB$', r' \1b', size) + if size is None: + print_warning(size, timestamp=False) + else: + print_standard(size, timestamp=False) + +def show_user_data_summary(all_users=True, indent=8, width=32): + users = get_user_data_size_info(all_users) + for user in sorted(users.keys()): + print_success(' User: {user}'.format(user=user)) + print_standard(users[user].get('ProfileSize', 'Unknown')) + print_standard(' '*indent + '-'*(width+6)) + for folder in sorted(users[user]['Shell Folders']): + print_standard(users[user]['Shell Folders'][folder]) + for folder in sorted(users[user]['Extra Folders']): + print_standard(users[user]['Shell Folders'][folder]) + +def upload_info(): + path = '{ClientDir}'.format(**global_vars) + file = 'Info_{Date-Time}.7z'.format(**global_vars) + upload_data(path, file) if __name__ == '__main__': print("This file is not meant to be called directly.") diff --git a/.bin/Scripts/init_client_dir.cmd b/.bin/Scripts/init_client_dir.cmd index 61462943..c88312ae 100644 --- a/.bin/Scripts/init_client_dir.cmd +++ b/.bin/Scripts/init_client_dir.cmd @@ -14,6 +14,7 @@ for %%f in (%*) do ( if /i "%%f" == "/Backups" set _backups=True if /i "%%f" == "/Info" set _info=True if /i "%%f" == "/Office" set _office=True + if /i "%%f" == "/QuickBooks" set _quickbooks=True if /i "%%f" == "/Quarantine" set _quarantine=True if /i "%%f" == "/Transfer" set _transfer=True ) @@ -45,6 +46,7 @@ set "log_dir=%client_dir%\Info\%iso_date%" if defined _backups mkdir "%client_dir%\Backups">nul 2>&1 if defined _info mkdir "%client_dir%\Info">nul 2>&1 if defined _office mkdir "%client_dir%\Office">nul 2>&1 +if defined _quickbooks mkdir "%client_dir%\QuickBooks">nul 2>&1 if defined _quarantine mkdir "%client_dir%\Quarantine">nul 2>&1 if defined _transfer mkdir "%client_dir%\Transfer">nul 2>&1 diff --git a/.bin/Scripts/install_sw_bundle.py b/.bin/Scripts/install_sw_bundle.py index 37298af6..db97cc95 100644 --- a/.bin/Scripts/install_sw_bundle.py +++ b/.bin/Scripts/install_sw_bundle.py @@ -15,7 +15,7 @@ if __name__ == '__main__': errors = False # Adobe Reader - if vars_wk['Version'] != 'Vista': + if vars_wk['OS']['Version'] != 'Vista': print('Installing Adobe Reader DC...') _prog = '{BaseDir}/Installers/Extras/Office/Adobe Reader DC.exe'.format(**vars_wk) _args = ['/sAll', '/msi', '/norestart', '/quiet', 'ALLUSERS=1', 'EULA_ACCEPT=YES'] @@ -69,19 +69,18 @@ if __name__ == '__main__': errors = True # Main Bundle - if vars_wk['Version'] in ['Vista', '7']: + if vars_wk['OS']['Version'] in ['Vista', '7']: # Legacy selection if ask('Install MSE?'): _prog = '{BaseDir}/Installers/Extras/Security/Microsoft Security Essentials.exe'.format(**vars_wk) subprocess.Popen(_prog) _prog = '{BaseDir}/Installers/Extras/Bundles/Legacy.exe'.format(**vars_wk) subprocess.Popen(_prog) - elif vars_wk['Version'] in ['8', '10']: + elif vars_wk['OS']['Version'] in ['8', '10']: # Modern selection _prog = '{BaseDir}/Installers/Extras/Bundles/Modern.exe'.format(**vars_wk) subprocess.Popen(_prog) if errors: pause("Press Enter to exit...") - kill_process('caffeine.exe') - quit() + exit_script(vars_wk) diff --git a/.bin/Scripts/reset_browsers.py b/.bin/Scripts/reset_browsers.py deleted file mode 100644 index 34bcc05c..00000000 --- a/.bin/Scripts/reset_browsers.py +++ /dev/null @@ -1,606 +0,0 @@ -# Wizard Kit: Browser Reset Tool - -import os -import re -import shutil -import subprocess -import winreg - -# Init -os.chdir(os.path.dirname(os.path.realpath(__file__))) -os.system('title Wizard Kit: Browser Reset Tool') -from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) -vars_wk['BackupDir'] = '{ClientDir}\\Backups\\{Date}\\{USERNAME}'.format(**vars_wk, **vars_wk['Env']) -vars_wk['LogFile'] = '{LogDir}\\Reset Browsers.log'.format(**vars_wk) -vars_wk['BleachBit'] = '{BinDir}\\BleachBit\\bleachbit_console.exe'.format(**vars_wk) -vars_wk['Notepad2'] = '{BinDir}\\Notepad2\\Notepad2-Mod.exe'.format(**vars_wk) -vars_wk['SevenZip'] = '{BinDir}\\7-Zip\\7za.exe'.format(**vars_wk) -if vars_wk['Arch'] == 64: - vars_wk['Notepad2'] = vars_wk['Notepad2'].replace('.exe', '64.exe') - vars_wk['SevenZip'] = vars_wk['SevenZip'].replace('.exe', '64.exe') -os.makedirs('{BackupDir}'.format(**vars_wk), exist_ok=True) -os.makedirs('{LogDir}'.format(**vars_wk), exist_ok=True) -os.makedirs('{TmpDir}'.format(**vars_wk), exist_ok=True) - -# VARIABLES -DEFAULT_HOMEPAGE = 'https://www.google.com/' -REGEX_CHROMIUM_ITEMS = re.compile(r'^(Bookmarks|Cookies|Favicons|Google Profile|History|Login Data|Top Sites|TransportSecurity|Visited Links|Web Data).*', re.IGNORECASE) -REGEX_FIREFOX = re.compile(r'^(bookmarkbackups|(cookies|formhistory|places).sqlite|key3.db|logins.json|persdict.dat)$', re.IGNORECASE) - -def abort(): - print_warning('Aborted.', vars_wk['LogFile']) - exit_script() - -def backup_browsers(): - """Create backups of all supported browsers in the BackupDir.""" - print_info('* Backing up browser data', vars_wk['LogFile']) - # Chromium - if os.path.exists('{LOCALAPPDATA}\\Chromium\\User Data'.format(**vars_wk['Env'])): - print_standard(' Chromium', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Chromium.7z" "{LOCALAPPDATA}\\Chromium\\User Data"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - - # Google Chrome - if os.path.exists('{LOCALAPPDATA}\\Google\\Chrome\\User Data'.format(**vars_wk['Env'])): - print_standard(' Google Chrome', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Google Chrome.7z" "{LOCALAPPDATA}\\Google\\Chrome\\User Data"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - - # Google Chrome Canary - if os.path.exists('{LOCALAPPDATA}\\Google\\Chrome SxS\\User Data'.format(**vars_wk['Env'])): - print_standard(' Google Chrome Canary', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Google Chrome Canary.7z" "{LOCALAPPDATA}\\Google\\Chrome SxS\\User Data"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - - # Internet Explorer - if os.path.exists('{USERPROFILE}\\Favorites'.format(**vars_wk['Env'])): - print_standard(' Internet Explorer', vars_wk['LogFile']) - _cmd = [ - vars_wk['SevenZip'], - 'a', - '-aoa', - '-bso0', - '-bse0', - '-mx=1', - '{BackupDir}\\Internet Explorer.7z'.format(**vars_wk), - '{USERPROFILE}\\Favorites'.format(**vars_wk['Env'])] - run_program(_cmd, check=False, pipe=False) - run_program('reg export "hkcu\\Software\\Microsoft\\Internet Explorer" "{TmpDir}\\Internet Explorer (HKCU).reg" /y'.format(**vars_wk), check=False, shell=True) - run_program('reg export "hklm\\Software\\Microsoft\\Internet Explorer" "{TmpDir}\\Internet Explorer (HKLM).reg" /y'.format(**vars_wk), check=False, shell=True) - _cmd = [ - vars_wk['SevenZip'], - 'a', - '-aoa', - '-bso0', - '-bse0', - '-mx=1', - '{BackupDir}\\Internet Explorer.7z'.format(**vars_wk), - '{TmpDir}\\Internet*.reg'.format(**vars_wk)] - run_program(_cmd, check=False, pipe=False) - - # Mozilla Firefox - if os.path.exists('{APPDATA}\\Mozilla\\Firefox'.format(**vars_wk['Env'])): - print_standard(' Mozilla Firefox', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Mozilla Firefox.7z" "{APPDATA}\\Mozilla\\Firefox\\Profile*"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - - # Opera - if os.path.exists('{APPDATA}\\Opera Software\\Opera Stable'.format(**vars_wk['Env'])): - print_standard(' Opera', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Opera.7z" "{APPDATA}\\Opera Software\\Opera Stable"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - - # Opera Beta - if os.path.exists('{APPDATA}\\Opera Software\\Opera Next'.format(**vars_wk['Env'])): - print_standard(' Opera Beta', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Opera Beta.7z" "{APPDATA}\\Opera Software\\Opera Next"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - - # Opera Dev - if os.path.exists('{APPDATA}\\Opera Software\\Opera Developer'.format(**vars_wk['Env'])): - print_standard(' Opera Dev', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Opera Dev.7z" "{APPDATA}\\Opera Software\\Opera Developer"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - -def clean_chromium_profile(profile): - """Renames profile folder as backup and then recreates the folder with only the essential files.""" - print_info(' Resetting profile: {name}'.format(name=profile.name), vars_wk['LogFile']) - backup_path = rename_as_backup(profile.path) - os.makedirs(profile.path, exist_ok=True) - - # Restore essential files from backup_path - for entry in os.scandir(backup_path): - if REGEX_CHROMIUM_ITEMS.search(entry.name): - shutil.copy(entry.path, '{path}\\{name}'.format(path=profile.path, name=entry.name)) - -def clean_firefox_profile(profile): - """Renames profile folder as backup and then recreates the folder with only the essential files.""" - print_info(' Resetting profile: {name}'.format(name=profile.name), vars_wk['LogFile']) - backup_path = rename_as_backup(profile.path) - homepages = [] - os.makedirs(profile.path, exist_ok=True) - - # Restore essential files from backup_path - for entry in os.scandir(backup_path): - if REGEX_FIREFOX.search(entry.name): - if entry.is_dir(): - shutil.copytree(entry.path, '{path}\\{name}'.format(path=profile.path, name=entry.name)) - else: - shutil.copy(entry.path, '{path}\\{name}'.format(path=profile.path, name=entry.name)) - - # Check current Homepage - try: - with open('{path}\\prefs.js'.format(path=backup_path), 'r') as f: - _search = re.search(r'browser\.startup\.homepage", "([^"]*)"', f.read(), re.IGNORECASE) - if _search: - homepages = _search.group(1).split('|') - except FileNotFoundError: - pass - - # Set profile defaults - with open('{path}\\prefs.js'.format(path=profile.path), 'a', encoding='ascii') as f: - f.write('user_pref("browser.search.geoSpecificDefaults", false);\n') - - # Set search to Google - f.write('user_pref("browser.search.defaultenginename", "Google");\n') - f.write('user_pref("browser.search.defaultenginename.US", "Google");\n') - - # Set homepage - if len(homepages) == 0: - homepages = [DEFAULT_HOMEPAGE] - elif len(homepages) > 1 or DEFAULT_HOMEPAGE not in homepages: - # Not set to [DEFAULT_HOMEPAGE], ask if switching - print_warning(' Current homepage: {url}'.format(url=homepages[0]), vars_wk['LogFile']) - for url in homepages[1:]: - print_warning(' : {url}'.format(url=url), vars_wk['LogFile']) - if ask(' Replace with {url}?'.format(url=DEFAULT_HOMEPAGE), vars_wk['LogFile']): - homepages = [DEFAULT_HOMEPAGE] - f.write('user_pref("browser.startup.homepage", "{urls}");\n'.format(urls='|'.join(homepages))) - -def clean_internet_explorer(): - """Uses the built-in function to reset IE and sets the homepage.""" - print_info(' Closing any open windows', vars_wk['LogFile']) - kill_process('iexplore.exe') - print_info(' Resetting internet options', vars_wk['LogFile']) - run_program('rundll32.exe', ['inetcpl.cpl,ResetIEtoDefaults'], check=False) - - # Set homepage - key = r'Software\Microsoft\Internet Explorer\Main' - with winreg.OpenKey(winreg.HKEY_CURRENT_USER, key) as _key: - homepage = winreg.QueryValueEx(_key, 'Start Page')[0] - try: - secondary_homepages = winreg.QueryValueEx(_key, 'Secondary Start Pages')[0] - except FileNotFoundError: - secondary_homepages = [] - print_standard(' Current homepage: ' + homepage, vars_wk['LogFile']) - for page in secondary_homepages: - print_standard(' : ' + page, vars_wk['LogFile']) - if homepage != DEFAULT_HOMEPAGE or len(secondary_homepages) > 0: - if ask(' Replace current homepage with google.com?', vars_wk['LogFile']): - with winreg.OpenKey(winreg.HKEY_CURRENT_USER, key, access=winreg.KEY_WRITE) as _key: - winreg.SetValueEx(_key, 'Start Page', 0, winreg.REG_SZ, DEFAULT_HOMEPAGE) - try: - winreg.DeleteValue(_key, 'Secondary Start Pages') - except FileNotFoundError: - pass - -def exit_script(): - pause("Press Enter to exit...") - quit() - -def get_chrome_exe(): - """Check for conflicting Chrome installations and return chrome.exe path as str.""" - install_multi = '{PROGRAMFILES}\\Google\\Chrome\\Application\\chrome.exe'.format(**vars_wk['Env']) - if 'PROGRAMFILES(X86)' in vars_wk['Env']: - install_multi = '{PROGRAMFILES(X86)}\\Google\\Chrome\\Application\\chrome.exe'.format(**vars_wk['Env']) - install_single = '{LOCALAPPDATA}\\Google\\Chrome\\Application\\chrome.exe'.format(**vars_wk['Env']) - if os.path.exists(install_multi): - if os.path.exists(install_single): - print_warning(' WARNING: Single-user and multi-user installations present.', vars_wk['LogFile']) - print_warning(' It is recommended to move to only having the multi-user installation.', vars_wk['LogFile']) - return install_multi - elif os.path.exists(install_single): - return install_single - else: - print_error(' ERROR: chrome.exe not found. Please verify installation.', vars_wk['LogFile']) - return None - -def get_chrome_profiles(): - """Find any existing Chrome profiles and return as a list of os.DirEntry objects.""" - profiles = [] - try: - for entry in os.scandir('{LOCALAPPDATA}\\Google\\Chrome\\User Data'.format(**vars_wk['Env'])): - if entry.is_dir() and re.search(r'^(Default|Profile)', entry.name, re.IGNORECASE): - profiles.append(entry) - profiles = [p for p in profiles if not re.search(r'\.(wk|)bak.*', p.name, re.IGNORECASE)] - except: - pass - - return profiles - -def get_chrome_canary_exe(): - """Check for Google Chrome Canary installation and return chrome.exe path as str.""" - prog_exe = '{LOCALAPPDATA}\\Google\\Chrome SxS\\Application\\chrome.exe'.format(**vars_wk['Env']) - if os.path.exists(prog_exe): - return prog_exe - else: - return None - -def get_chrome_canary_profiles(): - """Find any existing Chrome profiles and return as a list of os.DirEntry objects.""" - profiles = [] - try: - for entry in os.scandir('{LOCALAPPDATA}\\Google\\Chrome SxS\\User Data'.format(**vars_wk['Env'])): - if entry.is_dir() and re.search(r'^(Default|Profile)', entry.name, re.IGNORECASE): - profiles.append(entry) - profiles = [p for p in profiles if not re.search(r'\.(wk|)bak.*', p.name, re.IGNORECASE)] - except: - pass - - return profiles - -def get_iexplorer_exe(): - """Find and return iexplorer.exe path as str.""" - ie_exe = '{PROGRAMFILES}\\Internet Explorer\\iexplore.exe'.format(**vars_wk['Env']) - if 'PROGRAMFILES(X86)' in vars_wk['Env']: - ie_exe = '{PROGRAMFILES(X86)}\\Internet Explorer\\iexplore.exe'.format(**vars_wk['Env']) - return ie_exe - -def get_firefox_exe(): - """Check for Mozilla Firefox installation and return firefox.exe path as str.""" - prog_exe = '{PROGRAMFILES}\\Mozilla Firefox\\firefox.exe'.format(**vars_wk['Env']) - if 'PROGRAMFILES(X86)' in vars_wk['Env']: - prog_exe = '{PROGRAMFILES(X86)}\\Mozilla Firefox\\firefox.exe'.format(**vars_wk['Env']) - if os.path.exists(prog_exe): - return prog_exe - else: - return None - -def get_firefox_dev_exe(): - """Check for Mozilla Firefox Developer Edition installation and return firefox.exe path as str.""" - prog_exe = '{PROGRAMFILES}\\Firefox Developer Edition\\firefox.exe'.format(**vars_wk['Env']) - if 'PROGRAMFILES(X86)' in vars_wk['Env']: - prog_exe = '{PROGRAMFILES(X86)}\\Firefox Developer Edition\\firefox.exe'.format(**vars_wk['Env']) - if os.path.exists(prog_exe): - return prog_exe - else: - return None - -def get_opera_exe(): - """Check for Opera installation and return launcher.exe path as str.""" - prog_exe = '{PROGRAMFILES}\\Opera\\launcher.exe'.format(**vars_wk['Env']) - if 'PROGRAMFILES(X86)' in vars_wk['Env']: - prog_exe = '{PROGRAMFILES(X86)}\\Opera\\launcher.exe'.format(**vars_wk['Env']) - if os.path.exists(prog_exe): - return prog_exe - else: - return None - -def get_firefox_profiles(): - """Find any existing Chrome profiles and return as a list of os.DirEntry objects.""" - profiles = [] - try: - for entry in os.scandir('{APPDATA}\\Mozilla\\Firefox\\Profiles'.format(**vars_wk['Env'])): - if entry.is_dir(): - profiles.append(entry) - profiles = [p for p in profiles if not re.search(r'\.(wk|)bak.*', p.name, re.IGNORECASE)] - except: - pass - - return profiles - -def create_firefox_default_profiles(): - """Create new default profile for Mozilla Firefox for both stable and dev releases.""" - print_warning(' WARNING: Creating new default profile.', vars_wk['LogFile']) - firefox_exe = get_firefox_exe() - firefox_dev_exe = get_firefox_dev_exe() - profiles_ini_path = '{APPDATA}\\Mozilla\\Firefox\\profiles.ini'.format(**vars_wk['Env']) - - # Rename profiles.ini - if os.path.exists(profiles_ini_path): - rename_as_backup(profiles_ini_path) - - # Create profile(s) - if firefox_exe is not None: - run_program(firefox_exe, ['-createprofile', 'default'], check=False) - if firefox_dev_exe is not None: - run_program(firefox_dev_exe, ['-createprofile'], check=False) - -def get_opera_beta_exe(): - """Check for Opera Beta installation and return launcher.exe path as str.""" - prog_exe = '{PROGRAMFILES}\\Opera beta\\launcher.exe'.format(**vars_wk['Env']) - # Installs as 64-bit on a 64-bit OS so PROGRAMFILES should always be correct - - if os.path.exists(prog_exe): - return prog_exe - else: - return None - -def get_opera_dev_exe(): - """Check for Opera Beta installation and return launcher.exe path as str.""" - prog_exe = '{PROGRAMFILES}\\Opera developer\\launcher.exe'.format(**vars_wk['Env']) - # Installs as 64-bit on a 64-bit OS so PROGRAMFILES should always be correct - - if os.path.exists(prog_exe): - return prog_exe - else: - return None - -def get_opera_profile(): - """Find an existing Opera profile and return as a length-1 list of os.DirEntry objects.""" - profiles = [] - try: - for entry in os.scandir('{APPDATA}\\Opera Software'.format(**vars_wk['Env'])): - if entry.is_dir() and entry.name == 'Opera Stable': - return [entry] - except: - pass - - return profiles - -def get_opera_beta_profile(): - """Find an existing Opera Beta profile and return as a length-1 list of os.DirEntry objects.""" - profiles = [] - try: - for entry in os.scandir('{APPDATA}\\Opera Software'.format(**vars_wk['Env'])): - if entry.is_dir() and entry.name == 'Opera Next': - return [entry] - except: - pass - - return profiles - -def get_opera_dev_profile(): - """Find an existing Opera Dev profile and return as a length-1 list of os.DirEntry objects.""" - profiles = [] - try: - for entry in os.scandir('{APPDATA}\\Opera Software'.format(**vars_wk['Env'])): - if entry.is_dir() and entry.name == 'Opera Developer': - return [entry] - except: - pass - - return profiles - -def remove_temp_files(): - """Run BleachBit to delete cache, temp, and corrupt data from browsers.""" - print_info('* Deleting browser temp data', vars_wk['LogFile']) - if not ask(' Proceed?', vars_wk['LogFile']): - # Bail early - return - # Extract and delete - extract_item('BleachBit', vars_wk, silent=True) - _args = [ - '-c', - # Chromium - 'chromium.cache', - 'chromium.search_engines', - 'chromium.current_session', - 'chromium.vacuum', - # Google Chrome - 'google_chrome.cache', - 'google_chrome.search_engines', - 'google_chrome.session', - 'google_chrome.vacuum', - # Internet Explorer - 'internet_explorer.temporary_files', - # Mozilla Firefox - 'firefox.cache', - 'firefox.session_restore', - 'firefox.vacuum', - 'winapp2_mozilla.corrupt_sqlites', - # Opera - 'opera.cache', - 'opera.current_session'] - try: - _out = run_program(vars_wk['BleachBit'], _args, check=False) - except subprocess.CalledProcessError: - print_error(' ERROR: Failed to run BleachBit.', vars_wk['LogFile']) - if not ask(' Continue script?', vars_wk['LogFile']): - abort() - else: - # Save BleachBit log - with open('{LogDir}\\BleachBit.log'.format(**vars_wk), 'a') as f: - f.write(_out.stdout.decode()) - # Save BleachBit (error) log - with open('{LogDir}\\BleachBit.err.log'.format(**vars_wk), 'a') as f: - f.write(_out.stderr.decode()) - -def rename_as_backup(profile_path): - backup_path = '{path}.bak'.format(path=profile_path) - _i = 1; - while os.path.exists(backup_path): - backup_path = '{path}.bak{i}'.format(i=_i, path=profile_path) - _i += 1 - - # print_info(' Renaming "{path}" to "{backup}"'.format(path=profile_path, backup=backup_path), vars_wk['LogFile']) - shutil.move(profile_path, backup_path) - - return backup_path - -def reset_internet_explorer(): - print_standard(' Internet Explorer', vars_wk['LogFile']) - ie_exe = get_iexplorer_exe() - - if ask(' Reset to safe settings?', vars_wk['LogFile']): - clean_internet_explorer() - - if os.path.exists(ie_exe): - if ask(' Install Google Search and EasyLists?', vars_wk['LogFile']): - run_program(ie_exe, ['http://www.iegallery.com/en-us/Addons/Details/813'], check=False) - else: - print_error(' ERROR: iexplore.exe not found. Please verify OS health.', vars_wk['LogFile']) - -def reset_google_chrome(): - print_standard(' Google Chrome', vars_wk['LogFile']) - chrome_exe = get_chrome_exe() - profiles = get_chrome_profiles() - - if len(profiles) == 0: - print_warning(' WARNING: No profiles found.', vars_wk['LogFile']) - elif ask(' Reset profile(s) to safe settings?', vars_wk['LogFile']): - print_info(' Closing any open windows', vars_wk['LogFile']) - kill_process('chrome.exe') - for profile in profiles: - clean_chromium_profile(profile) - - if chrome_exe is not None: - # Set Chrome as default browser - run_program(chrome_exe, ['--make-default-browser'], check=False) - - # Install uBlock Origin? - if ask(' Install uBlock Origin?', vars_wk['LogFile']): - run_program(chrome_exe, ['https://chrome.google.com/webstore/detail/ublock-origin/cjpalhdlnbpafiamejdnhcphjbkeiagm?hl=en'], check=False) - - # Google Chrome Canary - chrome_canary_exe = get_chrome_canary_exe() - profiles = get_chrome_canary_profiles() - - if len(profiles) > 0: - print_standard(' Google Chrome Canary', vars_wk['LogFile']) - if ask(' Reset profile(s) to safe settings?', vars_wk['LogFile']): - print_info(' Closing any open windows', vars_wk['LogFile']) - kill_process('chrome.exe') - for profile in profiles: - clean_chromium_profile(profile) - - if chrome_canary_exe is not None: - # Install uBlock Origin? - if ask(' Install uBlock Origin?', vars_wk['LogFile']): - run_program(chrome_canary_exe, ['https://chrome.google.com/webstore/detail/ublock-origin/cjpalhdlnbpafiamejdnhcphjbkeiagm?hl=en'], check=False) - -def reset_mozilla_firefox(): - print_standard(' Mozilla Firefox', vars_wk['LogFile']) - firefox_exe = get_firefox_exe() - firefox_dev_exe = get_firefox_dev_exe() - profiles = get_firefox_profiles() - - if firefox_exe is None and firefox_dev_exe is None: - print_error(' ERROR: firefox.exe not found. Please verify installation.', vars_wk['LogFile']) - - if len(profiles) == 0: - print_warning(' WARNING: No profiles found.', vars_wk['LogFile']) - create_firefox_default_profiles() - elif ask(' Reset profile(s) to safe settings?', vars_wk['LogFile']): - print_info(' Closing any open windows', vars_wk['LogFile']) - kill_process('firefox.exe') - for profile in profiles: - clean_firefox_profile(profile) - - if ask(' Install uBlock Origin?', vars_wk['LogFile']): - # Install uBlock Origin - if firefox_exe is not None: - run_program(firefox_exe, ['https://addons.mozilla.org/en-us/firefox/addon/ublock-origin/'], check=False) - if firefox_dev_exe is not None: - run_program(firefox_dev_exe, ['https://addons.mozilla.org/en-us/firefox/addon/ublock-origin/'], check=False) - -def reset_opera(): - opera_exe = get_opera_exe() - profiles = get_opera_profile() - - # Bail early - if opera_exe is None and len(profiles) == 0: - # print_warning(' Opera not installed and no profiles found.') - return - else: - print_standard(' Opera', vars_wk['LogFile']) - - if opera_exe is None: - print_error(' ERROR: Opera not installed.', vars_wk['LogFile']) - - if len(profiles) == 0: - print_warning(' WARNING: No profiles found.', vars_wk['LogFile']) - else: - # Reset browser - if ask(' Reset profile to safe settings?', vars_wk['LogFile']): - print_info(' Closing any open windows', vars_wk['LogFile']) - kill_process('opera.exe') - clean_chromium_profile(profiles[0]) - - if opera_exe is not None: - # Install uBlock Origin? - if ask(' Install uBlock Origin?', vars_wk['LogFile']): - run_program(opera_exe, ['https://addons.opera.com/en/extensions/details/ublock/?display=en'], check=False) - -def reset_opera_beta(): - opera_beta_exe = get_opera_beta_exe() - profiles = get_opera_beta_profile() - - # Bail early - if opera_beta_exe is None and len(profiles) == 0: - # print_error(' Opera Beta not installed and no profiles found.') - return - else: - print_standard(' Opera Beta', vars_wk['LogFile']) - - if opera_beta_exe is None: - print_error(' ERROR: Opera Beta not installed.', vars_wk['LogFile']) - - if len(profiles) == 0: - print_warning(' WARNING: No profiles found.', vars_wk['LogFile']) - else: - # Reset browser - if ask(' Reset profile to safe settings?', vars_wk['LogFile']): - print_info(' Closing any open windows', vars_wk['LogFile']) - kill_process('opera.exe') - clean_chromium_profile(profiles[0]) - - if opera_beta_exe is not None: - # Install uBlock Origin? - if ask(' Install uBlock Origin?', vars_wk['LogFile']): - run_program(opera_beta_exe, ['https://addons.opera.com/en/extensions/details/ublock/?display=en'], check=False) - -def reset_opera_dev(): - opera_dev_exe = get_opera_dev_exe() - profiles = get_opera_dev_profile() - - # Bail early - if opera_dev_exe is None and len(profiles) == 0: - # print_error(' Opera Dev not installed and no profiles found.') - return - else: - print_standard(' Opera Dev', vars_wk['LogFile']) - - if opera_dev_exe is None: - print_error(' ERROR: Opera Dev not installed.', vars_wk['LogFile']) - - if len(profiles) == 0: - print_warning(' WARNING: No profiles found.', vars_wk['LogFile']) - else: - # Reset browser - if ask(' Reset profile to safe settings?', vars_wk['LogFile']): - print_info(' Closing any open windows', vars_wk['LogFile']) - kill_process('opera.exe') - clean_chromium_profile(profiles[0]) - - if opera_dev_exe is not None: - # Install uBlock Origin? - if ask(' Install uBlock Origin?', vars_wk['LogFile']): - run_program(opera_dev_exe, ['https://addons.opera.com/en/extensions/details/ublock/?display=en'], check=False) - -if __name__ == '__main__': - stay_awake(vars_wk) - - # Reset prep - backup_browsers() - remove_temp_files() - - # Reset Browsers - print_info('* Resetting browsers', vars_wk['LogFile']) - reset_internet_explorer() - reset_google_chrome() - reset_mozilla_firefox() - reset_opera() - reset_opera_beta() - reset_opera_dev() - - # Done - print_standard('Done.', vars_wk['LogFile']) - extract_item('Notepad2', vars_wk, silent=True) - subprocess.Popen([vars_wk['Notepad2'], vars_wk['LogFile']]) - - # Quit - kill_process('caffeine.exe') - exit_script() \ No newline at end of file diff --git a/.bin/Scripts/safemode_enter.py b/.bin/Scripts/safemode_enter.py index f47be6a4..5247c03c 100644 --- a/.bin/Scripts/safemode_enter.py +++ b/.bin/Scripts/safemode_enter.py @@ -21,4 +21,4 @@ if __name__ == '__main__': run_program('shutdown -r -t 3', check=False) # Quit - quit() \ No newline at end of file + quit() diff --git a/.bin/Scripts/safemode_exit.py b/.bin/Scripts/safemode_exit.py index 9a6713f9..aad99677 100644 --- a/.bin/Scripts/safemode_exit.py +++ b/.bin/Scripts/safemode_exit.py @@ -21,4 +21,4 @@ if __name__ == '__main__': run_program('shutdown -r -t 3', check=False) # Quit - quit() \ No newline at end of file + quit() diff --git a/.bin/Scripts/sfc_scan.py b/.bin/Scripts/sfc_scan.py index 0028fd98..52c48b45 100644 --- a/.bin/Scripts/sfc_scan.py +++ b/.bin/Scripts/sfc_scan.py @@ -7,48 +7,18 @@ import re os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: SFC Tool') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) -vars_wk['LogFile'] = '{LogDir}\\SFC.log'.format(**vars_wk) -vars_wk['Notepad2'] = '{BinDir}\\Notepad2\\Notepad2-Mod.exe'.format(**vars_wk) -if vars_wk['Arch'] == 64: - vars_wk['Notepad2'] = vars_wk['Notepad2'].replace('.exe', '64.exe') -os.makedirs(vars_wk['LogDir'], exist_ok=True) +init_global_vars() def abort(): - print_warning('Aborted.', vars_wk['LogFile']) + print_warning('Aborted.') pause("Press Enter to exit...") exit_script() -def exit_script(): - quit() - -def run_sfc_scan(): - """Run SFC in a "split window" and report errors.""" - print_info('* Checking system file health', vars_wk['LogFile']) - _cmd = [ - '{SYSTEMROOT}\\System32\\sfc.exe'.format(**vars_wk['Env']), - '/scannow'] - _out = run_program(_cmd, check=False, pipe=False) - # Save stderr - # with open('{LogDir}\\SFC.err'.format(**vars_wk), 'a') as f: - # f.write(out.stdout) - # Save stdout - # with open('{LogDir}\\SFC.log'.format(**vars_wk), 'a') as f: - # f.write(out.stdout) - if __name__ == '__main__': - stay_awake(vars_wk) - run_sfc_scan() + stay_awake() + try_and_print(message='SFC scan...', function=run_sfc_scan, cs='CS', ns='NS', other_results=other_results) # Done - print_standard('\nDone.', vars_wk['LogFile']) + print_standard('\nDone.') pause('Press Enter to exit...') - - # Open log - extract_item('Notepad2', vars_wk, silent=True) - subprocess.Popen([vars_wk['Notepad2'], vars_wk['LogFile']]) - - # Quit - kill_process('caffeine.exe') - exit_script() \ No newline at end of file + exit_script() diff --git a/.bin/Scripts/sw_checklist.py b/.bin/Scripts/sw_checklist.py index 8c03ac7c..0bc28464 100644 --- a/.bin/Scripts/sw_checklist.py +++ b/.bin/Scripts/sw_checklist.py @@ -1,415 +1,78 @@ -# Wizard Kit: Software Diagnostics +# Wizard Kit: Software Checklist import os -import re -import shutil -import subprocess -import winreg # Init os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: Software Checklist Tool') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) -vars_wk['BackupDir'] = '{ClientDir}\\Backups\\{Date}'.format(**vars_wk) -vars_wk['LogFile'] = '{LogDir}\\Software Checklist.log'.format(**vars_wk) -vars_wk['AIDA64'] = '{BinDir}\\AIDA64\\aida64.exe'.format(**vars_wk) -vars_wk['AutoRuns'] = '{BinDir}\\SysinternalsSuite\\autoruns.exe'.format(**vars_wk) -vars_wk['ERUNT'] = '{BinDir}\\erunt\\ERUNT.EXE'.format(**vars_wk) -vars_wk['Everything'] = '{BinDir}\\Everything\\Everything.exe'.format(**vars_wk) -vars_wk['HWiNFO'] = '{BinDir}\\HWiNFO\\HWiNFO.exe'.format(**vars_wk) -vars_wk['Notepad2'] = '{BinDir}\\Notepad2\\Notepad2-Mod.exe'.format(**vars_wk) -vars_wk['ProduKey'] = '{BinDir}\\ProduKey\\ProduKey.exe'.format(**vars_wk) -vars_wk['SevenZip'] = '{BinDir}\\7-Zip\\7za.exe'.format(**vars_wk) -vars_wk['XMPlay'] = '{BinDir}\\XMPlay\\xmplay.exe'.format(**vars_wk) -if vars_wk['Arch'] == 64: - vars_wk['AutoRuns'] = vars_wk['AutoRuns'].replace('.exe', '64.exe') - vars_wk['Everything'] = vars_wk['Everything'].replace('.exe', '64.exe') - vars_wk['HWiNFO'] = vars_wk['HWiNFO'].replace('.exe', '64.exe') - vars_wk['Notepad2'] = vars_wk['Notepad2'].replace('.exe', '64.exe') - vars_wk['ProduKey'] = vars_wk['ProduKey'].replace('.exe', '64.exe') - vars_wk['SevenZip'] = vars_wk['SevenZip'].replace('.exe', '64.exe') -os.makedirs(vars_wk['LogDir'], exist_ok=True) +init_global_vars() +set_global_vars(LogFile='{LogDir}\\Software Checklist.log'.format(**global_vars)) def abort(): - print_warning('Aborted.', vars_wk['LogFile']) + print_warning('Aborted.') exit_script() -def backup_power_plans(): - """Export current power plans.""" - print_info('* Backing up power plans', vars_wk['LogFile']) - os.makedirs('{BackupDir}\\Power Plans'.format(**vars_wk), exist_ok=True) - try: - _plans = run_program('powercfg /L') - _plans = _plans.stdout.decode().splitlines() - _plans = [p for p in _plans if re.search(r'^Power Scheme', p)] - for p in _plans: - _guid = re.sub(r'Power Scheme GUID:\s+([0-9a-f\-]+).*', r'\1', p) - _name = re.sub(r'Power Scheme GUID:\s+[0-9a-f\-]+\s+\(([^\)]+)\).*', r'\1', p) - print(' {name} ({guid})'.format(guid=_guid, name=_name)) - _out = '{BackupDir}\\Power Plans\\{name}.pow'.format(name=_name, **vars_wk) - if not os.path.exists(_out): - run_program('powercfg /export "{out}" {guid}'.format(out=_out, guid=_guid), check=False) - except subprocess.CalledProcessError: - print_error('ERROR: Failed to export power plans.') - -def backup_registry(): - print_info('* Backing up registry', vars_wk['LogFile']) - extract_item('erunt', vars_wk, silent=True) - _args = [ - '{LogDir}\\Registry'.format(**vars_wk), - 'sysreg', - 'curuser', - 'otherusers', - '/noprogresswindow'] - try: - run_program(vars_wk['ERUNT'], _args) - except subprocess.CalledProcessError: - print_error('ERROR: Failed to backup registry', vars_wk['LogFile']) - -def cleanup_adwcleaner(): - _path = '{SYSTEMDRIVE}\\AdwCleaner'.format(**vars_wk['Env']) - if os.path.exists(_path): - try: - print_info('* Uninstalling AdwCleaner', vars_wk['LogFile']) - os.makedirs('{ClientDir}\\Info'.format(**vars_wk), exist_ok=True) - for entry in os.scandir(_path): - if entry.is_file() and re.search(r'*.(log|txt)', entry.name): - shutil.move(entry.path, '{ClientDir}\\Info\\{name}'.format(name=entry.name, **vars_wk)) - elif entry.name == 'Quarantine': - os.makedirs('{ClientDir}\\Quarantine'.format(**vars_wk), exist_ok=True) - shutil.move(entry.path, '{ClientDir}\\Quarantine\\AdwCleaner'.format(**vars_wk)) - shutil.rmtree(_path) - except: - print_error('ERROR: Failed to uninstall AdwCleaner.', vars_wk['LogFile']) - -def cleanup_desktop(): - #~#TODO (Pseudo-code) - #~#for d in drives: - #~# for user in os.scandir('{drive}\\Users'.format(drive=d)): - #~# if os.path.exists('{drive}\\Users\\{user}\\Desktop'.format(drive=d, user=user)): - #~# for entry in os.scandir('{drive}\\Users\\{user}\\Desktop'.format(drive=d, user=user)): - #~# # JRT, RKill, Shortcut cleaner - #~# if re.search(r'^((JRT|RKill).*|sc-cleaner)', entry.name, re.IGNORECASE): - #~# shutil.move(entry.path, '{ClientDir}\\Info\\{name}'.format(name=entry.name, **vars_wk)) - print_info('* Checking Desktop for leftover files', vars_wk['LogFile']) - os.makedirs('{ClientDir}\\Info'.format(**vars_wk), exist_ok=True) - if os.path.exists('{USERPROFILE}\\Desktop'.format(**vars_wk['Env'])): - for entry in os.scandir('{USERPROFILE}\\Desktop'.format(**vars_wk['Env'])): - # JRT, RKill, Shortcut cleaner - if re.search(r'^((JRT|RKill).*|sc-cleaner)', entry.name, re.IGNORECASE): - shutil.move(entry.path, '{ClientDir}\\Info\\{name}'.format(name=entry.name, **vars_wk)) - run_program('rmdir "{path}"'.format(path='{ClientDir}\\Info'.format(**vars_wk)), check=False, shell=True) - -def exit_script(): - # pause("Press Enter to exit...") - quit() - -def get_battery_info(): - #~#print_info('* Battery', vars_wk['LogFile']) - #~#WK-write "==== Battery Check ====" "$log" - #~#& "$wd\check_battery.ps1" "$log" - #~#WK-write "" "$log" - pass - -def get_free_space(): - print_info('* Free space', vars_wk['LogFile']) - for drive in get_free_space_info(): - print_standard(' {} {}'.format(*drive), vars_wk['LogFile']) - -def get_installed_ram(): - print_info('* Installed RAM', vars_wk['LogFile']) - with open ('{LogDir}\\RAM Information (AIDA64).txt'.format(**vars_wk), 'r') as f: - _module = '' - for line in f.readlines(): - if re.search(r'Module Size', line, re.IGNORECASE): - _module = re.sub(r'\s*Module Size\s+(.*)\s+\(.*$', r' Module: \1', line.strip()) - if re.search(r'Memory Speed', line, re.IGNORECASE): - _module += re.sub(r'\s*Memory Speed\s+(.*)$', r' \1', line.strip()) - print_standard(_module, vars_wk['LogFile']) - -def get_os_info(): - print_info('* Operating System', vars_wk['LogFile']) - if vars_wk['Arch'] == 32: - # Show all 32-bit installs as an error message - print_error(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - else: - if vars_wk['CurrentVersion'] == '6.0': - # Vista - if vars_wk['CurrentBuildNumber'] < 6002: - print_error(' {Name} x{Arch} (very outdated)'.format(**vars_wk), vars_wk['LogFile']) - else: - print_warning(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentVersion'] == '6.1': - # Windows 7 - if vars_wk['CSDVersion'] == 'Service Pack 1': - print_standard(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - else: - print_error(' {Name} x{Arch} (very outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentVersion'] == '6.2': - # Windows 8 - print_error(' {Name} x{Arch} (very outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentVersion'] == '6.3': - if vars_wk['CurrentBuild'] == 9200: - # Windows 8.1 - print_error(' {Name} x{Arch} (very outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentBuild'] == 9600: - # Windows 8.1 Update - print_info(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentBuild'] == 10240: - # Windows 10 Threshold 1 - print_error(' {Name} x{Arch} (outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentBuild'] == 10586: - # Windows 10 Threshold 2 - print_warning(' {Name} x{Arch} (outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentBuild'] == 14393: - # Windows 10 Redstone 1 - print_standard(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - else: - print_warning(' {Name} x{Arch} (unrecognized)'.format(**vars_wk), vars_wk['LogFile']) - # OS Activation - if re.search(r'permanent', vars_wk['Activation'], re.IGNORECASE): - print_standard(' {Activation}'.format(**vars_wk), vars_wk['LogFile']) - elif re.search(r'unavailable', vars_wk['Activation'], re.IGNORECASE): - print_warning(' {Activation}'.format(**vars_wk), vars_wk['LogFile']) - else: - print_error(' {Activation}'.format(**vars_wk), vars_wk['LogFile']) - -def get_ticket_number(): - """Get TicketNumber from user and save it in the info folder.""" - vars_wk['TicketNumber'] = None - while vars_wk['TicketNumber'] is None: - _ticket = input('Enter ticket number: ') - if re.match(r'^([0-9]+([-_]?\w+|))$', _ticket): - vars_wk['TicketNumber'] = _ticket - with open('{LogDir}\\TicketNumber'.format(**vars_wk), 'w') as f: - f.write(_ticket) - else: - print_error('ERROR: Invalid ticket number', vars_wk['LogFile']) - -def get_user_data_summary(): - print_info('* User Data', vars_wk['LogFile']) - users = get_user_data_size_info(vars_wk) - for user in sorted(users): - print_standard(' User: {user}'.format(user=user), vars_wk['LogFile']) - print_standard(' ' + users[user].get('ProfileSize', 'Unknown'), vars_wk['LogFile']) - print_standard(' -------------------------------', vars_wk['LogFile']) - for folder in sorted(users[user]['Shell Folders']): - print_standard(' ' + users[user]['Shell Folders'][folder], vars_wk['LogFile']) - for folder in sorted(users[user]['Extra Folders']): - print_standard(' ' + users[user]['Shell Folders'][folder], vars_wk['LogFile']) - -def run_hwinfo_sensors(): - _path = '{BinDir}\\HWiNFO'.format(**vars_wk) - for bit in [32, 64]: - # Configure - _source = '{path}\\general.ini'.format(path=_path) - _dest = '{path}\\HWiNFO{bit}.ini'.format(bit=bit, path=_path) - shutil.copy(_source, _dest) - with open(_dest, 'a') as f: - f.write('SensorsOnly=1\n') - f.write('SummaryOnly=0\n') - subprocess.Popen(vars_wk['HWiNFO']) - -def run_produkey(): - extract_item('ProduKey', vars_wk, silent=True) - if not os.path.exists('{LogDir}\\Product Keys (ProduKey).txt'.format(**vars_wk)): - print_info('* Saving product keys (secondary method)', vars_wk['LogFile']) - # Clear current configuration - for config in ['ProduKey.cfg', 'ProduKey64.cfg']: - try: - if os.path.exists('{BinDir}\\ProduKey\\{config}'.format(config=config, **vars_wk)): - os.remove('{BinDir}\\ProduKey\\{config}'.format(config=config, **vars_wk)) - except: - pass - _args = ['/nosavereg', '/stext', '{LogDir}\\Product Keys (ProduKey).txt'.format(**vars_wk)] - run_program(vars_wk['ProduKey'], _args, check=False) - -def run_aida64(): - extract_item('AIDA64', vars_wk, silent=True) - # All system info - if not os.path.exists('{LogDir}\\System Information (AIDA64).html'.format(**vars_wk)): - print_info('* Saving System information', vars_wk['LogFile']) - _cmd = [ - vars_wk['AIDA64'], - '/R', - '{LogDir}\\System Information (AIDA64).html'.format(**vars_wk), - '/CUSTOM', - '{BinDir}\\AIDA64\\full.rpf'.format(**vars_wk), - '/HTML', - '/SILENT'] - run_program(_cmd, check=False) - - # RAM - if not os.path.exists('{LogDir}\\RAM Information (AIDA64).txt'.format(**vars_wk)): - _cmd = [ - vars_wk['AIDA64'], - '/R', - '{LogDir}\\RAM Information (AIDA64).txt'.format(**vars_wk), - '/CUSTOM', - '{BinDir}\\AIDA64\\ram.rpf'.format(**vars_wk), - '/TEXT', - '/SILENT'] - run_program(_cmd, check=False) - - # Installed Programs - if not os.path.exists('{LogDir}\\Installed Program List (AIDA64).txt'.format(**vars_wk)): - print_info('* Saving installed program list', vars_wk['LogFile']) - _cmd = [ - vars_wk['AIDA64'], - '/R', - '{LogDir}\\Installed Program List (AIDA64).txt'.format(**vars_wk), - '/CUSTOM', - '{BinDir}\\AIDA64\\installed_programs.rpf'.format(**vars_wk), - '/TEXT', - '/SILENT', - '/SAFEST'] - run_program(_cmd, check=False) - - # Product Keys - if not os.path.exists('{LogDir}\\Product Keys (AIDA64).txt'.format(**vars_wk)): - print_info('* Saving product keys', vars_wk['LogFile']) - _cmd = [ - vars_wk['AIDA64'], - '/R', - '{LogDir}\\Product Keys (AIDA64).txt'.format(**vars_wk), - '/CUSTOM', - '{BinDir}\\AIDA64\\licenses.rpf'.format(**vars_wk), - '/TEXT', - '/SILENT', - '/SAFEST'] - run_program(_cmd, check=False) - -def run_xmplay(): - extract_item('XMPlay', vars_wk, silent=True) - subprocess.Popen([vars_wk['XMPlay'], '{BinDir}\\XMPlay\\music.7z'.format(**vars_wk)]) - -def uninstall_eset(): - if 'PROGRAMFILES(X86)' in vars_wk['Env']: - _path = '{PROGRAMFILES(X86)}\\ESET'.format(**vars_wk['Env']) - else: - _path = '{PROGRAMFILES}\\ESET'.format(**vars_wk['Env']) - if os.path.exists('{path}\\ESET Online Scanner'.format(path=_path)): - try: - print_info('* Uninstalling ESET Online Scanner', vars_wk['LogFile']) - run_program('"{path}\\ESET Online Scanner\\OnlineScannerUninstaller.exe" -s'.format(path=_path)) - shutil.rmtree('{path}\\ESET Online Scanner'.format(path=_path)) - run_program('rmdir "{path}"'.format(path=_path), check=False) - except: - print_error('ERROR: Failed to uninstall ESET Online Scanner.', vars_wk['LogFile']) - -def uninstall_mbam(): - if 'PROGRAMFILES(X86)' in vars_wk['Env']: - _path = '{PROGRAMFILES(X86)}\\Malwarebytes Anti-Malware'.format(**vars_wk['Env']) - else: - _path = '{PROGRAMFILES}\\Malwarebytes Anti-Malware'.format(**vars_wk['Env']) - if os.path.exists('{path}'.format(path=_path)): - print_warning('* Malwarebytes Anti-Malware installed.', vars_wk['LogFile']) - if ask(' Uninstall?', vars_wk['LogFile']): - try: - run_program('"{path}\\unins000.exe" /SILENT'.format(path=_path)) - run_program('rmdir "{path}"'.format(path=_path), check=False) - except: - print_error('ERROR: Failed to uninstall Malwarebytes Anti-Malware.', vars_wk['LogFile']) - -def uninstall_sas(): - # It is always in programfiles (not x86) ?? - _path = '{PROGRAMFILES}\\SUPERAntiSpyware'.format(**vars_wk['Env']) - if os.path.exists(_path): - print_warning('* SUPERAntiSpyware installed.', vars_wk['LogFile']) - if ask(' Uninstall?', vars_wk['LogFile']): - try: - run_program('{path}\\Uninstall.exe'.format(path=_path)) - run_program('rmdir "{path}"'.format(path=_path), check=False) - except: - print_error('ERROR: Failed to uninstall SUPERAntiSpyware.', vars_wk['LogFile']) - -def update_clock(): - # Set Timezone and sync clock - print_info('* Updating system clock', vars_wk['LogFile']) - try: - run_program('tzutil /s "Pacific Standard Time"', check=False) - run_program('net stop w32ime', check=False) - run_program('w32tm /config /syncfromflags:manual /manualpeerlist:"us.pool.ntp.org time.nist.gov time.windows.com"', check=False) - run_program('net start w32ime', check=False) - run_program('w32tm /resync /nowait', check=False) - except: - print_error('ERROR: Failed to update system clock to PST/PDT', vars_wk['LogFile']) - -def upload_info(): - print_info('* Uploading info to NAS', vars_wk['LogFile']) - path = '{ClientDir}'.format(**vars_wk) - file = 'Info_{Date-Time}.7z'.format(**vars_wk) - - # Compress Info - _cmd = [ - vars_wk['SevenZip'], - 'a', '-t7z', '-mx=9', '-bso0', '-bse0', - '{path}\\{file}'.format(path=path, file=file), - '{ClientDir}\\Info'.format(**vars_wk)] - try: - run_program(_cmd, pipe=False) - except subprocess.CalledProcessError: - print_error(' ERROR: Failed to compress data for upload.', vars_wk['LogFile']) - return - - # Upload Info - try: - upload_data(path, file, vars_wk) - except: - print_error(' ERROR: Failed to upload info.', vars_wk['LogFile']) - if __name__ == '__main__': - stay_awake(vars_wk) - get_ticket_number() + stay_awake() + get_ticket_number() os.system('cls') - print_info('Starting Software Checklist for Ticket #{TicketNumber}\n'.format(**vars_wk), vars_wk['LogFile']) + print_info('Starting Software Checklist for Ticket #{TicketNumber}\n'.format(**global_vars)) + + # Configure + print_info('Configure') + try_and_print(message='Updating Clock...', function=update_clock, cs='Done') + if global_vars['OS']['Version'] in ['8', '10']: + try_and_print(message='Classic Start...', function=config_classicstart, cs='Done') + try_and_print(message='Explorer...', function=config_explorer, cs='Done') # Cleanup - cleanup_desktop() - cleanup_adwcleaner() - uninstall_eset() - uninstall_mbam() - uninstall_sas() + print_info('Cleanup') + try_and_print(message='Desktop...', function=cleanup_desktop, cs='Done') + try_and_print(message='AdwCleaner...', function=cleanup_adwcleaner, cs='Done') + try_and_print(message='ESET...', function=uninstall_eset, cs='Done') + # try_and_print(message='MBAM...', function=uninstall_mbam, cs='Done') + try_and_print(message='Super Anti-Spyware...', function=uninstall_sas, cs='Done') - # Last-minute backups and adjustments - update_clock() - backup_power_plans() - backup_registry() - run_aida64() - run_produkey() + # Export system info + print_info('Backup System Information') + try_and_print(message='AIDA64 reports...', function=run_aida64, cs='Done') + # try_and_print(message='Browsers...', function=backup_browsers, cs='Done') + try_and_print(message='File listing...', function=backup_file_list, cs='Done') + try_and_print(message='Power plans...', function=backup_power_plans, cs='Done') + try_and_print(message='Product Keys...', function=run_produkey, cs='Done') + try_and_print(message='Registry...', function=backup_registry, cs='Done') - ## System information ## - get_user_data_summary() - get_os_info() - if 'The machine is permanently activated.' not in vars_wk['Activation']: - subprocess.Popen('slui') - get_free_space() - get_installed_ram() - get_battery_info() + # User data + print_info('User Data') + show_user_data_summary() - # Play audio, show devices, and open Windows updates - subprocess.Popen('devmgmt.msc', shell=True) + # Summary + print_info('Summary') + try_and_print(message='Operating System:', function=show_os_name, ns='Unknown', silent_function=False) + try_and_print(message='', function=show_os_activation, ns='Unknown', silent_function=False) + try_and_print(message='Installed Office:', function=get_installed_office, ns='Unknown', print_return=True) + show_free_space() + try_and_print(message='Installed RAM:', function=show_installed_ram, ns='Unknown', silent_function=False) + + # Upload info + print_info('Finalizing') + try_and_print(message='Compressing Info...', function=compress_info, cs='Done') + try_and_print(message='Uploading to NAS...', function=upload_info, cs='Done') + + # Play audio, show devices, open Windows updates, and open Activation if necessary + popen_program('devmgmt.msc') run_hwinfo_sensors() - if vars_wk['Version'] == '10': - subprocess.Popen('control /name Microsoft.WindowsUpdate', shell=True) + if global_vars['OS']['Version'] == '10': + popen_program(['control', '/name', 'Microsoft.WindowsUpdate']) else: - subprocess.Popen('wuapp', shell=True) + popen_program('wuapp') + if 'The machine is permanently activated.' not in global_vars['OS']['Activation']: + popen_program('slui') sleep(3) run_xmplay() - # Upload info - upload_info() - # Done - print_standard('\nDone.', vars_wk['LogFile']) + print_standard('\nDone.') pause('Press Enter exit...') - - # Open log - extract_item('Notepad2', vars_wk, silent=True) - subprocess.Popen([vars_wk['Notepad2'], vars_wk['LogFile']]) - - # Quit - kill_process('caffeine.exe') - exit_script() \ No newline at end of file + exit_script() diff --git a/.bin/Scripts/sw_diagnostics.py b/.bin/Scripts/sw_diagnostics.py index 1fdb7c11..fd137f9c 100644 --- a/.bin/Scripts/sw_diagnostics.py +++ b/.bin/Scripts/sw_diagnostics.py @@ -1,584 +1,84 @@ # Wizard Kit: Software Diagnostics import os -import re -import subprocess -import winreg # Init os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: Software Diagnostics Tool') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) -vars_wk['BackupDir'] = '{ClientDir}\\Backups\\{Date}'.format(**vars_wk) -vars_wk['LogFile'] = '{LogDir}\\Software Diagnostics.log'.format(**vars_wk) -vars_wk['AIDA64'] = '{BinDir}\\AIDA64\\aida64.exe'.format(**vars_wk) -vars_wk['AutoRuns'] = '{BinDir}\\SysinternalsSuite\\autoruns.exe'.format(**vars_wk) -vars_wk['BleachBit'] = '{BinDir}\\BleachBit\\bleachbit_console.exe'.format(**vars_wk) -vars_wk['ERUNT'] = '{BinDir}\\erunt\\ERUNT.EXE'.format(**vars_wk) -vars_wk['Everything'] = '{BinDir}\\Everything\\Everything.exe'.format(**vars_wk) -vars_wk['HitmanPro'] = '{BinDir}\\HitmanPro\\HitmanPro.exe'.format(**vars_wk) -vars_wk['Notepad2'] = '{BinDir}\\Notepad2\\Notepad2-Mod.exe'.format(**vars_wk) -vars_wk['ProduKey'] = '{BinDir}\\ProduKey\\ProduKey.exe'.format(**vars_wk) -vars_wk['SevenZip'] = '{BinDir}\\7-Zip\\7za.exe'.format(**vars_wk) -if vars_wk['Arch'] == 64: - vars_wk['AutoRuns'] = vars_wk['AutoRuns'].replace('.exe', '64.exe') - vars_wk['Everything'] = vars_wk['Everything'].replace('.exe', '64.exe') - vars_wk['HitmanPro'] = vars_wk['HitmanPro'].replace('.exe', '64.exe') - vars_wk['Notepad2'] = vars_wk['Notepad2'].replace('.exe', '64.exe') - vars_wk['ProduKey'] = vars_wk['ProduKey'].replace('.exe', '64.exe') - vars_wk['SevenZip'] = vars_wk['SevenZip'].replace('.exe', '64.exe') -os.makedirs(vars_wk['LogDir'], exist_ok=True) +init_global_vars() +set_global_vars(LogFile='{LogDir}\\Software Diagnostics.log'.format(**global_vars)) def abort(): - print_warning('Aborted.', vars_wk['LogFile']) + print_warning('Aborted.') pause("Press Enter to exit...") exit_script() -def backup_browsers(): - print_info('* Backing up browser data', vars_wk['LogFile']) - # Chromium - if os.path.exists('{LOCALAPPDATA}\\Chromium'.format(**vars_wk['Env'])): - print_standard(' Chromium', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Browsers\\{USERNAME}\\Chromium.7z" "{LOCALAPPDATA}\\Chromium"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - # Google Chrome - if os.path.exists('{LOCALAPPDATA}\\Google\\Chrome'.format(**vars_wk['Env'])): - print_standard(' Google Chrome', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Browsers\\{USERNAME}\\Google Chrome.7z" "{LOCALAPPDATA}\\Google\\Chrome"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - # Internet Explorer - if os.path.exists('{USERPROFILE}\\Favorites'.format(**vars_wk['Env'])): - print_standard(' Internet Explorer', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Browsers\\{USERNAME}\\Internet Explorer.7z" "{USERPROFILE}\\Favorites"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - run_program('reg export "hkcu\\Software\\Microsoft\\Internet Explorer" "{BackupDir}\\Browsers\\{USERNAME}\\Internet Explorer (HKCU).reg" /y'.format(**vars_wk, **vars_wk['Env']), check=False) - run_program('reg export "hklm\\Software\\Microsoft\\Internet Explorer" "{BackupDir}\\Browsers\\{USERNAME}\\Internet Explorer (HKLM).reg" /y'.format(**vars_wk, **vars_wk['Env']), check=False) - # Mozilla Firefox - if os.path.exists('{APPDATA}\\Mozilla\\Firefox'.format(**vars_wk['Env'])): - print_standard(' Mozilla Firefox', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Browsers\\{USERNAME}\\Mozilla Firefox.7z" "{APPDATA}\\Mozilla\\Firefox\\Profile*"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - # Opera Chromium - if os.path.exists('{APPDATA}\\Opera Software\\Opera Stable'.format(**vars_wk['Env'])): - print_standard(' Opera Chromium', vars_wk['LogFile']) - _cmd = '{SevenZip} a -aoa -bso0 -bse0 -mx=1 "{BackupDir}\\Browsers\\{USERNAME}\\Opera Chromium.7z" "{APPDATA}\\Mozilla\\Opera Software\\Opera Stable*"'.format(**vars_wk, **vars_wk['Env']) - run_program(_cmd, check=False, pipe=False) - -def backup_file_list(): - """Export current file listing for the system.""" - print_info('* Backing up file list', vars_wk['LogFile']) - extract_item('Everything', vars_wk, silent=True) - _cmd = [ - vars_wk['Everything'], - '-nodb', - '-create-filelist', - '{LogDir}\\File List.txt'.format(**vars_wk), - '{SYSTEMDRIVE}'.format(**vars_wk['Env'])] - try: - run_program(_cmd) - except subprocess.CalledProcessError: - print_error('ERROR: Failed to save file list', vars_wk['LogFile']) - -def backup_power_plans(): - """Export current power plans.""" - print_info('* Backing up power plans', vars_wk['LogFile']) - os.makedirs('{BackupDir}\\Power Plans'.format(**vars_wk), exist_ok=True) - try: - _plans = run_program('powercfg /L') - _plans = _plans.stdout.decode().splitlines() - _plans = [p for p in _plans if re.search(r'^Power Scheme', p)] - for p in _plans: - _guid = re.sub(r'Power Scheme GUID:\s+([0-9a-f\-]+).*', r'\1', p) - _name = re.sub(r'Power Scheme GUID:\s+[0-9a-f\-]+\s+\(([^\)]+)\).*', r'\1', p) - print(' {name} ({guid})'.format(guid=_guid, name=_name)) - _out = '{BackupDir}\\Power Plans\\{name}.pow'.format(name=_name, **vars_wk) - if not os.path.exists(_out): - run_program('powercfg /export "{out}" {guid}'.format(out=_out, guid=_guid), check=False) - except subprocess.CalledProcessError: - print_error('ERROR: Failed to export power plans.') - -def backup_registry(): - print_info('* Backing up registry', vars_wk['LogFile']) - extract_item('erunt', vars_wk, silent=True) - _args = [ - '{LogDir}\\Registry'.format(**vars_wk), - 'sysreg', - 'curuser', - 'otherusers', - '/noprogresswindow'] - try: - run_program(vars_wk['ERUNT'], _args) - except subprocess.CalledProcessError: - print_error('ERROR: Failed to backup registry', vars_wk['LogFile']) - -def exit_script(): - quit() - -def get_battery_info(): - #~#print_info('* Battery', vars_wk['LogFile']) - #~#WK-write "==== Battery Check ====" "$log" - #~#& "$wd\check_battery.ps1" "$log" - #~#WK-write "" "$log" - pass - -def get_free_space(): - print_info('* Free space', vars_wk['LogFile']) - for drive in get_free_space_info(): - print_standard(' {} {}'.format(*drive), vars_wk['LogFile']) - -def get_installed_office(): - print_info('* Installed Office programs', vars_wk['LogFile']) - with open ('{LogDir}\\Installed Program List (AIDA64).txt'.format(**vars_wk), 'r') as f: - for line in sorted(f.readlines()): - if re.search(r'(Microsoft (Office\s+(365|Enterprise|Home|Pro(\s|fessional)|Single|Small|Standard|Starter|Ultimate|system)|Works[-\s\d]+\d)|(Libre|Open|Star)\s*Office|WordPerfect|Gnumeric|Abiword)', line, re.IGNORECASE): - print_standard(' ' + line[4:82].strip(), vars_wk['LogFile']) - -def get_installed_ram(): - print_info('* Installed RAM', vars_wk['LogFile']) - with open ('{LogDir}\\RAM Information (AIDA64).txt'.format(**vars_wk), 'r') as f: - _module = '' - for line in f.readlines(): - if re.search(r'Module Size', line, re.IGNORECASE): - _module = re.sub(r'\s*Module Size\s+(.*)\s+\(.*$', r' Module: \1', line.strip()) - if re.search(r'Memory Speed', line, re.IGNORECASE): - _module += re.sub(r'\s*Memory Speed\s+(.*)$', r' \1', line.strip()) - print_standard(_module, vars_wk['LogFile']) - -def get_os_info(): - print_info('* Operating System', vars_wk['LogFile']) - if vars_wk['Arch'] == 32: - # Show all 32-bit installs as an error message - print_error(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - else: - if vars_wk['CurrentVersion'] == '6.0': - # Vista - if vars_wk['CurrentBuildNumber'] < 6002: - print_error(' {Name} x{Arch} (very outdated)'.format(**vars_wk), vars_wk['LogFile']) - else: - print_warning(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentVersion'] == '6.1': - # Windows 7 - if vars_wk['CSDVersion'] == 'Service Pack 1': - print_standard(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - else: - print_error(' {Name} x{Arch} (very outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentVersion'] == '6.2': - # Windows 8 - print_error(' {Name} x{Arch} (very outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentVersion'] == '6.3': - if vars_wk['CurrentBuild'] == 9200: - # Windows 8.1 - print_error(' {Name} x{Arch} (very outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentBuild'] == 9600: - # Windows 8.1 Update - print_info(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentBuild'] == 10240: - # Windows 10 Threshold 1 - print_error(' {Name} x{Arch} (outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentBuild'] == 10586: - # Windows 10 Threshold 2 - print_warning(' {Name} x{Arch} (outdated)'.format(**vars_wk), vars_wk['LogFile']) - elif vars_wk['CurrentBuild'] == 14393: - # Windows 10 Redstone 1 - print_standard(' {Name} x{Arch}'.format(**vars_wk), vars_wk['LogFile']) - else: - print_warning(' {Name} x{Arch} (unrecognized)'.format(**vars_wk), vars_wk['LogFile']) - # OS Activation - if re.search(r'permanent', vars_wk['Activation'], re.IGNORECASE): - print_standard(' {Activation}'.format(**vars_wk), vars_wk['LogFile']) - elif re.search(r'unavailable', vars_wk['Activation'], re.IGNORECASE): - print_warning(' {Activation}'.format(**vars_wk), vars_wk['LogFile']) - else: - print_error(' {Activation}'.format(**vars_wk), vars_wk['LogFile']) - -def get_product_keys(): - print_info('* Product Keys', vars_wk['LogFile']) - # ProduKey - with open ('{LogDir}\\Product Keys (ProduKey).txt'.format(**vars_wk), 'r') as f: - _keys = [] - for line in f.readlines(): - if re.search(r'^Product Name', line): - line = re.sub(r'^Product Name\s+:\s+(.*)', r'\1', line) - _keys.append(line) - for k in sorted(_keys): - print_standard(' ' + k.strip(), vars_wk['LogFile']) - -def get_ticket_number(): - """Get TicketNumber from user and save it in the info folder.""" - vars_wk['TicketNumber'] = None - while vars_wk['TicketNumber'] is None: - _ticket = input('Enter ticket number: ') - if re.match(r'^([0-9]+([-_]?\w+|))$', _ticket): - vars_wk['TicketNumber'] = _ticket - with open('{LogDir}\\TicketNumber'.format(**vars_wk), 'w') as f: - f.write(_ticket) - else: - print_error('ERROR: Invalid ticket number', vars_wk['LogFile']) - -def get_user_data_summary(): - print_info('* User Data', vars_wk['LogFile']) - users = get_user_data_size_info(vars_wk) - for user in sorted(users): - print_standard(' User: {user}'.format(user=user), vars_wk['LogFile']) - print_standard(' ' + users[user].get('ProfileSize', 'Unknown'), vars_wk['LogFile']) - print_standard(' -------------------------------', vars_wk['LogFile']) - for folder in sorted(users[user]['Shell Folders']): - print_standard(' ' + users[user]['Shell Folders'][folder], vars_wk['LogFile']) - for folder in sorted(users[user]['Extra Folders']): - print_standard(' ' + users[user]['Shell Folders'][folder], vars_wk['LogFile']) - -def ping_test(addr='google.com'): - """Attempt to ping addr and if unsuccessful either retry or abort.""" - print_info('* Checking network connection', vars_wk['LogFile']) - _cmd = ['ping', '-n', '2', addr] - while True: - try: - run_program(_cmd) - break - except subprocess.CalledProcessError: - if not ask('ERROR: Can\'t ping {addr}, try again?'.format(addr=addr), vars_wk['LogFile']): - abort() - -def run_process_killer(): - """Kill most running processes skipping those in the whitelist.txt.""" - # borrowed from TronScript (reddit.com/r/TronScript) and credit to /u/cuddlychops06 - print_info('* Stopping all processes', vars_wk['LogFile']) - _prev_dir = os.getcwd() - extract_item('ProcessKiller', vars_wk, silent=True) - os.chdir('{BinDir}\\ProcessKiller'.format(**vars_wk)) - run_program(['ProcessKiller.exe', '/silent'], check=False) - os.chdir(_prev_dir) - -def run_autoruns(): - """Run AutoRuns in the background with VirusTotal checks enabled.""" - extract_item('SysinternalsSuite', vars_wk, filter='autoruns*', silent=True) - winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns') - with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns', access=winreg.KEY_WRITE) as _key: - winreg.SetValueEx(_key, 'checkvirustotal', 0, winreg.REG_DWORD, 1) - winreg.SetValueEx(_key, 'EulaAccepted', 0, winreg.REG_DWORD, 1) - winreg.SetValueEx(_key, 'shownomicrosoft', 0, winreg.REG_DWORD, 1) - winreg.SetValueEx(_key, 'shownowindows', 0, winreg.REG_DWORD, 1) - winreg.SetValueEx(_key, 'showonlyvirustotal', 0, winreg.REG_DWORD, 1) - winreg.SetValueEx(_key, 'submitvirustotal', 0, winreg.REG_DWORD, 0) - winreg.SetValueEx(_key, 'verifysignatures', 0, winreg.REG_DWORD, 1) - winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\SigCheck') - with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\SigCheck', access=winreg.KEY_WRITE) as _key: - winreg.SetValueEx(_key, 'EulaAccepted', 0, winreg.REG_DWORD, 1) - winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\Streams') - with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\Streams', access=winreg.KEY_WRITE) as _key: - winreg.SetValueEx(_key, 'EulaAccepted', 0, winreg.REG_DWORD, 1) - winreg.CreateKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\VirusTotal') - with winreg.OpenKey(winreg.HKEY_CURRENT_USER, r'Software\Sysinternals\AutoRuns\VirusTotal', access=winreg.KEY_WRITE) as _key: - winreg.SetValueEx(_key, 'VirusTotalTermsAccepted', 0, winreg.REG_DWORD, 1) - # Set autoruns to start minimized - info = subprocess.STARTUPINFO() - info.dwFlags = subprocess.STARTF_USESHOWWINDOW - info.wShowWindow = 6 - subprocess.Popen(vars_wk['AutoRuns'], startupinfo=info) - -def run_bleachbit(): - if not os.path.exists('{LogDir}\\BleachBit.log'.format(**vars_wk)): - print_info('* Checking for temp files', vars_wk['LogFile']) - extract_item('BleachBit', vars_wk, silent=True) - _args = ['--preview', '--preset'] - _out = run_program(vars_wk['BleachBit'], _args, check=False) - # Save stderr - if len(_out.stderr.decode().splitlines()) > 0: - with open('{LogDir}\\BleachBit.err'.format(**vars_wk), 'a') as f: - for line in _out.stderr.decode().splitlines(): - f.write(line.strip() + '\n') - # Save stdout - with open('{LogDir}\\BleachBit.log'.format(**vars_wk), 'a') as f: - for line in _out.stdout.decode().splitlines(): - f.write(line.strip() + '\n') - - # Temp file size - with open('{LogDir}\\BleachBit.log'.format(**vars_wk), 'r') as f: - for line in f.readlines(): - if re.search(r'^(disk space.*recovered|files.*deleted)', line, re.IGNORECASE): - print_standard(' ' + line.strip()) - -def run_chkdsk(): - """Run CHKDSK in a "split window" and report errors.""" - print_info('* Checking filesystem health', vars_wk['LogFile']) - _cmd = [ - 'chkdsk', - '{SYSTEMDRIVE}'.format(**vars_wk['Env'])] - _out = run_program(_cmd, check=False) - if int(_out.returncode) > 1: - # retcode == 0: no issues - # retcode == 1: fixed issues - # retcode == 2: issues - print_error(' ERROR: CHKDSK encountered errors', vars_wk['LogFile']) - - # Save stderr - with open('{LogDir}\\CHKDSK.err'.format(**vars_wk), 'a') as f: - for line in _out.stderr.decode().splitlines(): - f.write(line.strip() + '\n') - # Save stdout - with open('{LogDir}\\CHKDSK.log'.format(**vars_wk), 'a') as f: - for line in _out.stdout.decode().splitlines(): - f.write(line.strip() + '\n') - -def run_dism_health_check(): - """Run DISM /ScanHealth, then /CheckHealth, and then report errors.""" - if vars_wk['Version'] in ['8', '10']: - print_info('* Checking system image health', vars_wk['LogFile']) - # Scan Health - _args = [ - '/Online', - '/Cleanup-Image', - '/ScanHealth', - '/LogPath:{LogDir}\\DISM_ScanHealth.log'.format(**vars_wk), - '-new_console:n', - '-new_console:s33V'] - run_program('dism', _args, pipe=False, check=False) - wait_for_process('dism') - # Now check health - _args = [ - '/Online', - '/Cleanup-Image', - '/CheckHealth', - '/LogPath:{LogDir}\\DISM_CheckHealth.log'.format(**vars_wk)] - try: - _result = run_program('dism', _args).stdout.decode() - except subprocess.CalledProcessError: - print_error(' ERROR: failed to run DISM health check', vars_wk['LogFile']) - _result = ['Unknown'] - else: - # Check result - if not re.search(r'No component store corruption detected', _result, re.IGNORECASE): - for line in _result: - line = ' ' + line - print_warning(line, vars_wk['LogFile']) - print_error(' ERROR: DISM encountered errors, please review details above', vars_wk['LogFile']) - -def run_hitmanpro(): - """Run HitmanPro in the background.""" - print_info('* Running malware/virus scan (in the background)', vars_wk['LogFile']) - extract_item('HitmanPro', vars_wk, silent=True) - _cmd = [ - vars_wk['HitmanPro'], - '/quiet', - '/noinstall', - '/noupload', - '/log={LogDir}\\hitman.xml'.format(**vars_wk)] - subprocess.Popen(_cmd) - -def run_produkey(): - extract_item('ProduKey', vars_wk, silent=True) - if not os.path.exists('{LogDir}\\Product Keys (ProduKey).txt'.format(**vars_wk)): - print_info('* Saving product keys (secondary method)', vars_wk['LogFile']) - # Clear current configuration - for config in ['ProduKey.cfg', 'ProduKey64.cfg']: - try: - if os.path.exists('{BinDir}\\ProduKey\\{config}'.format(config=config, **vars_wk)): - os.remove('{BinDir}\\ProduKey\\{config}'.format(config=config, **vars_wk)) - except: - pass - _args = ['/nosavereg', '/stext', '{LogDir}\\Product Keys (ProduKey).txt'.format(**vars_wk)] - run_program(vars_wk['ProduKey'], _args, check=False) - -def run_rkill(): - """Run RKill and cleanup afterwards.""" - print_info('* Running RKill', vars_wk['LogFile']) - extract_item('RKill', vars_wk, silent=True) - _cmd = [ - '{BinDir}\\RKill\\RKill.exe'.format(**vars_wk), - '-l', - '{LogDir}\\RKill.log'.format(**vars_wk), - '-new_console:n', - '-new_console:s33V'] - run_program(_cmd, check=False) - wait_for_process('RKill') - kill_process('notepad.exe') - if not ask(' Did RKill run correctly?', vars_wk['LogFile']): - print_warning(' Opening folder for manual execution.', vars_wk['LogFile']) - try: - subprocess.Popen(['explorer.exe', '{BinDir}\\RKill'.format(**vars_wk)]) - except: - pass - if not ask(' Resume script?'): - abort() - - # RKill cleanup - if os.path.exists('{USERPROFILE}\\Desktop'.format(**vars_wk['Env'])): - for item in os.scandir('{USERPROFILE}\\Desktop'.format(**vars_wk['Env'])): - if re.search(r'^RKill', item.name, re.IGNORECASE): - shutil.move(item.path, '{ClientDir}\\Info\\{name}'.format(name=item.name, **vars_wk)) - -def run_aida64(): - extract_item('AIDA64', vars_wk, silent=True) - # All system info - if not os.path.exists('{LogDir}\\System Information (AIDA64).html'.format(**vars_wk)): - print_info('* Saving System information', vars_wk['LogFile']) - _cmd = [ - vars_wk['AIDA64'], - '/R', - '{LogDir}\\System Information (AIDA64).html'.format(**vars_wk), - '/CUSTOM', - '{BinDir}\\AIDA64\\full.rpf'.format(**vars_wk), - '/HTML', - '/SILENT'] - run_program(_cmd, check=False) - - # RAM - if not os.path.exists('{LogDir}\\RAM Information (AIDA64).txt'.format(**vars_wk)): - _cmd = [ - vars_wk['AIDA64'], - '/R', - '{LogDir}\\RAM Information (AIDA64).txt'.format(**vars_wk), - '/CUSTOM', - '{BinDir}\\AIDA64\\ram.rpf'.format(**vars_wk), - '/TEXT', - '/SILENT'] - run_program(_cmd, check=False) - - # Installed Programs - if not os.path.exists('{LogDir}\\Installed Program List (AIDA64).txt'.format(**vars_wk)): - print_info('* Saving installed program list', vars_wk['LogFile']) - _cmd = [ - vars_wk['AIDA64'], - '/R', - '{LogDir}\\Installed Program List (AIDA64).txt'.format(**vars_wk), - '/CUSTOM', - '{BinDir}\\AIDA64\\installed_programs.rpf'.format(**vars_wk), - '/TEXT', - '/SILENT', - '/SAFEST'] - run_program(_cmd, check=False) - - # Product Keys - if not os.path.exists('{LogDir}\\Product Keys (AIDA64).txt'.format(**vars_wk)): - print_info('* Saving product keys', vars_wk['LogFile']) - _cmd = [ - vars_wk['AIDA64'], - '/R', - '{LogDir}\\Product Keys (AIDA64).txt'.format(**vars_wk), - '/CUSTOM', - '{BinDir}\\AIDA64\\licenses.rpf'.format(**vars_wk), - '/TEXT', - '/SILENT', - '/SAFEST'] - run_program(_cmd, check=False) - -def run_sfc_scan(): - """Run SFC in a "split window" and report errors.""" - print_info('* Checking system file health', vars_wk['LogFile']) - _cmd = [ - '{SYSTEMROOT}\\System32\\sfc.exe'.format(**vars_wk['Env']), - '/scannow'] - _out = run_program(_cmd, check=False) - # Save stderr - with open('{LogDir}\\SFC.err'.format(**vars_wk), 'a') as f: - for line in _out.stderr.decode().splitlines(): - f.write(line.strip() + '\n') - # Save stdout - with open('{LogDir}\\SFC.log'.format(**vars_wk), 'a') as f: - for line in _out.stdout.decode().splitlines(): - f.write(line.strip() + '\n') - -def run_tdsskiller(): - """Run TDSSKiller.""" - print_info('* Running rootkit scan', vars_wk['LogFile']) - extract_item('TDSSKiller', vars_wk, silent=True) - os.makedirs('{ClientDir}\\Quarantine\\TDSSKiller'.format(**vars_wk), exist_ok=True) - _cmd = '{BinDir}\\TDSSKiller\\TDSSKiller.exe'.format(**vars_wk) - _args = [ - '-l', - '{LogDir}\\TDSSKiller.log'.format(**vars_wk), - '-qpath', - '{ClientDir}\\Quarantine\\TDSSKiller'.format(**vars_wk), - '-accepteula', - '-accepteulaksn', - '-dcexact', - '-tdlfs'] - try: - run_program(_cmd, _args, pipe=False) - except subprocess.CalledProcessError: - print_error('ERROR: Failed to run TDSSKiller.', vars_wk['LogFile']) - abort() - -def upload_info(): - print_info('* Uploading info to NAS', vars_wk['LogFile']) - path = '{ClientDir}'.format(**vars_wk) - file = 'Info_{Date-Time}.7z'.format(**vars_wk) - - # Compress Info - _cmd = [ - vars_wk['SevenZip'], - 'a', '-t7z', '-mx=9', '-bso0', '-bse0', - '{path}\\{file}'.format(path=path, file=file), - '{ClientDir}\\Info'.format(**vars_wk)] - try: - run_program(_cmd, pipe=False) - except subprocess.CalledProcessError: - print_error(' ERROR: Failed to compress data for upload.', vars_wk['LogFile']) - return - - # Upload Info - try: - upload_data(path, file, vars_wk) - except: - print_error(' ERROR: Failed to upload info.', vars_wk['LogFile']) - if __name__ == '__main__': - stay_awake(vars_wk) - get_ticket_number() + stay_awake() + get_ticket_number() os.system('cls') - print_info('Starting Software Diagnostics for Ticket #{TicketNumber}\n'.format(**vars_wk), vars_wk['LogFile']) + other_results = { + 'Error': { + 'CalledProcessError': 'Unknown Error', + }, + 'Warning': { + 'GenericRepair': 'Repaired', + 'UnsupportedOSError': 'Unsupported OS', + }} + print_info('Starting Software Diagnostics for Ticket #{TicketNumber}\n'.format(**global_vars)) # Sanitize Environment - run_process_killer() - run_rkill() - run_tdsskiller() + print_info('Sanitizing Environment') + try_and_print(message='Killing processes...', function=run_process_killer, cs='Done') + try_and_print(message='Running RKill...', function=run_rkill, cs='Done') + try_and_print(message='Running TDSSKiller...', function=run_tdsskiller, cs='Done') # Re-run if earlier process was stopped. - stay_awake(vars_wk) + stay_awake() - # Network Check - ping_test() - - # Start background scans - run_hitmanpro() - run_autoruns() + # Start diags + print_info('Starting Background Scans') + check_connection() + try_and_print(message='Running HitmanPro...', function=run_hitmanpro, cs='Started') + try_and_print(message='Running Autoruns...', function=run_autoruns, cs='Started') # OS Health Checks - run_chkdsk() - run_sfc_scan() - run_dism_health_check() + print_info('OS Health Checks') + try_and_print(message='CHKDSK ({SYSTEMDRIVE})...'.format(**global_vars['Env']), function=run_chkdsk, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='SFC scan...', function=run_sfc_scan, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='DISM CheckHealth...', function=run_dism_scan_health, cs='CS', ns='NS', other_results=other_results) # Export system info - backup_file_list() - backup_power_plans() - backup_registry() - backup_browsers() - run_aida64() - run_produkey() + print_info('Backup System Information') + try_and_print(message='AIDA64 reports...', function=run_aida64, cs='Done') + try_and_print(message='BleachBit report...', function=run_bleachbit, cs='Done') + try_and_print(message='Browsers...', function=backup_browsers, cs='Done') + try_and_print(message='File listing...', function=backup_file_list, cs='Done') + try_and_print(message='Power plans...', function=backup_power_plans, cs='Done') + try_and_print(message='Product Keys...', function=run_produkey, cs='Done') + try_and_print(message='Registry...', function=backup_registry, cs='Done') # Summary - run_bleachbit() - get_free_space() - get_installed_ram() - get_installed_office() - get_product_keys() - get_os_info() - get_battery_info() - get_user_data_summary() + print_info('Summary') + try_and_print(message='Temp Size:', function=show_temp_files_size, silent_function=False) + show_free_space() + try_and_print(message='Installed RAM:', function=show_installed_ram, ns='Unknown', silent_function=False) + try_and_print(message='Installed Office:', function=get_installed_office, ns='Unknown', print_return=True) + try_and_print(message='Product Keys:', function=get_product_keys, ns='Unknown', print_return=True) + try_and_print(message='Operating System:', function=show_os_name, ns='Unknown', silent_function=False) + try_and_print(message='', function=show_os_activation, ns='Unknown', silent_function=False) + + # User data + print_info('User Data') + show_user_data_summary() # Upload info - upload_info() + print_info('Finalizing') + try_and_print(message='Compressing Info...', function=compress_info, cs='Done') + try_and_print(message='Uploading to NAS...', function=upload_info, cs='Done') # Done - print_standard('\nDone.', vars_wk['LogFile']) + print_standard('\nDone.') pause('Press Enter to exit...') - - # Open log - extract_item('Notepad2', vars_wk, silent=True) - subprocess.Popen([vars_wk['Notepad2'], vars_wk['LogFile']]) - - # Quit - kill_process('caffeine.exe') - exit_script() \ No newline at end of file + exit_script() diff --git a/.bin/Scripts/transferred_keys.py b/.bin/Scripts/transferred_keys.py index ea6d86b9..ca6588b0 100644 --- a/.bin/Scripts/transferred_keys.py +++ b/.bin/Scripts/transferred_keys.py @@ -8,53 +8,21 @@ import subprocess os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: Key Tool') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) -vars_wk['LogFile'] = '{LogDir}\\Transferred Keys.log'.format(**vars_wk) -vars_wk['Notepad2'] = '{BinDir}\\Notepad2\\Notepad2-Mod.exe'.format(**vars_wk) -vars_wk['ProduKey'] = '{BinDir}\\ProduKey\\ProduKey.exe'.format(**vars_wk) -if vars_wk['Arch'] == 64: - vars_wk['Notepad2'] = vars_wk['Notepad2'].replace('.exe', '64.exe') - vars_wk['ProduKey'] = vars_wk['ProduKey'].replace('.exe', '64.exe') -os.makedirs(vars_wk['LogDir'], exist_ok=True) -REGEX_DIR = re.compile(r'^(config$|RegBack$|System32$|Transfer|Win)', re.IGNORECASE) -REGEX_FILE = re.compile(r'^Software$', re.IGNORECASE) +init_global_vars() +set_global_vars(LogFile='{LogDir}\\Transferred Keys.log'.format(**global_vars)) def abort(): - print_warning('Aborted.', vars_wk['LogFile']) - exit_script() + print_warning('Aborted.') + exit_script(global_vars) -def exit_script(): - pause("Press Enter to exit...") - quit() - -def find_hives(): - """Search for transferred SW hives and return a list.""" - hives = [] - search_paths = [vars_wk['ClientDir']] - - while len(search_paths) > 0: - for item in os.scandir(search_paths.pop(0)): - if item.is_dir() and REGEX_DIR.search(item.name): - search_paths.append(item.path) - if item.is_file() and REGEX_FILE.search(item.name): - hives.append(item.path) - - return hives - -def extract_keys(hives=None): +def extract_keys(): """Extract keys from provided hives and return a dict.""" keys = {} - # Bail early - if hives is None: - print_error(' ERROR: No hives found.') - abort() - # Extract keys - extract_item('ProduKey', vars_wk) - for hive in hives: - print_standard(' Scanning {hive}...'.format(hive=hive), vars_wk['LogFile']) + extract_item('ProduKey') + for hive in find_software_hives(): + print_standard(' Scanning {hive}...'.format(hive=hive)) _args = [ '/IEKeys', '0', '/WindowsKeys', '1', @@ -64,7 +32,7 @@ def extract_keys(hives=None): '/regfile', hive, '/scomma', ''] try: - _out = run_program(vars_wk['ProduKey'], _args) + _out = run_program(global_vars['Tools']['ProduKey'], _args) for line in _out.stdout.decode().splitlines(): # Add key to keys under product only if unique _tmp = line.split(',') @@ -75,7 +43,7 @@ def extract_keys(hives=None): if _key not in keys[_product]: keys[_product].append(_key) except subprocess.CalledProcessError: - print_error(' Failed to extract any keys', vars_wk['LogFile']) + print_error(' Failed to extract any keys') else: for line in _out.stdout.decode().splitlines(): _match = re.search(r'', line, re.IGNORECASE) @@ -83,23 +51,19 @@ def extract_keys(hives=None): return keys if __name__ == '__main__': - stay_awake(vars_wk) - hives = find_hives() - keys = extract_keys(hives) + stay_awake() + keys = extract_keys() # Save Keys if keys: for product in sorted(keys): - print_standard('{product}:'.format(product=product), vars_wk['LogFile']) + print_standard('{product}:'.format(product=product)) for key in sorted(keys[product]): - print_standard(' {key}'.format(key=key), vars_wk['LogFile']) + print_standard(' {key}'.format(key=key)) else: - print_error('No keys found.', vars_wk['LogFile']) + print_error('No keys found.') - # Open log - extract_item('Notepad2', vars_wk, silent=True) - subprocess.Popen([vars_wk['Notepad2'], vars_wk['LogFile']]) - - # Quit - kill_process('caffeine.exe') - exit_script() \ No newline at end of file + # Done + print_standard('\nDone.') + pause("Press Enter to exit...") + exit_script() diff --git a/.bin/Scripts/update_kit.py b/.bin/Scripts/update_kit.py index 204281f9..d26b0731 100644 --- a/.bin/Scripts/update_kit.py +++ b/.bin/Scripts/update_kit.py @@ -7,11 +7,12 @@ import re os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: Kit Update Tool') from functions import * -vars = init_vars() -vars_os = init_vars_os() -curl = '{BinDir}/curl/curl.exe'.format(**vars) -seven_zip = '{BinDir}/7-Zip/7za.exe'.format(**vars) -if vars_os['Arch'] == 64: +vars_wk = init_vars_wk() +vars_wk.update(init_vars_os()) +extract_item('curl', vars_wk, silent=True) +curl = '{BinDir}/curl/curl.exe'.format(**vars_wk) +seven_zip = '{BinDir}/7-Zip/7za.exe'.format(**vars_wk) +if vars_wk['OS']['Arch'] == 64: seven_zip = seven_zip.replace('7za', '7za64') def download_file(out_dir, out_name, source_url): @@ -31,10 +32,10 @@ def download_file(out_dir, out_name, source_url): def resolve_dynamic_url(source_url, regex): """Download the "download page" and scan for a url using the regex provided; returns str.""" # Download the file - _tmp_file = '{TmpDir}/webpage.tmp'.format(**vars) + _tmp_file = '{TmpDir}/webpage.tmp'.format(**vars_wk) _args = ['-#LSfo', _tmp_file, source_url] try: - os.makedirs(vars['TmpDir'], exist_ok=True) + os.makedirs(vars_wk['TmpDir'], exist_ok=True) run_program(curl, _args) except: print_error('Falied to resolve dynamic url') @@ -56,7 +57,7 @@ if __name__ == '__main__': stay_awake(vars_wk) ## Diagnostics ## # HitmanPro - _path = '{BinDir}/HitmanPro'.format(**vars) + _path = '{BinDir}/HitmanPro'.format(**vars_wk) _name = 'HitmanPro.exe' _url = 'http://dl.surfright.nl/HitmanPro.exe' download_file(_path, _name, _url) @@ -66,7 +67,7 @@ if __name__ == '__main__': ## VR-OSR ## # AdwCleaner - _path = vars['BinDir'] + _path = vars_wk['BinDir'] _name = 'AdwCleaner.exe' _dl_page = 'http://www.bleepingcomputer.com/download/adwcleaner/dl/125/' _regex = r'href=.*http(s|)://download\.bleepingcomputer\.com/dl/[a-zA-Z0-9]+/[a-zA-Z0-9]+/windows/security/security-utilities/a/adwcleaner/AdwCleaner\.exe' @@ -74,25 +75,25 @@ if __name__ == '__main__': download_file(_path, _name, _url) # ESET Online Scanner - _path = vars['BinDir'] + _path = vars_wk['BinDir'] _name = 'ESET.exe' _url = 'http://download.eset.com/special/eos/esetsmartinstaller_enu.exe' download_file(_path, _name, _url) # Junkware Removal Tool - _path = vars['BinDir'] + _path = vars_wk['BinDir'] _name = 'JRT.exe' _url = 'http://downloads.malwarebytes.org/file/jrt' download_file(_path, _name, _url) # Kaspersky Virus Removal Tool - _path = vars['BinDir'] + _path = vars_wk['BinDir'] _name = 'KVRT.exe' _url = 'http://devbuilds.kaspersky-labs.com/devbuilds/KVRT/latest/full/KVRT.exe' download_file(_path, _name, _url) # RKill - _path = '{BinDir}/RKill'.format(**vars) + _path = '{BinDir}/RKill'.format(**vars_wk) _name = 'RKill.exe' _dl_page = 'http://www.bleepingcomputer.com/download/rkill/dl/10/' _regex = r'href=.*http(s|)://download\.bleepingcomputer\.com/dl/[a-zA-Z0-9]+/[a-zA-Z0-9]+/windows/security/security-utilities/r/rkill/rkill\.exe' @@ -100,14 +101,14 @@ if __name__ == '__main__': download_file(_path, _name, _url) # TDSSKiller - _path = vars['BinDir'] + _path = vars_wk['BinDir'] _name = 'TDSSKiller.exe' _url = 'http://media.kaspersky.com/utilities/VirusUtilities/EN/tdsskiller.exe' download_file(_path, _name, _url) ## Driver Tools ## # Intel Driver Update Utility - _path = '{BinDir}/_Drivers'.format(**vars) + _path = '{BinDir}/_Drivers'.format(**vars_wk) _name = 'Intel Driver Update Utility.exe' _dl_page = 'http://www.intel.com/content/www/us/en/support/detect.html' _regex = r'a href.*http(s|)://downloadmirror\.intel\.com/[a-zA-Z0-9]+/[a-zA-Z0-9]+/Intel%20Driver%20Update%20Utility%20Installer.exe' @@ -116,7 +117,7 @@ if __name__ == '__main__': download_file(_path, _name, _url) # Intel SSD Toolbox - _path = '{BinDir}/_Drivers'.format(**vars) + _path = '{BinDir}/_Drivers'.format(**vars_wk) _name = 'Intel SSD Toolbox.exe' _dl_page = 'https://downloadcenter.intel.com/download/26085/Intel-Solid-State-Drive-Toolbox' _regex = r'href=./downloads/eula/[0-9]+/Intel-Solid-State-Drive-Toolbox.httpDown=https\%3A\%2F\%2Fdownloadmirror\.intel\.com\%2F[0-9]+\%2Feng\%2FIntel\%20SSD\%20Toolbox\%20-\%20v[0-9\.]+.exe' @@ -129,7 +130,7 @@ if __name__ == '__main__': #~Broken~# # Samsung Magician print_warning('Samsung Magician section is broken.') print('Please manually put "Samsung Magician.exe" into "{BinDir}\\_Drivers\\"') - #~Broken~# _path = '{BinDir}/_Drivers'.format(**vars) + #~Broken~# _path = '{BinDir}/_Drivers'.format(**vars_wk) #~Broken~# _name = 'Samsung Magician.zip' #~Broken~# _dl_page = 'http://www.samsung.com/semiconductor/minisite/ssd/download/tools.html' #~Broken~# _regex = r'href=./semiconductor/minisite/ssd/downloads/software/Samsung_Magician_Setup_v[0-9]+.zip' @@ -139,32 +140,32 @@ if __name__ == '__main__': #~Broken~# download_file(_path, _name, _url) #~Broken~# # Extract and replace old copy #~Broken~# _args = [ - #~Broken~# 'e', '"{BinDir}/_Drivers/Samsung Magician.zip"'.format(**vars), + #~Broken~# 'e', '"{BinDir}/_Drivers/Samsung Magician.zip"'.format(**vars_wk), #~Broken~# '-aoa', '-bso0', '-bsp0', - #~Broken~# '-o"{BinDir}/_Drivers"'.format(**vars) + #~Broken~# '-o"{BinDir}/_Drivers"'.format(**vars_wk) #~Broken~# ] #~Broken~# run_program(seven_zip, _args) #~Broken~# try: - #~Broken~# os.remove('{BinDir}/_Drivers/Samsung Magician.zip'.format(**vars)) + #~Broken~# os.remove('{BinDir}/_Drivers/Samsung Magician.zip'.format(**vars_wk)) #~Broken~# #~PoSH~# Move-Item "$bin\_Drivers\Samsung*exe" "$bin\_Drivers\Samsung Magician.exe" $path 2>&1 | Out-Null #~Broken~# except: #~Broken~# pass # SanDisk Express Cache - _path = '{BinDir}/_Drivers'.format(**vars) + _path = '{BinDir}/_Drivers'.format(**vars_wk) _name = 'SanDisk Express Cache.exe' _url = 'http://mp3support.sandisk.com/ReadyCache/ExpressCacheSetup.exe' download_file(_path, _name, _url) ## Installers ## # Ninite - Bundles - _path = '{BaseDir}/Installers/Extras/Bundles'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Bundles'.format(**vars_wk) download_file(_path, 'Runtimes.exe', 'https://ninite.com/.net4.6.2-air-java8-silverlight/ninite.exe') download_file(_path, 'Legacy.exe', 'https://ninite.com/.net4.6.2-7zip-air-chrome-firefox-java8-silverlight-vlc/ninite.exe') download_file(_path, 'Modern.exe', 'https://ninite.com/.net4.6.2-7zip-air-chrome-classicstart-firefox-java8-silverlight-vlc/ninite.exe') # Ninite - Audio-Video - _path = '{BaseDir}/Installers/Extras/Audio-Video'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Audio-Video'.format(**vars_wk) download_file(_path, 'AIMP.exe', 'https://ninite.com/aimp/ninite.exe') download_file(_path, 'Audacity.exe', 'https://ninite.com/audacity/ninite.exe') download_file(_path, 'CCCP.exe', 'https://ninite.com/cccp/ninite.exe') @@ -180,7 +181,7 @@ if __name__ == '__main__': download_file(_path, 'Winamp.exe', 'https://ninite.com/winamp/ninite.exe') # Ninite - Cloud Storage - _path = '{BaseDir}/Installers/Extras/Cloud Storage'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Cloud Storage'.format(**vars_wk) download_file(_path, 'BitTorrent Sync.exe', 'https://ninite.com/bittorrentsync/ninite.exe') download_file(_path, 'Dropbox.exe', 'https://ninite.com/dropbox/ninite.exe') download_file(_path, 'Google Drive.exe', 'https://ninite.com/googledrive/ninite.exe') @@ -189,20 +190,20 @@ if __name__ == '__main__': download_file(_path, 'SugarSync.exe', 'https://ninite.com/sugarsync/ninite.exe') # Ninite - Communication - _path = '{BaseDir}/Installers/Extras/Communication'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Communication'.format(**vars_wk) download_file(_path, 'AIM.exe', 'https://ninite.com/aim/ninite.exe') download_file(_path, 'Pidgin.exe', 'https://ninite.com/pidgin/ninite.exe') download_file(_path, 'Skype.exe', 'https://ninite.com/skype/ninite.exe') download_file(_path, 'Trillian.exe', 'https://ninite.com/trillian/ninite.exe') # Ninite - Compression - _path = '{BaseDir}/Installers/Extras/Compression'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Compression'.format(**vars_wk) download_file(_path, '7-Zip.exe', 'https://ninite.com/7zip/ninite.exe') download_file(_path, 'PeaZip.exe', 'https://ninite.com/peazip/ninite.exe') download_file(_path, 'WinRAR.exe', 'https://ninite.com/winrar/ninite.exe') # Ninite - Developer - _path = '{BaseDir}/Installers/Extras/Developer'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Developer'.format(**vars_wk) download_file(_path, 'Eclipse.exe', 'https://ninite.com/eclipse/ninite.exe') download_file(_path, 'FileZilla.exe', 'https://ninite.com/filezilla/ninite.exe') download_file(_path, 'JDK 8.exe', 'https://ninite.com/jdk8/ninite.exe') @@ -215,12 +216,12 @@ if __name__ == '__main__': download_file(_path, 'WinSCP.exe', 'https://ninite.com/winscp/ninite.exe') # Ninite - File Sharing - _path = '{BaseDir}/Installers/Extras/File Sharing'.format(**vars) + _path = '{BaseDir}/Installers/Extras/File Sharing'.format(**vars_wk) download_file(_path, 'eMule.exe', 'https://ninite.com/emule/ninite.exe') download_file(_path, 'qBittorrent.exe', 'https://ninite.com/qbittorrent/ninite.exe') # Ninite - Image-Photo - _path = '{BaseDir}/Installers/Extras/Image-Photo'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Image-Photo'.format(**vars_wk) download_file(_path, 'FastStone.exe', 'https://ninite.com/faststone/ninite.exe') download_file(_path, 'GIMP.exe', 'https://ninite.com/gimp/ninite.exe') download_file(_path, 'Greenshot.exe', 'https://ninite.com/greenshot/ninite.exe') @@ -231,7 +232,7 @@ if __name__ == '__main__': download_file(_path, 'XnView.exe', 'https://ninite.com/xnview/ninite.exe') # Ninite - Misc - _path = '{BaseDir}/Installers/Extras/Misc'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Misc'.format(**vars_wk) download_file(_path, 'Classic Start.exe', 'https://ninite.com/classicstart/ninite.exe') download_file(_path, 'Evernote.exe', 'https://ninite.com/evernote/ninite.exe') download_file(_path, 'Everything.exe', 'https://ninite.com/everything/ninite.exe') @@ -240,7 +241,7 @@ if __name__ == '__main__': download_file(_path, 'Steam.exe', 'https://ninite.com/steam/ninite.exe') # Ninite - Office - _path = '{BaseDir}/Installers/Extras/Office'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Office'.format(**vars_wk) download_file(_path, 'CutePDF.exe', 'https://ninite.com/cutepdf/ninite.exe') download_file(_path, 'Foxit Reader.exe', 'https://ninite.com/foxit/ninite.exe') download_file(_path, 'LibreOffice.exe', 'https://ninite.com/libreoffice/ninite.exe') @@ -250,7 +251,7 @@ if __name__ == '__main__': download_file(_path, 'Thunderbird.exe', 'https://ninite.com/thunderbird/ninite.exe') # Ninite - Runtimes - _path = '{BaseDir}/Installers/Extras/Runtimes'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Runtimes'.format(**vars_wk) download_file(_path, 'Adobe Air.exe', 'https://ninite.com/air/ninite.exe') download_file(_path, 'dotNET.exe', 'https://ninite.com/.net4.6.2/ninite.exe') download_file(_path, 'Java 8.exe', 'https://ninite.com/java8/ninite.exe') @@ -258,7 +259,7 @@ if __name__ == '__main__': download_file(_path, 'Silverlight.exe', 'https://ninite.com/silverlight/ninite.exe') # Ninite - Security - _path = '{BaseDir}/Installers/Extras/Security'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Security'.format(**vars_wk) download_file(_path, 'Ad-Aware.exe', 'https://ninite.com/adaware/ninite.exe') download_file(_path, 'Avast.exe', 'https://ninite.com/avast/ninite.exe') download_file(_path, 'AVG.exe', 'https://ninite.com/avg/ninite.exe') @@ -269,7 +270,7 @@ if __name__ == '__main__': download_file(_path, 'SUPERAntiSpyware.exe', 'https://ninite.com/super/ninite.exe') # Ninite - Utilities - _path = '{BaseDir}/Installers/Extras/Utilities'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Utilities'.format(**vars_wk) download_file(_path, 'Auslogics DiskDefrag.exe', 'https://ninite.com/auslogics/ninite.exe') download_file(_path, 'CDBurnerXP.exe', 'https://ninite.com/cdburnerxp/ninite.exe') download_file(_path, 'Glary Utilities.exe', 'https://ninite.com/glary/ninite.exe') @@ -284,28 +285,27 @@ if __name__ == '__main__': download_file(_path, 'WinDirStat.exe', 'https://ninite.com/windirstat/ninite.exe') # Ninite - Web Browsers - _path = '{BaseDir}/Installers/Extras/Web Browsers'.format(**vars) + _path = '{BaseDir}/Installers/Extras/Web Browsers'.format(**vars_wk) download_file(_path, 'Google Chrome.exe', 'https://ninite.com/chrome/ninite.exe') download_file(_path, 'Mozilla Firefox.exe', 'https://ninite.com/firefox/ninite.exe') download_file(_path, 'Opera Chromium.exe', 'https://ninite.com/operaChromium/ninite.exe') ## Misc ## # Sysinternals - _path = '{BinDir}/tmp'.format(**vars) + _path = '{BinDir}/tmp'.format(**vars_wk) _name = 'SysinternalsSuite.zip' _url = 'https://download.sysinternals.com/files/SysinternalsSuite.zip' download_file(_path, _name, _url) # Extract _args = [ - 'e', '"{BinDir}/tmp/SysinternalsSuite.zip"'.format(**vars), + 'e', '"{BinDir}/tmp/SysinternalsSuite.zip"'.format(**vars_wk), '-aoa', '-bso0', '-bsp0', - '-o"{BinDir}/SysinternalsSuite"'.format(**vars)] + '-o"{BinDir}/SysinternalsSuite"'.format(**vars_wk)] run_program(seven_zip, _args) try: - os.remove('{BinDir}/tmp/SysinternalsSuite.zip'.format(**vars)) + os.remove('{BinDir}/tmp/SysinternalsSuite.zip'.format(**vars_wk)) except: pass pause("Press Enter to exit...") - kill_process('caffeine.exe') - quit() + exit_script(vars_wk) diff --git a/.bin/Scripts/user_checklist.py b/.bin/Scripts/user_checklist.py new file mode 100644 index 00000000..86687a32 --- /dev/null +++ b/.bin/Scripts/user_checklist.py @@ -0,0 +1,87 @@ +# Wizard Kit: User Checklist + +import os + +# Init +os.chdir(os.path.dirname(os.path.realpath(__file__))) +os.system('title Wizard Kit: User Checklist Tool') +from functions import * +init_global_vars() +set_global_vars(LogFile='{LogDir}\\User Checklist ({USERNAME}).log'.format(**global_vars, **global_vars['Env'])) + +def abort(): + print_warning('Aborted.') + exit_script() + +if __name__ == '__main__': + stay_awake() + os.system('cls') + other_results = { + 'Warning': { + 'NotInstalledError': 'Not installed', + 'NoProfilesError': 'No profiles found', + }} + answer_config_browsers = ask('Configure Browsers to WK Standards?') + if answer_config_browsers: + answer_reset_browsers = ask('Reset browsers to safe defaults?') + if global_vars['OS']['Version'] == '10': + answer_config_classicshell = ask('Configure ClassicShell to WK Standards?') + answer_config_explorer = ask('Configure Explorer to WK Standards?') + + # Cleanup + print_info('Cleanup') + try_and_print(message='Desktop...', function=cleanup_desktop, cs='Done') + + # Homepages + print_info('Current homepages') + list_homepages() + + # Backup + print_info('Backing up browsers') + try_and_print(message='Chromium...', function=backup_chromium, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Google Chrome...', function=backup_chrome, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Google Chrome Canary...', function=backup_chrome_canary, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Internet Explorer...', function=backup_internet_explorer, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Mozilla Firefox (All)...', function=backup_firefox, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Opera...', function=backup_opera, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Opera Beta...', function=backup_opera_beta, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Opera Dev...', function=backup_opera_dev, cs='CS', ns='NS', other_results=other_results) + + # Reset + if answer_config_browsers and answer_reset_browsers: + print_info('Resetting browsers') + try_and_print(message='Internet Explorer...', function=clean_internet_explorer, cs='Done') + try_and_print(message='Google Chrome...', function=reset_google_chrome, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Google Chrome Canary...', function=reset_google_chrome_canary, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Mozilla Firefox...', function=reset_mozilla_firefox, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Opera...', function=reset_opera, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Opera Beta...', function=reset_opera_beta, cs='CS', ns='NS', other_results=other_results) + try_and_print(message='Opera Dev...', function=reset_opera_dev, cs='CS', ns='NS', other_results=other_results) + + # Configure + print_info('Configuring programs') + if answer_config_browsers: + try_and_print(message='Internet Explorer...', function=config_internet_explorer, cs='Done') + try_and_print(message='Google Chrome...', function=config_google_chrome, cs='Done', other_results=other_results) + try_and_print(message='Google Chrome Canary...', function=config_google_chrome_canary, cs='Done', other_results=other_results) + try_and_print(message='Mozilla Firefox...', function=config_mozilla_firefox, cs='Done', other_results=other_results) + try_and_print(message='Mozilla Firefox Dev...', function=config_mozilla_firefox_dev, cs='Done', other_results=other_results) + try_and_print(message='Opera...', function=config_opera, cs='Done', other_results=other_results) + try_and_print(message='Opera Beta...', function=config_opera_beta, cs='Done', other_results=other_results) + try_and_print(message='Opera Dev...', function=config_opera_dev, cs='Done', other_results=other_results) + try_and_print(message='Set default browser...', function=set_chrome_as_default, cs='Done', other_results=other_results) + if global_vars['OS']['Version'] == '10': + if answer_config_classicshell: + try_and_print(message='ClassicStart...', function=config_classicstart, cs='Done') + # if answer_config_explorer: + # try_and_print(message='Explorer...', function=config_explorer, cs='Done') + if not answer_config_browsers and not answer_config_classicshell and not answer_config_explorer: + print_warning(' Skipped') + else: + if not answer_config_browsers: + print_warning(' Skipped') + + # Done + print_standard('\nDone.') + pause('Press Enter to exit...') + exit_script() diff --git a/.bin/Scripts/user_data_transfer.py b/.bin/Scripts/user_data_transfer.py index 11901db4..775493f3 100644 --- a/.bin/Scripts/user_data_transfer.py +++ b/.bin/Scripts/user_data_transfer.py @@ -8,117 +8,40 @@ from operator import itemgetter os.chdir(os.path.dirname(os.path.realpath(__file__))) os.system('title Wizard Kit: Data 1') from functions import * -vars_wk = init_vars_wk() -vars_wk.update(init_vars_os()) -vars_wk['LogFile'] = '{LogDir}\\Data 1.log'.format(**vars_wk) -os.makedirs('{LogDir}'.format(**vars_wk), exist_ok=True) -vars_wk['TransferDir'] = '{ClientDir}\\Transfer'.format(**vars_wk) -vars_wk['FastCopy'] = '{BinDir}\\FastCopy\\FastCopy.exe'.format(**vars_wk) -vars_wk['FastCopyArgs'] = [ - '/cmd=noexist_only', - '/logfile={LogFile}'.format(**vars_wk), - '/utf8', - '/skip_empty_dir', - '/linkdest', - '/no_ui', - '/auto_close', - '/exclude=\\*.esd;\\*.swm;\\*.wim;\\*.dd;\\*.dd.tgz;\\*.dd.txz;\\*.map;\\*.dmg;\\*.image;$RECYCLE.BIN;$Recycle.Bin;.AppleDB;.AppleDesktop;.AppleDouble;.com.apple.timemachine.supported;.dbfseventsd;.DocumentRevisions-V100*;.DS_Store;.fseventsd;.PKInstallSandboxManager;.Spotlight*;.SymAV*;.symSchedScanLockxz;.TemporaryItems;.Trash*;.vol;.VolumeIcon.icns;desktop.ini;Desktop?DB;Desktop?DF;hiberfil.sys;lost+found;Network?Trash?Folder;pagefile.sys;Recycled;RECYCLER;System?Volume?Information;Temporary?Items;Thumbs.db'] -vars_wk['Notepad2'] = '{BinDir}\\Notepad2\\Notepad2-Mod.exe'.format(**vars_wk) -vars_wk['wimlib-imagex'] = '{BinDir}\\wimlib\\x32\\wimlib-imagex.exe'.format(**vars_wk) -if vars_wk['Arch'] == 64: - vars_wk['FastCopy'] = vars_wk['FastCopy'].replace('FastCopy.exe', 'FastCopy64.exe') - vars_wk['Notepad2'] = vars_wk['Notepad2'].replace('Notepad2-Mod.exe', 'Notepad2-Mod64.exe') - vars_wk['wimlib-imagex'] = vars_wk['wimlib-imagex'].replace('x32', 'x64') -re_included_root_items = re.compile(r'^\\(AdwCleaner|(My\s*|)(Doc(uments?( and Settings|)|s?)|Downloads|WK(-?Info|-?Transfer|)|Media|Music|Pic(ture|)s?|Vid(eo|)s?)|(ProgramData|Recovery|Temp.*|Users)$|.*\.(log|txt|rtf|qb\w*|avi|m4a|m4v|mp4|mkv|jpg|png|tiff?)$)', flags=re.IGNORECASE) -re_excluded_root_items = re.compile(r'^\\(boot(mgr|nxt)$|(eula|globdata|install|vc_?red)|.*.sys$|System Volume Information|RECYCLER|\$Recycle\.bin|\$?Win(dows(.old|\.~BT|)$|RE_)|\$GetCurrent|PerfLogs|Program Files|.*\.(esd|swm|wim|dd|map|dmg|image)$|SYSTEM.SAV|Windows10Upgrade)', flags=re.IGNORECASE) -re_excluded_items = re.compile(r'^(\.(AppleDB|AppleDesktop|AppleDouble|com\.apple\.timemachine\.supported|dbfseventsd|DocumentRevisions-V100.*|DS_Store|fseventsd|PKInstallSandboxManager|Spotlight.*|SymAV.*|symSchedScanLockxz|TemporaryItems|Trash.*|vol|VolumeIcon\.icns)|desktop\.(ini|.*DB|.*DF)|(hiberfil|pagefile)\.sys|lost\+found|Network\.*Trash\.*Folder|Recycle[dr]|System\.*Volume\.*Information|Temporary\.*Items|Thumbs\.db)$', flags=re.IGNORECASE) -wim_included_extra_items = [ - 'AdwCleaner\\*log', - 'AdwCleaner\\*txt', - '\\Windows.old*\\Doc*', - '\\Windows.old*\\Download*', - '\\Windows.old*\\WK*', - '\\Windows.old*\\Media*', - '\\Windows.old*\\Music*', - '\\Windows.old*\\Pic*', - '\\Windows.old*\\ProgramData', - '\\Windows.old*\\Recovery', - '\\Windows.old*\\Temp*', - '\\Windows.old*\\Users', - '\\Windows.old*\\Vid*', - '\\Windows.old*\\Windows\\System32\\OEM', - '\\Windows.old*\\Windows\\System32\\config', - '\\Windows\\System32\\OEM', - '\\Windows\\System32\\config'] +init_global_vars() +set_global_vars(LogFile='{LogDir}\\Data 1.log'.format(**global_vars)) +set_global_vars(TransferDir='{ClientDir}\\Transfer'.format(**global_vars)) def abort(): - print_warning('Aborted.', vars_wk['LogFile']) - exit_script() - -def cleanup_transfer(): - """Fix permissions and walk through transfer folder (from the bottom) and remove extraneous items.""" - run_program('attrib -a -h -r -s "{TransferDir}"'.format(**vars_wk), check=False) - if os.path.exists(vars_wk['TransferDir']): - for root, dirs, files in os.walk(vars_wk['TransferDir'], topdown=False): - for name in dirs: - # Remove empty directories and junction points - try: - os.rmdir(os.path.join(root, name)) - except OSError: - pass - for name in files: - # Remove files based on exclusion regex - if re_excluded_items.search(name): - try: - os.remove(os.path.join(root, name)) - except OSError: - pass - -def exit_script(): - umount_backup_shares() - pause("Press Enter to exit...") - extract_item('Notepad2', vars_wk, silent=True) - subprocess.Popen('"{Notepad2}" "{LogFile}"'.format(**vars_wk)) - quit() - -def is_valid_image(item): - _valid = item.is_file() and re.search(r'\.wim$', item.name, flags=re.IGNORECASE) - if _valid: - try: - _cmd = [vars_wk['wimlib-imagex'], 'info', '{image}'.format(image=item.path)] - run_program(_cmd) - except subprocess.CalledProcessError: - _valid = False - print_warning('WARNING: Image "{image}" damaged.'.format(image=item.name), vars_wk['LogFile']) - time.sleep(2) - return _valid + print_warning('Aborted.') + exit_script(global_vars) def transfer_file_based(source_path, subdir=None): # Set Destination if subdir is None: - dest_path = vars_wk['TransferDir'] + dest_path = global_vars['TransferDir'] else: - dest_path = '{TransferDir}\\{subdir}'.format(subdir=subdir, **vars_wk) + dest_path = '{TransferDir}\\{subdir}'.format(subdir=subdir, **global_vars) os.makedirs(dest_path, exist_ok=True) # Main copy selected_items = [] for item in os.scandir(source_path): - if re_included_root_items.search(item.name): + if REGEX_INCL_ROOT_ITEMS.search(item.name): selected_items.append(item.path) - elif not re_excluded_root_items.search(item.name): + elif not REGEX_EXCL_ROOT_ITEMS.search(item.name): if ask('Copy: "{name}" item?'.format(name=item.name)): selected_items.append(item.path) if len(selected_items) > 0: - _args = vars_wk['FastCopyArgs'].copy() + selected_items + _args = global_vars['FastCopyArgs'].copy() + selected_items _args.append('/to={dest_path}\\'.format(dest_path=dest_path)) try: - print_standard('Copying main user data...', vars_wk['LogFile']) - run_program(vars_wk['FastCopy'], _args, check=True) + print_standard('Copying main user data...') + run_program(global_vars['FastCopy'], _args, check=True) except subprocess.CalledProcessError: - print_warning('WARNING: Errors encountered while copying main user data', vars_wk['LogFile']) + print_warning('WARNING: Errors encountered while copying main user data') else: - print_error('ERROR: No files selected for transfer?', vars_wk['LogFile']) + print_error('ERROR: No files selected for transfer?') abort() # Fonts @@ -126,13 +49,13 @@ def transfer_file_based(source_path, subdir=None): if os.path.exists('{source}\\Windows\\Fonts'.format(source=source_path)): selected_items.append('{source}\\Windows\\Fonts'.format(source=source_path)) if len(selected_items) > 0: - _args = vars_wk['FastCopyArgs'].copy() + selected_items + _args = global_vars['FastCopyArgs'].copy() + selected_items _args.append('/to={dest_path}\\Windows\\'.format(dest_path=dest_path)) try: - print_standard('Copying Fonts...', vars_wk['LogFile']) - run_program(vars_wk['FastCopy'], _args, check=True) + print_standard('Copying Fonts...') + run_program(global_vars['FastCopy'], _args, check=True) except subprocess.CalledProcessError: - print_warning('WARNING: Errors encountered while copying Fonts', vars_wk['LogFile']) + print_warning('WARNING: Errors encountered while copying Fonts') # Registry selected_items = [] @@ -141,26 +64,26 @@ def transfer_file_based(source_path, subdir=None): if os.path.exists('{source}\\Windows\\System32\\OEM'.format(source=source_path)): selected_items.append('{source}\\Windows\\System32\\OEM'.format(source=source_path)) if len(selected_items) > 0: - _args = vars_wk['FastCopyArgs'].copy() + selected_items + _args = global_vars['FastCopyArgs'].copy() + selected_items _args.append('/to={dest_path}\\Windows\\System32\\'.format(dest_path=dest_path)) try: - print_standard('Copying Registry...', vars_wk['LogFile']) - run_program(vars_wk['FastCopy'], _args, check=True) + print_standard('Copying Registry...') + run_program(global_vars['FastCopy'], _args, check=True) except subprocess.CalledProcessError: - print_warning('WARNING: Errors encountered while copying registry', vars_wk['LogFile']) + print_warning('WARNING: Errors encountered while copying registry') def transfer_image_based(source_path): - print_standard('Assessing image...', vars_wk['LogFile']) - os.makedirs(vars_wk['TransferDir'], exist_ok=True) + print_standard('Assessing image...') + os.makedirs(global_vars['TransferDir'], exist_ok=True) # Scan source _args = [ 'dir', '{source}'.format(source=source_path), '1'] try: - _list = run_program(vars_wk['wimlib-imagex'], _args, check=True) + _list = run_program(global_vars['Tools']['wimlib-imagex'], _args, check=True) except subprocess.CalledProcessError as err: - print_error('ERROR: Failed to get file list.', vars_wk['LogFile']) + print_error('ERROR: Failed to get file list.') print(err) abort() @@ -168,50 +91,50 @@ def transfer_image_based(source_path): selected_items = [] root_items = [i.strip() for i in _list.stdout.decode('utf-8', 'ignore').splitlines() if i.count('\\') == 1 and i.strip() != '\\'] for item in root_items: - if re_included_root_items.search(item): + if REGEX_INCL_ROOT_ITEMS.search(item): selected_items.append(item) - elif not re_excluded_root_items.search(item): + elif not REGEX_EXCL_ROOT_ITEMS.search(item): if ask('Extract: "{name}" item?'.format(name=item)): selected_items.append(item) # Extract files if len(selected_items) > 0: # Write files.txt - with open('{TmpDir}\\wim_files.txt'.format(**vars_wk), 'w') as f: + with open('{TmpDir}\\wim_files.txt'.format(**global_vars), 'w') as f: # Defaults - for item in wim_included_extra_items: + for item in EXTRA_INCL_WIM_ITEMS: f.write('{item}\n'.format(item=item)) for item in selected_items: f.write('{item}\n'.format(item=item)) try: - print_standard('Extracting user data...', vars_wk['LogFile']) + print_standard('Extracting user data...') _args = [ 'extract', '{source}'.format(source=source_path), '1', - '@{TmpDir}\\wim_files.txt'.format(**vars_wk), - '--dest-dir={TransferDir}\\'.format(**vars_wk), + '@{TmpDir}\\wim_files.txt'.format(**global_vars), + '--dest-dir={TransferDir}\\'.format(**global_vars), '--no-acls', '--nullglob'] - run_program(vars_wk['wimlib-imagex'], _args, check=True) + run_program(global_vars['Tools']['wimlib-imagex'], _args, check=True) except subprocess.CalledProcessError: - print_warning('WARNING: Errors encountered while extracting user data', vars_wk['LogFile']) + print_warning('WARNING: Errors encountered while extracting user data') else: - print_error('ERROR: No files selected for extraction?', vars_wk['LogFile']) + print_error('ERROR: No files selected for extraction?') abort() if __name__ == '__main__': - stay_awake(vars_wk) + stay_awake(global_vars) # Check for existing TransferDir - if os.path.exists(vars_wk['TransferDir']): - print_warning('Folder "{TransferDir}" exists. This script will rename the existing folder in order to avoid overwriting data.'.format(**vars_wk), vars_wk['LogFile']) - if (ask('Rename existing folder and proceed?', vars_wk['LogFile'])): - _old_transfer = '{TransferDir}.old'.format(**vars_wk) + if os.path.exists(global_vars['TransferDir']): + print_warning('Folder "{TransferDir}" exists. This script will rename the existing folder in order to avoid overwriting data.'.format(**global_vars)) + if (ask('Rename existing folder and proceed?')): + _old_transfer = '{TransferDir}.old'.format(**global_vars) _i = 1; while os.path.exists(_old_transfer): - _old_transfer = '{TransferDir}.old{i}'.format(i=_i, **vars_wk) + _old_transfer = '{TransferDir}.old{i}'.format(i=_i, **global_vars) _i += 1 - print_info('Renaming "{TransferDir}" to "{old_transfer}"'.format(old_transfer=_old_transfer, **vars_wk), vars_wk['LogFile']) - os.rename(vars_wk['TransferDir'], _old_transfer) + print_info('Renaming "{TransferDir}" to "{old_transfer}"'.format(old_transfer=_old_transfer, **global_vars)) + os.rename(global_vars['TransferDir'], _old_transfer) else: abort() @@ -228,7 +151,7 @@ if __name__ == '__main__': abort() # Determine restore method - extract_item('wimlib', vars_wk, silent=True) + extract_item('wimlib', global_vars, silent=True) restore_source = None restore_options = [] _file_based = False @@ -237,9 +160,9 @@ if __name__ == '__main__': _file_based = True restore_options.append({'Name': 'File-Based:\t{source}'.format(source=item.name), 'Source': item}) for _subitem in os.scandir(item.path): - if is_valid_image(_subitem): + if is_valid_wim_image(_subitem): restore_options.append({'Name': 'Image-Based: {dir}\\{source}'.format(dir=item.name, source=_subitem.name), 'Source': _subitem}) - elif is_valid_image(item): + elif is_valid_wim_image(item): restore_options.append({'Name': 'Image-Based:\t{source}'.format(source=item.name), 'Source': item}) if _file_based: restore_options.append({'Name': 'File-Based:\t.', 'Source': backup_source}) @@ -252,11 +175,11 @@ if __name__ == '__main__': else: restore_source = restore_options[int(selection)-1]['Source'] else: - print_error('ERROR: No restoration options detected.', vars_wk['LogFile']) + print_error('ERROR: No restoration options detected.') abort() # Start transfer - print_info('Using backup: {path}'.format(path=restore_source.path), vars_wk['LogFile']) + print_info('Using backup: {path}'.format(path=restore_source.path)) if restore_source.is_dir(): transfer_file_based(restore_source.path) # Check for Windows.old* @@ -268,6 +191,8 @@ if __name__ == '__main__': cleanup_transfer() # Done - print_success('Done.', vars_wk['LogFile']) - kill_process('caffeine.exe') - exit_script() + umount_backup_shares() + print_success('Done.') + run_kvrt() + pause("Press Enter to exit...") + exit_script(global_vars) diff --git a/.gitignore b/.gitignore new file mode 100644 index 00000000..63bf2c0f --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +**/__pycache__/* +.bin/tmp \ No newline at end of file diff --git a/Diagnostics/Extras/CPU-Z.cmd b/Diagnostics/Extras/NK2Edit.cmd similarity index 98% rename from Diagnostics/Extras/CPU-Z.cmd rename to Diagnostics/Extras/NK2Edit.cmd index 0c22dfe0..b02c4ec2 100644 --- a/Diagnostics/Extras/CPU-Z.cmd +++ b/Diagnostics/Extras/NK2Edit.cmd @@ -30,8 +30,8 @@ call :FindBin :: Set L_NCMD to True to stay in the native console window :: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted set L_TYPE=Program -set L_PATH=CPU-Z -set L_ITEM=cpuz.exe +set L_PATH=NK2Edit +set L_ITEM=NK2Edit.exe set L_ARGS= set L_7ZIP= set L_CHCK=True diff --git a/Diagnostics/SIV.cmd b/Diagnostics/SIV.cmd deleted file mode 100644 index ef4027b4..00000000 --- a/Diagnostics/SIV.cmd +++ /dev/null @@ -1,111 +0,0 @@ -:: Wizard Kit: Launcher Script :: -:: -:: This script works by setting env variables and then calling Launch.cmd -:: which inherits the variables. This bypasses batch file argument parsing -:: which is awful. -@echo off - -:Init -setlocal -title Wizard Kit: Launcher -call :CheckFlags %* -call :FindBin - -:DefineLaunch -:: Set L_TYPE to one of these options: -:: Console, Folder, Office, Program, PSScript, or PyScript -:: Set L_PATH to the path to the program folder -:: NOTE: Launch.cmd will test for L_PATH in the following order: -:: 1: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) -:: 2: %bin%\L_PATH -:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) -:: Set L_ITEM to one of the following: -:: 1. The filename of the item to launch -:: 2. The Office product to install -:: 3. '.' to open extracted folder -:: Set L_ARGS to include any necessary arguments (if any) -:: Set L_7ZIP to include any necessary arguments for extraction -:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered -:: Set L_ELEV to True to launch with elevated permissions -:: Set L_NCMD to True to stay in the native console window -:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted -set L_TYPE=Program -set L_PATH=SIV -set L_ITEM=SIV.exe -set L_ARGS=-LOCAL -KEYS -UNICODE -NOWIZARD -set L_7ZIP= -set L_CHCK=True -set L_ELEV= -set L_NCMD=True -set L_WAIT= - -::::::::::::::::::::::::::::::::::::::::::: -:: Do not edit anything below this line! :: -::::::::::::::::::::::::::::::::::::::::::: - -:LaunchPrep -rem Verifies the environment before launching item -if not defined bin (goto ErrorNoBin) -if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) - -:Launch -rem Calls the Launch.cmd script using the variables defined above -call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD -goto Exit - -:: Functions :: -:CheckFlags -rem Loops through all arguments to check for accepted flags -set DEBUG= -for %%f in (%*) do ( - if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") -) -@exit /b 0 - -:FindBin -rem Checks the current directory and all parents for the ".bin" folder -rem NOTE: Has not been tested for UNC paths -set bin= -pushd "%~dp0" -:FindBinInner -if exist ".bin" (goto FindBinDone) -if "%~d0\" == "%cd%" (popd & @exit /b 1) -cd .. -goto FindBinInner -:FindBinDone -set "bin=%cd%\.bin" -set "cbin=%cd%\.cbin" -popd -@exit /b 0 - -:: Errors :: -:ErrorLaunchCMD -echo. -echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? -goto Abort - -:ErrorLaunchCMDMissing -echo. -echo ERROR: Launch.cmd script not found. -goto Abort - -:ErrorNoBin -echo. -echo ERROR: ".bin" folder not found. -goto Abort - -:Abort -color 4e -echo Aborted. -echo. -echo Press any key to exit... -pause>nul -color -rem Set errorlevel to 1 by calling color incorrectly -color 00 -goto Exit - -:: Cleanup and exit :: -:Exit -endlocal -exit /b %errorlevel% \ No newline at end of file diff --git a/Drivers/Extras/SanDisk ExpressCache (Deprecated).cmd b/Drivers/Samsung NVMe Driver.cmd similarity index 98% rename from Drivers/Extras/SanDisk ExpressCache (Deprecated).cmd rename to Drivers/Samsung NVMe Driver.cmd index 3faf56f8..c99e28de 100644 --- a/Drivers/Extras/SanDisk ExpressCache (Deprecated).cmd +++ b/Drivers/Samsung NVMe Driver.cmd @@ -31,7 +31,7 @@ call :FindBin :: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted set L_TYPE=Program set L_PATH=_Drivers -set L_ITEM=SanDisk Express Cache.exe +set L_ITEM=Samsung NVMe Driver.exe set L_ARGS= set L_7ZIP= set L_CHCK=True diff --git a/Misc/PerfMonitor2.cmd b/Installers/Extras/QuickBooks/2007/QuickBooksPremier2007_R13.cmd similarity index 79% rename from Misc/PerfMonitor2.cmd rename to Installers/Extras/QuickBooks/2007/QuickBooksPremier2007_R13.cmd index c5f0e4a6..a78b7881 100644 --- a/Misc/PerfMonitor2.cmd +++ b/Installers/Extras/QuickBooks/2007/QuickBooksPremier2007_R13.cmd @@ -13,30 +13,29 @@ call :FindBin :DefineLaunch :: Set L_TYPE to one of these options: -:: Console, Folder, Office, Program, PSScript, or PyScript +:: Console +:: Office +:: Program +:: PSScript +:: PyScript :: Set L_PATH to the path to the program folder :: NOTE: Launch.cmd will test for L_PATH in the following order: -:: 1: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) -:: 2: %bin%\L_PATH -:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) -:: Set L_ITEM to one of the following: -:: 1. The filename of the item to launch -:: 2. The Office product to install -:: 3. '.' to open extracted folder +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) :: Set L_ARGS to include any necessary arguments (if any) -:: Set L_7ZIP to include any necessary arguments for extraction :: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered :: Set L_ELEV to True to launch with elevated permissions :: Set L_NCMD to True to stay in the native console window :: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted -set L_TYPE=Program -set L_PATH=PerfMonitor2 -set L_ITEM=PerfMonitor2.exe +set L_TYPE=QuickBooks +set L_PATH=2007 +set L_ITEM=QuickBooksPremier2007_R13 set L_ARGS= -set L_7ZIP= set L_CHCK=True set L_ELEV= -set L_NCMD=True +set L_NCMD= set L_WAIT= ::::::::::::::::::::::::::::::::::::::::::: @@ -108,4 +107,4 @@ goto Exit :: Cleanup and exit :: :Exit endlocal -exit /b %errorlevel% \ No newline at end of file +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2007/QuickBooksPro2007_R13.cmd b/Installers/Extras/QuickBooks/2007/QuickBooksPro2007_R13.cmd new file mode 100644 index 00000000..f34410a3 --- /dev/null +++ b/Installers/Extras/QuickBooks/2007/QuickBooksPro2007_R13.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2007 +set L_ITEM=QuickBooksPro2007_R13 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2008/QuickBooksPremier2008_R10.cmd b/Installers/Extras/QuickBooks/2008/QuickBooksPremier2008_R10.cmd new file mode 100644 index 00000000..9575fa65 --- /dev/null +++ b/Installers/Extras/QuickBooks/2008/QuickBooksPremier2008_R10.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2008 +set L_ITEM=QuickBooksPremier2008_R10 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2008/QuickBooksPro2008_R10.cmd b/Installers/Extras/QuickBooks/2008/QuickBooksPro2008_R10.cmd new file mode 100644 index 00000000..da56a9d4 --- /dev/null +++ b/Installers/Extras/QuickBooks/2008/QuickBooksPro2008_R10.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2008 +set L_ITEM=QuickBooksPro2008_R10 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2009/QuickBooksPremier2009_R13.cmd b/Installers/Extras/QuickBooks/2009/QuickBooksPremier2009_R13.cmd new file mode 100644 index 00000000..c664c738 --- /dev/null +++ b/Installers/Extras/QuickBooks/2009/QuickBooksPremier2009_R13.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2009 +set L_ITEM=QuickBooksPremier2009_R13 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2009/QuickBooksPro2009_R13.cmd b/Installers/Extras/QuickBooks/2009/QuickBooksPro2009_R13.cmd new file mode 100644 index 00000000..4cee10b0 --- /dev/null +++ b/Installers/Extras/QuickBooks/2009/QuickBooksPro2009_R13.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2009 +set L_ITEM=QuickBooksPro2009_R13 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2010/QuickBooksPremier2010_R17.cmd b/Installers/Extras/QuickBooks/2010/QuickBooksPremier2010_R17.cmd new file mode 100644 index 00000000..58b53c91 --- /dev/null +++ b/Installers/Extras/QuickBooks/2010/QuickBooksPremier2010_R17.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2010 +set L_ITEM=QuickBooksPremier2010_R17 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2010/QuickBooksPro2010_R17.cmd b/Installers/Extras/QuickBooks/2010/QuickBooksPro2010_R17.cmd new file mode 100644 index 00000000..2268dc6f --- /dev/null +++ b/Installers/Extras/QuickBooks/2010/QuickBooksPro2010_R17.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2010 +set L_ITEM=QuickBooksPro2010_R17 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2011/QuickBooksPremier2011_R14.cmd b/Installers/Extras/QuickBooks/2011/QuickBooksPremier2011_R14.cmd new file mode 100644 index 00000000..015879fc --- /dev/null +++ b/Installers/Extras/QuickBooks/2011/QuickBooksPremier2011_R14.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2011 +set L_ITEM=QuickBooksPremier2011_R14 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2011/QuickBooksPro2011_R14.cmd b/Installers/Extras/QuickBooks/2011/QuickBooksPro2011_R14.cmd new file mode 100644 index 00000000..03b15b58 --- /dev/null +++ b/Installers/Extras/QuickBooks/2011/QuickBooksPro2011_R14.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2011 +set L_ITEM=QuickBooksPro2011_R14 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2012/QuickBooksPremier2012_R16.cmd b/Installers/Extras/QuickBooks/2012/QuickBooksPremier2012_R16.cmd new file mode 100644 index 00000000..6558fc11 --- /dev/null +++ b/Installers/Extras/QuickBooks/2012/QuickBooksPremier2012_R16.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2012 +set L_ITEM=QuickBooksPremier2012_R16 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2012/QuickBooksPro2012_R16.cmd b/Installers/Extras/QuickBooks/2012/QuickBooksPro2012_R16.cmd new file mode 100644 index 00000000..b3de80b0 --- /dev/null +++ b/Installers/Extras/QuickBooks/2012/QuickBooksPro2012_R16.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2012 +set L_ITEM=QuickBooksPro2012_R16 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2013/QuickBooksPremier2013_R18.cmd b/Installers/Extras/QuickBooks/2013/QuickBooksPremier2013_R18.cmd new file mode 100644 index 00000000..f04a13a8 --- /dev/null +++ b/Installers/Extras/QuickBooks/2013/QuickBooksPremier2013_R18.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2013 +set L_ITEM=QuickBooksPremier2013_R18 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2013/QuickBooksPro2013_R18.cmd b/Installers/Extras/QuickBooks/2013/QuickBooksPro2013_R18.cmd new file mode 100644 index 00000000..4283277e --- /dev/null +++ b/Installers/Extras/QuickBooks/2013/QuickBooksPro2013_R18.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2013 +set L_ITEM=QuickBooksPro2013_R18 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2014/QuickBooksPremier2014_R15.cmd b/Installers/Extras/QuickBooks/2014/QuickBooksPremier2014_R15.cmd new file mode 100644 index 00000000..a254b15f --- /dev/null +++ b/Installers/Extras/QuickBooks/2014/QuickBooksPremier2014_R15.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2014 +set L_ITEM=QuickBooksPremier2014_R15 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2014/QuickBooksPro2014_R15.cmd b/Installers/Extras/QuickBooks/2014/QuickBooksPro2014_R15.cmd new file mode 100644 index 00000000..617904ab --- /dev/null +++ b/Installers/Extras/QuickBooks/2014/QuickBooksPro2014_R15.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2014 +set L_ITEM=QuickBooksPro2014_R15 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2015/QuickBooksPremier2015_R13.cmd b/Installers/Extras/QuickBooks/2015/QuickBooksPremier2015_R13.cmd new file mode 100644 index 00000000..2f86c348 --- /dev/null +++ b/Installers/Extras/QuickBooks/2015/QuickBooksPremier2015_R13.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2015 +set L_ITEM=QuickBooksPremier2015_R13 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2015/QuickBooksPro2015_R13.cmd b/Installers/Extras/QuickBooks/2015/QuickBooksPro2015_R13.cmd new file mode 100644 index 00000000..65d7c555 --- /dev/null +++ b/Installers/Extras/QuickBooks/2015/QuickBooksPro2015_R13.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2015 +set L_ITEM=QuickBooksPro2015_R13 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2016/QuickBooksPremier2016_R9.cmd b/Installers/Extras/QuickBooks/2016/QuickBooksPremier2016_R9.cmd new file mode 100644 index 00000000..986f61e0 --- /dev/null +++ b/Installers/Extras/QuickBooks/2016/QuickBooksPremier2016_R9.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2016 +set L_ITEM=QuickBooksPremier2016_R9 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2016/QuickBooksPro2016_R9.cmd b/Installers/Extras/QuickBooks/2016/QuickBooksPro2016_R9.cmd new file mode 100644 index 00000000..d0f5a152 --- /dev/null +++ b/Installers/Extras/QuickBooks/2016/QuickBooksPro2016_R9.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2016 +set L_ITEM=QuickBooksPro2016_R9 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2017/QuickBooksPremier2017_R4.cmd b/Installers/Extras/QuickBooks/2017/QuickBooksPremier2017_R4.cmd new file mode 100644 index 00000000..487da248 --- /dev/null +++ b/Installers/Extras/QuickBooks/2017/QuickBooksPremier2017_R4.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2017 +set L_ITEM=QuickBooksPremier2017_R4 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/Installers/Extras/QuickBooks/2017/QuickBooksPro2017_R4.cmd b/Installers/Extras/QuickBooks/2017/QuickBooksPro2017_R4.cmd new file mode 100644 index 00000000..91ae4b82 --- /dev/null +++ b/Installers/Extras/QuickBooks/2017/QuickBooksPro2017_R4.cmd @@ -0,0 +1,110 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console +:: Office +:: Program +:: PSScript +:: PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %bin%\L_PATH +:: 2: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to the filename of the item to launch (or Office product to install) +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=QuickBooks +set L_PATH=2017 +set L_ITEM=QuickBooksPro2017_R4 +set L_ARGS= +set L_CHCK=True +set L_ELEV= +set L_NCMD= +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% diff --git a/LICENSE.txt b/LICENSE.txt index 7734ae70..7caf44d1 100644 --- a/LICENSE.txt +++ b/LICENSE.txt @@ -1,4 +1,4 @@ -Copyright (c) 2016 Alan Mason +Copyright (c) 2017 Alan Mason Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: diff --git a/Diagnostics/Extras/HWMonitor (Deprecated).cmd b/Misc/Notepad++.cmd similarity index 97% rename from Diagnostics/Extras/HWMonitor (Deprecated).cmd rename to Misc/Notepad++.cmd index b4b23375..385a08da 100644 --- a/Diagnostics/Extras/HWMonitor (Deprecated).cmd +++ b/Misc/Notepad++.cmd @@ -30,8 +30,8 @@ call :FindBin :: Set L_NCMD to True to stay in the native console window :: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted set L_TYPE=Program -set L_PATH=HWMonitor -set L_ITEM=HWMonitor.exe +set L_PATH=notepadplusplus +set L_ITEM=notepadplusplus.exe set L_ARGS= set L_7ZIP= set L_CHCK=True diff --git a/Misc/OutlookAddressBookView (as ADMIN).cmd b/Misc/OutlookAddressBookView (as ADMIN).cmd new file mode 100644 index 00000000..c46821b4 --- /dev/null +++ b/Misc/OutlookAddressBookView (as ADMIN).cmd @@ -0,0 +1,111 @@ +:: Wizard Kit: Launcher Script :: +:: +:: This script works by setting env variables and then calling Launch.cmd +:: which inherits the variables. This bypasses batch file argument parsing +:: which is awful. +@echo off + +:Init +setlocal +title Wizard Kit: Launcher +call :CheckFlags %* +call :FindBin + +:DefineLaunch +:: Set L_TYPE to one of these options: +:: Console, Folder, Office, Program, PSScript, or PyScript +:: Set L_PATH to the path to the program folder +:: NOTE: Launch.cmd will test for L_PATH in the following order: +:: 1: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) +:: 2: %bin%\L_PATH +:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) +:: Set L_ITEM to one of the following: +:: 1. The filename of the item to launch +:: 2. The Office product to install +:: 3. '.' to open extracted folder +:: Set L_ARGS to include any necessary arguments (if any) +:: Set L_7ZIP to include any necessary arguments for extraction +:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered +:: Set L_ELEV to True to launch with elevated permissions +:: Set L_NCMD to True to stay in the native console window +:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted +set L_TYPE=Program +set L_PATH=OutlookAddressBookView +set L_ITEM=OutlookAddressBookView.exe +set L_ARGS= +set L_7ZIP= +set L_CHCK=True +set L_ELEV=True +set L_NCMD=True +set L_WAIT= + +::::::::::::::::::::::::::::::::::::::::::: +:: Do not edit anything below this line! :: +::::::::::::::::::::::::::::::::::::::::::: + +:LaunchPrep +rem Verifies the environment before launching item +if not defined bin (goto ErrorNoBin) +if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) + +:Launch +rem Calls the Launch.cmd script using the variables defined above +call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD +goto Exit + +:: Functions :: +:CheckFlags +rem Loops through all arguments to check for accepted flags +set DEBUG= +for %%f in (%*) do ( + if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") +) +@exit /b 0 + +:FindBin +rem Checks the current directory and all parents for the ".bin" folder +rem NOTE: Has not been tested for UNC paths +set bin= +pushd "%~dp0" +:FindBinInner +if exist ".bin" (goto FindBinDone) +if "%~d0\" == "%cd%" (popd & @exit /b 1) +cd .. +goto FindBinInner +:FindBinDone +set "bin=%cd%\.bin" +set "cbin=%cd%\.cbin" +popd +@exit /b 0 + +:: Errors :: +:ErrorLaunchCMD +echo. +echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? +goto Abort + +:ErrorLaunchCMDMissing +echo. +echo ERROR: Launch.cmd script not found. +goto Abort + +:ErrorNoBin +echo. +echo ERROR: ".bin" folder not found. +goto Abort + +:Abort +color 4e +echo Aborted. +echo. +echo Press any key to exit... +pause>nul +color +rem Set errorlevel to 1 by calling color incorrectly +color 00 +goto Exit + +:: Cleanup and exit :: +:Exit +endlocal +exit /b %errorlevel% \ No newline at end of file diff --git a/Misc/Notepad2.cmd b/Misc/OutlookAddressBookView.cmd similarity index 97% rename from Misc/Notepad2.cmd rename to Misc/OutlookAddressBookView.cmd index 87d1e0b2..fa113586 100644 --- a/Misc/Notepad2.cmd +++ b/Misc/OutlookAddressBookView.cmd @@ -30,8 +30,8 @@ call :FindBin :: Set L_NCMD to True to stay in the native console window :: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted set L_TYPE=Program -set L_PATH=Notepad2 -set L_ITEM=Notepad2-Mod.exe +set L_PATH=OutlookAddressBookView +set L_ITEM=OutlookAddressBookView.exe set L_ARGS= set L_7ZIP= set L_CHCK=True diff --git a/README.md b/README.md index 0179c68d..b3a3f94f 100644 --- a/README.md +++ b/README.md @@ -1,3 +1,3 @@ # README -A collection of scripts to help a technician service Windows systems. +A collection of scripts to help technicians service Windows systems. diff --git a/Repairs/SAS (Deprecated).cmd b/Repairs/SAS (Deprecated).cmd deleted file mode 100644 index 6992d70c..00000000 --- a/Repairs/SAS (Deprecated).cmd +++ /dev/null @@ -1,114 +0,0 @@ -:: Wizard Kit: Launcher Script :: -:: -:: This script works by setting env variables and then calling Launch.cmd -:: which inherits the variables. This bypasses batch file argument parsing -:: which is awful. -@echo off - -:Init -setlocal -title Wizard Kit: Launcher -call :CheckFlags %* -call :FindBin - -:InstallOrUpdate -start "" /wait "%bin%\..\Installers\Extras\Security\SUPERAntiSpyware.exe" - -:DefineLaunch -:: Set L_TYPE to one of these options: -:: Console, Folder, Office, Program, PSScript, or PyScript -:: Set L_PATH to the path to the program folder -:: NOTE: Launch.cmd will test for L_PATH in the following order: -:: 1: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) -:: 2: %bin%\L_PATH -:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) -:: Set L_ITEM to one of the following: -:: 1. The filename of the item to launch -:: 2. The Office product to install -:: 3. '.' to open extracted folder -:: Set L_ARGS to include any necessary arguments (if any) -:: Set L_7ZIP to include any necessary arguments for extraction -:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered -:: Set L_ELEV to True to launch with elevated permissions -:: Set L_NCMD to True to stay in the native console window -:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted -set L_TYPE=Program -set L_PATH=%programfiles%\SUPERAntiSpyware -set L_ITEM=SUPERAntiSpyware.exe -set L_ARGS= -set L_7ZIP= -set L_CHCK=True -set L_ELEV= -set L_NCMD=True -set L_WAIT= - -::::::::::::::::::::::::::::::::::::::::::: -:: Do not edit anything below this line! :: -::::::::::::::::::::::::::::::::::::::::::: - -:LaunchPrep -rem Verifies the environment before launching item -if not defined bin (goto ErrorNoBin) -if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) - -:Launch -rem Calls the Launch.cmd script using the variables defined above -call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD -goto Exit - -:: Functions :: -:CheckFlags -rem Loops through all arguments to check for accepted flags -set DEBUG= -for %%f in (%*) do ( - if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") -) -@exit /b 0 - -:FindBin -rem Checks the current directory and all parents for the ".bin" folder -rem NOTE: Has not been tested for UNC paths -set bin= -pushd "%~dp0" -:FindBinInner -if exist ".bin" (goto FindBinDone) -if "%~d0\" == "%cd%" (popd & @exit /b 1) -cd .. -goto FindBinInner -:FindBinDone -set "bin=%cd%\.bin" -set "cbin=%cd%\.cbin" -popd -@exit /b 0 - -:: Errors :: -:ErrorLaunchCMD -echo. -echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? -goto Abort - -:ErrorLaunchCMDMissing -echo. -echo ERROR: Launch.cmd script not found. -goto Abort - -:ErrorNoBin -echo. -echo ERROR: ".bin" folder not found. -goto Abort - -:Abort -color 4e -echo Aborted. -echo. -echo Press any key to exit... -pause>nul -color -rem Set errorlevel to 1 by calling color incorrectly -color 00 -goto Exit - -:: Cleanup and exit :: -:Exit -endlocal -exit /b %errorlevel% \ No newline at end of file diff --git a/Repairs/Shortcut Cleaner.cmd b/Repairs/Shortcut Cleaner.cmd deleted file mode 100644 index 0d30f88a..00000000 --- a/Repairs/Shortcut Cleaner.cmd +++ /dev/null @@ -1,111 +0,0 @@ -:: Wizard Kit: Launcher Script :: -:: -:: This script works by setting env variables and then calling Launch.cmd -:: which inherits the variables. This bypasses batch file argument parsing -:: which is awful. -@echo off - -:Init -setlocal -title Wizard Kit: Launcher -call :CheckFlags %* -call :FindBin - -:DefineLaunch -:: Set L_TYPE to one of these options: -:: Console, Folder, Office, Program, PSScript, or PyScript -:: Set L_PATH to the path to the program folder -:: NOTE: Launch.cmd will test for L_PATH in the following order: -:: 1: %cbin%\L_PATH.7z (which will be extracted to %bin%\L_PATH) -:: 2: %bin%\L_PATH -:: 3. %L_PATH% (i.e. treat L_PATH as an absolute path) -:: Set L_ITEM to one of the following: -:: 1. The filename of the item to launch -:: 2. The Office product to install -:: 3. '.' to open extracted folder -:: Set L_ARGS to include any necessary arguments (if any) -:: Set L_7ZIP to include any necessary arguments for extraction -:: Set L_CHCK to True to have Launch.cmd to stay open if an error is encountered -:: Set L_ELEV to True to launch with elevated permissions -:: Set L_NCMD to True to stay in the native console window -:: Set L_WAIT to True to have the script wait until L_ITEM has comlpeted -set L_TYPE=Program -set L_PATH=Shortcut Cleaner -set L_ITEM=Shortcut Cleaner.exe -set L_ARGS= -set L_7ZIP= -set L_CHCK=True -set L_ELEV= -set L_NCMD=True -set L_WAIT= - -::::::::::::::::::::::::::::::::::::::::::: -:: Do not edit anything below this line! :: -::::::::::::::::::::::::::::::::::::::::::: - -:LaunchPrep -rem Verifies the environment before launching item -if not defined bin (goto ErrorNoBin) -if not exist "%bin%\Scripts\Launch.cmd" (goto ErrorLaunchCMDMissing) - -:Launch -rem Calls the Launch.cmd script using the variables defined above -call "%bin%\Scripts\Launch.cmd" || goto ErrorLaunchCMD -goto Exit - -:: Functions :: -:CheckFlags -rem Loops through all arguments to check for accepted flags -set DEBUG= -for %%f in (%*) do ( - if /i "%%f" == "/DEBUG" (@echo on & set "DEBUG=/DEBUG") -) -@exit /b 0 - -:FindBin -rem Checks the current directory and all parents for the ".bin" folder -rem NOTE: Has not been tested for UNC paths -set bin= -pushd "%~dp0" -:FindBinInner -if exist ".bin" (goto FindBinDone) -if "%~d0\" == "%cd%" (popd & @exit /b 1) -cd .. -goto FindBinInner -:FindBinDone -set "bin=%cd%\.bin" -set "cbin=%cd%\.cbin" -popd -@exit /b 0 - -:: Errors :: -:ErrorLaunchCMD -echo. -echo ERROR: Launch.cmd did not run correctly. Try using the /DEBUG flag? -goto Abort - -:ErrorLaunchCMDMissing -echo. -echo ERROR: Launch.cmd script not found. -goto Abort - -:ErrorNoBin -echo. -echo ERROR: ".bin" folder not found. -goto Abort - -:Abort -color 4e -echo Aborted. -echo. -echo Press any key to exit... -pause>nul -color -rem Set errorlevel to 1 by calling color incorrectly -color 00 -goto Exit - -:: Cleanup and exit :: -:Exit -endlocal -exit /b %errorlevel% \ No newline at end of file