oliver@167: #!/bin/env python oliver@167: # -*- coding: utf-8 -*- oliver@167: oliver@167: # ------------------------------------------------------------ oliver@167: # cygwin command oliver@167: # oliver@167: # executes a cygwin command inside the opensecurity project oliver@167: # oliver@167: # Autor: Mihai Bartha, oliver@167: # Oliver Maurhart, oliver@167: # oliver@167: # Copyright (C) 2013 AIT Austrian Institute of Technology oliver@167: # AIT Austrian Institute of Technology GmbH oliver@167: # Donau-City-Strasse 1 | 1220 Vienna | Austria oliver@167: # http://www.ait.ac.at oliver@167: # oliver@167: # This program is free software; you can redistribute it and/or oliver@167: # modify it under the terms of the GNU General Public License oliver@167: # as published by the Free Software Foundation version 2. oliver@167: # oliver@167: # This program is distributed in the hope that it will be useful, oliver@167: # but WITHOUT ANY WARRANTY; without even the implied warranty of oliver@167: # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the oliver@167: # GNU General Public License for more details. oliver@167: # oliver@167: # You should have received a copy of the GNU General Public License oliver@167: # along with this program; if not, write to the Free Software oliver@167: # Foundation, Inc., 51 Franklin Street, Fifth Floor, oliver@167: # Boston, MA 02110-1301, USA. oliver@167: # ------------------------------------------------------------ oliver@167: oliver@167: oliver@167: # ------------------------------------------------------------ oliver@167: # imports oliver@167: oliver@167: import os oliver@167: import subprocess oliver@167: import sys oliver@167: import _winreg oliver@167: from subprocess import Popen, PIPE, STARTUPINFO, _subprocess oliver@167: import threading oliver@167: oliver@167: # local oliver@167: from environment import Environment oliver@167: from opensecurity_util import logger, setupLogger, OpenSecurityException oliver@167: import time oliver@167: oliver@167: oliver@167: # ------------------------------------------------------------ oliver@167: # code oliver@167: oliver@167: def once(theClass): oliver@167: """get the path to our local cygwin installment""" oliver@167: home_drive = os.path.expandvars("%HOMEDRIVE%") + os.sep oliver@167: path_hint = [ oliver@167: os.path.abspath(os.path.join(Environment('OpenSecurity').prefix_path, 'cygwin')), oliver@167: os.path.abspath(os.path.join(Environment('OpenSecurity').prefix_path, 'cygwin64')), oliver@167: os.path.abspath(os.path.join(home_drive, 'cygwin')), oliver@167: os.path.abspath(os.path.join(home_drive, 'cygwin64')) oliver@167: ] oliver@167: path_valid = [ p for p in path_hint if os.path.exists(p) ] oliver@167: oliver@167: theClass.cygwin_root = path_valid[0] oliver@167: theClass.cygwin_bin = os.path.join(theClass.cygwin_root, 'bin') + os.path.sep oliver@167: theClass.cygwin_bash = os.path.join(theClass.cygwin_bin, 'bash.exe') oliver@167: theClass.cygwin_ssh = os.path.join(theClass.cygwin_bin, 'ssh.exe') oliver@167: theClass.cygwin_scp = os.path.join(theClass.cygwin_bin, 'scp.exe') oliver@167: theClass.cygwin_x11 = os.path.join(theClass.cygwin_bin, 'XWin.exe') oliver@167: theClass.win_cmd = os.environ.get("COMSPEC", "cmd.exe") oliver@167: """get the path to the VirtualBox installation on this system""" oliver@167: theClass.vbox_root = theClass.getRegEntry('SOFTWARE\Oracle\VirtualBox', 'InstallDir')[0] oliver@167: theClass.vbox_man = os.path.join(theClass.vbox_root, 'VBoxManage.exe') oliver@167: #theClass.user_home = os.path.expanduser("~") oliver@167: theClass.user_home = os.environ['APPDATA']#os.path.expandvars("%APPDATA%") oliver@167: return theClass oliver@167: oliver@167: oliver@167: @once oliver@167: class Cygwin(object): oliver@167: cygwin_root = '' oliver@167: cygwin_bin = '' oliver@167: cygwin_bash = '' oliver@167: cygwin_ssh = '' oliver@167: cygwin_x11 = '' oliver@167: cygwin_scp = '' oliver@167: vbox_root = '' oliver@167: vbox_man = '' oliver@167: win_cmd = '' oliver@167: user_home = '' oliver@167: """Some nifty methods working with Cygwin""" oliver@167: oliver@167: def __call__(self, command, arguments, wait_return=True, window = False): oliver@167: """make an instance of this object act as a function""" oliver@167: return self.execute(command, arguments, wait_return, window) oliver@167: oliver@167: @staticmethod oliver@167: def getRegEntry(key, value): oliver@167: try: oliver@167: k = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE, key) oliver@167: value = _winreg.QueryValueEx(k, value) oliver@167: _winreg.CloseKey(k) oliver@167: return value oliver@167: except: oliver@167: pass oliver@167: oliver@167: oliver@167: @staticmethod oliver@167: def root(): oliver@167: return Cygwin.cygwin_root oliver@167: oliver@167: @staticmethod oliver@167: def bin(): oliver@167: return Cygwin.cygwin_bin oliver@167: oliver@167: @staticmethod oliver@167: def bash(): oliver@167: return Cygwin.cygwin_bash oliver@167: oliver@167: @staticmethod oliver@167: def ssh(): oliver@167: return Cygwin.cygwin_ssh oliver@167: oliver@167: @staticmethod oliver@167: def scp(): oliver@167: return Cygwin.cygwin_scp oliver@167: oliver@167: @staticmethod oliver@167: def x11(): oliver@167: return Cygwin.cygwin_x11 oliver@167: oliver@167: @staticmethod oliver@167: def vboxman(): oliver@167: return Cygwin.vbox_man oliver@167: oliver@167: @staticmethod oliver@167: def cmd(): oliver@167: return Cygwin.win_cmd oliver@167: oliver@167: @staticmethod oliver@167: def home(): oliver@167: return Cygwin.user_home oliver@167: oliver@167: executeLock = threading.Lock() oliver@167: #executes command on host system oliver@167: @staticmethod oliver@167: def execute(program, arguments, wait_return=True, window = False, stdin = PIPE, stdout = PIPE, stderr = PIPE): oliver@167: _startupinfo = STARTUPINFO() oliver@167: if not window: oliver@167: _startupinfo.dwFlags |= _subprocess.STARTF_USESHOWWINDOW oliver@167: _startupinfo.wShowWindow = _subprocess.SW_HIDE oliver@167: #logger.debug('trying to launch: ' + program + ' ' + ''.join(arguments)) oliver@167: oliver@167: result, res_stdout, res_stderr = None, None, None oliver@167: oliver@167: try: oliver@167: # quote the executable otherwise we run into troubles oliver@167: # when the path contains spaces and additonal arguments oliver@167: # are presented as well. oliver@167: # special: invoking bash as login shell here with oliver@167: # an unquoted command does not execute /etc/profile oliver@167: args = '"' + program + '" ' + arguments oliver@167: process = Popen(args, startupinfo = _startupinfo, stdin = stdin, stdout = stdout, stderr = stderr, shell = False) oliver@167: logger.debug('Launched: ' + program + ' ' + ''.join(arguments)) oliver@167: if not wait_return: oliver@167: return [0, 'working in background', ''] oliver@167: oliver@167: res_stdout, res_stderr = process.communicate() oliver@167: result = process.returncode oliver@167: oliver@167: #result = process.wait() oliver@167: #res_stdout = process.stdout.read(); oliver@167: #res_stderr = process.stderr.read(); oliver@167: oliver@167: except Exception as ex: oliver@167: res_stderr = ''.join(str(ex.args)) oliver@167: result = 1 oliver@167: oliver@167: return result, res_stdout, res_stderr oliver@167: oliver@167: @staticmethod oliver@167: def vboxExecute(command, wait_return=True, window = False, bash_opts=''): oliver@167: retry = 0 oliver@167: result = None oliver@167: while retry < 3: oliver@167: if Cygwin.executeLock.acquire(True): oliver@167: result = Cygwin.execute(Cygwin.vbox_man, command, wait_return, window) oliver@167: Cygwin.executeLock.release() oliver@167: if result[0] == 0: oliver@167: return result oliver@167: retry+=1 oliver@167: return result oliver@167: oliver@167: oliver@167: @staticmethod oliver@167: def bashExecute(command, wait_return=True, window = False, bash_opts='', stdin = PIPE, stdout = PIPE, stderr = PIPE): oliver@167: # for some reason, the '-l' is ignored when started via python oliver@167: # so the same behavior is triggered by calling /etc/profile oliver@167: # directly oliver@167: command = bash_opts + ' -l -c "' + command + '"' oliver@167: return Cygwin.execute(Cygwin.cygwin_bash, command, wait_return, window, stdin = stdin, stdout = stdout, stderr = stderr) oliver@167: oliver@167: @staticmethod oliver@167: def cmdExecute(command, wait_return=True, window = False): oliver@167: command = ' /c ' + command oliver@167: return Cygwin.execute(Cygwin.win_cmd, command, wait_return, window) oliver@167: oliver@167: # executes command over ssh on guest vm oliver@167: @staticmethod oliver@167: def sshExecute(command, address, user_name, certificate, wait_return=True, window = False): oliver@167: command = ' -v -o StrictHostKeyChecking=no -i "' + certificate + '" ' + user_name + '@' + address + ' ' + command oliver@167: return Cygwin.execute(Cygwin.cygwin_ssh, command, wait_return, window) oliver@167: oliver@167: # executes command over ssh on guest vm oliver@167: @staticmethod oliver@167: def sshBackgroundExecute(command, address, user_name, certificate, wait_return=True, window = False): oliver@167: command = ' -f -v -o StrictHostKeyChecking=no -i "' + certificate + '" ' + user_name + '@' + address + ' ' + command oliver@167: return Cygwin.execute(Cygwin.cygwin_ssh, command, wait_return, window) oliver@167: oliver@167: #machineFolder + '/' + vm_name + '/dvm_key oliver@167: #address = self.getHostOnlyIP(vm_name) oliver@167: #machineFolder = self.getDefaultMachineFolder() oliver@167: #machineFolder = Cygwin.cygwinPath(machineFolder) oliver@167: oliver@167: # executes command over ssh on guest vm with X forwarding oliver@167: @staticmethod oliver@167: def sshExecuteX11(command, address, user_name, certificate, wait_return=True): oliver@167: return Cygwin.bashExecute('DISPLAY=:0.0 ssh -Y -o StrictHostKeyChecking=no -i \\\"' + certificate +'\\\" ' + user_name + '@' + address + ' ' + command + '') oliver@167: oliver@167: @staticmethod oliver@167: def is_X11_running(): oliver@167: """check if we can connect to a X11 running instance""" oliver@167: p = Cygwin.bashExecute('xset -display :0 q', wait_return = True, window = False) oliver@167: return p[0] == 0 oliver@167: oliver@167: @staticmethod oliver@167: def start_X11(): oliver@167: """start X11 in the background (if not already running) on DISPLAY=:0 oliver@167: oliver@167: If there is already a X11 running then exit silently, calling this oliver@167: method as often as needed. oliver@167: """ oliver@167: Popen('"' + Cygwin.cygwin_x11 + '" :0 -multiwindow -resize -silent-dup-error') oliver@167: return (0, None, None) oliver@167: oliver@167: @staticmethod oliver@167: def cygPath(path): oliver@167: cmd = 'cygpath -u \'' + path + '\'' oliver@167: return Cygwin.bashExecute(cmd)[1].rstrip('\n') oliver@167: oliver@167: @staticmethod oliver@167: def checkResult(result): oliver@167: if result[0] != 0: oliver@167: logger.error('Command failed:' + ''.join(result[2])) oliver@167: raise OpenSecurityException('Command failed:' + ''.join(result[2])) oliver@167: return result oliver@167: oliver@167: # start oliver@167: import os oliver@167: import win32api oliver@167: import win32con oliver@167: import win32security oliver@167: oliver@167: if __name__ == "__main__": oliver@167: logger = setupLogger('Cygwin') oliver@167: c = Cygwin() oliver@167: #logger.info(c.root()) oliver@167: #logger.info(c.bin()) oliver@167: #logger.info(c.bash()) oliver@167: #logger.info(c.ssh()) oliver@167: #logger.info(c.x11()) oliver@167: #logger.info(c.home()) oliver@167: oliver@167: #PSEXEC -i -s -d CMD oliver@167: #tasklist /v /fo list /fi "IMAGENAME eq explorer.exe" oliver@167: oliver@167: #runner = XRunner() oliver@167: #runner.start() oliver@167: oliver@167: #Cygwin.start_X11() oliver@167: oliver@167: oliver@167: oliver@167: #time.sleep(500) oliver@167: oliver@167: #Cygwin.start_X11() oliver@167: #print (Cygwin.is_X11_running()) oliver@167: #print (Cygwin.is_X11_running()) oliver@167: #new_sdvm = 'SecurityDVM0' oliver@167: #new_ip = Cygwin.vboxExecute('guestproperty get ' + new_sdvm + ' /VirtualBox/GuestInfo/Net/0/V4/IP')[1] oliver@167: #new_ip = new_ip[new_ip.index(':')+1:].strip() oliver@167: #new_ip = '+' oliver@167: #result = Cygwin.bashExecute('DISPLAY=:0.0 xhost '+new_ip) oliver@167: #browser = '/usr/bin/midori ' oliver@167: #print(Cygwin.sshExecuteX11(browser, new_ip, 'osecuser', '/cygdrive/c/Users/BarthaM/VirtualBox VMs' + '/' + new_sdvm + '/dvm_key')) oliver@167: oliver@167: #print(Cygwin.bashExecute('echo $PATH')[1]) oliver@167: #print(Cygwin.cygPath('C:')) oliver@167: #print('C:\\Program Files\\OpenSecurity: ' + c.cygPath('C:\\Program Files\\OpenSecurity')) oliver@167: oliver@167: sys.exit(0) oliver@167: