Source code for implant.bootstrap
# Copyright 2018 Oliver Berger
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
"""Bootstrap of a remote python process."""
import base64
import inspect
import logging
import types
import zlib
import pkg_resources
from .. import core, msgpack
log = logging.getLogger(__name__)
VENV_DEFAULT = '~/.implant'
[docs]class Bootstrap(dict):
"""Provide an iterator over the bootstrap code."""
def __init__(self, code, options=None):
super(Bootstrap, self).__init__()
self.__dict__ = self
if options is None:
options = {}
self.options = base64.b64encode(msgpack.encode(options)).decode(),
venv = options.get('venv')
self.venv = VENV_DEFAULT if venv is True\
else None if venv is False\
else venv
if isinstance(code, types.ModuleType):
code_source = inspect.getsource(code).encode()
self.code_path = 'remote://{}'.format(inspect.getsourcefile(code))
else:
code_source = code
self.code_path = 'remote-string://'
self.code = base64.b64encode(zlib.compress(code_source, 9)).decode()
raw_len = len(code_source)
comp_len = len(self.code)
log.debug("Code compression ratio of %s -> %s: %.2f%%",
raw_len, comp_len, comp_len * 100 / raw_len)
msgpack_code_source = inspect.getsource(msgpack).encode()
self.msgpack_code_path = 'remote://{}'.format(
inspect.getsourcefile(msgpack))
self.msgpack_code = base64.b64encode(
zlib.compress(msgpack_code_source, 9)).decode(),
def __iter__(self):
if self.venv:
_with_venv_fmt = pkg_resources.resource_stream(
__name__, '_with_venv.py.fmt')
yield from self.formatsourcelines(_with_venv_fmt.readlines())
_main_fmt = pkg_resources.resource_stream(__name__, '_main.py.fmt')
yield from self.formatsourcelines(_main_fmt.readlines())
def __str__(self):
return ''.join(self)