mirror of
https://github.com/freedomofpress/dangerzone.git
synced 2025-04-28 18:02:38 +02:00
Split Vm class from SysTray, and make it launch hyperkit
This commit is contained in:
parent
e8f7d96f90
commit
d7cd8584f2
5 changed files with 137 additions and 42 deletions
|
@ -8,6 +8,7 @@ from PySide2 import QtCore, QtWidgets
|
||||||
|
|
||||||
from .common import GuiCommon
|
from .common import GuiCommon
|
||||||
from .main_window import MainWindow
|
from .main_window import MainWindow
|
||||||
|
from .vm import Vm
|
||||||
from .systray import SysTray
|
from .systray import SysTray
|
||||||
from .docker_installer import (
|
from .docker_installer import (
|
||||||
is_docker_installed,
|
is_docker_installed,
|
||||||
|
@ -101,6 +102,17 @@ def gui_main(custom_container, filename):
|
||||||
docker_installer.start()
|
docker_installer.start()
|
||||||
return
|
return
|
||||||
|
|
||||||
|
# The dangerzone VM, for non-Linux platforms
|
||||||
|
if platform.system() == "Darwin":
|
||||||
|
vm = Vm(global_common)
|
||||||
|
else:
|
||||||
|
vm = None
|
||||||
|
|
||||||
|
# Create the system tray
|
||||||
|
systray = SysTray(global_common, gui_common, app, vm)
|
||||||
|
if vm:
|
||||||
|
vm.start()
|
||||||
|
|
||||||
closed_windows = {}
|
closed_windows = {}
|
||||||
windows = {}
|
windows = {}
|
||||||
|
|
||||||
|
@ -156,7 +168,4 @@ def gui_main(custom_container, filename):
|
||||||
# If the application is activated and all windows are closed, open a new one
|
# If the application is activated and all windows are closed, open a new one
|
||||||
app_wrapper.application_activated.connect(application_activated)
|
app_wrapper.application_activated.connect(application_activated)
|
||||||
|
|
||||||
# Create a system tray, which also handles the VM subprocess
|
|
||||||
systray = SysTray(global_common, gui_common, app)
|
|
||||||
|
|
||||||
sys.exit(app.exec_())
|
sys.exit(app.exec_())
|
||||||
|
|
|
@ -1,59 +1,51 @@
|
||||||
import os
|
import platform
|
||||||
from PySide2 import QtWidgets
|
from PySide2 import QtWidgets
|
||||||
|
|
||||||
|
|
||||||
class SysTray(QtWidgets.QSystemTrayIcon):
|
class SysTray(QtWidgets.QSystemTrayIcon):
|
||||||
def __init__(self, global_common, gui_common, app):
|
def __init__(self, global_common, gui_common, app, vm):
|
||||||
super(SysTray, self).__init__()
|
super(SysTray, self).__init__()
|
||||||
self.global_common = global_common
|
self.global_common = global_common
|
||||||
self.gui_common = gui_common
|
self.gui_common = gui_common
|
||||||
self.app = app
|
self.app = app
|
||||||
|
self.vm = vm
|
||||||
|
|
||||||
self.setIcon(self.gui_common.get_window_icon())
|
self.setIcon(self.gui_common.get_window_icon())
|
||||||
|
|
||||||
menu = QtWidgets.QMenu()
|
menu = QtWidgets.QMenu()
|
||||||
self.status_action = menu.addAction("...")
|
|
||||||
self.status_action.setEnabled(False)
|
if platform.system() == "Darwin":
|
||||||
menu.addSeparator()
|
self.status_action = menu.addAction("...")
|
||||||
self.restart_action = menu.addAction("Restart")
|
self.status_action.setEnabled(False)
|
||||||
self.restart_action.triggered.connect(self.restart_clicked)
|
menu.addSeparator()
|
||||||
|
self.restart_action = menu.addAction("Restart")
|
||||||
|
self.restart_action.triggered.connect(self.restart_clicked)
|
||||||
|
|
||||||
self.quit_action = menu.addAction("Quit")
|
self.quit_action = menu.addAction("Quit")
|
||||||
self.quit_action.triggered.connect(self.quit_clicked)
|
self.quit_action.triggered.connect(self.quit_clicked)
|
||||||
|
|
||||||
self.setContextMenu(menu)
|
self.setContextMenu(menu)
|
||||||
self.show()
|
self.show()
|
||||||
|
|
||||||
# Dangerzone VM
|
if self.vm:
|
||||||
self.vpnkit_p = None
|
self.vm.vm_state_change.connect(self.vm_state_change)
|
||||||
self.hyperkit_p = None
|
|
||||||
self.hyperkit_path = self.global_common.get_resource_path("bin/hyperkit")
|
|
||||||
self.vpnkit_path = self.global_common.get_resource_path("bin/vpnkit")
|
|
||||||
self.vm_iso_path = self.global_common.get_resource_path(
|
|
||||||
"vm/alpine-dangerzone-v3.14-x86_64.iso"
|
|
||||||
)
|
|
||||||
self.vm_kernel_path = self.global_common.get_resource_path("vm/vmlinuz-virt")
|
|
||||||
self.vm_initramfs_path = self.global_common.get_resource_path(
|
|
||||||
"vm/initramfs-virt"
|
|
||||||
)
|
|
||||||
self.vm_state_dir = os.path.join(self.global_common.appdata_path, "vm-state")
|
|
||||||
os.makedirs(self.vm_state_dir, exist_ok=True)
|
|
||||||
self.vm_start()
|
|
||||||
|
|
||||||
def vm_start(self):
|
def vm_state_change(self, state):
|
||||||
self.status_action.setText("Starting Dangerzone ...")
|
if state == self.vm.STATE_OFF:
|
||||||
|
self.status_action.setText("Dangerzone VM is off")
|
||||||
# Kill existing processes
|
self.restart_action.setEnabled(True)
|
||||||
if self.vpnkit_p is not None:
|
elif state == self.vm.STATE_STARTING:
|
||||||
self.vpnkit_p.terminate()
|
self.status_action.setText("Dangerzone VM is starting...")
|
||||||
if self.hyperkit_p is not None:
|
self.restart_action.setEnabled(False)
|
||||||
self.hyperkit_p.terminate()
|
elif state == self.vm.STATE_ON:
|
||||||
|
self.status_action.setText("Dangerzone VM is running")
|
||||||
# Run VPNKit
|
self.restart_action.setEnabled(True)
|
||||||
|
elif state == self.vm.STATE_STOPPING:
|
||||||
# Run Hyperkit
|
self.status_action.setText("Dangerzone VM is stopping...")
|
||||||
|
self.restart_action.setEnabled(False)
|
||||||
|
|
||||||
def restart_clicked(self):
|
def restart_clicked(self):
|
||||||
self.status_action.setText("Restarting Dangerzone ...")
|
self.vm.restart()
|
||||||
|
|
||||||
def quit_clicked(self):
|
def quit_clicked(self):
|
||||||
self.app.quit()
|
self.app.quit()
|
||||||
|
|
91
dangerzone/gui/vm.py
Normal file
91
dangerzone/gui/vm.py
Normal file
|
@ -0,0 +1,91 @@
|
||||||
|
import os
|
||||||
|
import sys
|
||||||
|
import subprocess
|
||||||
|
import uuid
|
||||||
|
import pipes
|
||||||
|
from PySide2 import QtCore
|
||||||
|
|
||||||
|
|
||||||
|
class Vm(QtCore.QObject):
|
||||||
|
STATE_OFF = 0
|
||||||
|
STATE_STARTING = 1
|
||||||
|
STATE_ON = 2
|
||||||
|
STATE_STOPPING = 3
|
||||||
|
|
||||||
|
vm_state_change = QtCore.Signal(int)
|
||||||
|
|
||||||
|
def __init__(self, global_common):
|
||||||
|
super(Vm, self).__init__()
|
||||||
|
self.global_common = global_common
|
||||||
|
|
||||||
|
# VM starts off
|
||||||
|
self.state = self.STATE_OFF
|
||||||
|
|
||||||
|
# Hyperkit subprocess
|
||||||
|
self.hyperkit_p = None
|
||||||
|
|
||||||
|
# Relevant paths
|
||||||
|
self.hyperkit_path = self.global_common.get_resource_path("bin/hyperkit")
|
||||||
|
self.vm_iso_path = self.global_common.get_resource_path("vm/dangerzone.iso")
|
||||||
|
self.vm_kernel_path = self.global_common.get_resource_path("vm/kernel")
|
||||||
|
self.vm_initramfs_path = self.global_common.get_resource_path(
|
||||||
|
"vm/initramfs.img"
|
||||||
|
)
|
||||||
|
|
||||||
|
# Folder to hold files related to the VM
|
||||||
|
self.vm_state_dir = os.path.join(self.global_common.appdata_path, "vm-state")
|
||||||
|
os.makedirs(self.vm_state_dir, exist_ok=True)
|
||||||
|
|
||||||
|
# UDID for VM
|
||||||
|
self.vm_uuid = str(uuid.uuid4())
|
||||||
|
self.vm_cmdline = "modules=virtio_net console=ttyS0"
|
||||||
|
|
||||||
|
def start(self):
|
||||||
|
self.state = self.STATE_STARTING
|
||||||
|
self.vm_state_change.emit(self.state)
|
||||||
|
|
||||||
|
# Kill existing process
|
||||||
|
if self.hyperkit_p is not None:
|
||||||
|
self.hyperkit_p.terminate()
|
||||||
|
self.hyperkit_p = None
|
||||||
|
|
||||||
|
# Run Hyperkit
|
||||||
|
args = [
|
||||||
|
self.hyperkit_path,
|
||||||
|
"-F",
|
||||||
|
os.path.join(self.vm_state_dir, "hyperkit.pid"),
|
||||||
|
"-A",
|
||||||
|
"-u",
|
||||||
|
"-m",
|
||||||
|
"4G",
|
||||||
|
"-c",
|
||||||
|
"2",
|
||||||
|
"-s",
|
||||||
|
"0:0,hostbridge",
|
||||||
|
"-s",
|
||||||
|
"31,lpc",
|
||||||
|
"-l",
|
||||||
|
"com1,stdio",
|
||||||
|
"-s",
|
||||||
|
f"1:0,ahci-cd,{self.vm_iso_path}",
|
||||||
|
"-s",
|
||||||
|
"2:0,virtio-net",
|
||||||
|
"-U",
|
||||||
|
self.vm_uuid,
|
||||||
|
"-f",
|
||||||
|
f'kexec,{self.vm_kernel_path},{self.vm_initramfs_path},"{self.vm_cmdline}"',
|
||||||
|
]
|
||||||
|
args_str = " ".join(pipes.quote(s) for s in args)
|
||||||
|
print("> " + args_str)
|
||||||
|
|
||||||
|
self.hyperkit_p = subprocess.Popen(
|
||||||
|
args,
|
||||||
|
stdout=sys.stdout,
|
||||||
|
stderr=sys.stderr,
|
||||||
|
)
|
||||||
|
|
||||||
|
def restart(self):
|
||||||
|
pass
|
||||||
|
|
||||||
|
def stop(self):
|
||||||
|
pass
|
|
@ -38,6 +38,7 @@ sudo -u user sh mkimage.sh --tag v3.14 \
|
||||||
--repository http://dl-cdn.alpinelinux.org/alpine/v3.14/main \
|
--repository http://dl-cdn.alpinelinux.org/alpine/v3.14/main \
|
||||||
--repository http://dl-cdn.alpinelinux.org/alpine/v3.14/community \
|
--repository http://dl-cdn.alpinelinux.org/alpine/v3.14/community \
|
||||||
--profile dangerzone
|
--profile dangerzone
|
||||||
|
mv alpine-dangerzone-v3.14-x86_64.iso dangerzone.iso
|
||||||
|
|
||||||
# Fix permissions
|
# Fix permissions
|
||||||
chmod 755 /vagrant/vm
|
chmod 755 /vagrant/vm
|
||||||
|
@ -45,7 +46,9 @@ chmod 644 /vagrant/vm/*
|
||||||
|
|
||||||
# Extract vmlinuz and initramfs
|
# Extract vmlinuz and initramfs
|
||||||
cd /vagrant/vm
|
cd /vagrant/vm
|
||||||
7z x alpine-dangerzone-v3.14-x86_64.iso boot/vmlinuz-virt
|
7z x dangerzone.iso boot/vmlinuz-virt
|
||||||
7z x alpine-dangerzone-v3.14-x86_64.iso boot/initramfs-virt
|
7z x dangerzone.iso boot/initramfs-virt
|
||||||
mv boot/* .
|
mv boot/* .
|
||||||
rm -r boot
|
rm -r boot
|
||||||
|
mv vmlinuz-virt kernel
|
||||||
|
mv initramfs-virt initramfs.img
|
||||||
|
|
|
@ -22,10 +22,10 @@ $HYPERKIT \
|
||||||
-c 2 \
|
-c 2 \
|
||||||
-s 0:0,hostbridge -s 31,lpc \
|
-s 0:0,hostbridge -s 31,lpc \
|
||||||
-l com1,stdio \
|
-l com1,stdio \
|
||||||
-s 1:0,ahci-cd,$ROOT/alpine-dangerzone-v3.14-x86_64.iso \
|
-s 1:0,ahci-cd,$ROOT/dangerzone.iso \
|
||||||
-s 2:0,virtio-net \
|
-s 2:0,virtio-net \
|
||||||
-U 9efa82d7-ebd5-4287-b1cc-ac4160a39fa7 \
|
-U 9efa82d7-ebd5-4287-b1cc-ac4160a39fa7 \
|
||||||
-f kexec,$ROOT/vmlinuz-virt,$ROOT/initramfs-virt,"earlyprintk=serial console=ttyS0 modules=loop,squashfs,sd-mod,usb-storage vpnkit.connect=connect://2/1999"
|
-f kexec,$ROOT/kernel,$ROOT/initramfs.img,"earlyprintk=serial console=ttyS0 modules=loop,squashfs,sd-mod,usb-storage vpnkit.connect=connect://2/1999"
|
||||||
|
|
||||||
# hyperkit
|
# hyperkit
|
||||||
# -c 1 -m 1024M
|
# -c 1 -m 1024M
|
||||||
|
|
Loading…
Reference in a new issue