summaryrefslogtreecommitdiff
path: root/src/leap/bitmask/backend
diff options
context:
space:
mode:
authorKali Kaneko <kali@leap.se>2016-04-25 21:32:54 -0400
committerKali Kaneko <kali@leap.se>2016-04-25 21:32:54 -0400
commit434d0534661d7c222e5dabc4e5e237b060d2212b (patch)
tree2e7bf0e556f983bd5404481a9aa4fb0fd7d75778 /src/leap/bitmask/backend
parent9ee728108f3b894d097206cc6ff6d0a70808f2d5 (diff)
parentf47416804ad2f88ba27aa032e0d2fc1c9fd314c8 (diff)
Merge branch 'develop' into debian/experimental
Diffstat (limited to 'src/leap/bitmask/backend')
-rw-r--r--src/leap/bitmask/backend/api.py4
-rw-r--r--src/leap/bitmask/backend/components.py90
-rw-r--r--src/leap/bitmask/backend/leapbackend.py13
-rw-r--r--src/leap/bitmask/backend/leapsignaler.py1
4 files changed, 93 insertions, 15 deletions
diff --git a/src/leap/bitmask/backend/api.py b/src/leap/bitmask/backend/api.py
index 48aa2090..2fd983ae 100644
--- a/src/leap/bitmask/backend/api.py
+++ b/src/leap/bitmask/backend/api.py
@@ -42,6 +42,8 @@ API = (
"keymanager_export_keys",
"keymanager_get_key_details",
"keymanager_list_keys",
+ "pixelated_start_service",
+ "pixelated_stop_service",
"provider_bootstrap",
"provider_cancel_setup",
"provider_get_all_services",
@@ -57,6 +59,7 @@ API = (
"soledad_change_password",
"soledad_close",
"soledad_load_offline",
+ "soledad_get_service_token",
"tear_fw_down",
"bitmask_root_vpn_down",
"user_cancel_login",
@@ -135,6 +138,7 @@ SIGNALS = (
"soledad_offline_finished",
"soledad_password_change_error",
"soledad_password_change_ok",
+ "soledad_got_service_token",
"srp_auth_bad_user_or_password",
"srp_auth_connection_error",
"srp_auth_error",
diff --git a/src/leap/bitmask/backend/components.py b/src/leap/bitmask/backend/components.py
index 5f34d290..3192e1c4 100644
--- a/src/leap/bitmask/backend/components.py
+++ b/src/leap/bitmask/backend/components.py
@@ -20,13 +20,16 @@ Backend components
# TODO [ ] Get rid of all this deferToThread mess, or at least contain
# all of it into its own threadpool.
+import json
import os
+import shutil
import socket
+import tempfile
import time
from functools import partial
-from twisted.internet import threads, defer
+from twisted.internet import threads, defer, reactor
from twisted.python import log
import zope.interface
@@ -38,9 +41,10 @@ from leap.bitmask.crypto.srpauth import SRPAuth
from leap.bitmask.crypto.srpregister import SRPRegister
from leap.bitmask.logs.utils import get_logger
from leap.bitmask.platform_init import IS_LINUX
+from leap.bitmask import pix
from leap.bitmask.provider.pinned import PinnedProviders
from leap.bitmask.provider.providerbootstrapper import ProviderBootstrapper
-from leap.bitmask.services import get_supported
+from leap.bitmask.services import get_supported, EIP_SERVICE
from leap.bitmask.services.eip import eipconfig
from leap.bitmask.services.eip import get_openvpn_management
from leap.bitmask.services.eip.eipbootstrapper import EIPBootstrapper
@@ -572,8 +576,10 @@ class EIP(object):
self._signaler.eip_uninitialized_provider)
return
- eip_config = eipconfig.EIPConfig()
provider_config = ProviderConfig.get_provider_config(domain)
+ if EIP_SERVICE not in provider_config.get_services():
+ return
+ eip_config = eipconfig.EIPConfig()
api_version = provider_config.get_api_version()
eip_config.set_api_version(api_version)
@@ -643,12 +649,14 @@ class EIP(object):
:param domain: the domain for the provider to check
:type domain: str
"""
- if not LinuxPolicyChecker.is_up():
+ if IS_LINUX and not LinuxPolicyChecker.is_up():
logger.error("No polkit agent running.")
return False
- eip_config = eipconfig.EIPConfig()
provider_config = ProviderConfig.get_provider_config(domain)
+ if EIP_SERVICE not in provider_config.get_services():
+ return False
+ eip_config = eipconfig.EIPConfig()
api_version = provider_config.get_api_version()
eip_config.set_api_version(api_version)
@@ -763,6 +771,7 @@ class Soledad(object):
self._signaler = signaler
self._soledad_bootstrapper = SoledadBootstrapper(signaler)
self._soledad_defer = None
+ self._service_tokens = {}
def bootstrap(self, username, domain, password):
"""
@@ -786,6 +795,9 @@ class Soledad(object):
provider_config, username, password,
download_if_needed=True)
self._soledad_defer.addCallback(self._set_proxies_cb)
+ self._soledad_defer.addCallback(self._set_service_tokens_cb)
+ self._soledad_defer.addCallback(self._write_tokens_file,
+ username, domain)
else:
if self._signaler is not None:
self._signaler.signal(self._signaler.soledad_bootstrap_failed)
@@ -793,6 +805,38 @@ class Soledad(object):
return self._soledad_defer
+ def _set_service_tokens_cb(self, result):
+
+ def register_service_token(token, service):
+ self._service_tokens[service] = token
+ if self._signaler is not None:
+ self._signaler.signal(
+ self._signaler.soledad_got_service_token,
+ (service, token))
+
+ sol = self._soledad_bootstrapper.soledad
+ d = sol.get_or_create_service_token('mail_auth')
+ d.addCallback(register_service_token, 'mail_auth')
+ d.addCallback(lambda _: result)
+ return d
+
+ def _write_tokens_file(self, result, username, domain):
+ tokens_folder = os.path.join(tempfile.gettempdir(), "bitmask_tokens")
+ if os.path.exists(tokens_folder):
+ try:
+ shutil.rmtree(tokens_folder)
+ except OSError as e:
+ logger.error("Can't remove tokens folder %s: %s"
+ % (tokens_folder, e))
+ return
+ os.mkdir(tokens_folder, 0700)
+
+ tokens_path = os.path.join(tokens_folder,
+ "%s@%s.json" % (username, domain))
+ with open(tokens_path, 'w') as ftokens:
+ json.dump(self._service_tokens, ftokens)
+ return result
+
def _set_proxies_cb(self, _):
"""
Update the soledad and keymanager proxies to reference the ones created
@@ -803,6 +847,12 @@ class Soledad(object):
zope.proxy.setProxiedObject(self._keymanager_proxy,
self._soledad_bootstrapper.keymanager)
+ def get_service_token(self, service):
+ """
+ Get an authentication token for a given service.
+ """
+ return self._service_tokens.get(service, '')
+
def load_offline(self, username, password, uuid):
"""
Load the soledad database in offline mode.
@@ -955,12 +1005,11 @@ class Keymanager(object):
def get_key_details(self, username):
"""
- List all the keys stored in the local DB.
+ Get information on our primary key pair
"""
def signal_details(public_key):
- details = (public_key.key_id, public_key.fingerprint)
self._signaler.signal(self._signaler.keymanager_key_details,
- details)
+ public_key.get_dict())
d = self._keymanager_proxy.get_key(username,
openpgp.OpenPGPKey)
@@ -1012,7 +1061,8 @@ class Mail(object):
"""
return threads.deferToThread(
self._smtp_bootstrapper.start_smtp_service,
- self._keymanager_proxy, full_user_id, download_if_needed)
+ self._soledad_proxy, self._keymanager_proxy, full_user_id,
+ download_if_needed)
def start_imap_service(self, full_user_id, offline=False):
"""
@@ -1058,6 +1108,18 @@ class Mail(object):
"""
return threads.deferToThread(self._stop_imap_service)
+ def start_pixelated_service(self, full_user_id):
+ if pix.HAS_PIXELATED:
+ reactor.callFromThread(
+ pix.start_pixelated_user_agent,
+ full_user_id,
+ self._soledad_proxy,
+ self._keymanager_proxy)
+
+ def stop_pixelated_service(self):
+ # TODO stop it, somehow
+ pass
+
class Authenticate(object):
"""
@@ -1153,15 +1215,13 @@ class Authenticate(object):
def get_logged_in_status(self):
"""
- Signal if the user is currently logged in or not.
+ Signal if the user is currently logged in or not. If logged in,
+ authenticated username is passed as argument to the signal.
"""
if self._signaler is None:
return
- signal = None
if self._is_logged_in():
- signal = self._signaler.srp_status_logged_in
+ self._signaler.signal(self._signaler.srp_status_logged_in)
else:
- signal = self._signaler.srp_status_not_logged_in
-
- self._signaler.signal(signal)
+ self._signaler.signal(self._signaler.srp_status_not_logged_in)
diff --git a/src/leap/bitmask/backend/leapbackend.py b/src/leap/bitmask/backend/leapbackend.py
index cf45c4f8..56b1597c 100644
--- a/src/leap/bitmask/backend/leapbackend.py
+++ b/src/leap/bitmask/backend/leapbackend.py
@@ -35,6 +35,7 @@ class LeapBackend(Backend):
"""
Backend server subclass, used to implement the API methods.
"""
+
def __init__(self, bypass_checks=False, frontend_pid=None):
"""
Constructor for the backend.
@@ -438,6 +439,12 @@ class LeapBackend(Backend):
"""
self._soledad.load_offline(username, password, uuid)
+ def soledad_get_service_token(self, service):
+ """
+ Attempt to get an authentication token for a given service.
+ """
+ self._soledad.get_service_token(service)
+
def soledad_cancel_bootstrap(self):
"""
Cancel the ongoing soledad bootstrapping process (if any).
@@ -524,6 +531,12 @@ class LeapBackend(Backend):
"""
self._mail.stop_imap_service()
+ def pixelated_start_service(self, full_user_id):
+ self._mail.start_pixelated_service(full_user_id)
+
+ def pixelated_stop_service(self):
+ self._mail.stop_pixelated_service()
+
def settings_set_selected_gateway(self, provider, gateway):
"""
Set the selected gateway for a given provider.
diff --git a/src/leap/bitmask/backend/leapsignaler.py b/src/leap/bitmask/backend/leapsignaler.py
index 1ac51f5e..13a9fa5f 100644
--- a/src/leap/bitmask/backend/leapsignaler.py
+++ b/src/leap/bitmask/backend/leapsignaler.py
@@ -97,6 +97,7 @@ class LeapSignaler(SignalerQt):
soledad_offline_finished = QtCore.Signal()
soledad_password_change_error = QtCore.Signal()
soledad_password_change_ok = QtCore.Signal()
+ soledad_got_service_token = QtCore.Signal(object)
srp_auth_bad_user_or_password = QtCore.Signal()
srp_auth_connection_error = QtCore.Signal()