예제 #1
0
 def __getattr__(self, name):
     if name == 'web_protocol':
         if not self.ssl:
             return 'http'
         return 'https'
     elif name == 'password_data':
         if self.password[:2] == '1$':
             pass_split = self.password.split('$')
             return (1, pass_split[1], pass_split[2])
         else:
             return (0, PASSWORD_SALT_V0, self.password)
     elif name == 'ssl':
         if self.debug:
             return False
     elif name == 'localhost_ip':
         localhost_ip = cache_db.get('localhost_ip')
         if not localhost_ip:
             try:
                 localhost_ip = socket.gethostbyname('localhost')
             except:
                 localhost_ip = '127.0.0.1'
             cache_db.expire('localhost_ip', LOCALHOST_IP_TTL)
             cache_db.set('localhost_ip', localhost_ip)
         return localhost_ip
     return Config.__getattr__(self, name)
예제 #2
0
파일: utils.py 프로젝트: ogrishman/pritunl
def check_auth(username, password, remote_addr=None):
    if remote_addr:
        cache_key = 'ip_' + remote_addr
        count = cache_db.list_length(cache_key)
        if count and count > 10:
            raise flask.abort(403)

        key_exists = cache_db.exists(cache_key)
        cache_db.list_rpush(cache_key, '')
        if not key_exists:
            cache_db.expire(cache_key, 20)

    db_username = persist_db.dict_get('auth', 'username') or DEFAULT_USERNAME
    if username != db_username:
        return False

    db_password = persist_db.dict_get('auth', 'password')
    if not db_password:
        if password == DEFAULT_PASSWORD:
            return True
        return False

    pass_ver, pass_salt, db_pass_hash = db_password.split('$')
    if pass_ver == '0':
        pass_hash = _hash_password_v0(pass_salt, password)
    elif pass_ver == '1':
        pass_hash = _hash_password_v1(pass_salt, password)
    else:
        return False
    return pass_hash == db_pass_hash
예제 #3
0
파일: utils.py 프로젝트: WrongChao/pritunl
def check_session():
    from pritunl import app_server

    auth_token = flask.request.headers.get("Auth-Token", None)
    if auth_token:
        auth_timestamp = flask.request.headers.get("Auth-Timestamp", None)
        auth_nonce = flask.request.headers.get("Auth-Nonce", None)
        auth_signature = flask.request.headers.get("Auth-Signature", None)
        if not auth_token or not auth_timestamp or not auth_nonce or not auth_signature:
            return False

        try:
            if abs(int(auth_timestamp) - int(time.time())) > AUTH_TIME_WINDOW:
                return False
        except ValueError:
            return False

        cache_key = "auth_nonce-%s" % auth_nonce
        if cache_db.exists(cache_key):
            return False
        cache_db.expire(cache_key, int(AUTH_TIME_WINDOW * 2.1))
        cache_db.set(cache_key, auth_timestamp)

        auth_token_hash = persist_db.dict_get("auth", "token")
        auth_secret = persist_db.dict_get("auth", "secret")
        if not auth_token_hash or not auth_secret:
            return False
        if not _test_password_hash(auth_token_hash, auth_token):
            return False

        auth_string = "&".join(
            [auth_token, auth_timestamp, auth_nonce, flask.request.method, flask.request.path]
            + ([flask.request.data] if flask.request.data else [])
        )

        if len(auth_string) > AUTH_SIG_STRING_MAX_LEN:
            return False

        auth_test_signature = base64.b64encode(hmac.new(auth_secret.encode(), auth_string, hashlib.sha256).digest())
        if auth_signature != auth_test_signature:
            return False
    else:
        if not flask.session:
            return False

        if not flask.session.get("auth"):
            flask.session.clear()
            return False

        if not app_server.ssl and flask.session.get("source") != get_remote_addr():
            flask.session.clear()
            return False

        if app_server.session_timeout and int(time.time()) - flask.session["timestamp"] > app_server.session_timeout:
            flask.session.clear()
            return False
    return True
예제 #4
0
파일: user.py 프로젝트: monsterChen/pritunl
    def verify_otp_code(self, code, remote_ip=None):
        if remote_ip:
            otp_cache = cache_db.get(self.get_cache_key('otp_cache'))
            if otp_cache:
                cur_code, cur_remote_ip = otp_cache.split(',')
                if cur_code == code and cur_remote_ip == remote_ip:
                    cache_db.expire(self.get_cache_key('otp_cache'),
                        OTP_CACHE_TTL)
                    return True
                else:
                    cache_db.remove(self.get_cache_key('otp_cache'))

        otp_secret = self.otp_secret
        padding = 8 - len(otp_secret) % 8
        if padding != 8:
            otp_secret = otp_secret.ljust(len(otp_secret) + padding, '=')
        otp_secret = base64.b32decode(otp_secret.upper())
        valid_codes = []
        epoch = int(time.time() / 30)
        for epoch_offset in range(-1, 2):
            value = struct.pack('>q', epoch + epoch_offset)
            hmac_hash = hmac.new(otp_secret, value, hashlib.sha1).digest()
            offset = ord(hmac_hash[-1]) & 0x0F
            truncated_hash = hmac_hash[offset:offset + 4]
            truncated_hash = struct.unpack('>L', truncated_hash)[0]
            truncated_hash &= 0x7FFFFFFF
            truncated_hash %= 1000000
            valid_codes.append('%06d' % truncated_hash)
        if code not in valid_codes:
            return False

        used_codes = cache_db.dict_get_all(self.get_cache_key('otp'))
        for auth_time, used_code in used_codes.items():
            if int(time.time()) - int(auth_time) > 120:
                cache_db.dict_remove(self.get_cache_key('otp'), auth_time)
            if used_code == code:
                return False

        cache_db.dict_set(self.get_cache_key('otp'),
            str(int(time.time())), code)
        cache_db.expire(self.get_cache_key('otp_cache'), OTP_CACHE_TTL)
        cache_db.set(self.get_cache_key('otp_cache'),
            ','.join((code, remote_ip)))
        return True
예제 #5
0
파일: utils.py 프로젝트: bitland/pritunl
def check_auth(username, password, remote_addr=None):
    from administrator import Administrator

    if remote_addr:
        # TODO
        cache_key = 'ip_' + remote_addr
        count = cache_db.list_length(cache_key)
        if count and count > 10:
            raise flask.abort(403)

        # TODO
        key_exists = cache_db.exists(cache_key)
        cache_db.list_rpush(cache_key, '')
        if not key_exists:
            cache_db.expire(cache_key, 20)

    administrator = Administrator.find_user(username=username)
    if not administrator:
        return
    if not administrator.test_password(password):
        return
    return administrator
예제 #6
0
파일: utils.py 프로젝트: WrongChao/pritunl
def check_auth(username, password, remote_addr=None):
    if remote_addr:
        cache_key = "ip_" + remote_addr
        count = cache_db.list_length(cache_key)
        if count and count > 10:
            raise flask.abort(403)

        key_exists = cache_db.exists(cache_key)
        cache_db.list_rpush(cache_key, "")
        if not key_exists:
            cache_db.expire(cache_key, 20)

    db_username = persist_db.dict_get("auth", "username") or DEFAULT_USERNAME
    if username != db_username:
        return False

    db_password = persist_db.dict_get("auth", "password")
    if not db_password:
        if password == DEFAULT_PASSWORD:
            return True
        return False
    return _test_password_hash(db_password, password)
예제 #7
0
파일: utils.py 프로젝트: bitland/pritunl
def check_session():
    from administrator import Administrator

    auth_token = flask.request.headers.get('Auth-Token', None)
    if auth_token:
        auth_timestamp = flask.request.headers.get('Auth-Timestamp', None)
        auth_nonce = flask.request.headers.get('Auth-Nonce', None)
        auth_signature = flask.request.headers.get('Auth-Signature', None)
        if not auth_token or not auth_timestamp or not auth_nonce or \
                not auth_signature:
            return False
        auth_nonce = auth_nonce[:32]

        try:
            if abs(int(auth_timestamp) - int(time.time())) > AUTH_TIME_WINDOW:
                return False
        except ValueError:
            return False

        # TODO
        cache_key = 'auth_nonce-%s' % auth_nonce
        if cache_db.exists(cache_key):
            return False

        administrator = Administrator.find_user(token=auth_token)
        if not administrator:
            return False

        auth_string = '&'.join([
            auth_token, auth_timestamp, auth_nonce, flask.request.method,
            flask.request.path] +
            ([flask.request.data] if flask.request.data else []))

        if len(auth_string) > AUTH_SIG_STRING_MAX_LEN:
            return False

        auth_test_signature = base64.b64encode(hmac.new(
            administrator.secret.encode(), auth_string,
            hashlib.sha256).digest())
        if auth_signature != auth_test_signature:
            return False

        # TODO
        cache_db.expire(cache_key, int(AUTH_TIME_WINDOW * 2.1))
        cache_db.set(cache_key, auth_timestamp)

        flask.request.administrator = administrator
    else:
        from pritunl import app_server
        if not flask.session:
            return False

        admin_id = flask.session.get('admin_id')
        if not admin_id:
            return False

        administrator = Administrator.get_user(id=admin_id)
        if not administrator:
            return False

        if not app_server.ssl and flask.session.get(
                'source') != get_remote_addr():
            flask.session.clear()
            return False

        if SESSION_TIMEOUT and int(time.time()) - \
                flask.session['timestamp'] > SESSION_TIMEOUT:
            flask.session.clear()
            return False

        flask.request.administrator = administrator
    return True
예제 #8
0
    def create_user_key_link(self, user_id):
        key_id = uuid.uuid4().hex
        key_id_key = 'key_token-%s' % key_id

        view_id = None
        uri_id = None
        for i in xrange(2):
            for i in xrange(2048):
                temp_id = ''.join(random.sample(
                    SHORT_URL_CHARS, SHORT_URL_LEN))
                if not view_id:
                    if not cache_db.exists('view_token-%s' % temp_id):
                        view_id = temp_id
                        break
                else:
                    if not cache_db.exists('uri_token-%s' % temp_id):
                        uri_id = temp_id
                        break
            if not view_id and not uri_id:
                raise KeyLinkError('Failed to generate random id')
        view_id_key = 'view_token-%s' % view_id
        uri_id_key = 'uri_token-%s' % uri_id

        cache_db.expire(key_id_key, KEY_LINK_TIMEOUT)
        cache_db.dict_set(key_id_key, 'org_id', self.id)
        cache_db.dict_set(key_id_key, 'user_id', user_id)
        cache_db.dict_set(key_id_key, 'view_id', view_id)
        cache_db.dict_set(key_id_key, 'uri_id', uri_id)

        conf_urls = []
        if app_server.inline_certs:
            for server in self.iter_servers():
                conf_id = uuid.uuid4().hex
                conf_id_key = 'conf_token-%s' % conf_id

                cache_db.expire(conf_id_key, KEY_LINK_TIMEOUT)
                cache_db.dict_set(conf_id_key, 'org_id', self.id)
                cache_db.dict_set(conf_id_key, 'user_id', user_id)
                cache_db.dict_set(conf_id_key, 'server_id', server.id)

                conf_urls.append({
                    'id': conf_id,
                    'server_name': server.name,
                    'url': '/key/%s.ovpn' % conf_id,
                })

        cache_db.expire(view_id_key, KEY_LINK_TIMEOUT)
        cache_db.dict_set(view_id_key, 'org_id', self.id)
        cache_db.dict_set(view_id_key, 'user_id', user_id)
        cache_db.dict_set(view_id_key, 'key_id', key_id)
        cache_db.dict_set(view_id_key, 'uri_id', uri_id)
        cache_db.dict_set(view_id_key,
            'conf_urls', json.dumps(conf_urls))

        cache_db.expire(uri_id_key, KEY_LINK_TIMEOUT)
        cache_db.dict_set(uri_id_key, 'org_id', self.id)
        cache_db.dict_set(uri_id_key, 'user_id', user_id)

        return {
            'id': key_id,
            'key_url': '/key/%s.tar' % key_id,
            'view_url': '/k/%s' % view_id,
            'uri_url': '/ku/%s' % uri_id,
        }
예제 #9
0
def check_session():
    from pritunl import app_server
    auth_valid = True
    auth_token = flask.request.headers.get('Auth-Token', None)
    if auth_token:
        auth_timestamp = flask.request.headers.get('Auth-Timestamp', None)
        auth_nonce = flask.request.headers.get('Auth-Nonce', None)
        auth_signature = flask.request.headers.get('Auth-Signature', None)
        if not auth_token or not auth_timestamp or not auth_nonce or \
                not auth_signature:
            return False
        auth_nonce = auth_nonce[:32]

        try:
            if abs(int(auth_timestamp) - int(time.time())) > AUTH_TIME_WINDOW:
                return False
        except ValueError:
            return False

        cache_key = 'auth_nonce-%s' % auth_nonce
        if cache_db.exists(cache_key):
            return False

        auth_token_hash = persist_db.dict_get('auth', 'token')
        auth_secret = persist_db.dict_get('auth', 'secret')
        if not auth_token_hash or not auth_secret:
            return False
        if not _test_password_hash(auth_token_hash, auth_token):
            auth_valid = False

        auth_string = '&'.join([
            auth_token, auth_timestamp, auth_nonce, flask.request.method,
            flask.request.path] +
            ([flask.request.data] if flask.request.data else []))

        if len(auth_string) > AUTH_SIG_STRING_MAX_LEN:
            return False

        auth_test_signature = base64.b64encode(hmac.new(
            auth_secret.encode(), auth_string, hashlib.sha256).digest())
        if auth_signature != auth_test_signature:
            auth_valid = False

        if auth_valid:
            cache_db.expire(cache_key, int(AUTH_TIME_WINDOW * 2.1))
            cache_db.set(cache_key, auth_timestamp)
    else:
        if not flask.session:
            return False

        if not flask.session.get('auth'):
            flask.session.clear()
            return False

        if not app_server.ssl and flask.session.get(
                'source') != get_remote_addr():
            flask.session.clear()
            return False

        if app_server.session_timeout and int(time.time()) - \
                flask.session['timestamp'] > app_server.session_timeout:
            flask.session.clear()
            return False
    return auth_valid