Exemplo n.º 1
0
def compss_worker(persistent_storage):
    """
    Worker main method (invocated from __main__).

    :param persistent_storage: Persistent storage boolean
    :return: None
    """

    logger = logging.getLogger('pycompss.worker.worker')

    logger.debug("Starting Worker")

    # Set the binding in worker mode
    set_pycompss_context('WORKER')

    args = sys.argv[6:]
    path = args[0]
    method_name = args[1]

    num_slaves = int(args[2])
    slaves = []
    for i in range(2, 2 + num_slaves):
        slaves.append(args[i])
    arg_position = 3 + num_slaves

    args = args[arg_position:]
    cus = args[0]

    args = args[1:]
    has_target = args[0]
    return_type = args[1]
    num_returns = int(args[2])
    num_params = int(args[3])

    args = args[4:]

    # COMPSs keywords for tasks (ie: tracing, process name...)
    compss_kwargs = {
        'compss_tracing': tracing,
        'compss_process_name': "GAT",
        'compss_storage_conf': storage_conf,
        'compss_return_length': num_returns
    }

    values = []
    types = []
    streams = []
    prefixes = []

    if tracing:
        pyextrae.event(TASK_EVENTS, 0)
        pyextrae.event(TASK_EVENTS, PARAMETER_PROCESSING)

    if persistent_storage:
        from pycompss.util.persistent_storage import storage_task_context

    # Get all parameter values
    logger.debug("Processing parameters:")
    pos = 0
    for i in range(0, num_params):
        p_type = int(args[pos])
        p_stream = int(args[pos + 1])
        p_prefix = args[pos + 2]
        p_value = args[pos + 3]

        logger.debug("Parameter : " + str(i))
        logger.debug("\t * Type : " + str(p_type))
        logger.debug("\t * Stream : " + str(p_stream))
        logger.debug("\t * Prefix : " + str(p_prefix))
        logger.debug("\t * Value: " + str(p_value))

        types.append(p_type)
        streams.append(p_stream)
        prefixes.append(p_prefix)

        if p_type == TYPE.FILE:
            values.append(p_value)
        elif p_type == TYPE.EXTERNAL_PSCO:
            po = get_by_id(p_value)
            values.append(po)
            pos += 1  # Skip info about direction (R, W)
        elif p_type == TYPE.STRING:
            num_substrings = int(p_value)
            aux = ''
            first_substring = True
            for j in range(4, num_substrings + 4):
                if not first_substring:
                    aux += ' '
                first_substring = False
                aux += args[pos + j]
            # Decode the string received
            aux = base64.b64decode(aux.encode())
            if aux.decode() == EMPTY_STRING_KEY:
                # Then it is an empty string
                aux = ""
            else:
                #######
                # Check if the string is really an object
                # Required in order to recover objects passed as parameters.
                # - Option object_conversion
                real_value = aux
                try:
                    # try to recover the real object
                    if IS_PYTHON3:
                        # decode removes double backslash, and encode returns as binary
                        aux = deserialize_from_string(aux.decode(STR_ESCAPE).encode())
                    else:
                        # decode removes double backslash, and str casts the output
                        aux = deserialize_from_string(str(aux.decode(STR_ESCAPE)))
                except (SerializerException, ValueError, EOFError):
                    # was not an object
                    aux = str(real_value.decode())
                #######
            values.append(aux)
            logger.debug("\t * Final Value: " + str(aux))
            pos += num_substrings
        elif p_type == TYPE.INT:
            values.append(int(p_value))
        elif p_type == TYPE.LONG:
            my_l = long(p_value)
            if my_l > JAVA_MAX_INT or my_l < JAVA_MIN_INT:
                # A Python int was converted to a Java long to prevent overflow
                # We are sure we will not overflow Python int, otherwise this
                # would have been passed as a serialized object.
                my_l = int(my_l)
            values.append(my_l)
        elif p_type == TYPE.DOUBLE:
            values.append(float(p_value))
        elif p_type == TYPE.BOOLEAN:
            if p_value == 'true':
                values.append(True)
            else:
                values.append(False)
        # elif (p_type == TYPE.OBJECT):
        #    pass
        else:
            logger.fatal("Invalid type (%d) for parameter %d" % (p_type, i))
            exit(1)
        pos += 4

    if tracing:
        pyextrae.event(TASK_EVENTS, 0)
        pyextrae.event(TASK_EVENTS, LOGGING)

    if logger.isEnabledFor(logging.DEBUG):
        values_str = ''
        types_str = ''
        for v in values:
            values_str += "\t\t" + str(v) + "\n"
        for t in types:
            types_str += str(t) + " "
        logger.debug("RUN TASK with arguments\n" +
                     "\t- Path: " + path + "\n" +
                     "\t- Method/function name: " + method_name + "\n" +
                     "\t- Has target: " + has_target + "\n" +
                     "\t- # parameters: " + str(num_params) + "\n" +
                     "\t- Values:\n" + values_str +
                     "\t- COMPSs types: " + types_str)

    if tracing:
        pyextrae.event(TASK_EVENTS, 0)
        pyextrae.event(TASK_EVENTS, MODULES_IMPORT)

    try:
        # Try to import the module (for functions)
        logger.debug("Trying to import the user module.")
        if sys.version_info >= (2, 7):
            module = importlib.import_module(path)  # Python 2.7
            logger.debug("Module successfully loaded (Python version >= 2.7)")
        else:
            module = __import__(path, globals(), locals(), [path], -1)
            logger.debug("Module successfully loaded (Python version < 2.7")

        if persistent_storage:
            with storage_task_context(logger, values, config_file_path=storage_conf):
                getattr(module, method_name)(*values, compss_types=types, **compss_kwargs)
                if tracing:
                    pyextrae.eventandcounters(TASK_EVENTS, 0)
                    pyextrae.eventandcounters(TASK_EVENTS, WORKER_END)
        else:
            getattr(module, method_name)(*values, compss_types=types, **compss_kwargs)
            if tracing:
                pyextrae.eventandcounters(TASK_EVENTS, 0)
                pyextrae.eventandcounters(TASK_EVENTS, WORKER_END)
    # ==========================================================================
    except AttributeError:
        # Appears with functions that have not been well defined.
        exc_type, exc_value, exc_traceback = sys.exc_info()
        lines = traceback.format_exception(exc_type, exc_value, exc_traceback)
        logger.exception("WORKER EXCEPTION - Attribute Error Exception")
        logger.exception(''.join(line for line in lines))
        logger.exception("Check that all parameters have been defined with " +
                         "an absolute import path (even if in the same file)")
        exit(1)
    # ==========================================================================
    except ImportError:
        logger.debug("Could not import the module. Reason: Method in class.")
        # Not the path of a module, it ends with a class name
        class_name = path.split('.')[-1]
        module_name = '.'.join(path.split('.')[0:-1])

        if '.' in path:
            module_name = '.'.join(path.split('.')[0:-1])
        else:
            module_name = path
        module = __import__(module_name, fromlist=[class_name])
        klass = getattr(module, class_name)
        logger.debug("Method in class %s of module %s" % (class_name, module_name))

        if has_target == 'true':
            # Instance method
            file_name = values.pop()
            logger.debug("Deserialize self from file.")
            obj = deserialize_from_file(file_name)

            logger.debug("Processing callee, a hidden object of %s in file %s" % (file_name, type(obj)))
            values.insert(0, obj)
            types.pop()
            types.insert(0, TYPE.OBJECT)

            if persistent_storage:
                with storage_task_context(logger, values, config_file_path=storage_conf):
                    getattr(klass, method_name)(*values, compss_types=types, **compss_kwargs)
                    if tracing:
                        pyextrae.eventandcounters(TASK_EVENTS, 0)
                        pyextrae.eventandcounters(TASK_EVENTS, WORKER_END)
            else:
                getattr(klass, method_name)(*values, compss_types=types, **compss_kwargs)
                if tracing:
                    pyextrae.eventandcounters(TASK_EVENTS, 0)
                    pyextrae.eventandcounters(TASK_EVENTS, WORKER_END)

            logger.debug("Serializing self to file")
            logger.debug("Obj: " + str(obj))
            serialize_to_file(obj, file_name)
        else:
            # Class method - class is not included in values (e.g. values = [7])
            types.insert(0, None)  # class must be first type

            if persistent_storage:
                with storage_task_context(logger, values, config_file_path=storage_conf):
                    getattr(klass, method_name)(*values, compss_types=types, **compss_kwargs)
                    if tracing:
                        pyextrae.eventandcounters(TASK_EVENTS, 0)
                        pyextrae.eventandcounters(TASK_EVENTS, WORKER_END)
            else:
                getattr(klass, method_name)(*values, compss_types=types, **compss_kwargs)
                if tracing:
                    pyextrae.eventandcounters(TASK_EVENTS, 0)
                    pyextrae.eventandcounters(TASK_EVENTS, WORKER_END)
    # ==========================================================================
    except Exception:
        exc_type, exc_value, exc_traceback = sys.exc_info()
        lines = traceback.format_exception(exc_type, exc_value, exc_traceback)
        logger.exception("WORKER EXCEPTION")
        logger.exception(''.join(line for line in lines))
        exit(1)
Exemplo n.º 2
0
def compss_persistent_worker():
    """
    Persistent worker main function.
    Retrieves the initial configuration and spawns the worker processes.

    :return: None
    """

    # Set the binding in worker mode
    set_pycompss_context('WORKER')

    # Get args
    debug = (sys.argv[1] == 'true')
    global TRACING
    TRACING = (sys.argv[2] == 'true')
    storage_conf = sys.argv[3]
    tasks_x_node = int(sys.argv[4])
    in_pipes = sys.argv[5:5 + tasks_x_node]
    out_pipes = sys.argv[5 + tasks_x_node:]

    if TRACING:
        import pyextrae.multiprocessing as pyextrae
        pyextrae.eventandcounters(SYNC_EVENTS, 1)
        pyextrae.eventandcounters(TASK_EVENTS, WORKER_RUNNING)

    if debug:
        assert tasks_x_node == len(in_pipes)
        assert tasks_x_node == len(out_pipes)

    persistent_storage = False
    if storage_conf != 'null':
        persistent_storage = True
        from storage.api import initWorker as initStorageAtWorker
        from storage.api import finishWorker as finishStorageAtWorker

    # Load log level configuration file
    worker_path = os.path.dirname(os.path.realpath(__file__))
    if debug:
        # Debug
        init_logging_worker(worker_path + '/../../log/logging.json.debug')
    else:
        # Default
        init_logging_worker(worker_path + '/../../log/logging.json.off')

    if __debug__:
        logger = logging.getLogger('pycompss.worker.worker')
        logger.debug("[PYTHON WORKER] piper_worker.py wake up")
        logger.debug("[PYTHON WORKER] -----------------------------")
        logger.debug("[PYTHON WORKER] Persistent worker parameters:")
        logger.debug("[PYTHON WORKER] -----------------------------")
        logger.debug("[PYTHON WORKER] Debug          : " + str(debug))
        logger.debug("[PYTHON WORKER] Tracing        : " + str(TRACING))
        logger.debug("[PYTHON WORKER] Tasks per node : " + str(tasks_x_node))
        logger.debug("[PYTHON WORKER] In Pipes       : " + str(in_pipes))
        logger.debug("[PYTHON WORKER] Out Pipes      : " + str(out_pipes))
        logger.debug("[PYTHON WORKER] Storage conf.  : " + str(storage_conf))
        logger.debug("[PYTHON WORKER] -----------------------------")

    if persistent_storage:
        # Initialize storage
        initStorageAtWorker(config_file_path=storage_conf)

    # Create new threads
    queues = []
    for i in range(0, tasks_x_node):
        if __debug__:
            logger.debug("[PYTHON WORKER] Launching process " + str(i))
        process_name = 'Process-' + str(i)
        queues.append(Queue())

        def create_threads():
            PROCESSES.append(
                Process(target=worker,
                        args=(queues[i], process_name, in_pipes[i],
                              out_pipes[i], storage_conf)))
            PROCESSES[i].start()

        create_threads()

    # Catch SIGTERM send by bindings_piper to exit all PROCESSES
    signal.signal(signal.SIGTERM, shutdown_handler)

    # Wait for all threads
    for i in range(0, tasks_x_node):
        PROCESSES[i].join()

    # Check if there is any exception message from the threads
    for i in range(0, tasks_x_node):
        if not queues[i].empty:
            print(queues[i].get())

    for q in queues:
        q.close()
        q.join_thread()

    if persistent_storage:
        # Finish storage
        finishStorageAtWorker()

    if __debug__:
        logger.debug("[PYTHON WORKER] Finished")

    if TRACING:
        pyextrae.eventandcounters(TASK_EVENTS, 0)
        pyextrae.eventandcounters(SYNC_EVENTS, 0)
Exemplo n.º 3
0
def launch_pycompss_application(
        app,
        func,
        log_level='off',
        o_c=False,
        debug=False,
        graph=False,
        trace=False,
        monitor=None,
        project_xml=None,
        resources_xml=None,
        summary=False,
        task_execution='compss',
        storage_impl=None,
        storage_conf=None,
        task_count=50,
        app_name=None,
        uuid=None,
        base_log_dir=None,
        specific_log_dir=None,
        extrae_cfg=None,
        comm='NIO',
        conn='es.bsc.compss.connectors.DefaultSSHConnector',
        master_name='',
        master_port='',
        scheduler='es.bsc.compss.scheduler.loadBalancingScheduler.LoadBalancingScheduler',
        jvm_workers='-Xms1024m,-Xmx1024m,-Xmn400m',
        obj_conv=False,
        cpu_affinity='automatic',
        gpu_affinity='automatic',
        fpga_affinity='automatic',
        fpga_reprogram='',
        profile_input='',
        profile_output='',
        scheduler_config='',
        external_adaptation=False,
        python_propagate_virtual_environment=True,
        *args,
        **kwargs):
    """
    Launch pycompss application.

    :param app: Application path
    :param func: Function
    :param args: Arguments
    :param kwargs: Keyword arguments
    :param log_level: Logging level [ 'on' | 'off'] (default: 'off')
    :param o_c: Objects to string conversion [ True | False ] (default: False)
    :param debug: Debug mode [ True | False ] (default: False)
    :param graph: Generate graph [ True | False ] (default: False)
    :param trace: Generate trace [ True | False ] (default: False)
    :param monitor: Monitor refresh rate (default: None)
    :param project_xml: Project xml file path
    :param resources_xml: Resources xml file path
    :param summary: Execution summary [ True | False ] (default: False)
    :param task_execution: Task execution (default: 'compss')
    :param storage_impl: Storage implementation path
    :param storage_conf: Storage configuration file path
    :param task_count: Task count (default: 50)
    :param app_name: Application name (default: Interactive_date)
    :param uuid: UUId
    :param base_log_dir: Base logging directory
    :param specific_log_dir: Specific logging directory
    :param extrae_cfg: Extrae configuration file path
    :param comm: Communication library (default: NIO)
    :param conn: Connector (default: DefaultSSHConnector)
    :param master_name: Master Name (default: '')
    :param master_port: Master port (default: '')
    :param scheduler: Scheduler (default: LoadBalancingScheduler)
    :param jvm_workers: Java VM parameters (default: '-Xms1024m,-Xmx1024m,-Xmn400m')
    :param cpu_affinity: CPU Core affinity (default: 'automatic')
    :param gpu_affinity: GPU Core affinity (default: 'automatic')
    :param fpga_affinity: FPA Core affinity (default: 'automatic')
    :param fpga_reprogram: FPGA repogram command (default: '')
    :param profile_input: Input profile  (default: '')
    :param profile_output: Output profile  (default: '')
    :param scheduler_config: Scheduler configuration  (default: '')
    :param external_adaptation: External adaptation [ True | False ] (default: False)
    :param python_propagate_virtual_environment: Propagate virtual environment [ True | False ] (default: False)
    :return: Execution result
    """

    global app_path

    # Let the Python binding know we are at master
    set_pycompss_context('MASTER')

    launch_path = os.path.dirname(os.path.abspath(__file__))
    # compss_home = launch_path without the last 4 folders:
    # (Bindings/python/pycompss/runtime)
    compss_home = os.path.sep.join(launch_path.split(os.path.sep)[:-4])

    # Grab the existing PYTHONPATH and CLASSPATH values
    pythonpath = os.environ['PYTHONPATH']
    classpath = os.environ['CLASSPATH']
    ld_library_path = os.environ['LD_LIBRARY_PATH']

    # Enable/Disable object to string conversion
    binding.object_conversion = obj_conv

    # Get the filename and its path.
    file_name = os.path.splitext(os.path.basename(app))[0]
    cp = os.path.dirname(app)

    # Set storage classpath
    if storage_impl:
        if storage_impl == 'redis':
            cp = cp + ':' + compss_home + '/Tools/storage/redis/compss-redisPSCO.jar'
        else:
            cp = cp + ':' + storage_impl

    if RUNNING_IN_SUPERCOMPUTER:
        # Since the deployment in supercomputers is done through the use of enqueue_compss
        # and consequently launch_compss - the project and resources xmls are already created
        project_xml, resources_xml = get_xmls()
        # It also exported some environment variables that we need here
        master_name = get_master_node()
        master_port = get_master_port()
        uuid = get_uuid()
        base_log_dir = get_base_log_dir()
        specific_log_dir = get_specific_log_dir()
        storage_conf = get_storage_conf()
        # Override debug considering the parameter defined in pycompss_interactive_sc script
        # and exported by launch_compss
        log_level = get_log_level()
        if log_level == 'off':
            debug = False
        else:
            debug = True
        # Override tracing considering the parameter defined in pycompss_interactive_sc script
        # and exported by launch_compss
        if get_tracing():
            trace = 1
        else:
            trace = 0

    # Build a dictionary with all variables needed for initializing the runtime.
    config = dict()
    config['compss_home'] = compss_home
    config['debug'] = debug
    if project_xml is None:
        project_xml = 'Runtime/configuration/xml/projects/default_project.xml'
        config['project_xml'] = compss_home + os.path.sep + project_xml
    else:
        config['project_xml'] = project_xml
    if resources_xml is None:
        resources_xml = 'Runtime/configuration/xml/resources/default_resources.xml'
        config['resources_xml'] = compss_home + os.path.sep + resources_xml
    else:
        config['resources_xml'] = resources_xml
    config['summary'] = summary
    config['task_execution'] = task_execution
    config['storage_conf'] = storage_conf
    config['task_count'] = task_count
    if app_name is None:
        config['app_name'] = file_name
    else:
        config['app_name'] = app_name
    config['uuid'] = uuid
    config['base_log_dir'] = base_log_dir
    config['specific_log_dir'] = specific_log_dir
    config['graph'] = graph
    config['monitor'] = monitor
    config['trace'] = trace
    config['extrae_cfg'] = extrae_cfg
    config['comm'] = comm
    config['conn'] = conn
    config['master_name'] = master_name
    config['master_port'] = master_port
    config['scheduler'] = scheduler
    config['cp'] = cp
    config['classpath'] = classpath
    config['ld_library_path'] = ld_library_path
    config['jvm_workers'] = jvm_workers
    config['pythonpath'] = pythonpath
    config['cpu_affinity'] = cpu_affinity
    config['gpu_affinity'] = gpu_affinity
    config['fpga_affinity'] = fpga_affinity
    config['fpga_reprogram'] = fpga_reprogram
    config['profile_input'] = profile_input
    config['profile_output'] = profile_output
    config['scheduler_config'] = scheduler_config
    if external_adaptation:
        config['external_adaptation'] = 'true'
    else:
        config['external_adaptation'] = 'false'
    major_version = str(sys.version_info[0])
    config['python_interpreter'] = 'python' + major_version
    config['python_version'] = major_version
    if 'VIRTUAL_ENV' in os.environ:
        # Running within a virtual environment
        python_virtual_environment = os.environ['VIRTUAL_ENV']
    else:
        python_virtual_environment = 'null'
    config['python_virtual_environment'] = python_virtual_environment
    config[
        'python_propagate_virtual_environment'] = python_propagate_virtual_environment

    initialize_compss(config)

    # Runtime start
    compss_start()

    # Configure logging
    app_path = app
    log_path = get_log_path()
    # Logging setup
    if debug or log_level == "debug":
        json_path = '/Bindings/python/' + major_version + '/log/logging.json.debug'
        init_logging(compss_home + json_path, log_path)
    elif log_level == "info":
        json_path = '/Bindings/python/' + major_version + '/log/logging.json.off'
        init_logging(compss_home + json_path, log_path)
    elif log_level == "off":
        json_path = '/Bindings/python/' + major_version + '/log/logging.json.off'
        init_logging(compss_home + json_path, log_path)
    else:
        # Default
        json_path = '/Bindings/python/' + str(
            major_version) + '/log/logging.json'
        init_logging(compss_home + json_path, log_path)
    logger = logging.getLogger("pycompss.runtime.launch")

    logger.debug('--- START ---')
    logger.debug('PyCOMPSs Log path: %s' % log_path)
    saved_argv = sys.argv
    sys.argv = args
    # Execution:
    if func is None or func == '__main__':
        execfile(app)
        result = None
    else:
        import imp
        imported_module = imp.load_source(file_name, app)
        method_to_call = getattr(imported_module, func)
        result = method_to_call(*args, **kwargs)
    # Recover the system arguments
    sys.argv = saved_argv
    logger.debug('--- END ---')

    compss_stop()

    return result
Exemplo n.º 4
0
def compss_main():
    """
    General call:
    python $PYCOMPSS_HOME/pycompss/runtime/launch.py $log_level $PyObject_serialize $storage_conf $fullAppPath $application_args

    :return: None
    """
    global app_path

    # Let the Python binding know we are at master
    set_pycompss_context('MASTER')

    # Start the runtime, see bindings commons
    compss_start()
    # See parse_arguments, defined above
    # In order to avoid parsing user arguments, we are going to remove user
    # args from sys.argv
    user_sys_argv = sys.argv[5:]
    sys.argv = sys.argv[:5]
    args = parse_arguments()
    # We are done, now sys.argv must contain user args only
    sys.argv = [args.app_path] + user_sys_argv

    # Get log_level
    log_level = args.log_level

    # Get object_conversion boolean
    binding.object_conversion = args.object_conversion == 'true'

    # Get storage configuration at master
    storage_conf = args.storage_configuration
    persistent_storage = False
    if storage_conf != 'null':
        persistent_storage = True
        from storage.api import init as init_storage
        from storage.api import finish as finish_storage

    # Get application execution path
    app_path = args.app_path

    binding_log_path = get_log_path()
    log_path = os.path.join(os.getenv('COMPSS_HOME'), 'Bindings', 'python',
                            str(_py_version), 'log')
    binding.temp_dir = mkdtemp(prefix='pycompss',
                               dir=os.path.join(binding_log_path, 'tmpFiles/'))

    logging_cfg_file = get_logging_cfg_file(log_level)

    init_logging(os.path.join(log_path, logging_cfg_file), binding_log_path)
    if __debug__:
        logger = logging.getLogger('pycompss.runtime.launch')

    # Get JVM options
    # jvm_opts = os.environ['JVM_OPTIONS_FILE']
    # opts = convert_to_dict(jvm_opts)
    # storage_conf = opts.get('-Dcompss.storage.conf')

    try:
        if __debug__:
            logger.debug('--- START ---')
            logger.debug('PyCOMPSs Log path: %s' % binding_log_path)
        if persistent_storage:
            if __debug__:
                logger.debug('Storage configuration file: %s' % storage_conf)
            init_storage(config_file_path=storage_conf)
        show_optional_module_warnings()
        # MAIN EXECUTION
        if IS_PYTHON3:
            exec(compile(open(app_path).read(), app_path, 'exec'), globals())
        else:
            execfile(app_path, globals())  # MAIN EXECUTION
        if persistent_storage:
            finish_storage()
        if __debug__:
            logger.debug('--- END ---')
    except SystemExit as e:
        if e.code != 0:  # Seems this is not happening
            print('[ ERROR ]: User program ended with exitcode %s.' % e.code)
            print('\t\tShutting down runtime...')
    except SerializerException:
        # If an object that can not be serialized has been used as a parameter.
        exc_type, exc_value, exc_traceback = sys.exc_info()
        lines = traceback.format_exception(exc_type, exc_value, exc_traceback)
        for line in lines:
            if app_path in line:
                print('[ ERROR ]: In: %s', line)
    finally:
        compss_stop()
        sys.stdout.flush()
        sys.stderr.flush()
Exemplo n.º 5
0
"""
PyCOMPSs Binding - Launch
=========================
This file contains the __main__ method.
It is called from pycompssext script with the user and environment parameters.
"""

import os
import sys
import logging
import traceback
from tempfile import mkdtemp

# Let the Python binding know we are during libraries initialization
from pycompss.util.location import set_pycompss_context
set_pycompss_context('INITIALIZATION')

import pycompss.runtime.binding as binding
from pycompss.api.api import compss_start, compss_stop
from pycompss.runtime.binding import get_log_path
from pycompss.runtime.commons import IS_PYTHON3
from pycompss.runtime.commons import RUNNING_IN_SUPERCOMPUTER
from pycompss.util.scs import get_master_node
from pycompss.util.scs import get_master_port
from pycompss.util.scs import get_xmls
from pycompss.util.scs import get_uuid
from pycompss.util.scs import get_base_log_dir
from pycompss.util.scs import get_specific_log_dir
from pycompss.util.scs import get_log_level
from pycompss.util.scs import get_tracing
from pycompss.util.scs import get_storage_conf
Exemplo n.º 6
0
def start(
        log_level='off',
        o_c=False,
        debug=False,
        graph=False,
        trace=False,
        monitor=None,
        project_xml=None,
        resources_xml=None,
        summary=False,
        task_execution='compss',
        storage_impl=None,
        storage_conf=None,
        task_count=50,
        app_name='Interactive',
        uuid=None,
        base_log_dir=None,
        specific_log_dir=None,
        extrae_cfg=None,
        comm='NIO',
        conn='es.bsc.compss.connectors.DefaultSSHConnector',
        master_name='',
        master_port='',
        scheduler='es.bsc.compss.scheduler.loadBalancingScheduler.LoadBalancingScheduler',
        jvm_workers='-Xms1024m,-Xmx1024m,-Xmn400m',
        cpu_affinity='automatic',
        gpu_affinity='automatic',
        fpga_affinity='automatic',
        fpga_reprogram='',
        profile_input='',
        profile_output='',
        scheduler_config='',
        external_adaptation=False,
        propagate_virtual_environment=False,
        verbose=False):
    """
    Start the runtime in interactive mode.

    :param log_level: Logging level [ 'on' | 'off'] (default: 'off')
    :param o_c: Objects to string conversion [ True | False ] (default: False)
    :param debug: Debug mode [ True | False ] (default: False)
    :param graph: Generate graph [ True | False ] (default: False)
    :param trace: Generate trace [ True | False ] (default: False)
    :param monitor: Monitor refresh rate (default: None)
    :param project_xml: Project xml file path
    :param resources_xml: Resources xml file path
    :param summary: Execution summary [ True | False ] (default: False)
    :param task_execution: Task execution (default: 'compss')
    :param storage_impl: Storage implementation path
    :param storage_conf: Storage configuration file path
    :param task_count: Task count (default: 50)
    :param app_name: Application name (default: Interactive_date)
    :param uuid: UUId
    :param base_log_dir: Base logging directory
    :param specific_log_dir: Specific logging directory
    :param extrae_cfg: Extrae configuration file path
    :param comm: Communication library (default: NIO)
    :param conn: Connector (default: DefaultSSHConnector)
    :param master_name: Master Name (default: '')
    :param master_port: Master port (default: '')
    :param scheduler: Scheduler (default: LoadBalancingScheduler)
    :param jvm_workers: Java VM parameters (default: '-Xms1024m,-Xmx1024m,-Xmn400m')
    :param cpu_affinity: CPU Core affinity (default: 'automatic')
    :param gpu_affinity: GPU Core affinity (default: 'automatic')
    :param fpga_affinity: FPA Core affinity (default: 'automatic')
    :param fpga_reprogram: FPGA repogram command (default: '')
    :param profile_input: Input profile  (default: '')
    :param profile_output: Output profile  (default: '')
    :param scheduler_config: Scheduler configuration  (default: '')
    :param external_adaptation: External adaptation [ True | False ] (default: False)
    :param propagate_virtual_environment: Propagate virtual environment [ True | False ] (default: False)
    :param verbose: Verbose mode [ True | False ] (default: False)
    :return: None
    """

    # Let the Python binding know we are at master
    set_pycompss_context('MASTER')

    # Prepare the environment
    launch_path = os.path.dirname(os.path.realpath(__file__))
    # compss_home = launch_path without the last 4 folders:
    # Bindings/python/version/pycompss
    compss_home = os.path.sep.join(launch_path.split(os.path.sep)[:-4])
    os.environ['COMPSS_HOME'] = compss_home

    # Get environment variables
    cp = os.getcwd() + '/'
    pythonpath = os.environ['PYTHONPATH']
    classpath = os.environ['CLASSPATH']
    ld_library_path = os.environ['LD_LIBRARY_PATH']

    # Set storage classpath
    if storage_impl:
        if storage_impl == 'redis':
            cp = cp + ':' + compss_home + '/Tools/storage/redis/compss-redisPSCO.jar'
        else:
            cp = cp + ':' + storage_impl

    # Set extrae dependencies
    if not "EXTRAE_HOME" in os.environ:
        # It can be defined by the user or by launch_compss when running in Supercomputer
        extrae_home = compss_home + '/Dependencies/extrae'
        os.environ['EXTRAE_HOME'] = extrae_home
    else:
        extrae_home = os.environ['EXTRAE_HOME']
    extrae_lib = extrae_home + '/lib'

    # Include extrae into ld_library_path
    ld_library_path = extrae_lib + ':' + ld_library_path
    os.environ['LD_LIBRARY_PATH'] = ld_library_path

    if monitor is not None:
        # Enable the graph if the monitoring is enabled
        graph = True

    # Export global variables
    global graphing
    graphing = graph

    __export_globals__()

    print("******************************************************")
    print("*************** PyCOMPSs Interactive *****************")
    print("******************************************************")
    print("*          .-~~-.--.            ____        ____     *")
    print("*         :         )          |___ \      |___ \    *")
    print("*   .~ ~ -.\       /.- ~~ .      __) |       __) |   *")
    print("*   >       `.   .'       <     / __/   _   ___) |   *")
    print("*  (         .- -.         )   |_____| |_| |____/    *")
    print("*   `- -.-~  `- -'  ~-.- -'                          *")
    print("*     (        :        )           _ _ .-:          *")
    print("*      ~--.    :    .--~        .-~  .-~  }          *")
    print("*          ~-.-^-.-~ \_      .~  .-~   .~            *")
    print("*                   \ \ '     \ '_ _ -~              *")
    print("*                    \`.\`.    //                    *")
    print("*           . - ~ ~-.__\`.\`-.//                     *")
    print("*       .-~   . - ~  }~ ~ ~-.~-.                     *")
    print("*     .' .-~      .-~       :/~-.~-./:               *")
    print("*    /_~_ _ . - ~                 ~-.~-._            *")
    print("*                                     ~-.<           *")
    print("******************************************************")

    ##############################################################
    # INITIALIZATION
    ##############################################################

    if RUNNING_IN_SUPERCOMPUTER:
        # Since the deployment in supercomputers is done through the use of enqueue_compss
        # and consequently launch_compss - the project and resources xmls are already created
        project_xml, resources_xml = get_xmls()
        # It also exported some environment variables that we need here
        master_name = get_master_node()
        master_port = get_master_port()
        uuid = get_uuid()
        base_log_dir = get_base_log_dir()
        specific_log_dir = get_specific_log_dir()
        storage_conf = get_storage_conf()
        # Override debug considering the parameter defined in pycompss_interactive_sc script
        # and exported by launch_compss
        log_level = get_log_level()
        if log_level == 'off':
            debug = False
        else:
            debug = True
        # Override tracing considering the parameter defined in pycompss_interactive_sc script
        # and exported by launch_compss
        trace = get_tracing()
        if verbose:
            print("- Overridden project xml with: " + project_xml)
            print("- Overridden resources xml with: " + resources_xml)
            print("- Overridden master name with: " + master_name)
            print("- Overridden master port with: " + master_port)
            print("- Overridden uuid with: " + uuid)
            print("- Overridden base log dir with: " + base_log_dir)
            print("- Overridden specific log dir with: " + specific_log_dir)
            print("- Overridden storage conf with: " + storage_conf)
            print("- Overridden log level with: " + str(log_level))
            print("- Overridden debug with: " + str(debug))
            print("- Overridden trace with: " + str(trace))

    if debug:
        # Add environment variable to get binding-commons debug information
        os.environ['COMPSS_BINDINGS_DEBUG'] = '1'

    if trace is False:
        trace = 0
    elif trace == 'basic' or trace is True:
        trace = 1
        os.environ['LD_PRELOAD'] = extrae_lib + '/libpttrace.so'
    elif trace == 'advanced':
        trace = 2
        os.environ['LD_PRELOAD'] = extrae_lib + '/libpttrace.so'
    else:
        print(
            "ERROR: Wrong tracing parameter ( [ True | basic ] | advanced | False)"
        )
        return -1

    # Build a dictionary with all variables needed for initializing the runtime
    config = dict()
    config['compss_home'] = compss_home
    config['debug'] = debug
    if project_xml is None:
        project_path = 'Runtime/configuration/xml/projects/default_project.xml'
        config['project_xml'] = compss_home + os.path.sep + project_path
    else:
        config['project_xml'] = project_xml
    if resources_xml is None:
        resources_path = 'Runtime/configuration/xml/resources/default_resources.xml'
        config['resources_xml'] = compss_home + os.path.sep + resources_path
    else:
        config['resources_xml'] = resources_xml
    config['summary'] = summary
    config['task_execution'] = task_execution
    config['storage_conf'] = storage_conf
    config['task_count'] = task_count
    if app_name is None:
        config['app_name'] = 'Interactive'
    else:
        config['app_name'] = app_name
    config['uuid'] = uuid
    config['base_log_dir'] = base_log_dir
    config['specific_log_dir'] = specific_log_dir
    config['graph'] = graph
    config['monitor'] = monitor
    config['trace'] = trace
    config['extrae_cfg'] = extrae_cfg
    config['comm'] = comm
    config['conn'] = conn
    config['master_name'] = master_name
    config['master_port'] = master_port
    config['scheduler'] = scheduler
    config['cp'] = cp
    config['pythonpath'] = pythonpath
    config['classpath'] = classpath
    config['ld_library_path'] = ld_library_path
    config['jvm_workers'] = jvm_workers
    config['cpu_affinity'] = cpu_affinity
    config['gpu_affinity'] = gpu_affinity
    config['fpga_affinity'] = fpga_affinity
    config['fpga_reprogram'] = fpga_reprogram
    config['profile_input'] = profile_input
    config['profile_output'] = profile_output
    config['scheduler_config'] = scheduler_config
    if external_adaptation:
        config['external_adaptation'] = 'true'
    else:
        config['external_adaptation'] = 'false'

    major_version = sys.version_info[0]
    python_interpreter = 'python' + str(major_version)
    config['python_interpreter'] = python_interpreter
    config['python_version'] = str(major_version)

    if 'VIRTUAL_ENV' in os.environ:
        # Running within a virtual environment
        python_virtual_environment = os.environ['VIRTUAL_ENV']
    else:
        python_virtual_environment = 'null'
    config['python_virtual_environment'] = python_virtual_environment
    config[
        'python_propagate_virtual_environment'] = propagate_virtual_environment

    initialize_compss(config)

    ##############################################################
    # RUNTIME START
    ##############################################################

    print("* - Starting COMPSs runtime...                       *")
    sys.stdout.flush()  # Force flush
    compss_start()

    if o_c is True:
        # set cross-module variable
        binding.object_conversion = True
    else:
        # set cross-module variable
        binding.object_conversion = False

    # Remove launch.py, log_level and object_conversion from sys.argv,
    # It will be inherited by the app through execfile
    # sys.argv = sys.argv[3:]
    # Get application execution path
    # app_path = sys.argv[0]  # not needed in interactive mode

    global log_path
    log_path = get_log_path()
    binding.temp_dir = mkdtemp(prefix='pycompss', dir=log_path + '/tmpFiles/')
    print("* - Log path : " + log_path)

    # Logging setup - messages before this step are ignored (need log_path to configure the logger).
    if debug or log_level == "debug":
        json_path = '/Bindings/python/' + str(
            major_version) + '/log/logging.json.debug'
        init_logging(os.getenv('COMPSS_HOME') + json_path, log_path)
    elif log_level == "info":
        json_path = '/Bindings/python/' + str(
            major_version) + '/log/logging.json.off'
        init_logging(os.getenv('COMPSS_HOME') + json_path, log_path)
    elif log_level == "off":
        json_path = '/Bindings/python/' + str(
            major_version) + '/log/logging.json.off'
        init_logging(os.getenv('COMPSS_HOME') + json_path, log_path)
    else:
        # Default
        json_path = '/Bindings/python/' + str(
            major_version) + '/log/logging.json'
        init_logging(os.getenv('COMPSS_HOME') + json_path, log_path)
    logger = logging.getLogger("pycompss.runtime.launch")

    __print_setup__(verbose, log_level, o_c, debug, graph, trace, monitor,
                    project_xml, resources_xml, summary, task_execution,
                    storage_conf, pythonpath, classpath, ld_library_path,
                    task_count, app_name, uuid, base_log_dir, specific_log_dir,
                    extrae_cfg, comm, conn, master_name, master_port,
                    scheduler, jvm_workers, cpu_affinity, gpu_affinity,
                    fpga_affinity, fpga_reprogram, profile_input,
                    profile_output, scheduler_config, external_adaptation,
                    python_interpreter, major_version,
                    python_virtual_environment, propagate_virtual_environment)

    logger.debug("--- START ---")
    logger.debug("PyCOMPSs Log path: %s" % log_path)
    if storage_conf is not None:
        logger.debug("Storage configuration file: %s" % storage_conf)
        from storage.api import init as init_storage
        init_storage(config_file_path=storage_conf)
        global persistent_storage
        persistent_storage = True

    # MAIN EXECUTION
    # let the user write an interactive application
    print("* - PyCOMPSs Runtime started... Have fun!            *")
    print("******************************************************")