1.1 --- a/OpenSecurity.iss Mon Mar 03 15:05:17 2014 +0100
1.2 +++ b/OpenSecurity.iss Tue Mar 04 16:54:51 2014 +0100
1.3 @@ -8,12 +8,12 @@
1.4 AppContact=AIT Austrian Institute of Technology
1.5 AppPublisher=AIT Austrian Institute of Technology
1.6 AppPublisherURL=http://www.ait.ac.at/
1.7 -AppVersion=0.1
1.8 +AppVersion=0.2
1.9 ArchitecturesInstallIn64BitMode=x64
1.10 DefaultDirName={pf}\OpenSecurity
1.11 DefaultGroupName=OpenSecurity
1.12 OutputDir="."
1.13 -OutputBaseFilename="OpenSecurity Setup V0.1"
1.14 +OutputBaseFilename="OpenSecurity Setup V0.2"
1.15 OutputManifestFile=OpenSecurity-Setup-Manifest.txt
1.16 SetupIconFile=OpenSecurity\gfx\OpenSecurity.ico
1.17 SolidCompression=yes
1.18 @@ -33,23 +33,27 @@
1.19
1.20 [Registry]
1.21 ; Registry entries to set
1.22 -;Root: HKCU; Subkey: "SOFTWARE\Microsoft\Windows\CurrentVersion\Run"; ValueName: "OpenSecurity Daemon"; ValueType: string; ValueData: "{app}\python27\pythonw.exe ""{app}\bin\opensecurityd.pyw"""; Flags: uninsdeletevalue
1.23 Root: HKCU; Subkey: "SOFTWARE\Microsoft\Windows\CurrentVersion\Run"; ValueName: "OpenSecurity Tray Icon"; ValueType: string; ValueData: "{app}\python27\pythonw.exe ""{app}\bin\opensecurity_tray.pyw"""; Flags: uninsdeletevalue
1.24
1.25 [Icons]
1.26 ; Program Icons in start menu
1.27 Name: "{group}\OpenSecurity Initial VM"; Filename: "{app}\python27\pythonw.exe"; Parameters: """{app}\bin\download-image.pyw"""; WorkingDir: "{app}"; Comment: "Download and install the initial OpenSecurity VM image"; IconFilename: "{app}\gfx\OpenSecurity.ico"
1.28 Name: "{group}\OpenSecurity Tray Icon"; Filename: "{app}\python27\pythonw.exe"; Parameters: """{app}\bin\opensecurity_tray.pyw"""; WorkingDir: "{userappdata}"; Comment: "The OpenSecurity Tray Icon"; IconFilename: "{app}\gfx\OpenSecurity.ico"
1.29 -;Name: "{group}\OpenSecurity Server"; Filename: "{app}\python27\pythonw.exe"; Parameters: """{app}\bin\opensecurityd.pyw"""; WorkingDir: "{userappdata}"; Comment: "The OpenSecurity VM System Orchestrating Server"; IconFilename: "{app}\gfx\OpenSecurity.ico"
1.30 -;Name: "{group}\Initial VM import"; Filename: "{app}\install\initial_vm.bat"; WorkingDir: "{userappdata}"; Comment: "The OpenSecurity VM System Orchestrating Server"; IconFilename: "{app}\gfx\OpenSecurity.ico"
1.31 +Name: "{group}\Initial VM import"; Filename: "{app}\cygwin64\bin\bash.exe"; Parameters: "-i -l /OpenSecurity/install/initial_vm.sh"; WorkingDir: "{app}"; Comment: "Import the initial OpenSecurity VM"; IconFilename: "{app}\gfx\OpenSecurity.ico"
1.32 Name: "{group}\Uninstall OpenSecurity"; Filename: "{uninstallexe}"
1.33
1.34 [Run]
1.35 ; Run after installment
1.36 Filename: "{app}\cygwin64\bin\dash.exe"; Parameters: "/bin/rebaseall"; Description: "Rebasing background system"; WorkingDir: "{app}"; StatusMsg: "Rebasing background system..."; Flags: runascurrentuser
1.37 Filename: "{app}\install\fix_cygwin_paths.bat"; Description: "Fixing Cygwin paths"; WorkingDir: "{app}\install"; StatusMsg: "Fixing Cygwin Paths..";
1.38 -;Filename: "{app}\install\initial_vm.bat"; Description: "Loading initial VM"; WorkingDir: "{app}\install"; StatusMsg: "Setting up initial VM..."; Flags: runasoriginaluser
1.39 -Filename: "{app}\python27\pythonw.exe"; Parameters: "{app}\bin\opensecurity_service.pyw install"; Description: "Installing the OpenSecurity Service"; WorkingDir: "{app}"; StatusMsg: "Installing the OpenSecurity Service";
1.40 +Filename: "{app}\python27\pythonw.exe"; Parameters: """{app}\bin\opensecurity_service.pyw"" --startup auto install"; Description: "Installing the OpenSecurity Service"; WorkingDir: "{app}"; StatusMsg: "Installing the OpenSecurity Service"; Flags: runascurrentuser
1.41 +Filename: "{app}\python27\pythonw.exe"; Parameters: """{app}\bin\download-image.pyw"""; WorkingDir: "{app}"; Description: "Download and install the initial OpenSecurity VM image"; Flags: postinstall runascurrentuser
1.42 +Filename: "{app}\cygwin64\bin\bash.exe"; Parameters: "-i -l /OpenSecurity/install/initial_vm.sh"; WorkingDir: "{app}"; Description: "Import the initial OpenSecurity VM"; Flags: postinstall runascurrentuser
1.43 +
1.44 +[UninstallRun]
1.45 +; When uninstalling run this command prior
1.46 +Filename: "{app}\python27\pythonw.exe"; Parameters: """{app}\bin\opensecurity_service.pyw"" stop"; WorkingDir: "{app}"; StatusMsg: "Stopping the OpenSecurity Service"; Flags: runascurrentuser
1.47 +Filename: "{app}\python27\pythonw.exe"; Parameters: """{app}\bin\opensecurity_service.pyw"" remove"; WorkingDir: "{app}"; StatusMsg: "Removing the OpenSecurity Service"; Flags: runascurrentuser
1.48
1.49 [UninstallDelete]
1.50 Type: filesandordirs; Name: "{app}"
2.1 --- a/OpenSecurity/bin/cygwin.py Mon Mar 03 15:05:17 2014 +0100
2.2 +++ b/OpenSecurity/bin/cygwin.py Tue Mar 04 16:54:51 2014 +0100
2.3 @@ -1,229 +1,229 @@
2.4 -#!/bin/env python
2.5 -# -*- coding: utf-8 -*-
2.6 -
2.7 -# ------------------------------------------------------------
2.8 -# cygwin command
2.9 -#
2.10 -# executes a cygwin command inside the opensecurity project
2.11 -#
2.12 -# Autor: Mihai Bartha, <mihai.bartha@ait.ac.at>
2.13 -# Oliver Maurhart, <oliver.maurhart@ait.ac.at>
2.14 -#
2.15 -# Copyright (C) 2013 AIT Austrian Institute of Technology
2.16 -# AIT Austrian Institute of Technology GmbH
2.17 -# Donau-City-Strasse 1 | 1220 Vienna | Austria
2.18 -# http://www.ait.ac.at
2.19 -#
2.20 -# This program is free software; you can redistribute it and/or
2.21 -# modify it under the terms of the GNU General Public License
2.22 -# as published by the Free Software Foundation version 2.
2.23 -#
2.24 -# This program is distributed in the hope that it will be useful,
2.25 -# but WITHOUT ANY WARRANTY; without even the implied warranty of
2.26 -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2.27 -# GNU General Public License for more details.
2.28 -#
2.29 -# You should have received a copy of the GNU General Public License
2.30 -# along with this program; if not, write to the Free Software
2.31 -# Foundation, Inc., 51 Franklin Street, Fifth Floor,
2.32 -# Boston, MA 02110-1301, USA.
2.33 -# ------------------------------------------------------------
2.34 -
2.35 -
2.36 -# ------------------------------------------------------------
2.37 -# imports
2.38 -
2.39 -import os
2.40 -import subprocess
2.41 -import sys
2.42 -import _winreg
2.43 -from subprocess import Popen, PIPE, call, STARTUPINFO, _subprocess
2.44 -import threading
2.45 -# local
2.46 -from environment import Environment
2.47 -from opensecurity_util import logger, setupLogger, OpenSecurityException
2.48 -
2.49 -# ------------------------------------------------------------
2.50 -# code
2.51 -
2.52 -def once(theClass):
2.53 - """get the path to our local cygwin installment"""
2.54 - home_drive = os.path.expandvars("%HOMEDRIVE%") + os.sep
2.55 - path_hint = [
2.56 - os.path.abspath(os.path.join(Environment('OpenSecurity').prefix_path, '..', 'cygwin')),
2.57 - os.path.abspath(os.path.join(Environment('OpenSecurity').prefix_path, '..', 'cygwin64')),
2.58 - os.path.abspath(os.path.join(home_drive, 'cygwin')),
2.59 - os.path.abspath(os.path.join(home_drive, 'cygwin64'))
2.60 - ]
2.61 - path_valid = [ p for p in path_hint if os.path.exists(p) ]
2.62 -
2.63 - theClass.cygwin_root = path_valid[0]
2.64 - theClass.cygwin_bin = os.path.join(theClass.cygwin_root, 'bin') + os.path.sep
2.65 - theClass.cygwin_bash = os.path.join(theClass.cygwin_bin, 'bash.exe')
2.66 - theClass.cygwin_ssh = os.path.join(theClass.cygwin_bin, 'ssh.exe')
2.67 - theClass.cygwin_x11 = os.path.join(theClass.cygwin_bin, 'XWin.exe')
2.68 - theClass.win_cmd = os.environ.get("COMSPEC", "cmd.exe")
2.69 -
2.70 - """get the path to the VirtualBox installation on this system"""
2.71 - try:
2.72 - k = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE, 'SOFTWARE\Oracle\VirtualBox')
2.73 - theClass.vbox_root = _winreg.QueryValueEx(k, 'InstallDir')[0]
2.74 - theClass.vbox_man = os.path.join(theClass.vbox_root, 'VBoxManage.exe')
2.75 - _winreg.CloseKey(k)
2.76 - except:
2.77 - pass
2.78 - return theClass
2.79 -
2.80 -@once
2.81 -class Cygwin(object):
2.82 - cygwin_root = ''
2.83 - cygwin_bin = ''
2.84 - cygwin_bash = ''
2.85 - cygwin_ssh = ''
2.86 - cygwin_x11 = ''
2.87 - vbox_root = ''
2.88 - vbox_man = ''
2.89 - win_cmd = ''
2.90 - """Some nifty methods working with Cygwin"""
2.91 -
2.92 - def __call__(self, command, arguments, wait_return=True, window = False):
2.93 - """make an instance of this object act as a function"""
2.94 - return self.execute(command, arguments, wait_return, window)
2.95 -
2.96 -
2.97 - @staticmethod
2.98 - def root():
2.99 - return Cygwin.cygwin_root
2.100 -
2.101 - @staticmethod
2.102 - def bin():
2.103 - return Cygwin.cygwin_bin
2.104 -
2.105 - @staticmethod
2.106 - def bash():
2.107 - return Cygwin.cygwin_bash
2.108 -
2.109 - @staticmethod
2.110 - def ssh():
2.111 - return Cygwin.cygwin_ssh
2.112 -
2.113 - @staticmethod
2.114 - def x11():
2.115 - return Cygwin.cygwin_x11
2.116 -
2.117 - @staticmethod
2.118 - def vboxman():
2.119 - return Cygwin.vbox_man
2.120 -
2.121 - @staticmethod
2.122 - def cmd():
2.123 - return Cygwin.win_cmd
2.124 -
2.125 - executeLock = threading.Lock()
2.126 - #executes command on host system
2.127 - @staticmethod
2.128 - def execute(program, arguments, wait_return=True, window = False):
2.129 - _startupinfo = STARTUPINFO()
2.130 - if not window:
2.131 - _startupinfo.dwFlags |= _subprocess.STARTF_USESHOWWINDOW
2.132 - _startupinfo.wShowWindow = _subprocess.SW_HIDE
2.133 -
2.134 - #logger.debug('trying to launch: ' + program + ' ' + ''.join(arguments))
2.135 - res_stderr = None
2.136 - try:
2.137 - process = Popen(executable=program, args=' ' + arguments, startupinfo = _startupinfo, stdin=PIPE, stdout=PIPE, stderr=PIPE, shell = False)
2.138 - logger.debug('Launched: ' + program + ' ' + ''.join(arguments))
2.139 - if not wait_return:
2.140 - return [0, 'working in background', '']
2.141 - result = process.wait()
2.142 - res_stdout = process.stdout.read();
2.143 - res_stderr = process.stderr.read();
2.144 -
2.145 - except Exception as ex:
2.146 - res_stderr = ''.join(ex.args)
2.147 - result = -1
2.148 -
2.149 - if result != 0:
2.150 - logger.error('Failed to execute cygwin command.\n\tcommand=' + program + ' ' + ''.join(arguments) + '\n' + res_stderr)
2.151 - raise OpenSecurityException('Failed to execute cygwin command.\n\tcommand=' + program + ' ' + ''.join(arguments) + '\n' + res_stderr)
2.152 -
2.153 - return result, res_stdout, res_stderr
2.154 -
2.155 - @staticmethod
2.156 - def vboxExecute(command, wait_return=True, window = False, bash_opts=''):
2.157 - if Cygwin.executeLock.acquire(True):
2.158 - retry = 0
2.159 - while retry < 3:
2.160 - try:
2.161 - result = Cygwin.execute(Cygwin.vbox_man, command, wait_return, window)
2.162 - Cygwin.executeLock.release()
2.163 - return result
2.164 - except OpenSecurityException as inst:
2.165 - retry+=1
2.166 - Cygwin.executeLock.release()
2.167 - raise inst
2.168 - return result
2.169 -
2.170 -
2.171 - @staticmethod
2.172 - def bashExecute(command, wait_return=True, window = False, bash_opts=''):
2.173 - command = bash_opts + ' -l -c ' + command
2.174 - return Cygwin.execute(Cygwin.cygwin_bash, command, wait_return, window)
2.175 -
2.176 - @staticmethod
2.177 - def cmdExecute(command, wait_return=True, window = False, bash_opts=''):
2.178 - command = ' /c ' + command
2.179 - return Cygwin.execute(Cygwin.win_cmd, command, wait_return, window)
2.180 -
2.181 - # executes command over ssh on guest vm
2.182 - @staticmethod
2.183 - def sshExecute(command, address, user_name, certificate, wait_return=True, window = False):
2.184 - command = ' -v -i "' + certificate + '" ' + user_name + '@' + address + ' ' + command
2.185 - return Cygwin.execute(Cygwin.cygwin_ssh, command, wait_return, window)
2.186 -
2.187 - #machineFolder + '/' + vm_name + '/dvm_key
2.188 - #address = self.getHostOnlyIP(vm_name)
2.189 - #machineFolder = self.getDefaultMachineFolder()
2.190 - #machineFolder = Cygwin.cygwinPath(machineFolder)
2.191 -
2.192 - # executes command over ssh on guest vm with X forwarding
2.193 - @staticmethod
2.194 - def sshExecuteX11(command, address, user_name, certificate, wait_return=True):
2.195 - return Cygwin.bashExecute('"DISPLAY=:0.0 /usr/bin/ssh -v -Y -i \\"' + certificate +'\\" ' + user_name + '@' + address + ' ' + command + '\"')
2.196 -
2.197 - @staticmethod
2.198 - def is_X11_running():
2.199 - """check if we can connect to a X11 running instance"""
2.200 - p = Cygwin.bashExecute('"DISPLAY=:0 /usr/bin/xset -q"')
2.201 - return p[0] == 0
2.202 -
2.203 -
2.204 - @staticmethod
2.205 - def start_X11():
2.206 - """start X11 in the background (if not already running) on DISPLAY=:0"""
2.207 - # do not start if already running
2.208 - if Cygwin.is_X11_running():
2.209 - return
2.210 - # launch X11 (forget output and return immediately)
2.211 - return Cygwin.execute(Cygwin.cygwin_x11, ':0 -multiwindow', wait_return = False, window = False)
2.212 -
2.213 - @staticmethod
2.214 - def cygPath(path):
2.215 - cmd = '"/usr/bin/cygpath -u \\"' + path + '\\""'
2.216 - return Cygwin.bashExecute(cmd)[1].rstrip('\n')
2.217 -
2.218 -# start
2.219 -if __name__ == "__main__":
2.220 - logger = setupLogger('Cygwin')
2.221 - c = Cygwin()
2.222 - logger.info(c.root())
2.223 - logger.info(c.bin())
2.224 - logger.info(c.bash())
2.225 - logger.info(c.ssh())
2.226 -
2.227 - c.cygPath('C:')
2.228 - c.start_X11()
2.229 -
2.230 -
2.231 -
2.232 -
2.233 +#!/bin/env python
2.234 +# -*- coding: utf-8 -*-
2.235 +
2.236 +# ------------------------------------------------------------
2.237 +# cygwin command
2.238 +#
2.239 +# executes a cygwin command inside the opensecurity project
2.240 +#
2.241 +# Autor: Mihai Bartha, <mihai.bartha@ait.ac.at>
2.242 +# Oliver Maurhart, <oliver.maurhart@ait.ac.at>
2.243 +#
2.244 +# Copyright (C) 2013 AIT Austrian Institute of Technology
2.245 +# AIT Austrian Institute of Technology GmbH
2.246 +# Donau-City-Strasse 1 | 1220 Vienna | Austria
2.247 +# http://www.ait.ac.at
2.248 +#
2.249 +# This program is free software; you can redistribute it and/or
2.250 +# modify it under the terms of the GNU General Public License
2.251 +# as published by the Free Software Foundation version 2.
2.252 +#
2.253 +# This program is distributed in the hope that it will be useful,
2.254 +# but WITHOUT ANY WARRANTY; without even the implied warranty of
2.255 +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
2.256 +# GNU General Public License for more details.
2.257 +#
2.258 +# You should have received a copy of the GNU General Public License
2.259 +# along with this program; if not, write to the Free Software
2.260 +# Foundation, Inc., 51 Franklin Street, Fifth Floor,
2.261 +# Boston, MA 02110-1301, USA.
2.262 +# ------------------------------------------------------------
2.263 +
2.264 +
2.265 +# ------------------------------------------------------------
2.266 +# imports
2.267 +
2.268 +import os
2.269 +import subprocess
2.270 +import sys
2.271 +import _winreg
2.272 +from subprocess import Popen, PIPE, call, STARTUPINFO, _subprocess
2.273 +import threading
2.274 +# local
2.275 +from environment import Environment
2.276 +from opensecurity_util import logger, setupLogger, OpenSecurityException
2.277 +
2.278 +# ------------------------------------------------------------
2.279 +# code
2.280 +
2.281 +def once(theClass):
2.282 + """get the path to our local cygwin installment"""
2.283 + home_drive = os.path.expandvars("%HOMEDRIVE%") + os.sep
2.284 + path_hint = [
2.285 + os.path.abspath(os.path.join(Environment('OpenSecurity').prefix_path, '..', 'cygwin')),
2.286 + os.path.abspath(os.path.join(Environment('OpenSecurity').prefix_path, '..', 'cygwin64')),
2.287 + os.path.abspath(os.path.join(home_drive, 'cygwin')),
2.288 + os.path.abspath(os.path.join(home_drive, 'cygwin64'))
2.289 + ]
2.290 + path_valid = [ p for p in path_hint if os.path.exists(p) ]
2.291 +
2.292 + theClass.cygwin_root = path_valid[0]
2.293 + theClass.cygwin_bin = os.path.join(theClass.cygwin_root, 'bin') + os.path.sep
2.294 + theClass.cygwin_bash = os.path.join(theClass.cygwin_bin, 'bash.exe')
2.295 + theClass.cygwin_ssh = os.path.join(theClass.cygwin_bin, 'ssh.exe')
2.296 + theClass.cygwin_x11 = os.path.join(theClass.cygwin_bin, 'XWin.exe')
2.297 + theClass.win_cmd = os.environ.get("COMSPEC", "cmd.exe")
2.298 +
2.299 + """get the path to the VirtualBox installation on this system"""
2.300 + try:
2.301 + k = _winreg.OpenKey(_winreg.HKEY_LOCAL_MACHINE, 'SOFTWARE\Oracle\VirtualBox')
2.302 + theClass.vbox_root = _winreg.QueryValueEx(k, 'InstallDir')[0]
2.303 + theClass.vbox_man = os.path.join(theClass.vbox_root, 'VBoxManage.exe')
2.304 + _winreg.CloseKey(k)
2.305 + except:
2.306 + pass
2.307 + return theClass
2.308 +
2.309 +@once
2.310 +class Cygwin(object):
2.311 + cygwin_root = ''
2.312 + cygwin_bin = ''
2.313 + cygwin_bash = ''
2.314 + cygwin_ssh = ''
2.315 + cygwin_x11 = ''
2.316 + vbox_root = ''
2.317 + vbox_man = ''
2.318 + win_cmd = ''
2.319 + """Some nifty methods working with Cygwin"""
2.320 +
2.321 + def __call__(self, command, arguments, wait_return=True, window = False):
2.322 + """make an instance of this object act as a function"""
2.323 + return self.execute(command, arguments, wait_return, window)
2.324 +
2.325 +
2.326 + @staticmethod
2.327 + def root():
2.328 + return Cygwin.cygwin_root
2.329 +
2.330 + @staticmethod
2.331 + def bin():
2.332 + return Cygwin.cygwin_bin
2.333 +
2.334 + @staticmethod
2.335 + def bash():
2.336 + return Cygwin.cygwin_bash
2.337 +
2.338 + @staticmethod
2.339 + def ssh():
2.340 + return Cygwin.cygwin_ssh
2.341 +
2.342 + @staticmethod
2.343 + def x11():
2.344 + return Cygwin.cygwin_x11
2.345 +
2.346 + @staticmethod
2.347 + def vboxman():
2.348 + return Cygwin.vbox_man
2.349 +
2.350 + @staticmethod
2.351 + def cmd():
2.352 + return Cygwin.win_cmd
2.353 +
2.354 + executeLock = threading.Lock()
2.355 + #executes command on host system
2.356 + @staticmethod
2.357 + def execute(program, arguments, wait_return=True, window = False):
2.358 + _startupinfo = STARTUPINFO()
2.359 + if not window:
2.360 + _startupinfo.dwFlags |= _subprocess.STARTF_USESHOWWINDOW
2.361 + _startupinfo.wShowWindow = _subprocess.SW_HIDE
2.362 +
2.363 + #logger.debug('trying to launch: ' + program + ' ' + ''.join(arguments))
2.364 + res_stderr = None
2.365 + try:
2.366 + process = Popen(executable=program, args=' ' + arguments, startupinfo = _startupinfo, stdin=PIPE, stdout=PIPE, stderr=PIPE, shell = False)
2.367 + logger.debug('Launched: ' + program + ' ' + ''.join(arguments))
2.368 + if not wait_return:
2.369 + return [0, 'working in background', '']
2.370 + result = process.wait()
2.371 + res_stdout = process.stdout.read();
2.372 + res_stderr = process.stderr.read();
2.373 +
2.374 + except Exception as ex:
2.375 + res_stderr = ''.join(ex.args)
2.376 + result = -1
2.377 +
2.378 + if result != 0:
2.379 + logger.error('Failed to execute cygwin command.\n\tcommand=' + program + ' ' + ''.join(arguments) + '\n' + res_stderr)
2.380 + raise OpenSecurityException('Failed to execute cygwin command.\n\tcommand=' + program + ' ' + ''.join(arguments) + '\n' + res_stderr)
2.381 +
2.382 + return result, res_stdout, res_stderr
2.383 +
2.384 + @staticmethod
2.385 + def vboxExecute(command, wait_return=True, window = False, bash_opts=''):
2.386 + if Cygwin.executeLock.acquire(True):
2.387 + retry = 0
2.388 + while retry < 3:
2.389 + try:
2.390 + result = Cygwin.execute(Cygwin.vbox_man, command, wait_return, window)
2.391 + Cygwin.executeLock.release()
2.392 + return result
2.393 + except OpenSecurityException as inst:
2.394 + retry+=1
2.395 + Cygwin.executeLock.release()
2.396 + raise inst
2.397 + return result
2.398 +
2.399 +
2.400 + @staticmethod
2.401 + def bashExecute(command, wait_return=True, window = False, bash_opts=''):
2.402 + command = bash_opts + ' -l -c ' + command
2.403 + return Cygwin.execute(Cygwin.cygwin_bash, command, wait_return, window)
2.404 +
2.405 + @staticmethod
2.406 + def cmdExecute(command, wait_return=True, window = False, bash_opts=''):
2.407 + command = ' /c ' + command
2.408 + return Cygwin.execute(Cygwin.win_cmd, command, wait_return, window)
2.409 +
2.410 + # executes command over ssh on guest vm
2.411 + @staticmethod
2.412 + def sshExecute(command, address, user_name, certificate, wait_return=True, window = False):
2.413 + command = ' -v -i "' + certificate + '" ' + user_name + '@' + address + ' ' + command
2.414 + return Cygwin.execute(Cygwin.cygwin_ssh, command, wait_return, window)
2.415 +
2.416 + #machineFolder + '/' + vm_name + '/dvm_key
2.417 + #address = self.getHostOnlyIP(vm_name)
2.418 + #machineFolder = self.getDefaultMachineFolder()
2.419 + #machineFolder = Cygwin.cygwinPath(machineFolder)
2.420 +
2.421 + # executes command over ssh on guest vm with X forwarding
2.422 + @staticmethod
2.423 + def sshExecuteX11(command, address, user_name, certificate, wait_return=True):
2.424 + return Cygwin.bashExecute('"DISPLAY=:0.0 /usr/bin/ssh -v -Y -i \\"' + certificate +'\\" ' + user_name + '@' + address + ' ' + command + '\"')
2.425 +
2.426 + @staticmethod
2.427 + def is_X11_running():
2.428 + """check if we can connect to a X11 running instance"""
2.429 + p = Cygwin.bashExecute('"DISPLAY=:0 /usr/bin/xset -q"')
2.430 + return p[0] == 0
2.431 +
2.432 +
2.433 + @staticmethod
2.434 + def start_X11():
2.435 + """start X11 in the background (if not already running) on DISPLAY=:0"""
2.436 + # do not start if already running
2.437 + if Cygwin.is_X11_running():
2.438 + return
2.439 + # launch X11 (forget output and return immediately)
2.440 + return Cygwin.execute(Cygwin.cygwin_x11, ':0 -multiwindow', wait_return = False, window = False)
2.441 +
2.442 + @staticmethod
2.443 + def cygPath(path):
2.444 + cmd = '"/usr/bin/cygpath -u \\"' + path + '\\""'
2.445 + return Cygwin.bashExecute(cmd)[1].rstrip('\n')
2.446 +
2.447 +# start
2.448 +if __name__ == "__main__":
2.449 + logger = setupLogger('Cygwin')
2.450 + c = Cygwin()
2.451 + logger.info(c.root())
2.452 + logger.info(c.bin())
2.453 + logger.info(c.bash())
2.454 + logger.info(c.ssh())
2.455 +
2.456 + c.cygPath('C:')
2.457 + c.start_X11()
2.458 +
2.459 +
2.460 +
2.461 +
3.1 --- a/OpenSecurity/bin/opensecurity_service.pyw Mon Mar 03 15:05:17 2014 +0100
3.2 +++ b/OpenSecurity/bin/opensecurity_service.pyw Tue Mar 04 16:54:51 2014 +0100
3.3 @@ -82,7 +82,7 @@
3.4
3.5 """Run the Service"""
3.6
3.7 - self.log('OpenSecurity Service stared now')
3.8 + self.log('OpenSecurity Service started now')
3.9 servicemanager.LogMsg(servicemanager.EVENTLOG_INFORMATION_TYPE,
3.10 servicemanager.PYS_SERVICE_STARTED,
3.11 (self._svc_name_, ''))
3.12 @@ -110,3 +110,4 @@
3.13 """startup"""
3.14 win32serviceutil.HandleCommandLine(OpenSecurityService)
3.15
3.16 +
4.1 --- a/OpenSecurity/bin/opensecurityd.pyw Mon Mar 03 15:05:17 2014 +0100
4.2 +++ b/OpenSecurity/bin/opensecurityd.pyw Tue Mar 04 16:54:51 2014 +0100
4.3 @@ -39,7 +39,7 @@
4.4 import web
4.5 from cygwin import Cygwin
4.6
4.7 -from vmmanager import VMManager
4.8 +import vmmanager
4.9
4.10 # local
4.11 from environment import Environment
4.12 @@ -54,8 +54,6 @@
4.13
4.14 """All the URLs we know mapping to class handler"""
4.15 opensecurity_urls = (
4.16 - #'/device_change', 'os_device_change', # http://localhost:8080/device_change GET
4.17 - #'/sdvm_started', 'os_sdvm_started', # http://localhost:8080/sdvm_started GET
4.18 '/browsing', 'os_browsing', # http://localhost:8080/browsing GET
4.19 '/sdvms', 'os_sdvms', # http://localhost:8080/sdvms GET, PUT
4.20 '/sdvms/(.*)/application/(.*)', 'os_sdvm_application', # http://localhost:8080/sdvms/[VMNAME]/application/[COMMAND] GET
4.21 @@ -65,10 +63,12 @@
4.22 '/sdvms/(.*)', 'os_sdvm', # http://localhost:8080/sdvms/[VMNAME] GET, DELETE
4.23 '/vms', 'os_vms', # http://localhost:8080/vms GET
4.24 '/vms/(.*)', 'os_vm', # http://localhost:8080/vms/[VMNAME] GET
4.25 - '/', 'os_root', # http://localhost:8080/ GET
4.26 - '/update_template', 'os_update_template' # http://localhost:8080/update_template GET
4.27 + '/update_template', 'os_update_template', # http://localhost:8080/update_template GET
4.28 + '/terminate', 'os_terminate', # http://localhost:8080/terminate GET
4.29 + '/', 'os_root' # http://localhost:8080/ GET
4.30 )
4.31
4.32 +
4.33 # ------------------------------------------------------------
4.34 # vars
4.35
4.36 @@ -80,18 +80,6 @@
4.37 # code
4.38
4.39
4.40 -#class os_device_change:
4.41 -# """OpenSecurity '/device_change' handler"""
4.42 -#
4.43 -# def GET(self):
4.44 -# log_call(web.ctx.environ)
4.45 -# try:
4.46 -# new_ip = gvm_mgr.handleDeviceChange()
4.47 -# return new_ip
4.48 -# except:
4.49 -# raise web.internalerror()
4.50 -
4.51 -
4.52 class os_browsing:
4.53 """OpenSecurity '/browsing' handler
4.54
4.55 @@ -100,21 +88,30 @@
4.56
4.57 def GET(self):
4.58 log_call(web.ctx.environ)
4.59 + global gvm_mgr
4.60 try:
4.61 - browsingVM = vmmanager().handleBrowsingRequest()
4.62 + browsingVM = gvm_mgr.handleBrowsingRequest()
4.63 return browsingVM
4.64 except:
4.65 raise web.internalerror()
4.66
4.67 -#class os_sdvm_started:
4.68 -# """OpenSecurity '/sdvm_started' handler"""
4.69 -#
4.70 -# def GET(self):
4.71 -# log_call(web.ctx.environ)
4.72 -# remote_ip = web.ctx.environ['REMOTE_ADDR']
4.73 -# gvm_mgr.putStartNotification(remote_ip)
4.74 -# return "os_sdvm_started"
4.75 -
4.76 +
4.77 +class os_root:
4.78 + """OpenSecurity '/' handler
4.79 +
4.80 + - GET: give information about current installation.
4.81 + """
4.82 +
4.83 + def GET(self):
4.84 + log_call(web.ctx.environ)
4.85 + global gvm_mgr
4.86 + res = "'os_server': { "
4.87 + res += "'version': '" + __version__ + "', "
4.88 + res += "'machine_folder': '" + gvm_mgr.getDefaultMachineFolder() + "' "
4.89 + res += "}"
4.90 + return res
4.91 +
4.92 +
4.93 class os_sdvm:
4.94 """OpenSecurity '/sdvms/[VM]' handler
4.95
4.96 @@ -124,11 +121,13 @@
4.97
4.98 def GET(self, name):
4.99 log_call(web.ctx.environ)
4.100 - return vmmanager().getVMInfo(name)
4.101 + global gvm_mgr
4.102 + return gvm_mgr.getVMInfo(name)
4.103
4.104 def DELETE(self, name):
4.105 log_call(web.ctx.environ)
4.106 - return vmmanager().removeVM(name)
4.107 + global gvm_mgr
4.108 + return gvm_mgr.removeVM(name)
4.109
4.110
4.111 class os_sdvm_application:
4.112 @@ -139,10 +138,11 @@
4.113
4.114 def GET(self, name, command):
4.115 log_call(web.ctx.environ)
4.116 + global gvm_mgr
4.117 command = '/' + command
4.118 - result = Cygwin.sshExecuteX11(command, vmmanager().getHostOnlyIP(name), 'osecuser', Cygwin.cygPath(gvm_mgr.getMachineFolder()) + '/' + name + '/dvm_key' )
4.119 + result = Cygwin.sshExecuteX11(command, gvm_mgr.getHostOnlyIP(name), 'osecuser', Cygwin.cygPath(gvm_mgr.getMachineFolder()) + '/' + name + '/dvm_key' )
4.120 self.poweroffVM(name)
4.121 - return vmmanager().removeVM(name)
4.122 + return gvm_mgr.removeVM(name)
4.123
4.124
4.125 class os_sdvm_ip:
4.126 @@ -153,7 +153,8 @@
4.127
4.128 def GET(self, name):
4.129 log_call(web.ctx.environ)
4.130 - return vmmanager().getHostOnlyIP(name)
4.131 + global gvm_mgr
4.132 + return gvm_mgr.getHostOnlyIP(name)
4.133
4.134
4.135 class os_sdvm_start:
4.136 @@ -164,7 +165,8 @@
4.137
4.138 def GET(self, name):
4.139 log_call(web.ctx.environ)
4.140 - return vmmanager().startVM(name)
4.141 + global gvm_mgr
4.142 + return gvm_mgr.startVM(name)
4.143
4.144
4.145 class os_sdvm_stop:
4.146 @@ -175,7 +177,8 @@
4.147
4.148 def GET(self, name):
4.149 log_call(web.ctx.environ)
4.150 - return vmmanager().stopVM(name)
4.151 + global gvm_mgr
4.152 + return gvm_mgr.stopVM(name)
4.153
4.154
4.155 class os_sdvms:
4.156 @@ -188,21 +191,62 @@
4.157 def GET(self):
4.158 """get the list of SDVMs"""
4.159 log_call(web.ctx.environ)
4.160 - return vmmanager().listSDVM()
4.161 + global gvm_mgr
4.162 + return gvm_mgr.listSDVM()
4.163
4.164 def POST(self):
4.165 """create a new SDVM"""
4.166 log_call(web.ctx.environ)
4.167 + global gvm_mgr
4.168
4.169 # get a new vm-name
4.170 - name = vmmanager().generateSDVMName()
4.171 + name = gvm_mgr.generateSDVMName()
4.172 try:
4.173 - vmmanager().createVM(name)
4.174 + gvm_mgr.createVM(name)
4.175 except:
4.176 raise web.internalerror()
4.177
4.178 return name
4.179
4.180 +
4.181 +class os_terminate:
4.182 + """OpenSecurity '/terminate' handler
4.183 +
4.184 + - GET: terminate the opensecurityd.
4.185 +
4.186 + YES: this here is bonkers. But the web.py http
4.187 + server runs infinite until a SystemExit exception
4.188 + or KeyboardInterrupt exception is raised.
4.189 +
4.190 + see: site-packages/web/httpserver.py - line 157ff
4.191 + see: site-packages/web/wsgiserver/__init__.py - line 1682ff
4.192 +
4.193 + So, we invoke a sys.exit(0) here to trigger server.stop().
4.194 +
4.195 + TODO: need to find a better way doing this, and not via the
4.196 + REST api. Maybe hack web.py server code?
4.197 + """
4.198 +
4.199 + def GET(self):
4.200 + log_call(web.ctx.environ)
4.201 + global gvm_mgr
4.202 + sys.exit(0)
4.203 + return None
4.204 +
4.205 +
4.206 +class os_update_template:
4.207 + """OpenSecurity '/update_template' handler
4.208 +
4.209 + - GET: update template vm
4.210 + """
4.211 +
4.212 + def GET(self):
4.213 + #return gvm_mgr.guestExecute('SecurityDVM', 'sudo apt-get -y update')
4.214 + global gvm_mgr
4.215 + log_call(web.ctx.environ)
4.216 + return gvm_mgr.updateTemplate()
4.217 +
4.218 +
4.219 class os_vm:
4.220 """OpenSecurity '/vms/[VM]' handler
4.221
4.222 @@ -211,7 +255,8 @@
4.223
4.224 def GET(self, name):
4.225 log_call(web.ctx.environ)
4.226 - return vmmanager().getVMInfo(name)
4.227 + global gvm_mgr
4.228 + return gvm_mgr.getVMInfo(name)
4.229
4.230
4.231 class os_vms:
4.232 @@ -222,35 +267,10 @@
4.233
4.234 def GET(self):
4.235 log_call(web.ctx.environ)
4.236 - return vmmanager().listVM()
4.237 + global gvm_mgr
4.238 + return gvm_mgr.listVM()
4.239
4.240
4.241 -class os_root:
4.242 - """OpenSecurity '/' handler
4.243 -
4.244 - - GET: give information about current installation.
4.245 - """
4.246 -
4.247 - def GET(self):
4.248 - log_call(web.ctx.environ)
4.249 - res = "'os_server': { "
4.250 - res += "'version': '" + __version__ + "', "
4.251 - res += "'machine_folder': '" + vmmanager().getDefaultMachineFolder() + "' "
4.252 - res += "}"
4.253 - return res
4.254 -
4.255 -class os_update_template:
4.256 - """OpenSecurity '/update_template' handler
4.257 -
4.258 - - GET: update template vm
4.259 - """
4.260 -
4.261 - def GET(self):
4.262 - #return gvm_mgr.guestExecute('SecurityDVM', 'sudo apt-get -y update')
4.263 - log_call(web.ctx.environ)
4.264 - return vmmanager().updateTemplate()
4.265 -
4.266 -
4.267 def log_call(web_environ):
4.268 """log the incoming call to the REST api"""
4.269 try:
4.270 @@ -262,16 +282,17 @@
4.271
4.272 def main():
4.273 """main startup for the opensecuirityd"""
4.274 - server = web.application(opensecurity_urls, globals())
4.275 +
4.276 + logger.debug('Starting OpenSecurity REST server')
4.277 +
4.278 + # ensure a VMManger is yet loaded
4.279 + global gvm_mgr
4.280 + gvm_mgr = vmmanager.VMManager.getInstance()
4.281 +
4.282 + server = web.application(opensecurity_urls, globals(), autoreload = False)
4.283 server.run()
4.284 -
4.285 -
4.286 -def vmmanager():
4.287 -
4.288 - """helper method to make lazy init of VMManager"""
4.289 - if gvm_mgr is None:
4.290 - gvm_mgr = VMManager.getInstance()
4.291 - return gvm_mgr
4.292 +
4.293 + logger.debug('Stopped OpenSecurity REST server')
4.294
4.295
4.296 # start
5.1 --- a/OpenSecurity/bin/vmmanager.pyw Mon Mar 03 15:05:17 2014 +0100
5.2 +++ b/OpenSecurity/bin/vmmanager.pyw Tue Mar 04 16:54:51 2014 +0100
5.3 @@ -1,598 +1,598 @@
5.4 -'''
5.5 -Created on Nov 19, 2013
5.6 -
5.7 -@author: BarthaM
5.8 -'''
5.9 -import os
5.10 -import os.path
5.11 -from subprocess import Popen, PIPE, call, STARTUPINFO, _subprocess
5.12 -import sys
5.13 -import re
5.14 -
5.15 -from cygwin import Cygwin
5.16 -from environment import Environment
5.17 -import threading
5.18 -import time
5.19 -import string
5.20 -
5.21 -import shutil
5.22 -import stat
5.23 -import tempfile
5.24 -from opensecurity_util import logger, setupLogger, OpenSecurityException
5.25 -import ctypes
5.26 -import itertools
5.27 -DEBUG = True
5.28 -
5.29 -class VMManagerException(Exception):
5.30 - def __init__(self, value):
5.31 - self.value = value
5.32 - def __str__(self):
5.33 - return repr(self.value)
5.34 -
5.35 -class USBFilter:
5.36 - vendorid = ""
5.37 - productid = ""
5.38 - revision = ""
5.39 -
5.40 - def __init__(self, vendorid, productid, revision):
5.41 - self.vendorid = vendorid.lower()
5.42 - self.productid = productid.lower()
5.43 - self.revision = revision.lower()
5.44 - return
5.45 -
5.46 - def __eq__(self, other):
5.47 - return self.vendorid == other.vendorid and self.productid == other.productid and self.revision == other.revision
5.48 -
5.49 - def __hash__(self):
5.50 - return hash(self.vendorid) ^ hash(self.productid) ^ hash(self.revision)
5.51 -
5.52 - def __repr__(self):
5.53 - return "VendorId = \'" + str(self.vendorid) + "\' ProductId = \'" + str(self.productid) + "\' Revision = \'" + str(self.revision) + "\'"
5.54 -
5.55 -class VMManager(object):
5.56 - vmRootName = "SecurityDVM"
5.57 - systemProperties = None
5.58 - _instance = None
5.59 - machineFolder = ''
5.60 - rsdHandler = None
5.61 -
5.62 - def __init__(self):
5.63 - self.systemProperties = self.getSystemProperties()
5.64 - self.machineFolder = self.systemProperties["Default machine folder"]
5.65 - self.cleanup()
5.66 - self.rsdHandler = DeviceHandler(self)
5.67 - self.rsdHandler.start()
5.68 - return
5.69 -
5.70 - @staticmethod
5.71 - def getInstance():
5.72 - if VMManager._instance == None:
5.73 - VMManager._instance = VMManager()
5.74 - return VMManager._instance
5.75 -
5.76 - def cleanup(self):
5.77 - if self.rsdHandler != None:
5.78 - self.rsdHandler.stop()
5.79 - self.rsdHandler.join()
5.80 - drives = self.getNetworkDrives()
5.81 - for drive in drives.keys():
5.82 - self.unmapNetworkDrive(drive)
5.83 - for vm in self.listSDVM():
5.84 - self.poweroffVM(vm)
5.85 - self.removeVM(vm)
5.86 -
5.87 - # return hosty system properties
5.88 - def getSystemProperties(self):
5.89 - result = Cygwin.vboxExecute('list systemproperties')
5.90 - if result[1]=='':
5.91 - return None
5.92 - props = dict((k.strip(),v.strip().strip('"')) for k,v in (line.split(':', 1) for line in result[1].strip().splitlines()))
5.93 - #logger.debug(props)
5.94 - return props
5.95 -
5.96 - # return the folder containing the guest VMs
5.97 - def getMachineFolder(self):
5.98 - return self.machineFolder
5.99 -
5.100 - # list all existing VMs registered with VBox
5.101 - def listVM(self):
5.102 - result = Cygwin.vboxExecute('list vms')[1]
5.103 - vms = list(k.strip().strip('"') for k,_ in (line.split(' ') for line in result.splitlines()))
5.104 - return vms
5.105 -
5.106 - # list running VMs
5.107 - def listRunningVMS(self):
5.108 - result = Cygwin.vboxExecute('list runningvms')[1]
5.109 - vms = list(k.strip().strip('"') for k,_ in (line.split(' ') for line in result.splitlines()))
5.110 - return vms
5.111 -
5.112 - # list existing SDVMs
5.113 - def listSDVM(self):
5.114 - vms = self.listVM()
5.115 - svdms = []
5.116 - for vm in vms:
5.117 - if vm.startswith(self.vmRootName) and vm != self.vmRootName:
5.118 - svdms.append(vm)
5.119 - return svdms
5.120 -
5.121 - # generate valid (not already existing SDVM name). necessary for creating a new VM
5.122 - def generateSDVMName(self):
5.123 - vms = self.listVM()
5.124 - for i in range(0,999):
5.125 - if(not self.vmRootName+str(i) in vms):
5.126 - return self.vmRootName+str(i)
5.127 - return ''
5.128 -
5.129 - # return the RSDs connected to the host
5.130 - def getConnectedRSDS(self):
5.131 - results = Cygwin.vboxExecute('list usbhost')[1]
5.132 - results = results.split('Host USB Devices:')[1].strip()
5.133 -
5.134 - items = list( "UUID:"+result for result in results.split('UUID:') if result != '')
5.135 - rsds = dict()
5.136 - for item in items:
5.137 - props = dict()
5.138 - for line in item.splitlines():
5.139 - if line != "":
5.140 - k,v = line[:line.index(':')].strip(), line[line.index(':')+1:].strip()
5.141 - props[k] = v
5.142 -
5.143 - if 'Product' in props.keys() and props['Product'] == 'Mass Storage':
5.144 - usb_filter = USBFilter( re.search(r"\((?P<vid>[0-9A-Fa-f]+)\)", props['VendorId']).groupdict()['vid'],
5.145 - re.search(r"\((?P<pid>[0-9A-Fa-f]+)\)", props['ProductId']).groupdict()['pid'],
5.146 - re.search(r"\((?P<rev>[0-9A-Fa-f]+)\)", props['Revision']).groupdict()['rev'] )
5.147 - rsds[props['UUID']] = usb_filter;
5.148 - logger.debug(usb_filter)
5.149 - return rsds
5.150 -
5.151 - # return the RSDs attached to all existing SDVMs
5.152 - def getAttachedRSDs(self):
5.153 - vms = self.listSDVM()
5.154 - attached_devices = dict()
5.155 - for vm in vms:
5.156 - rsd_filter = self.getUSBFilter(vm)
5.157 - if rsd_filter != None:
5.158 - attached_devices[vm] = rsd_filter
5.159 - return attached_devices
5.160 -
5.161 - # configures hostonly networking and DHCP server. requires admin rights
5.162 - def configureHostNetworking(self):
5.163 - #cmd = 'vboxmanage list hostonlyifs'
5.164 - #Cygwin.vboxExecute(cmd)
5.165 - #cmd = 'vboxmanage hostonlyif remove \"VirtualBox Host-Only Ethernet Adapter\"'
5.166 - #Cygwin.vboxExecute(cmd)
5.167 - #cmd = 'vboxmanage hostonlyif create'
5.168 - #Cygwin.vboxExecute(cmd)
5.169 - Cygwin.vboxExecute('hostonlyif ipconfig \"VirtualBox Host-Only Ethernet Adapter\" --ip 192.168.56.1 --netmask 255.255.255.0')
5.170 - #cmd = 'vboxmanage dhcpserver add'
5.171 - #Cygwin.vboxExecute(cmd)
5.172 - Cygwin.vboxExecute('dhcpserver modify --ifname \"VirtualBox Host-Only Ethernet Adapter\" --ip 192.168.56.100 --netmask 255.255.255.0 --lowerip 192.168.56.101 --upperip 192.168.56.200')
5.173 -
5.174 - #create new virtual machine instance based on template vm named SecurityDVM (\SecurityDVM\SecurityDVM.vmdk)
5.175 - def createVM(self, vm_name):
5.176 - hostonly_if = self.getHostOnlyIFs()
5.177 - Cygwin.vboxExecute('createvm --name ' + vm_name + ' --ostype Debian --register')
5.178 - Cygwin.vboxExecute('modifyvm ' + vm_name + ' --memory 512 --vram 10 --cpus 1 --usb on --usbehci on --nic1 hostonly --hostonlyadapter1 \"' + hostonly_if['Name'] + '\" --nic2 nat')
5.179 - Cygwin.vboxExecute('storagectl ' + vm_name + ' --name SATA --add sata --portcount 2')
5.180 - return
5.181 -
5.182 - # attach storage image to controller
5.183 - def storageAttach(self, vm_name):
5.184 - if self.isStorageAttached(vm_name):
5.185 - self.storageDetach(vm_name)
5.186 - Cygwin.vboxExecute('storageattach ' + vm_name + ' --storagectl SATA --port 0 --device 0 --type hdd --medium \"'+ self.machineFolder + '\SecurityDVM\SecurityDVM.vmdk\"')
5.187 - return
5.188 -
5.189 - # return true if storage is attached
5.190 - def isStorageAttached(self, vm_name):
5.191 - info = self.getVMInfo(vm_name)
5.192 - return (info['SATA-0-0']!='none')
5.193 -
5.194 - # detach storage from controller
5.195 - def storageDetach(self, vm_name):
5.196 - if self.isStorageAttached(vm_name):
5.197 - Cygwin.vboxExecute('storageattach ' + vm_name + ' --storagectl SATA --port 0 --device 0 --type hdd --medium none')
5.198 - return
5.199 -
5.200 - def changeStorageType(self, filename, storage_type):
5.201 - Cygwin.vboxExecute('modifyhd \"' + filename + '\" --type ' + storage_type)
5.202 - return
5.203 -
5.204 - # list storage snaphots for VM
5.205 - def updateTemplate(self):
5.206 - self.cleanup()
5.207 - self.poweroffVM('SecurityDVM')
5.208 - self.waitShutdown('SecurityDVM')
5.209 -
5.210 - # check for updates
5.211 - self.genCertificateISO('SecurityDVM')
5.212 - self.attachCertificateISO('SecurityDVM')
5.213 -
5.214 - self.storageDetach('SecurityDVM')
5.215 - results = Cygwin.vboxExecute('list hdds')[1]
5.216 - results = results.replace('Parent UUID', 'Parent')
5.217 - items = list( "UUID:"+result for result in results.split('UUID:') if result != '')
5.218 -
5.219 - snaps = dict()
5.220 - for item in items:
5.221 - props = dict()
5.222 - for line in item.splitlines():
5.223 - if line != "":
5.224 - k,v = line[:line.index(':')].strip(), line[line.index(':')+1:].strip()
5.225 - props[k] = v;
5.226 - snaps[props['UUID']] = props
5.227 -
5.228 -
5.229 - template_storage = self.machineFolder + '\SecurityDVM\SecurityDVM.vmdk'
5.230 -
5.231 - # find template uuid
5.232 - template_uuid = ''
5.233 - for hdd in snaps.values():
5.234 - if hdd['Location'] == template_storage:
5.235 - template_uuid = hdd['UUID']
5.236 - logger.debug('found parent uuid ' + template_uuid)
5.237 -
5.238 - # remove snapshots
5.239 - for hdd in snaps.values():
5.240 - if hdd['Parent'] == template_uuid:
5.241 - #template_uuid = hdd['UUID']
5.242 - logger.debug('removing snapshot ' + hdd['UUID'])
5.243 - results = Cygwin.vboxExecute('closemedium disk {' + hdd['UUID'] + '} --delete')[1]
5.244 - # parse result 0%...10%...20%...30%...40%...50%...60%...70%...80%...90%...100%
5.245 -
5.246 - self.changeStorageType(template_storage,'normal')
5.247 - self.storageAttach('SecurityDVM')
5.248 - self.startVM('SecurityDVM')
5.249 - self.waitStartup('SecurityDVM')
5.250 - Cygwin.sshExecute('"sudo apt-get -y update"', VMManager.getHostOnlyIP('SecurityDVM'), 'osecuser', Cygwin.cygPath(self.machineFolder) + '/' + 'SecurityDVM' + '/dvm_key' )
5.251 - Cygwin.sshExecute('"sudo apt-get -y upgrade"', VMManager.getHostOnlyIP('SecurityDVM'), 'osecuser', Cygwin.cygPath(self.machineFolder) + '/' + 'SecurityDVM' + '/dvm_key' )
5.252 - #self.stopVM('SecurityDVM')
5.253 - self.hibernateVM('SecurityDVM')
5.254 - self.waitShutdown('SecurityDVM')
5.255 - self.storageDetach('SecurityDVM')
5.256 - self.changeStorageType(template_storage,'immutable')
5.257 - self.storageAttach('SecurityDVM')
5.258 - self.rsdHandler = DeviceHandler(self)
5.259 - self.rsdHandler.start()
5.260 -
5.261 - #remove VM from the system. should be used on VMs returned by listSDVMs
5.262 - def removeVM(self, vm_name):
5.263 - logger.info('Removing ' + vm_name)
5.264 - Cygwin.vboxExecute('unregistervm ' + vm_name + ' --delete')
5.265 - machineFolder = Cygwin.cygPath(self.machineFolder)
5.266 - Cygwin.bashExecute('"/usr/bin/rm -rf ' + machineFolder + '/' + vm_name + '"')
5.267 -
5.268 - # start VM
5.269 - def startVM(self, vm_name):
5.270 - logger.info('Starting ' + vm_name)
5.271 - result = Cygwin.vboxExecute('startvm ' + vm_name + ' --type headless' )
5.272 - while not string.find(str(result), 'successfully started',):
5.273 - logger.error("Failed to start SDVM: " + vm_name + " retrying")
5.274 - time.sleep(1)
5.275 - result = Cygwin.vboxExecute('startvm ' + vm_name + ' --type headless')
5.276 - return result[0]
5.277 -
5.278 - # return wether VM is running or not
5.279 - def isVMRunning(self, vm_name):
5.280 - return vm_name in self.listRunningVMS()
5.281 -
5.282 - # stop VM
5.283 - def stopVM(self, vm_name):
5.284 - logger.info('Sending shutdown signal to ' + vm_name)
5.285 - Cygwin.sshExecute( '"sudo shutdown -h now"', VMManager.getHostOnlyIP(vm_name), 'osecuser', Cygwin.cygPath(self.machineFolder) + '/' + vm_name + '/dvm_key' )
5.286 -
5.287 - # stop VM
5.288 - def hibernateVM(self, vm_name):
5.289 - logger.info('Sending shutdown signal to ' + vm_name)
5.290 - Cygwin.sshExecute( '"sudo hibernate-disk&"', VMManager.getHostOnlyIP(vm_name), 'osecuser', Cygwin.cygPath(self.machineFolder) + '/' + vm_name + '/dvm_key', wait_return=False )
5.291 -
5.292 - # poweroff VM
5.293 - def poweroffVM(self, vm_name):
5.294 - if not self.isVMRunning(vm_name):
5.295 - return
5.296 - logger.info('Powering off ' + vm_name)
5.297 - return Cygwin.vboxExecute('controlvm ' + vm_name + ' poweroff')
5.298 -
5.299 - #list the hostonly IFs exposed by the VBox host
5.300 - @staticmethod
5.301 - def getHostOnlyIFs():
5.302 - result = Cygwin.vboxExecute('list hostonlyifs')[1]
5.303 - if result=='':
5.304 - return None
5.305 - props = dict((k.strip(),v.strip().strip('"')) for k,v in (line.split(':', 1) for line in result.strip().splitlines()))
5.306 - return props
5.307 -
5.308 - # return the hostOnly IP for a running guest or the host
5.309 - @staticmethod
5.310 - def getHostOnlyIP(vm_name):
5.311 - if vm_name == None:
5.312 - logger.info('Gettting hostOnly IP address for Host')
5.313 - return VMManager.getHostOnlyIFs()['IPAddress']
5.314 - else:
5.315 - logger.info('Gettting hostOnly IP address ' + vm_name)
5.316 - result = Cygwin.vboxExecute('guestproperty get ' + vm_name + ' /VirtualBox/GuestInfo/Net/0/V4/IP')
5.317 - if result=='':
5.318 - return None
5.319 - result = result[1]
5.320 - if result.startswith('No value set!'):
5.321 - return None
5.322 - return result[result.index(':')+1:].strip()
5.323 -
5.324 - # attach removable storage device to VM by provision of filter
5.325 - def attachRSD(self, vm_name, rsd_filter):
5.326 - return Cygwin.vboxExecute('usbfilter add 0 --target ' + vm_name + ' --name OpenSecurityRSD --vendorid ' + rsd_filter.vendorid + ' --productid ' + rsd_filter.productid + ' --revision ' + rsd_filter.revision)
5.327 -
5.328 - # detach removable storage from VM by
5.329 - def detachRSD(self, vm_name):
5.330 - return Cygwin.vboxExecute('usbfilter remove 0 --target ' + vm_name )
5.331 -
5.332 -
5.333 - # return the description set for an existing VM
5.334 - def getVMInfo(self, vm_name):
5.335 - results = Cygwin.vboxExecute('showvminfo ' + vm_name + ' --machinereadable')[1]
5.336 - props = dict((k.strip().strip('"'),v.strip().strip('"')) for k,v in (line.split('=', 1) for line in results.splitlines()))
5.337 - #logger.debug(props)
5.338 - return props
5.339 -
5.340 - # return the configured USB filter for an existing VM
5.341 - def getUSBFilter(self, vm_name):
5.342 - props = self.getVMInfo(vm_name)
5.343 - keys = set(['USBFilterVendorId1', 'USBFilterProductId1', 'USBFilterRevision1'])
5.344 - keyset = set(props.keys())
5.345 - usb_filter = None
5.346 - if keyset.issuperset(keys):
5.347 - usb_filter = USBFilter(props['USBFilterVendorId1'], props['USBFilterProductId1'], props['USBFilterRevision1'])
5.348 - return usb_filter
5.349 -
5.350 - #generates ISO containing authorized_keys for use with guest VM
5.351 - def genCertificateISO(self, vm_name):
5.352 - machineFolder = Cygwin.cygPath(self.machineFolder)
5.353 - # remove .ssh folder if exists
5.354 - cmd = '\"/usr/bin/rm -rf \\\"' + machineFolder + '/' + vm_name + '/.ssh\\\"\"'
5.355 - Cygwin.bashExecute(cmd)
5.356 - # remove .ssh folder if exists
5.357 - Cygwin.bashExecute('\"/usr/bin/rm -rf \\\"' + machineFolder + '/' + vm_name + '/dvm_key\\\"\"')
5.358 - # create .ssh folder in vm_name
5.359 - Cygwin.bashExecute('\"/usr/bin/mkdir -p \\\"' + machineFolder + '/' + vm_name + '/.ssh\\\"\"')
5.360 - # generate dvm_key pair in vm_name / .ssh
5.361 - Cygwin.bashExecute('\"/usr/bin/ssh-keygen -q -t rsa -N \\"\\" -C \\\"' + vm_name + '\\\" -f \\\"' + machineFolder + '/' + vm_name + '/.ssh/dvm_key\\\"\"')
5.362 - # move out private key
5.363 - Cygwin.bashExecute('\"/usr/bin/mv \\\"' + machineFolder + '/' + vm_name + '/.ssh/dvm_key\\\" \\\"' + machineFolder + '/' + vm_name + '\\\"')
5.364 - # set permissions for private key
5.365 - Cygwin.bashExecute('\"/usr/bin/chmod 500 \\\"' + machineFolder + '/' + vm_name + '/dvm_key\\\"\"')
5.366 - # rename public key to authorized_keys
5.367 - Cygwin.bashExecute('\"/usr/bin/mv \\\"' + machineFolder + '/' + vm_name + '/.ssh/dvm_key.pub\\\" \\\"' + machineFolder + '/' + vm_name + '/.ssh/authorized_keys\\\"')
5.368 - # set permissions for authorized_keys
5.369 - Cygwin.bashExecute('\"/usr/bin/chmod 500 \\\"' + machineFolder + '/' + vm_name + '/.ssh/authorized_keys\\\"\"')
5.370 - # generate iso image with .ssh/authorized keys
5.371 - Cygwin.bashExecute('\"/usr/bin/genisoimage -J -R -o \\\"' + machineFolder + '/' + vm_name + '/'+ vm_name + '.iso\\\" \\\"' + machineFolder + '/' + vm_name + '/.ssh\\\"\"')
5.372 -
5.373 - # attaches generated ssh public cert to guest vm
5.374 - def attachCertificateISO(self, vm_name):
5.375 - result = Cygwin.vboxExecute('storageattach ' + vm_name + ' --storagectl SATA --port 1 --device 0 --type dvddrive --mtype readonly --medium \"' + self.machineFolder + '\\' + vm_name + '\\'+ vm_name + '.iso\"')
5.376 - return result
5.377 -
5.378 - # wait for machine to come up
5.379 - def waitStartup(self, vm_name, timeout_ms = 30000):
5.380 - result = Cygwin.vboxExecute('guestproperty wait ' + vm_name + ' SDVMStarted --timeout ' + str(timeout_ms) + ' --fail-on-timeout')
5.381 - return VMManager.getHostOnlyIP(vm_name)
5.382 -
5.383 - # wait for machine to shutdown
5.384 - def waitShutdown(self, vm_name):
5.385 - while vm_name in self.listRunningVMS():
5.386 - time.sleep(1)
5.387 - return
5.388 -
5.389 - # handles browsing request
5.390 - def handleBrowsingRequest(self):
5.391 - if VMManager.handleDeviceChangeLock.acquire(True):
5.392 - new_sdvm = self.generateSDVMName()
5.393 - self.createVM(new_sdvm)
5.394 - self.storageAttach(new_sdvm)
5.395 - self.genCertificateISO(new_sdvm)
5.396 - self.attachCertificateISO(new_sdvm)
5.397 - self.startVM(new_sdvm)
5.398 - new_ip = self.waitStartup(new_sdvm)
5.399 - if new_ip != None:
5.400 - self.mapNetworkDrive('g:', '\\\\' + new_ip + '\\Download', None, None)
5.401 - #TODO: cleanup notifications somwhere else (eg. machine shutdown)
5.402 - VMManager.handleDeviceChangeLock.release()
5.403 - return new_sdvm
5.404 -
5.405 - #Small function to check the availability of network resource.
5.406 - #def isAvailable(self, path):
5.407 - #return os.path.exists(path)
5.408 - #result = Cygwin.cmdExecute('IF EXIST "' + path + '" echo YES')
5.409 - #return string.find(result[1], 'YES',)
5.410 -
5.411 - #Small function to check if the mention location is a directory
5.412 - def isDirectory(self, path):
5.413 - result = Cygwin.cmdExecute('dir ' + path + ' | FIND ".."')
5.414 - return string.find(result[1], 'DIR',)
5.415 -
5.416 - def mapNetworkDrive(self, drive, networkPath, user, password):
5.417 - self.unmapNetworkDrive(drive)
5.418 - #Check for drive availability
5.419 - if os.path.exists(drive):
5.420 - logger.error("Drive letter is already in use: " + drive)
5.421 - return -1
5.422 - #Check for network resource availability
5.423 - while not os.path.exists(networkPath):
5.424 - time.sleep(1)
5.425 - logger.info("Path not accessible: " + networkPath + " retrying")
5.426 - #return -1
5.427 -
5.428 - command = 'USE ' + drive + ' ' + networkPath + ' /PERSISTENT:NO'
5.429 - if user != None:
5.430 - command += ' ' + password + ' /User' + user
5.431 -
5.432 - #TODO: Execute 'NET USE' command with authentication
5.433 - result = Cygwin.execute('C:\\Windows\\system32\\net.exe', command)
5.434 - if string.find(result[1], 'successfully',) == -1:
5.435 - logger.error("Failed: NET " + command)
5.436 - return -1
5.437 - return 1
5.438 -
5.439 - def unmapNetworkDrive(self, drive):
5.440 - drives = self.getNetworkDrives()
5.441 - if drive not in drives.keys():
5.442 - return 1
5.443 - result = Cygwin.execute('C:\\Windows\\system32\\net.exe', 'USE ' + drive + ' /DELETE /YES')
5.444 - if string.find(str(result[1]), 'successfully',) == -1:
5.445 - logger.error(result[2])
5.446 - return -1
5.447 - return 1
5.448 -
5.449 - def getNetworkDrives(self):
5.450 - ip = VMManager.getHostOnlyIP(None)
5.451 - ip = ip[:ip.rindex('.')]
5.452 - drives = dict()
5.453 - result = Cygwin.execute('C:\\Windows\\system32\\net.exe', 'USE')
5.454 - for line in result[1].splitlines():
5.455 - if ip in line:
5.456 - parts = line.split()
5.457 - drives[parts[1]] = parts[2]
5.458 - return drives
5.459 -
5.460 - def genNetworkDrive(self):
5.461 - network_drives = self.getNetworkDrives()
5.462 - logical_drives = self.getLogicalDrives()
5.463 - drives = list(map(chr, range(68, 91)))
5.464 - for drive in drives:
5.465 - if drive+':' not in network_drives and drive not in logical_drives:
5.466 - return drive+':'
5.467 -
5.468 - def getNetworkDrive(self, vm_name):
5.469 - ip = self.getHostOnlyIP(vm_name)
5.470 - result = Cygwin.execute('C:\\Windows\\system32\\net.exe', 'USE')
5.471 - for line in result[1].splitlines():
5.472 - if ip in line:
5.473 - parts = line.split()
5.474 - return parts[0]
5.475 -
5.476 - def getLogicalDrives(self):
5.477 - drive_bitmask = ctypes.cdll.kernel32.GetLogicalDrives()
5.478 - return list(itertools.compress(string.ascii_uppercase, map(lambda x:ord(x) - ord('0'), bin(drive_bitmask)[:1:-1])))
5.479 -
5.480 - #vms = self.listSDVM()
5.481 - #for vm in vms:
5.482 - # ip = self.getHostOnlyIP(vm)
5.483 -
5.484 -class DeviceHandler(threading.Thread):
5.485 - vmm = None
5.486 - #handleDeviceChangeLock = threading.Lock()
5.487 - attachedRSDs = None
5.488 - connectedRSDs = None
5.489 - running = True
5.490 - def __init__(self, vmmanger):
5.491 - threading.Thread.__init__(self)
5.492 - self.vmm = vmmanger
5.493 -
5.494 - def stop(self):
5.495 - self.running = False
5.496 -
5.497 - def run(self):
5.498 - self.connectedRSDs = dict()#self.vmm.getConnectedRSDS()
5.499 - self.attachedRSDs = self.vmm.getAttachedRSDs()
5.500 - while self.running:
5.501 - tmp_rsds = self.vmm.getConnectedRSDS()
5.502 - if tmp_rsds.keys() == self.connectedRSDs.keys():
5.503 - logger.debug("Nothing's changed. sleep(3)")
5.504 - time.sleep(3)
5.505 - continue
5.506 -
5.507 - logger.info("Something's changed")
5.508 -
5.509 - self.connectedRSDs = tmp_rsds
5.510 - self.attachedRSDs = self.vmm.getAttachedRSDs()
5.511 -
5.512 -
5.513 - for vm_name in self.attachedRSDs.keys():
5.514 - if self.attachedRSDs[vm_name] not in self.connectedRSDs.values():
5.515 - drive = self.vmm.getNetworkDrive(vm_name)
5.516 - self.vmm.unmapNetworkDrive(drive)
5.517 - #self.stopVM(vm_name)
5.518 - self.vmm.detachRSD(vm_name)
5.519 - self.vmm.poweroffVM(vm_name)
5.520 - self.vmm.removeVM(vm_name)
5.521 - #create new vm for attached device if any
5.522 - self.attachedRSDs = self.vmm.getAttachedRSDs()
5.523 - self.connectedRSDs = self.vmm.getConnectedRSDS()
5.524 -
5.525 - new_ip = None
5.526 - for connected_device in self.connectedRSDs.values():
5.527 - if (self.attachedRSDs and False) or (connected_device not in self.attachedRSDs.values()):
5.528 - new_sdvm = self.vmm.generateSDVMName()
5.529 - self.vmm.createVM(new_sdvm)
5.530 - self.vmm.storageAttach(new_sdvm)
5.531 - self.vmm.attachRSD(new_sdvm, connected_device)
5.532 - self.vmm.startVM(new_sdvm)
5.533 - new_ip = self.vmm.waitStartup(new_sdvm)
5.534 - drive = self.vmm.genNetworkDrive()
5.535 - if new_ip != None:
5.536 - self.vmm.mapNetworkDrive(drive, '\\\\' + new_ip + '\\USB', None, None)
5.537 - #TODO: cleanup notifications somwhere else (eg. machine shutdown)
5.538 - #self.handleDeviceChangeLock.release()
5.539 -
5.540 -
5.541 -if __name__ == '__main__':
5.542 - #man = VMManager.getInstance()
5.543 - #man.listVM()
5.544 - #print man.getConnectedRSDs()
5.545 - #print man.getNetworkDrives()
5.546 - #man.genNetworkDrive()
5.547 - drive_bitmask = ctypes.cdll.kernel32.GetLogicalDrives()
5.548 - print list(itertools.compress(string.ascii_uppercase, map(lambda x:ord(x) - ord('0'), bin(drive_bitmask)[:1:-1])))
5.549 - #print list(map(chr, range(68, 91)))
5.550 -
5.551 - #time.sleep(-1)
5.552 - #man.listVM()
5.553 - #man.listVM()
5.554 - #man.listVM()
5.555 - #man.listVM()
5.556 - #man.genCertificateISO('SecurityDVM0')
5.557 - #man.guestExecute('SecurityDVM0', '/bin/ls -la')
5.558 - #logger = setupLogger('VMManager')
5.559 - #c = Cygwin()
5.560 -
5.561 - #man.sshExecute('/bin/ls -la', 'SecurityDVM0')
5.562 - #man.sshExecuteX11('/usr/bin/iceweasel', 'SecurityDVM0')
5.563 - #man.removeVM('SecurityDVM0')
5.564 - #man.netUse('192.168.56.134', 'USB\\')
5.565 - #ip = '192.168.56.139'
5.566 -
5.567 - #man.cygwin_path = 'c:\\cygwin64\\bin\\'
5.568 - #man.handleDeviceChange()
5.569 - #print man.listSDVM()
5.570 - #man.configureHostNetworking()
5.571 - #new_vm = man.generateSDVMName()
5.572 - #man.createVM(new_vm)
5.573 -
5.574 - #print Cygwin.cmd()
5.575 - #man.isAvailable('c:')
5.576 - #ip = man.getHostOnlyIP('SecurityDVM0')
5.577 - #man.mapNetworkDrive('h:', '\\\\' + ip + '\Download', None, None)
5.578 -
5.579 - #man.genCertificateISO(new_vm)
5.580 - #man.attachCertificateISO(new_vm)
5.581 -
5.582 - #man.attachCertificateISO(vm_name)
5.583 - #man.guestExecute(vm_name, "ls")
5.584 - #man.sshGuestX11Execute('SecurityDVM1', '/usr/bin/iceweasel')
5.585 - #time.sleep(60)
5.586 - #print man.cygwinPath("C:\Users\BarthaM\VirtualBox VMs\SecurityDVM\.ssh\*")
5.587 - #man.genCertificateISO('SecurityDVM')
5.588 - #man.attachCertificateISO('SecurityDVM')
5.589 - #man.isStorageAttached('SecurityDVM')
5.590 - #man.guestExecute('SecurityDVM', 'sudo apt-get -y update')
5.591 - #man.guestExecute('SecurityDVM', 'sudo apt-get -y upgrade' )
5.592 -
5.593 - #man.stopVM('SecurityDVM')
5.594 - #man.storageDetach('SecurityDVM')
5.595 - #man.changeStorageType('C:\Users\BarthaM\VirtualBox VMs\SecurityDVM\SecurityDVM.vmdk','immutable')
5.596 - #man.storageAttach('SecurityDVM')
5.597 -
5.598 -
5.599 - #cmd = "c:\\cygwin64\\bin\\bash.exe --login -c \"/bin/ls\""
5.600 - #man.execute(cmd)
5.601 -
5.602 +'''
5.603 +Created on Nov 19, 2013
5.604 +
5.605 +@author: BarthaM
5.606 +'''
5.607 +import os
5.608 +import os.path
5.609 +from subprocess import Popen, PIPE, call, STARTUPINFO, _subprocess
5.610 +import sys
5.611 +import re
5.612 +
5.613 +from cygwin import Cygwin
5.614 +from environment import Environment
5.615 +import threading
5.616 +import time
5.617 +import string
5.618 +
5.619 +import shutil
5.620 +import stat
5.621 +import tempfile
5.622 +from opensecurity_util import logger, setupLogger, OpenSecurityException
5.623 +import ctypes
5.624 +import itertools
5.625 +DEBUG = True
5.626 +
5.627 +class VMManagerException(Exception):
5.628 + def __init__(self, value):
5.629 + self.value = value
5.630 + def __str__(self):
5.631 + return repr(self.value)
5.632 +
5.633 +class USBFilter:
5.634 + vendorid = ""
5.635 + productid = ""
5.636 + revision = ""
5.637 +
5.638 + def __init__(self, vendorid, productid, revision):
5.639 + self.vendorid = vendorid.lower()
5.640 + self.productid = productid.lower()
5.641 + self.revision = revision.lower()
5.642 + return
5.643 +
5.644 + def __eq__(self, other):
5.645 + return self.vendorid == other.vendorid and self.productid == other.productid and self.revision == other.revision
5.646 +
5.647 + def __hash__(self):
5.648 + return hash(self.vendorid) ^ hash(self.productid) ^ hash(self.revision)
5.649 +
5.650 + def __repr__(self):
5.651 + return "VendorId = \'" + str(self.vendorid) + "\' ProductId = \'" + str(self.productid) + "\' Revision = \'" + str(self.revision) + "\'"
5.652 +
5.653 +class VMManager(object):
5.654 + vmRootName = "SecurityDVM"
5.655 + systemProperties = None
5.656 + _instance = None
5.657 + machineFolder = ''
5.658 + rsdHandler = None
5.659 +
5.660 + def __init__(self):
5.661 + self.systemProperties = self.getSystemProperties()
5.662 + self.machineFolder = self.systemProperties["Default machine folder"]
5.663 + self.cleanup()
5.664 + self.rsdHandler = DeviceHandler(self)
5.665 + self.rsdHandler.start()
5.666 + return
5.667 +
5.668 + @staticmethod
5.669 + def getInstance():
5.670 + if VMManager._instance == None:
5.671 + VMManager._instance = VMManager()
5.672 + return VMManager._instance
5.673 +
5.674 + def cleanup(self):
5.675 + if self.rsdHandler != None:
5.676 + self.rsdHandler.stop()
5.677 + self.rsdHandler.join()
5.678 + drives = self.getNetworkDrives()
5.679 + for drive in drives.keys():
5.680 + self.unmapNetworkDrive(drive)
5.681 + for vm in self.listSDVM():
5.682 + self.poweroffVM(vm)
5.683 + self.removeVM(vm)
5.684 +
5.685 + # return hosty system properties
5.686 + def getSystemProperties(self):
5.687 + result = Cygwin.vboxExecute('list systemproperties')
5.688 + if result[1]=='':
5.689 + return None
5.690 + props = dict((k.strip(),v.strip().strip('"')) for k,v in (line.split(':', 1) for line in result[1].strip().splitlines()))
5.691 + #logger.debug(props)
5.692 + return props
5.693 +
5.694 + # return the folder containing the guest VMs
5.695 + def getMachineFolder(self):
5.696 + return self.machineFolder
5.697 +
5.698 + # list all existing VMs registered with VBox
5.699 + def listVM(self):
5.700 + result = Cygwin.vboxExecute('list vms')[1]
5.701 + vms = list(k.strip().strip('"') for k,_ in (line.split(' ') for line in result.splitlines()))
5.702 + return vms
5.703 +
5.704 + # list running VMs
5.705 + def listRunningVMS(self):
5.706 + result = Cygwin.vboxExecute('list runningvms')[1]
5.707 + vms = list(k.strip().strip('"') for k,_ in (line.split(' ') for line in result.splitlines()))
5.708 + return vms
5.709 +
5.710 + # list existing SDVMs
5.711 + def listSDVM(self):
5.712 + vms = self.listVM()
5.713 + svdms = []
5.714 + for vm in vms:
5.715 + if vm.startswith(self.vmRootName) and vm != self.vmRootName:
5.716 + svdms.append(vm)
5.717 + return svdms
5.718 +
5.719 + # generate valid (not already existing SDVM name). necessary for creating a new VM
5.720 + def generateSDVMName(self):
5.721 + vms = self.listVM()
5.722 + for i in range(0,999):
5.723 + if(not self.vmRootName+str(i) in vms):
5.724 + return self.vmRootName+str(i)
5.725 + return ''
5.726 +
5.727 + # return the RSDs connected to the host
5.728 + def getConnectedRSDS(self):
5.729 + results = Cygwin.vboxExecute('list usbhost')[1]
5.730 + results = results.split('Host USB Devices:')[1].strip()
5.731 +
5.732 + items = list( "UUID:"+result for result in results.split('UUID:') if result != '')
5.733 + rsds = dict()
5.734 + for item in items:
5.735 + props = dict()
5.736 + for line in item.splitlines():
5.737 + if line != "":
5.738 + k,v = line[:line.index(':')].strip(), line[line.index(':')+1:].strip()
5.739 + props[k] = v
5.740 +
5.741 + if 'Product' in props.keys() and props['Product'] == 'Mass Storage':
5.742 + usb_filter = USBFilter( re.search(r"\((?P<vid>[0-9A-Fa-f]+)\)", props['VendorId']).groupdict()['vid'],
5.743 + re.search(r"\((?P<pid>[0-9A-Fa-f]+)\)", props['ProductId']).groupdict()['pid'],
5.744 + re.search(r"\((?P<rev>[0-9A-Fa-f]+)\)", props['Revision']).groupdict()['rev'] )
5.745 + rsds[props['UUID']] = usb_filter;
5.746 + logger.debug(usb_filter)
5.747 + return rsds
5.748 +
5.749 + # return the RSDs attached to all existing SDVMs
5.750 + def getAttachedRSDs(self):
5.751 + vms = self.listSDVM()
5.752 + attached_devices = dict()
5.753 + for vm in vms:
5.754 + rsd_filter = self.getUSBFilter(vm)
5.755 + if rsd_filter != None:
5.756 + attached_devices[vm] = rsd_filter
5.757 + return attached_devices
5.758 +
5.759 + # configures hostonly networking and DHCP server. requires admin rights
5.760 + def configureHostNetworking(self):
5.761 + #cmd = 'vboxmanage list hostonlyifs'
5.762 + #Cygwin.vboxExecute(cmd)
5.763 + #cmd = 'vboxmanage hostonlyif remove \"VirtualBox Host-Only Ethernet Adapter\"'
5.764 + #Cygwin.vboxExecute(cmd)
5.765 + #cmd = 'vboxmanage hostonlyif create'
5.766 + #Cygwin.vboxExecute(cmd)
5.767 + Cygwin.vboxExecute('hostonlyif ipconfig \"VirtualBox Host-Only Ethernet Adapter\" --ip 192.168.56.1 --netmask 255.255.255.0')
5.768 + #cmd = 'vboxmanage dhcpserver add'
5.769 + #Cygwin.vboxExecute(cmd)
5.770 + Cygwin.vboxExecute('dhcpserver modify --ifname \"VirtualBox Host-Only Ethernet Adapter\" --ip 192.168.56.100 --netmask 255.255.255.0 --lowerip 192.168.56.101 --upperip 192.168.56.200')
5.771 +
5.772 + #create new virtual machine instance based on template vm named SecurityDVM (\SecurityDVM\SecurityDVM.vmdk)
5.773 + def createVM(self, vm_name):
5.774 + hostonly_if = self.getHostOnlyIFs()
5.775 + Cygwin.vboxExecute('createvm --name ' + vm_name + ' --ostype Debian --register')
5.776 + Cygwin.vboxExecute('modifyvm ' + vm_name + ' --memory 512 --vram 10 --cpus 1 --usb on --usbehci on --nic1 hostonly --hostonlyadapter1 \"' + hostonly_if['Name'] + '\" --nic2 nat')
5.777 + Cygwin.vboxExecute('storagectl ' + vm_name + ' --name SATA --add sata --portcount 2')
5.778 + return
5.779 +
5.780 + # attach storage image to controller
5.781 + def storageAttach(self, vm_name):
5.782 + if self.isStorageAttached(vm_name):
5.783 + self.storageDetach(vm_name)
5.784 + Cygwin.vboxExecute('storageattach ' + vm_name + ' --storagectl SATA --port 0 --device 0 --type hdd --medium \"'+ self.machineFolder + '\SecurityDVM\SecurityDVM.vmdk\"')
5.785 + return
5.786 +
5.787 + # return true if storage is attached
5.788 + def isStorageAttached(self, vm_name):
5.789 + info = self.getVMInfo(vm_name)
5.790 + return (info['SATA-0-0']!='none')
5.791 +
5.792 + # detach storage from controller
5.793 + def storageDetach(self, vm_name):
5.794 + if self.isStorageAttached(vm_name):
5.795 + Cygwin.vboxExecute('storageattach ' + vm_name + ' --storagectl SATA --port 0 --device 0 --type hdd --medium none')
5.796 + return
5.797 +
5.798 + def changeStorageType(self, filename, storage_type):
5.799 + Cygwin.vboxExecute('modifyhd \"' + filename + '\" --type ' + storage_type)
5.800 + return
5.801 +
5.802 + # list storage snaphots for VM
5.803 + def updateTemplate(self):
5.804 + self.cleanup()
5.805 + self.poweroffVM('SecurityDVM')
5.806 + self.waitShutdown('SecurityDVM')
5.807 +
5.808 + # check for updates
5.809 + self.genCertificateISO('SecurityDVM')
5.810 + self.attachCertificateISO('SecurityDVM')
5.811 +
5.812 + self.storageDetach('SecurityDVM')
5.813 + results = Cygwin.vboxExecute('list hdds')[1]
5.814 + results = results.replace('Parent UUID', 'Parent')
5.815 + items = list( "UUID:"+result for result in results.split('UUID:') if result != '')
5.816 +
5.817 + snaps = dict()
5.818 + for item in items:
5.819 + props = dict()
5.820 + for line in item.splitlines():
5.821 + if line != "":
5.822 + k,v = line[:line.index(':')].strip(), line[line.index(':')+1:].strip()
5.823 + props[k] = v;
5.824 + snaps[props['UUID']] = props
5.825 +
5.826 +
5.827 + template_storage = self.machineFolder + '\SecurityDVM\SecurityDVM.vmdk'
5.828 +
5.829 + # find template uuid
5.830 + template_uuid = ''
5.831 + for hdd in snaps.values():
5.832 + if hdd['Location'] == template_storage:
5.833 + template_uuid = hdd['UUID']
5.834 + logger.debug('found parent uuid ' + template_uuid)
5.835 +
5.836 + # remove snapshots
5.837 + for hdd in snaps.values():
5.838 + if hdd['Parent'] == template_uuid:
5.839 + #template_uuid = hdd['UUID']
5.840 + logger.debug('removing snapshot ' + hdd['UUID'])
5.841 + results = Cygwin.vboxExecute('closemedium disk {' + hdd['UUID'] + '} --delete')[1]
5.842 + # parse result 0%...10%...20%...30%...40%...50%...60%...70%...80%...90%...100%
5.843 +
5.844 + self.changeStorageType(template_storage,'normal')
5.845 + self.storageAttach('SecurityDVM')
5.846 + self.startVM('SecurityDVM')
5.847 + self.waitStartup('SecurityDVM')
5.848 + Cygwin.sshExecute('"sudo apt-get -y update"', VMManager.getHostOnlyIP('SecurityDVM'), 'osecuser', Cygwin.cygPath(self.machineFolder) + '/' + 'SecurityDVM' + '/dvm_key' )
5.849 + Cygwin.sshExecute('"sudo apt-get -y upgrade"', VMManager.getHostOnlyIP('SecurityDVM'), 'osecuser', Cygwin.cygPath(self.machineFolder) + '/' + 'SecurityDVM' + '/dvm_key' )
5.850 + #self.stopVM('SecurityDVM')
5.851 + self.hibernateVM('SecurityDVM')
5.852 + self.waitShutdown('SecurityDVM')
5.853 + self.storageDetach('SecurityDVM')
5.854 + self.changeStorageType(template_storage,'immutable')
5.855 + self.storageAttach('SecurityDVM')
5.856 + self.rsdHandler = DeviceHandler(self)
5.857 + self.rsdHandler.start()
5.858 +
5.859 + #remove VM from the system. should be used on VMs returned by listSDVMs
5.860 + def removeVM(self, vm_name):
5.861 + logger.info('Removing ' + vm_name)
5.862 + Cygwin.vboxExecute('unregistervm ' + vm_name + ' --delete')
5.863 + machineFolder = Cygwin.cygPath(self.machineFolder)
5.864 + Cygwin.bashExecute('"/usr/bin/rm -rf ' + machineFolder + '/' + vm_name + '"')
5.865 +
5.866 + # start VM
5.867 + def startVM(self, vm_name):
5.868 + logger.info('Starting ' + vm_name)
5.869 + result = Cygwin.vboxExecute('startvm ' + vm_name + ' --type headless' )
5.870 + while not string.find(str(result), 'successfully started',):
5.871 + logger.error("Failed to start SDVM: " + vm_name + " retrying")
5.872 + time.sleep(1)
5.873 + result = Cygwin.vboxExecute('startvm ' + vm_name + ' --type headless')
5.874 + return result[0]
5.875 +
5.876 + # return wether VM is running or not
5.877 + def isVMRunning(self, vm_name):
5.878 + return vm_name in self.listRunningVMS()
5.879 +
5.880 + # stop VM
5.881 + def stopVM(self, vm_name):
5.882 + logger.info('Sending shutdown signal to ' + vm_name)
5.883 + Cygwin.sshExecute( '"sudo shutdown -h now"', VMManager.getHostOnlyIP(vm_name), 'osecuser', Cygwin.cygPath(self.machineFolder) + '/' + vm_name + '/dvm_key' )
5.884 +
5.885 + # stop VM
5.886 + def hibernateVM(self, vm_name):
5.887 + logger.info('Sending shutdown signal to ' + vm_name)
5.888 + Cygwin.sshExecute( '"sudo hibernate-disk&"', VMManager.getHostOnlyIP(vm_name), 'osecuser', Cygwin.cygPath(self.machineFolder) + '/' + vm_name + '/dvm_key', wait_return=False )
5.889 +
5.890 + # poweroff VM
5.891 + def poweroffVM(self, vm_name):
5.892 + if not self.isVMRunning(vm_name):
5.893 + return
5.894 + logger.info('Powering off ' + vm_name)
5.895 + return Cygwin.vboxExecute('controlvm ' + vm_name + ' poweroff')
5.896 +
5.897 + #list the hostonly IFs exposed by the VBox host
5.898 + @staticmethod
5.899 + def getHostOnlyIFs():
5.900 + result = Cygwin.vboxExecute('list hostonlyifs')[1]
5.901 + if result=='':
5.902 + return None
5.903 + props = dict((k.strip(),v.strip().strip('"')) for k,v in (line.split(':', 1) for line in result.strip().splitlines()))
5.904 + return props
5.905 +
5.906 + # return the hostOnly IP for a running guest or the host
5.907 + @staticmethod
5.908 + def getHostOnlyIP(vm_name):
5.909 + if vm_name == None:
5.910 + logger.info('Gettting hostOnly IP address for Host')
5.911 + return VMManager.getHostOnlyIFs()['IPAddress']
5.912 + else:
5.913 + logger.info('Gettting hostOnly IP address ' + vm_name)
5.914 + result = Cygwin.vboxExecute('guestproperty get ' + vm_name + ' /VirtualBox/GuestInfo/Net/0/V4/IP')
5.915 + if result=='':
5.916 + return None
5.917 + result = result[1]
5.918 + if result.startswith('No value set!'):
5.919 + return None
5.920 + return result[result.index(':')+1:].strip()
5.921 +
5.922 + # attach removable storage device to VM by provision of filter
5.923 + def attachRSD(self, vm_name, rsd_filter):
5.924 + return Cygwin.vboxExecute('usbfilter add 0 --target ' + vm_name + ' --name OpenSecurityRSD --vendorid ' + rsd_filter.vendorid + ' --productid ' + rsd_filter.productid + ' --revision ' + rsd_filter.revision)
5.925 +
5.926 + # detach removable storage from VM by
5.927 + def detachRSD(self, vm_name):
5.928 + return Cygwin.vboxExecute('usbfilter remove 0 --target ' + vm_name )
5.929 +
5.930 +
5.931 + # return the description set for an existing VM
5.932 + def getVMInfo(self, vm_name):
5.933 + results = Cygwin.vboxExecute('showvminfo ' + vm_name + ' --machinereadable')[1]
5.934 + props = dict((k.strip().strip('"'),v.strip().strip('"')) for k,v in (line.split('=', 1) for line in results.splitlines()))
5.935 + #logger.debug(props)
5.936 + return props
5.937 +
5.938 + # return the configured USB filter for an existing VM
5.939 + def getUSBFilter(self, vm_name):
5.940 + props = self.getVMInfo(vm_name)
5.941 + keys = set(['USBFilterVendorId1', 'USBFilterProductId1', 'USBFilterRevision1'])
5.942 + keyset = set(props.keys())
5.943 + usb_filter = None
5.944 + if keyset.issuperset(keys):
5.945 + usb_filter = USBFilter(props['USBFilterVendorId1'], props['USBFilterProductId1'], props['USBFilterRevision1'])
5.946 + return usb_filter
5.947 +
5.948 + #generates ISO containing authorized_keys for use with guest VM
5.949 + def genCertificateISO(self, vm_name):
5.950 + machineFolder = Cygwin.cygPath(self.machineFolder)
5.951 + # remove .ssh folder if exists
5.952 + cmd = '\"/usr/bin/rm -rf \\\"' + machineFolder + '/' + vm_name + '/.ssh\\\"\"'
5.953 + Cygwin.bashExecute(cmd)
5.954 + # remove .ssh folder if exists
5.955 + Cygwin.bashExecute('\"/usr/bin/rm -rf \\\"' + machineFolder + '/' + vm_name + '/dvm_key\\\"\"')
5.956 + # create .ssh folder in vm_name
5.957 + Cygwin.bashExecute('\"/usr/bin/mkdir -p \\\"' + machineFolder + '/' + vm_name + '/.ssh\\\"\"')
5.958 + # generate dvm_key pair in vm_name / .ssh
5.959 + Cygwin.bashExecute('\"/usr/bin/ssh-keygen -q -t rsa -N \\"\\" -C \\\"' + vm_name + '\\\" -f \\\"' + machineFolder + '/' + vm_name + '/.ssh/dvm_key\\\"\"')
5.960 + # move out private key
5.961 + Cygwin.bashExecute('\"/usr/bin/mv \\\"' + machineFolder + '/' + vm_name + '/.ssh/dvm_key\\\" \\\"' + machineFolder + '/' + vm_name + '\\\"')
5.962 + # set permissions for private key
5.963 + Cygwin.bashExecute('\"/usr/bin/chmod 500 \\\"' + machineFolder + '/' + vm_name + '/dvm_key\\\"\"')
5.964 + # rename public key to authorized_keys
5.965 + Cygwin.bashExecute('\"/usr/bin/mv \\\"' + machineFolder + '/' + vm_name + '/.ssh/dvm_key.pub\\\" \\\"' + machineFolder + '/' + vm_name + '/.ssh/authorized_keys\\\"')
5.966 + # set permissions for authorized_keys
5.967 + Cygwin.bashExecute('\"/usr/bin/chmod 500 \\\"' + machineFolder + '/' + vm_name + '/.ssh/authorized_keys\\\"\"')
5.968 + # generate iso image with .ssh/authorized keys
5.969 + Cygwin.bashExecute('\"/usr/bin/genisoimage -J -R -o \\\"' + machineFolder + '/' + vm_name + '/'+ vm_name + '.iso\\\" \\\"' + machineFolder + '/' + vm_name + '/.ssh\\\"\"')
5.970 +
5.971 + # attaches generated ssh public cert to guest vm
5.972 + def attachCertificateISO(self, vm_name):
5.973 + result = Cygwin.vboxExecute('storageattach ' + vm_name + ' --storagectl SATA --port 1 --device 0 --type dvddrive --mtype readonly --medium \"' + self.machineFolder + '\\' + vm_name + '\\'+ vm_name + '.iso\"')
5.974 + return result
5.975 +
5.976 + # wait for machine to come up
5.977 + def waitStartup(self, vm_name, timeout_ms = 30000):
5.978 + result = Cygwin.vboxExecute('guestproperty wait ' + vm_name + ' SDVMStarted --timeout ' + str(timeout_ms) + ' --fail-on-timeout')
5.979 + return VMManager.getHostOnlyIP(vm_name)
5.980 +
5.981 + # wait for machine to shutdown
5.982 + def waitShutdown(self, vm_name):
5.983 + while vm_name in self.listRunningVMS():
5.984 + time.sleep(1)
5.985 + return
5.986 +
5.987 + # handles browsing request
5.988 + def handleBrowsingRequest(self):
5.989 + if VMManager.handleDeviceChangeLock.acquire(True):
5.990 + new_sdvm = self.generateSDVMName()
5.991 + self.createVM(new_sdvm)
5.992 + self.storageAttach(new_sdvm)
5.993 + self.genCertificateISO(new_sdvm)
5.994 + self.attachCertificateISO(new_sdvm)
5.995 + self.startVM(new_sdvm)
5.996 + new_ip = self.waitStartup(new_sdvm)
5.997 + if new_ip != None:
5.998 + self.mapNetworkDrive('g:', '\\\\' + new_ip + '\\Download', None, None)
5.999 + #TODO: cleanup notifications somwhere else (eg. machine shutdown)
5.1000 + VMManager.handleDeviceChangeLock.release()
5.1001 + return new_sdvm
5.1002 +
5.1003 + #Small function to check the availability of network resource.
5.1004 + #def isAvailable(self, path):
5.1005 + #return os.path.exists(path)
5.1006 + #result = Cygwin.cmdExecute('IF EXIST "' + path + '" echo YES')
5.1007 + #return string.find(result[1], 'YES',)
5.1008 +
5.1009 + #Small function to check if the mention location is a directory
5.1010 + def isDirectory(self, path):
5.1011 + result = Cygwin.cmdExecute('dir ' + path + ' | FIND ".."')
5.1012 + return string.find(result[1], 'DIR',)
5.1013 +
5.1014 + def mapNetworkDrive(self, drive, networkPath, user, password):
5.1015 + self.unmapNetworkDrive(drive)
5.1016 + #Check for drive availability
5.1017 + if os.path.exists(drive):
5.1018 + logger.error("Drive letter is already in use: " + drive)
5.1019 + return -1
5.1020 + #Check for network resource availability
5.1021 + while not os.path.exists(networkPath):
5.1022 + time.sleep(1)
5.1023 + logger.info("Path not accessible: " + networkPath + " retrying")
5.1024 + #return -1
5.1025 +
5.1026 + command = 'USE ' + drive + ' ' + networkPath + ' /PERSISTENT:NO'
5.1027 + if user != None:
5.1028 + command += ' ' + password + ' /User' + user
5.1029 +
5.1030 + #TODO: Execute 'NET USE' command with authentication
5.1031 + result = Cygwin.execute('C:\\Windows\\system32\\net.exe', command)
5.1032 + if string.find(result[1], 'successfully',) == -1:
5.1033 + logger.error("Failed: NET " + command)
5.1034 + return -1
5.1035 + return 1
5.1036 +
5.1037 + def unmapNetworkDrive(self, drive):
5.1038 + drives = self.getNetworkDrives()
5.1039 + if drive not in drives.keys():
5.1040 + return 1
5.1041 + result = Cygwin.execute('C:\\Windows\\system32\\net.exe', 'USE ' + drive + ' /DELETE /YES')
5.1042 + if string.find(str(result[1]), 'successfully',) == -1:
5.1043 + logger.error(result[2])
5.1044 + return -1
5.1045 + return 1
5.1046 +
5.1047 + def getNetworkDrives(self):
5.1048 + ip = VMManager.getHostOnlyIP(None)
5.1049 + ip = ip[:ip.rindex('.')]
5.1050 + drives = dict()
5.1051 + result = Cygwin.execute('C:\\Windows\\system32\\net.exe', 'USE')
5.1052 + for line in result[1].splitlines():
5.1053 + if ip in line:
5.1054 + parts = line.split()
5.1055 + drives[parts[1]] = parts[2]
5.1056 + return drives
5.1057 +
5.1058 + def genNetworkDrive(self):
5.1059 + network_drives = self.getNetworkDrives()
5.1060 + logical_drives = self.getLogicalDrives()
5.1061 + drives = list(map(chr, range(68, 91)))
5.1062 + for drive in drives:
5.1063 + if drive+':' not in network_drives and drive not in logical_drives:
5.1064 + return drive+':'
5.1065 +
5.1066 + def getNetworkDrive(self, vm_name):
5.1067 + ip = self.getHostOnlyIP(vm_name)
5.1068 + result = Cygwin.execute('C:\\Windows\\system32\\net.exe', 'USE')
5.1069 + for line in result[1].splitlines():
5.1070 + if ip in line:
5.1071 + parts = line.split()
5.1072 + return parts[0]
5.1073 +
5.1074 + def getLogicalDrives(self):
5.1075 + drive_bitmask = ctypes.cdll.kernel32.GetLogicalDrives()
5.1076 + return list(itertools.compress(string.ascii_uppercase, map(lambda x:ord(x) - ord('0'), bin(drive_bitmask)[:1:-1])))
5.1077 +
5.1078 + #vms = self.listSDVM()
5.1079 + #for vm in vms:
5.1080 + # ip = self.getHostOnlyIP(vm)
5.1081 +
5.1082 +class DeviceHandler(threading.Thread):
5.1083 + vmm = None
5.1084 + #handleDeviceChangeLock = threading.Lock()
5.1085 + attachedRSDs = None
5.1086 + connectedRSDs = None
5.1087 + running = True
5.1088 + def __init__(self, vmmanger):
5.1089 + threading.Thread.__init__(self)
5.1090 + self.vmm = vmmanger
5.1091 +
5.1092 + def stop(self):
5.1093 + self.running = False
5.1094 +
5.1095 + def run(self):
5.1096 + self.connectedRSDs = dict()#self.vmm.getConnectedRSDS()
5.1097 + self.attachedRSDs = self.vmm.getAttachedRSDs()
5.1098 + while self.running:
5.1099 + tmp_rsds = self.vmm.getConnectedRSDS()
5.1100 + if tmp_rsds.keys() == self.connectedRSDs.keys():
5.1101 + logger.debug("Nothing's changed. sleep(3)")
5.1102 + time.sleep(3)
5.1103 + continue
5.1104 +
5.1105 + logger.info("Something's changed")
5.1106 +
5.1107 + self.connectedRSDs = tmp_rsds
5.1108 + self.attachedRSDs = self.vmm.getAttachedRSDs()
5.1109 +
5.1110 +
5.1111 + for vm_name in self.attachedRSDs.keys():
5.1112 + if self.attachedRSDs[vm_name] not in self.connectedRSDs.values():
5.1113 + drive = self.vmm.getNetworkDrive(vm_name)
5.1114 + self.vmm.unmapNetworkDrive(drive)
5.1115 + #self.stopVM(vm_name)
5.1116 + self.vmm.detachRSD(vm_name)
5.1117 + self.vmm.poweroffVM(vm_name)
5.1118 + self.vmm.removeVM(vm_name)
5.1119 + #create new vm for attached device if any
5.1120 + self.attachedRSDs = self.vmm.getAttachedRSDs()
5.1121 + self.connectedRSDs = self.vmm.getConnectedRSDS()
5.1122 +
5.1123 + new_ip = None
5.1124 + for connected_device in self.connectedRSDs.values():
5.1125 + if (self.attachedRSDs and False) or (connected_device not in self.attachedRSDs.values()):
5.1126 + new_sdvm = self.vmm.generateSDVMName()
5.1127 + self.vmm.createVM(new_sdvm)
5.1128 + self.vmm.storageAttach(new_sdvm)
5.1129 + self.vmm.attachRSD(new_sdvm, connected_device)
5.1130 + self.vmm.startVM(new_sdvm)
5.1131 + new_ip = self.vmm.waitStartup(new_sdvm)
5.1132 + drive = self.vmm.genNetworkDrive()
5.1133 + if new_ip != None:
5.1134 + self.vmm.mapNetworkDrive(drive, '\\\\' + new_ip + '\\USB', None, None)
5.1135 + #TODO: cleanup notifications somwhere else (eg. machine shutdown)
5.1136 + #self.handleDeviceChangeLock.release()
5.1137 +
5.1138 +
5.1139 +if __name__ == '__main__':
5.1140 + #man = VMManager.getInstance()
5.1141 + #man.listVM()
5.1142 + #print man.getConnectedRSDs()
5.1143 + #print man.getNetworkDrives()
5.1144 + #man.genNetworkDrive()
5.1145 + drive_bitmask = ctypes.cdll.kernel32.GetLogicalDrives()
5.1146 + print list(itertools.compress(string.ascii_uppercase, map(lambda x:ord(x) - ord('0'), bin(drive_bitmask)[:1:-1])))
5.1147 + #print list(map(chr, range(68, 91)))
5.1148 +
5.1149 + #time.sleep(-1)
5.1150 + #man.listVM()
5.1151 + #man.listVM()
5.1152 + #man.listVM()
5.1153 + #man.listVM()
5.1154 + #man.genCertificateISO('SecurityDVM0')
5.1155 + #man.guestExecute('SecurityDVM0', '/bin/ls -la')
5.1156 + #logger = setupLogger('VMManager')
5.1157 + #c = Cygwin()
5.1158 +
5.1159 + #man.sshExecute('/bin/ls -la', 'SecurityDVM0')
5.1160 + #man.sshExecuteX11('/usr/bin/iceweasel', 'SecurityDVM0')
5.1161 + #man.removeVM('SecurityDVM0')
5.1162 + #man.netUse('192.168.56.134', 'USB\\')
5.1163 + #ip = '192.168.56.139'
5.1164 +
5.1165 + #man.cygwin_path = 'c:\\cygwin64\\bin\\'
5.1166 + #man.handleDeviceChange()
5.1167 + #print man.listSDVM()
5.1168 + #man.configureHostNetworking()
5.1169 + #new_vm = man.generateSDVMName()
5.1170 + #man.createVM(new_vm)
5.1171 +
5.1172 + #print Cygwin.cmd()
5.1173 + #man.isAvailable('c:')
5.1174 + #ip = man.getHostOnlyIP('SecurityDVM0')
5.1175 + #man.mapNetworkDrive('h:', '\\\\' + ip + '\Download', None, None)
5.1176 +
5.1177 + #man.genCertificateISO(new_vm)
5.1178 + #man.attachCertificateISO(new_vm)
5.1179 +
5.1180 + #man.attachCertificateISO(vm_name)
5.1181 + #man.guestExecute(vm_name, "ls")
5.1182 + #man.sshGuestX11Execute('SecurityDVM1', '/usr/bin/iceweasel')
5.1183 + #time.sleep(60)
5.1184 + #print man.cygwinPath("C:\Users\BarthaM\VirtualBox VMs\SecurityDVM\.ssh\*")
5.1185 + #man.genCertificateISO('SecurityDVM')
5.1186 + #man.attachCertificateISO('SecurityDVM')
5.1187 + #man.isStorageAttached('SecurityDVM')
5.1188 + #man.guestExecute('SecurityDVM', 'sudo apt-get -y update')
5.1189 + #man.guestExecute('SecurityDVM', 'sudo apt-get -y upgrade' )
5.1190 +
5.1191 + #man.stopVM('SecurityDVM')
5.1192 + #man.storageDetach('SecurityDVM')
5.1193 + #man.changeStorageType('C:\Users\BarthaM\VirtualBox VMs\SecurityDVM\SecurityDVM.vmdk','immutable')
5.1194 + #man.storageAttach('SecurityDVM')
5.1195 +
5.1196 +
5.1197 + #cmd = "c:\\cygwin64\\bin\\bash.exe --login -c \"/bin/ls\""
5.1198 + #man.execute(cmd)
5.1199 +
6.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
6.2 +++ b/OpenSecurity/cygwin64/mod/Readme.md Tue Mar 04 16:54:51 2014 +0100
6.3 @@ -0,0 +1,7 @@
6.4 +This folder contains OpenSecurity modifications
6.5 +to a cygwin installation.
6.6 +
6.7 +The content óf this folder is meant to be copy
6.8 +directly as-is into a cygwin root.
6.9 +
6.10 +
7.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
7.2 +++ b/OpenSecurity/cygwin64/mod/bin/os-install-path.sh Tue Mar 04 16:54:51 2014 +0100
7.3 @@ -0,0 +1,16 @@
7.4 +#!/bin/sh
7.5 +
7.6 +# ensure we have a /OpenSecurity path
7.7 +# pointing to our Windows install folder
7.8 +# inside the cygwin environment
7.9 +
7.10 +# explicitly set a new PATH here, since
7.11 +# this script may be called from a
7.12 +# non-login shell
7.13 +PATH=/usr/local/bin:/usr/bin:/bin
7.14 +
7.15 +# do not set twice
7.16 +test -h /OpenSecurity && exit 0
7.17 +OPENSECRUITY_WINDOWS_INSTALL_PATH=$(cygpath "$(cat /proc/mounts | grep 'cygwin64 / ' | sed 's/\/cygwin64 \/.*$//')")
7.18 +ln -s "$OPENSECRUITY_WINDOWS_INSTALL_PATH" /OpenSecurity
7.19 +
8.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
8.2 +++ b/OpenSecurity/cygwin64/mod/etc/bash.bashrc Tue Mar 04 16:54:51 2014 +0100
8.3 @@ -0,0 +1,34 @@
8.4 +# To the extent possible under law, the author(s) have dedicated all
8.5 +# copyright and related and neighboring rights to this software to the
8.6 +# public domain worldwide. This software is distributed without any warranty.
8.7 +# You should have received a copy of the CC0 Public Domain Dedication along
8.8 +# with this software.
8.9 +# If not, see <http://creativecommons.org/publicdomain/zero/1.0/>.
8.10 +
8.11 +# base-files version 4.1-1
8.12 +
8.13 +# /etc/bash.bashrc: executed by bash(1) for interactive shells.
8.14 +
8.15 +# The latest version as installed by the Cygwin Setup program can
8.16 +# always be found at /etc/defaults/etc/bash.bashrc
8.17 +
8.18 +# Modifying /etc/bash.bashrc directly will prevent
8.19 +# setup from updating it.
8.20 +
8.21 +# System-wide bashrc file
8.22 +
8.23 +# Check that we haven't already been sourced.
8.24 +([[ -z ${CYG_SYS_BASHRC} ]] && CYG_SYS_BASHRC="1") || return
8.25 +
8.26 +# If not running interactively, don't do anything
8.27 +[[ "$-" != *i* ]] && return
8.28 +
8.29 +# Set a default prompt of: user@host and current_directory
8.30 +PS1='\[\e]0;\w\a\]\n\[\e[32m\]\u@\h \[\e[33m\]\w\[\e[0m\]\n\$ '
8.31 +
8.32 +# Uncomment to use the terminal colours set in DIR_COLORS
8.33 +# eval "$(dircolors -b /etc/DIR_COLORS)"
8.34 +
8.35 +# ensure we have the OpenSecurity install path at hand
8.36 +/bin/os-install-path.sh
8.37 +
9.1 --- a/OpenSecurity/install/fix_cygwin_paths.bat Mon Mar 03 15:05:17 2014 +0100
9.2 +++ b/OpenSecurity/install/fix_cygwin_paths.bat Tue Mar 04 16:54:51 2014 +0100
9.3 @@ -1,5 +1,5 @@
9.4 -@echo off
9.5 -cd %0%\..\..
9.6 -echo %windir%\Temp /tmp ntfs binary,auto 1 1 >> cygwin64/etc/fstab
9.7 -echo %HOMEDRIVE%/Users /home ntfs binary,auto 1 1 >> cygwin64/etc/fstab
9.8 -rem copy install\initial_vm.sh cygwin64\usr\local\bin
9.9 +@echo off
9.10 +cd %0%\..\..
9.11 +echo %windir%\Temp /tmp ntfs binary,auto 1 1 >> cygwin64/etc/fstab
9.12 +echo %HOMEDRIVE%/Users /home ntfs binary,auto 1 1 >> cygwin64/etc/fstab
9.13 +rem copy install\initial_vm.sh cygwin64\usr\local\bin
10.1 --- a/OpenSecurity/install/initial_vm.bat Mon Mar 03 15:05:17 2014 +0100
10.2 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000
10.3 @@ -1,3 +0,0 @@
10.4 -@echo off
10.5 -CD %0%\..
10.6 -CMD /C ..\cygwin64\bin\bash.exe -l -i -c initial_vm.sh
11.1 --- a/OpenSecurity/install/initial_vm.sh Mon Mar 03 15:05:17 2014 +0100
11.2 +++ b/OpenSecurity/install/initial_vm.sh Tue Mar 04 16:54:51 2014 +0100
11.3 @@ -1,4 +1,4 @@
11.4 -#!/bin/sh
11.5 +#!/bin/bash
11.6
11.7 # ------------------------------------------------------------
11.8 # install the initial VM for
11.9 @@ -22,21 +22,6 @@
11.10 OPENSECURITY_PORT=8080
11.11
11.12
11.13 -# change to prefix folder
11.14 -# this script is supposed to be run
11.15 -# in
11.16 -# /usr/bin
11.17 -# /usr/local/bin
11.18 -# C:\Program Files\OpenSecurity\bin
11.19 -# or
11.20 -# C:\Program Files\OpenSecurity\install
11.21 -#
11.22 -# So, ensure we are relativ inside the
11.23 -# prefix installment path
11.24 -#
11.25 -cd $(dirname $(readlink -f ${0})) && cd ..
11.26 -
11.27 -
11.28 # ------------------------------------------------------------
11.29 # code
11.30
11.31 @@ -86,12 +71,27 @@
11.32 # main ...
11.33 #
11.34
11.35 -# check opensecurity folder
11.36 +# check if we do have elevated rights
11.37 +# that is "Run as Administrator" invocation
11.38 +id -G | grep 544 &> /dev/null
11.39 +if [ "${?}" != 0 ]; then
11.40 + echo "Insufficient privileges."
11.41 + echo "Is this script executed with 'Run As Administrator'?"
11.42 + press_a_key
11.43 + exit 1
11.44 +fi
11.45 +
11.46 +# ensure we have /OpenSecurity as install folder
11.47 +os-install-path.sh
11.48 +
11.49 +# check OpenSecurity Initial VM Image
11.50 #
11.51 -OPENSECURITY_DIR=$(sanitize_path "${OPENSECURITY_DIR}")
11.52 -OSECVM_IMAGE="${OPENSECURITY_DIR}/vm/OsecVM.ova"
11.53 -if [ ! -d "${OPENSECURITY_DIR}" ]; then
11.54 - echo "warning: no valid installation folder specified"
11.55 +OSECVM_IMAGE="/OpenSecurity/vm/OsecVM.ova"
11.56 +if [ ! -f "${OSECVM_IMAGE}" ]; then
11.57 + echo "Warning: no OpenSecurity Initial Image found."
11.58 + echo "Please download using the OpenSecurity download tool."
11.59 + press_a_key
11.60 + exit 1
11.61 fi
11.62
11.63 # look up VirtulBox installation
11.64 @@ -105,76 +105,22 @@
11.65 exit 1
11.66 fi
11.67
11.68 +# VirtualBox works on different folders which do
11.69 +# have admin privileges and sensible data.
11.70 +# Don't mingle with any User data.
11.71 +export HOME="$(cygpath.exe -w /OpenSecurity/vm)"
11.72 +export VBOX_USER_HOME=${HOME}
11.73 +export USERPROFILE=${HOME}
11.74 +
11.75 # enforce VirtualBox to "feel good" by calling a function
11.76 # (that is to "warm up" VirtualBox DCOM server ...)
11.77 #
11.78 VBOX_VERSION=$("${VBOX_MANAGER}" -version)
11.79 "${VBOX_MANAGER}" list vms &> /dev/null
11.80
11.81 -# download OSec.VM
11.82 -#
11.83 -if [ ! -e "${OSECVM_IMAGE}" ]; then
11.84 -
11.85 - echo "checking for local OsecVM.ova image instance ..."
11.86
11.87 - # we would like to place the OsecVM.ova image
11.88 - # inside the installation folder:
11.89 - #
11.90 - # C:\Program Files\OpenSecurity
11.91 - #
11.92 - # BUT: this script also works in deep with
11.93 - # VirtualBox and this one has a very
11.94 - # picky understanding of user/admin
11.95 - # permissions on Windows
11.96 - #
11.97 - # So, in oder to place any files under
11.98 - # C:\Program Files\OpenSecurity we need
11.99 - # this script running with elevated
11.100 - # user rights.
11.101 - #
11.102 - # ... which make VirtualBox managed VMs
11.103 - # by the install user impossible, since
11.104 - # VirtualBox gets confused by the User
11.105 - # privileges setup here in Windows
11.106 - # (Well, who doesn't anyway?).
11.107 -
11.108 - # user space place of OsecVM.ova image
11.109 - # ---> USER/AppData/Roaming/OpenSecurity
11.110 -
11.111 - mkdir -p $(cygpath -O)/../AppData/Roaming/OpenSecurity &> /dev/null
11.112 - if [ ! "${?}" = "0" ]; then
11.113 - echo "failed to create folder $(cygpath -O)/../AppData/Roaming/OpenSecurity"
11.114 - echo "unable to proceed ..."
11.115 - press_a_key
11.116 - exit 1
11.117 - fi
11.118 -
11.119 - OSECVM_IMAGE=$(cygpath -O)/../AppData/Roaming/OpenSecurity/OsecVM.ova
11.120 - if [ ! -e "${OSECVM_IMAGE}" ]; then
11.121 - echo "downloading OSecVM.ova image ..."
11.122 - wget -O "${OSECVM_IMAGE}" "${OVA_TEMPLATE_URL}"
11.123 - if [ "${?}" != "0" ]; then
11.124 - echo "failed to download OsecVM.ova"
11.125 - press_a_key
11.126 - exit 1
11.127 - fi
11.128 - fi
11.129 -fi
11.130 -echo "using $(cygpath -w ${OSECVM_IMAGE}) as inital VM image to import ..."
11.131 -
11.132 -
11.133 -# the next operations to produce some file I/O
11.134 -# (especially SecurityDVM/SecurityDVM,vmdk)
11.135 -# we therefore switch into the user's home
11.136 -pushd $(cygpath -O)/.. &> /dev/null
11.137 -
11.138 -# VirtualBox works on the User's home ...
11.139 -# which is different in cygwin and pure windows
11.140 -# yet another idiosyncrasy ... -.-
11.141 -export HOME="$(cygpath -w "$(cygpath -O)/..")"
11.142 -echo "HOME: ${HOME}"
11.143 -
11.144 -VDISK_IMAGE="VirtualBox VMs\SecurityDVM\SecurityDVM.vmdk"
11.145 +# the Security VM disk image
11.146 +VDISK_IMAGE=$(cygpath -w "/OpenSecurity/vm/SecurityDVM/SecurityDVM.vmdk")
11.147
11.148 # import VM
11.149 #
11.150 @@ -185,6 +131,8 @@
11.151 else
11.152 echo "found SecurityDVM already present in VBox reusing it."
11.153 echo "if you want a complete new import please remove the VM first."
11.154 + press_a_key
11.155 + exit 1
11.156 fi
11.157
11.158 # grab VM storage controller and port
11.159 @@ -197,7 +145,6 @@
11.160 echo "unable to grab virtual disk controller in VM."
11.161 echo "this shouldn't happen. It's a bug."
11.162 press_a_key
11.163 - popd
11.164 exit 1
11.165 fi
11.166
11.167 @@ -221,7 +168,8 @@
11.168 echo "reattach immutable disk image ..."
11.169 "${VBOX_MANAGER}" storageattach SecurityDVM --storagectl ${VDISK_CONTROLLER} --port ${VDISK_PORT} --device ${VDISK_DEVICE} --type hdd --mtype immutable --medium "${VDISK_IMAGE}"
11.170
11.171 -# return to current working dir
11.172 -popd &> /dev/null
11.173 +echo "imported initial OsecVM.ova image"
11.174
11.175 -echo "imported initial OsecVM.ova image"
11.176 +"${VBOX_MANAGER}" list vms
11.177 +
11.178 +