<commit_before>import sublime

from concurrent.futures import ThreadPoolExecutor, wait, FIRST_EXCEPTION
from contextlib import contextmanager
from itertools import chain, count
from functools import partial
import hashlib
import json
import logging
import multiprocessing
import os
import time
import threading

from . import style, util, linter as linter_module

logger = logging.getLogger(__name__)

WILDCARD_SYNTAX = '*'
MAX_CONCURRENT_TASKS = multiprocessing.cpu_count() or 1

task_count = count(start=1)
counter_lock = threading.Lock()
process_limit = threading.BoundedSemaphore(MAX_CONCURRENT_TASKS)

def lint_view(linters, view, view_has_changed, next):
    """Lint the given view.

    This is the top level lint dispatcher. It is called
    asynchronously.
    """
    lint_tasks = get_lint_tasks(linters, view, view_has_changed)

    run_concurrently(
        partial(run_tasks, tasks, next=partial(next, linter))
        for linter, tasks in lint_tasks
    )

def run_tasks(tasks, next):
    results = run_concurrently(tasks)
    if results is None:
        return  # ABORT

    errors = list(chain.from_iterable(results))  # flatten and consume

    # We don't want to guarantee that our consumers/views are thread aware.
    # So we merge here into Sublime's shared worker thread. Sublime guarantees
    # here to execute all scheduled tasks ordered and sequentially.
    sublime.set_timeout_async(lambda: next(errors))

def get_lint_tasks(linters, view, view_has_changed):
    for (linter, regions) in get_lint_regions(linters, view):
        tasks = []
        for region in regions:
            code = view.substr(region)
            offset = view.rowcol(region.begin())

            # Due to a limitation in python 3.3, we cannot 'name' a thread when
            # using the ThreadPoolExecutor. (This feature has been introduced
            # in python 3.6.) So, we pass the name down.
            task_name = make_good_task_name(linter, view)
            tasks.append(partial(
                execute_lint_task, linter, code, offset, view_has_changed,
                task_name
            ))
        yield linter, tasks

def make_good_task_name(linter, view):
    with counter_lock:
        task_number = next(task_count)

    canonical_filename = (
        os.path.basename(view.file_name()) if view.file_name()
        else '<untitled {}>'.format(view.buffer_id()))

    return 'LintTask|{}|{}|{}|{}'.format(
        task_number, linter.name, canonical_filename, view.id())

def execute_lint_task(linter, code, offset, view_has_changed, task_name):
    # We 'name' our threads, for logging purposes.
    threading.current_thread().name = task_name

    with reduced_concurrency():
        try:
            errors = linter.lint(code, view_has_changed) or []
            finalize_errors(linter, errors, offset)

            return errors
        except linter_module.TransientError:
            raise
        except Exception:
            linter.notify_failure()
            # Log while multi-threaded to get a nicer log message
            logger.exception('Unhandled exception:\n', extra={'demote': True})
            return []  # Empty list here to clear old errors

@contextmanager
def reduced_concurrency():
    start_time = time.time()
    with process_limit:
        end_time = time.time()
        waittime = end_time - start_time
        if waittime > 0.1:
            logger.warning('Waited in queue for {:.2f}s'.format(waittime))

        yield

def finalize_errors(linter, errors, offset):
    linter_name = linter.name
    view = linter.view
    line_offset, col_offset = offset

    for error in errors:
        line, start, end = error['line'], error['start'], error['end']
        if line == 0:
            start += col_offset
            end += col_offset

        line += line_offset

        error.update({
            'line': line,
            'start': start,
            'end': end,
            'linter': linter_name
        })

        uid = hashlib.sha256(
            json.dumps(error, sort_keys=True).encode('utf-8')).hexdigest()

        line_start = view.text_point(line, 0)
        region = sublime.Region(line_start + start, line_start + end)
        if len(region) == 0:
            region.b = region.b + 1

        error.update({
            'uid': uid,
            'region': region,
            'priority': style.get_value('priority', error, 0)
        })

def get_lint_regions(linters, view):
    syntax = util.get_syntax(view)
    for linter in linters:
        settings = linter.get_view_settings()
        selector = settings.get('selector', None)
        if selector is not None:
            # Inspecting just the first char is faster
            if view.score_selector(0, selector):
                yield linter, [sublime.Region(0, view.size())]
            else:
                yield linter, [
                    region for region in view.find_by_selector(selector)
                ]

            continue

        # Fallback using deprecated `cls.syntax` and `cls.selectors`
        if (
            syntax not in linter.selectors and
            WILDCARD_SYNTAX not in linter.selectors
        ):
            yield linter, [sublime.Region(0, view.size())]

        else:
            yield linter, [
                region
                for selector in get_selectors(linter, syntax)
                for region in view.find_by_selector(selector)
            ]

def get_selectors(linter, wanted_syntax):
    for syntax in [wanted_syntax, WILDCARD_SYNTAX]:
        try:
            yield linter.selectors[syntax]
        except KeyError:
            pass

def run_concurrently(tasks, max_workers=MAX_CONCURRENT_TASKS):
    with ThreadPoolExecutor(max_workers=max_workers) as executor:
        work = [executor.submit(task) for task in tasks]
        return await_futures(work)

def await_futures(fs):
    done, not_done = wait(fs, return_when=FIRST_EXCEPTION)

    try:
        return [future.result() for future in done]
    except Exception:
        for future in not_done:
            future.cancel()
        return None
<commit_msg>Extract `modify_thread_name` decorator<commit_after>import sublime

from concurrent.futures import ThreadPoolExecutor, wait, FIRST_EXCEPTION
from contextlib import contextmanager
from itertools import chain, count
from functools import partial
import hashlib
import json
import logging
import multiprocessing
import os
import time
import threading

from . import style, util, linter as linter_module

logger = logging.getLogger(__name__)

WILDCARD_SYNTAX = '*'
MAX_CONCURRENT_TASKS = multiprocessing.cpu_count() or 1

task_count = count(start=1)
counter_lock = threading.Lock()
process_limit = threading.BoundedSemaphore(MAX_CONCURRENT_TASKS)

def lint_view(linters, view, view_has_changed, next):
    """Lint the given view.

    This is the top level lint dispatcher. It is called
    asynchronously.
    """
    lint_tasks = get_lint_tasks(linters, view, view_has_changed)

    run_concurrently(
        partial(run_tasks, tasks, next=partial(next, linter))
        for linter, tasks in lint_tasks
    )

def run_tasks(tasks, next):
    results = run_concurrently(tasks)
    if results is None:
        return  # ABORT

    errors = list(chain.from_iterable(results))  # flatten and consume

    # We don't want to guarantee that our consumers/views are thread aware.
    # So we merge here into Sublime's shared worker thread. Sublime guarantees
    # here to execute all scheduled tasks ordered and sequentially.
    sublime.set_timeout_async(lambda: next(errors))

def get_lint_tasks(linters, view, view_has_changed):
    for (linter, regions) in get_lint_regions(linters, view):
        tasks = []
        for region in regions:
            code = view.substr(region)
            offset = view.rowcol(region.begin())

            # Due to a limitation in python 3.3, we cannot 'name' a thread when
            # using the ThreadPoolExecutor. (This feature has been introduced
            # in python 3.6.) So, we do this manually.
            task_name = make_good_task_name(linter, view)
            task = partial(execute_lint_task, linter, code, offset, view_has_changed)
            executor = partial(modify_thread_name, task_name, task)
            tasks.append(executor)

        yield linter, tasks

def make_good_task_name(linter, view):
    with counter_lock:
        task_number = next(task_count)

    canonical_filename = (
        os.path.basename(view.file_name()) if view.file_name()
        else '<untitled {}>'.format(view.buffer_id()))

    return 'LintTask|{}|{}|{}|{}'.format(
        task_number, linter.name, canonical_filename, view.id())

def modify_thread_name(name, sink):
    # We 'name' our threads, for logging purposes.
    threading.current_thread().name = name
    return sink()

def execute_lint_task(linter, code, offset, view_has_changed):
    with reduced_concurrency():
        try:
            errors = linter.lint(code, view_has_changed) or []
            finalize_errors(linter, errors, offset)

            return errors
        except linter_module.TransientError:
            raise
        except Exception:
            linter.notify_failure()
            # Log while multi-threaded to get a nicer log message
            logger.exception('Unhandled exception:\n', extra={'demote': True})
            return []  # Empty list here to clear old errors

@contextmanager
def reduced_concurrency():
    start_time = time.time()
    with process_limit:
        end_time = time.time()
        waittime = end_time - start_time
        if waittime > 0.1:
            logger.warning('Waited in queue for {:.2f}s'.format(waittime))

        yield

def finalize_errors(linter, errors, offset):
    linter_name = linter.name
    view = linter.view
    line_offset, col_offset = offset

    for error in errors:
        line, start, end = error['line'], error['start'], error['end']
        if line == 0:
            start += col_offset
            end += col_offset

        line += line_offset

        error.update({
            'line': line,
            'start': start,
            'end': end,
            'linter': linter_name
        })

        uid = hashlib.sha256(
            json.dumps(error, sort_keys=True).encode('utf-8')).hexdigest()

        line_start = view.text_point(line, 0)
        region = sublime.Region(line_start + start, line_start + end)
        if len(region) == 0:
            region.b = region.b + 1

        error.update({
            'uid': uid,
            'region': region,
            'priority': style.get_value('priority', error, 0)
        })

def get_lint_regions(linters, view):
    syntax = util.get_syntax(view)
    for linter in linters:
        settings = linter.get_view_settings()
        selector = settings.get('selector', None)
        if selector is not None:
            # Inspecting just the first char is faster
            if view.score_selector(0, selector):
                yield linter, [sublime.Region(0, view.size())]
            else:
                yield linter, [
                    region for region in view.find_by_selector(selector)
                ]

            continue

        # Fallback using deprecated `cls.syntax` and `cls.selectors`
        if (
            syntax not in linter.selectors and
            WILDCARD_SYNTAX not in linter.selectors
        ):
            yield linter, [sublime.Region(0, view.size())]

        else:
            yield linter, [
                region
                for selector in get_selectors(linter, syntax)
                for region in view.find_by_selector(selector)
            ]

def get_selectors(linter, wanted_syntax):
    for syntax in [wanted_syntax, WILDCARD_SYNTAX]:
        try:
            yield linter.selectors[syntax]
        except KeyError:
            pass

def run_concurrently(tasks, max_workers=MAX_CONCURRENT_TASKS):
    with ThreadPoolExecutor(max_workers=max_workers) as executor:
        work = [executor.submit(task) for task in tasks]
        return await_futures(work)

def await_futures(fs):
    done, not_done = wait(fs, return_when=FIRST_EXCEPTION)

    try:
        return [future.result() for future in done]
    except Exception:
        for future in not_done:
            future.cancel()
        return None
<|endoftext|>


<commit_before>"""
This module provides Python helper classes ("glue code") for use with code generated by F2x.
"""
import ctypes

from F2x.glue import main

# Impoort Fortran library.
libF2x = ctypes.cdll.LoadLibrary(main.find_library_path())

# 2D array helpers
libF2x.F2x_int2d_alloc.argtypes = [ctypes.c_void_p]
libF2x.F2x_int2d_alloc.restype = ctypes.c_void_p
libF2x.F2x_int2d_getitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_int2d_getitem.restype = ctypes.c_int32
libF2x.F2x_int2d_setitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p, ctypes.c_int32]
libF2x.F2x_int2d_setitem.restype = None
libF2x.F2x_int2d_free.argtypes = [ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_int2d_free.restype = None

# 3D array helpers
libF2x.F2x_int3d_alloc.argtypes = [ctypes.c_void_p]
libF2x.F2x_int3d_alloc.restype = ctypes.c_void_p
libF2x.F2x_int3d_getitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_int3d_getitem.restype = ctypes.c_int32
libF2x.F2x_int3d_setitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p, ctypes.c_int32]
libF2x.F2x_int3d_setitem.restype = None
libF2x.F2x_int3d_free.argtypes = [ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_int3d_free.restype = None

class F2Array(object):
    def __init__(self, *sizes):
        self._sizes = (ctypes.c_int32 * len(sizes))(*sizes)

        if len(self._sizes) == 2:
            self._ptr = libF2x.F2x_int2d_alloc(ctypes.cast(self._sizes, ctypes.POINTER(ctypes.c_int32)))

        elif len(self._sizes) == 3:
            self._ptr = libF2x.F2x_int3d_alloc(ctypes.cast(self._sizes, ctypes.POINTER(ctypes.c_int32)))

    def __getitem__(self, index):
        _indices = (ctypes.c_int32 * len(self._sizes))(*index)
        return libF2x.F2x_int2d_getitem(self._ptr, ctypes.cast(self._sizes, ctypes.POINTER(ctypes.c_int32)), ctypes.cast(_indices, ctypes.POINTER(ctypes.c_int32)))

    def __setitem__(self, index, value):
        _indices = (ctypes.c_int32 * len(self._sizes))(*index)
        libF2x.F2x_int2d_setitem(self._ptr, ctypes.cast(self._sizes, ctypes.POINTER(ctypes.c_int32)), ctypes.cast(_indices, ctypes.POINTER(ctypes.c_int32)), value)

    def __del__(self):
        if len(self._sizes) == 2:
            libF2x.F2x_int2d_free(self._ptr, ctypes.cast(self._sizes, ctypes.POINTER(ctypes.c_int32)))

        elif len(self._sizes) == 3:
            libF2x.F2x_int3d_free(self._ptr, ctypes.cast(self._sizes, ctypes.POINTER(ctypes.c_int32)))

if __name__ == '__main__':
    a = F2Array(3, 3)
    a[0, 0] = 1
    a[1, 1] = 3
    print(a[0, 0], a[1, 1])

    b = F2Array(2, 2, 2)
<commit_msg>Completed Python-CTypes-Wrapper (aka. F2x.glue) for 2D/3D arrays.<commit_after>"""
This module provides Python helper classes ("glue code") for use with code generated by F2x.
"""
import ctypes

from F2x.glue import main

class F2Array(object):
    """
    This class provides access to multi-dimensional Fortran arrays.  It provides the basic interface, however,
    please use one of the concrete implementations (F2IntArray, F2DoubleArray).

    Currently, two and three dimensions are supported. The memory is managed by F2x in the Fortran space for
    maximum compatibility. However, note that the index is 0-based.

    >>> a = F2IntArray(2, 2)
    """

    _LIB = {
    }

    def __init__(self, *sizes):
        """
        Constructor allocates a new multi-dimensional Fortran array.

        @param sizes: The size in each dimension to be allocated.
        """
        self._lib = self._LIB[len(sizes)]
        self._sizes = (ctypes.c_int32 * len(sizes))(*sizes)
        self._sizes_ptr = ctypes.cast(self._sizes, ctypes.POINTER(ctypes.c_int32))
        self._ptr = self._lib.alloc(self._sizes_ptr)

    def _check_index(self, indices):
        """
        Validate index or raise ValueError (if number of indices does not match dimensions) or
        IndexError (if one of the indices is out of bounds).
        """
        if len(indices) != len(self._sizes):
            raise ValueError()

        for index, size in zip(indices, self._sizes):
            if index < 0 \
            or index >= size:
                raise IndexError()

    def __getitem__(self, indices):
        self._check_index(indices)
        indices = (ctypes.c_int32 * len(self._sizes))(*indices)
        return self._lib.getitem(self._ptr, self._sizes_ptr, ctypes.cast(indices, ctypes.POINTER(ctypes.c_int32)))

    def __setitem__(self, indices, value):
        self._check_index(indices)
        indices = (ctypes.c_int32 * len(self._sizes))(*indices)
        self._lib.setitem(self._ptr, self._sizes_ptr, ctypes.cast(indices, ctypes.POINTER(ctypes.c_int32)), value)

    def __del__(self):
        self._lib.free(self._ptr, self._sizes_ptr)

# Import Fortran library.
libF2x = ctypes.cdll.LoadLibrary(main.find_library_path())

# 2D integer array helpers
libF2x.F2x_int2d_alloc.argtypes = [ctypes.c_void_p]
libF2x.F2x_int2d_alloc.restype = ctypes.c_void_p
libF2x.F2x_int2d_getitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_int2d_getitem.restype = ctypes.c_int32
libF2x.F2x_int2d_setitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p, ctypes.c_int32]
libF2x.F2x_int2d_setitem.restype = None
libF2x.F2x_int2d_free.argtypes = [ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_int2d_free.restype = None

class _FArray_int2d(object):
    alloc = staticmethod(libF2x.F2x_int2d_alloc)
    getitem = staticmethod(libF2x.F2x_int2d_getitem)
    setitem = staticmethod(libF2x.F2x_int2d_setitem)
    free = staticmethod(libF2x.F2x_int2d_free)

# 3D integer array helpers
libF2x.F2x_int3d_alloc.argtypes = [ctypes.c_void_p]
libF2x.F2x_int3d_alloc.restype = ctypes.c_void_p
libF2x.F2x_int3d_getitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_int3d_getitem.restype = ctypes.c_int32
libF2x.F2x_int3d_setitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p, ctypes.c_int32]
libF2x.F2x_int3d_setitem.restype = None
libF2x.F2x_int3d_free.argtypes = [ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_int3d_free.restype = None

class _FArray_int3d(object):
    alloc = staticmethod(libF2x.F2x_int3d_alloc)
    getitem = staticmethod(libF2x.F2x_int3d_getitem)
    setitem = staticmethod(libF2x.F2x_int3d_setitem)
    free = staticmethod(libF2x.F2x_int3d_free)

class F2IntArray(F2Array):
    """ Multi-dimensional INTEGER Fortran array. """
    _LIB = {
        2: _FArray_int2d,
        3: _FArray_int3d,
    }

# 2D double array helpers
libF2x.F2x_real2d_alloc.argtypes = [ctypes.c_void_p]
libF2x.F2x_real2d_alloc.restype = ctypes.c_void_p
libF2x.F2x_real2d_getitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_real2d_getitem.restype = ctypes.c_double
libF2x.F2x_real2d_setitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p, ctypes.c_double]
libF2x.F2x_real2d_setitem.restype = None
libF2x.F2x_real2d_free.argtypes = [ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_real2d_free.restype = None

class _FArray_real2d(object):
    alloc = staticmethod(libF2x.F2x_real2d_alloc)
    getitem = staticmethod(libF2x.F2x_real2d_getitem)
    setitem = staticmethod(libF2x.F2x_real2d_setitem)
    free = staticmethod(libF2x.F2x_real2d_free)

# 3D double array helpers
libF2x.F2x_real3d_alloc.argtypes = [ctypes.c_void_p]
libF2x.F2x_real3d_alloc.restype = ctypes.c_void_p
libF2x.F2x_real3d_getitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_real3d_getitem.restype = ctypes.c_double
libF2x.F2x_real3d_setitem.argtypes = [ctypes.c_void_p, ctypes.c_void_p, ctypes.c_void_p, ctypes.c_double]
libF2x.F2x_real3d_setitem.restype = None
libF2x.F2x_real3d_free.argtypes = [ctypes.c_void_p, ctypes.c_void_p]
libF2x.F2x_real3d_free.restype = None

class _FArray_real3d(object):
    alloc = staticmethod(libF2x.F2x_real3d_alloc)
    getitem = staticmethod(libF2x.F2x_real3d_getitem)
    setitem = staticmethod(libF2x.F2x_real3d_setitem)
    free = staticmethod(libF2x.F2x_real3d_free)

class F2DoubleArray(F2Array):
    """ Multi-dimensional REAL(8) Fortran array. """
    _LIB = {
        2: _FArray_real2d,
        3: _FArray_real3d,
    }
<|endoftext|>


<commit_before>import ply.lex as lex

tokens = ('TYPE_LINE', 'COST_LINE', 'PT_LINE', 'TEXT_LINE', 'BLANK_LINE')

type = r"(Artifact|Creature|Enchantment|Instant|Land|Planeswalker|Sorcery|Tribal)"

t_TYPE_LINE = type + r"(\ " + type + r")*(\ -\ .*)?\n"
t_COST_LINE = r"\d*(W|U|B|R|G)\n"
t_PT_LINE = r"\d*/\d*\n"
t_TEXT_LINE = r".+\n"
t_BLANK_LINE = r"\n"

lex.lex()

sample = (
'''
Squire
1W
Artifact Creature - Human Soldier
1/2
''')

lex.input(sample)
for tok in iter(lex.token, None):
    print (repr(tok.type), repr(tok.value))

def p_cardfile_more(p):
    'cardfile : BLANK_LINE card cardfile'
    p[3].append(p[2])
    p[0] = p[3]

def p_cardfile_done(p):
    'cardfile : empty'
    p[0] = []

def p_card(p):
    '''card : creature
            | noncreature'''
    p[0] = p[1]

def p_creature(p):
    'creature : TEXT_LINE COST_LINE TYPE_LINE PT_LINE rules_text'
    p[0] = {'name': p[1], 'cost': p[2], 'types': p[3], 'pt': p[4], 'rules_text': p[5]}

def p_noncreature(p):
    'noncreature : TEXT_LINE COST_LINE TYPE_LINE rules_text'
    p[0] = {'name': p[1], 'cost': p[2], 'types': p[3], 'rules_text': p[4]}

def p_rules_text_more(p):
    'rules_text : TEXT_LINE rules_text'
    p[0] = p[1] + p[2]

def p_rules_text_done(p):
    'rules_text : empty'
    p[0] = ''

def p_empty(p):
    ' empty : '
    pass

import ply.yacc as yacc
yacc.yacc()

yacc.parse(sample)
<commit_msg>Error handing and unit test function.<commit_after>import ply.lex as lex
import ply.yacc as yacc

tokens = ('TYPE_LINE', 'COST_LINE', 'PT_LINE', 'TEXT_LINE', 'BLANK_LINE')

type = r"(Artifact|Creature|Enchantment|Instant|Land|Planeswalker|Sorcery|Tribal)"

t_TYPE_LINE = type + r"(\ " + type + r")*(\ -\ .*)?\n"
t_COST_LINE = r"\d*(W|U|B|R|G)\n"
t_PT_LINE = r"\d*/\d*\n"
t_TEXT_LINE = r".+\n"
t_BLANK_LINE = r"\n"

lex.lex()

def p_cardfile_more(p):
    'cardfile : BLANK_LINE card cardfile'
    p[3].append(p[2])
    p[0] = p[3]

def p_cardfile_done(p):
    'cardfile : empty'
    p[0] = []

def p_card(p):
    '''card : creature
            | noncreature'''
    p[0] = p[1]

def p_creature(p):
    'creature : TEXT_LINE COST_LINE TYPE_LINE PT_LINE rules_text'
    p[0] = {'name': p[1], 'cost': p[2], 'types': p[3], 'pt': p[4], 'rules_text': p[5]}

def p_noncreature(p):
    'noncreature : TEXT_LINE COST_LINE TYPE_LINE rules_text'
    p[0] = {'name': p[1], 'cost': p[2], 'types': p[3], 'rules_text': p[4]}

def p_rules_text_more(p):
    'rules_text : TEXT_LINE rules_text'
    p[0] = p[1] + p[2]

def p_rules_text_done(p):
    'rules_text : empty'
    p[0] = ''

def p_empty(p):
    ' empty : '
    pass

def p_error(p):
    print("Error at " + str(p))
    # look for the blank line separating block
    while 1:
        tok = yacc.token()
        if not tok:
            break
        if tok.type == 'BLANK_LINE':
            yacc.restart()
            yacc.errok()
            return tok

yacc.yacc()

def unit_test():
    sample = (
'''
Squire
1W1
Artifact Creature - Human Soldier
1/2

Squire
1W2
Artifact Creature - Human Soldier
1/2
''')
    mvalid(sample)

def mvalid(filestr):
    lex.input(filestr)
    yacc.parse(filestr,debug=0)

if __name__ == "__main__":
    unit_test()
<|endoftext|>


<commit_before>import bot_input_struct as bi
import ctypes
from ctypes import *
from datetime import datetime
import game_data_struct as gd
import importlib
import mmap
import os
import rate_limiter
import sys
import imp

OUTPUT_SHARED_MEMORY_TAG = 'Local\\RLBotOutput'
INPUT_SHARED_MEMORY_TAG = 'Local\\RLBotInput'
RATE_LIMITED_ACTIONS_PER_SECOND = 60
REFRESH_IN_PROGRESS = 1
REFRESH_NOT_IN_PROGRESS = 0
MAX_CARS = 10

class BotManager:

    def __init__(self, terminateEvent, callbackEvent, name, team, index, modulename):
        self.terminateEvent = terminateEvent
        self.callbackEvent = callbackEvent
        self.name = name
        self.team = team
        self.index = index
        self.module_name = modulename

    def run(self):
        # Set up shared memory map (offset makes it so bot only writes to its own input!) and map to buffer
        buff = mmap.mmap(-1, ctypes.sizeof(bi.GameInputPacket), INPUT_SHARED_MEMORY_TAG)
        bot_input = bi.GameInputPacket.from_buffer(buff)
        player_input = bot_input.sPlayerInput[self.index]
        player_input_lock = (ctypes.c_long).from_address(ctypes.addressof(player_input))

        # Set up shared memory for game data
        game_data_shared_memory = mmap.mmap(-1, ctypes.sizeof(gd.GameTickPacketWithLock), OUTPUT_SHARED_MEMORY_TAG)
        bot_output = gd.GameTickPacketWithLock.from_buffer(game_data_shared_memory)
        lock = ctypes.c_long(0)
        game_tick_packet = gd.GameTickPacket() # We want to do a deep copy for game inputs so people don't mess with em

        # Create Ratelimiter
        r = rate_limiter.RateLimiter(RATE_LIMITED_ACTIONS_PER_SECOND)

        # Find car with same name and assign index
        for i in range(MAX_CARS):
            if str(bot_output.gamecars[i].wName) == self.name:
                self.index = i
                continue

        # Get bot module
        agent_module = importlib.import_module(self.module_name)
        # Create bot from module
        agent = agent_module.Agent(self.name, self.team, self.index)
        last_module_modification_time = os.stat(agent_module.__file__).st_mtime

        # Run until main process tells to stop
        while not self.terminateEvent.is_set():
            before = datetime.now()

            try:
                # Read from game data shared memory
                game_data_shared_memory.seek(0)  # Move to beginning of shared memory
                ctypes.memmove(ctypes.addressof(lock), game_data_shared_memory.read(ctypes.sizeof(lock)), ctypes.sizeof(lock)) # dll uses InterlockedExchange so this read will return the correct value!

                if lock.value != REFRESH_IN_PROGRESS:
                    game_data_shared_memory.seek(4, os.SEEK_CUR) # Move 4 bytes past error code
                    ctypes.memmove(ctypes.addressof(game_tick_packet), game_data_shared_memory.read(ctypes.sizeof(gd.GameTickPacket)),ctypes.sizeof(gd.GameTickPacket))  # copy shared memory into struct

                # Reload the Agent if it has been modified.
                new_module_modification_time = os.stat(agent_module.__file__).st_mtime
                if new_module_modification_time != last_module_modification_time:
                    last_module_modification_time = new_module_modification_time
                    print ("Reloading Agent: " + agent_module.__file__)
                    imp.reload(agent_module)
                    agent = agent_module.Agent(self.name, self.team, self.index)

                # Call agent
                controller_input = agent.get_output_vector(game_tick_packet)

                # Write all player inputs
                player_input.fThrottle = controller_input[0]
                player_input.fSteer = controller_input[1]
                player_input.fPitch = controller_input[2]
                player_input.fYaw = controller_input[3]
                player_input.fRoll = controller_input[4]
                player_input.bJump = controller_input[5]
                player_input.bBoost = controller_input[6]
                player_input.bHandbrake = controller_input[7]

                # Workaround for windows streams behaving weirdly when not in command prompt
                sys.stdout.flush()
                sys.stderr.flush()

            except Exception as e:
                print(e)

            # Ratelimit here
            after = datetime.now()
            # print('Latency of ' + self.name + ': ' + str(after - before))

            r.acquire(after-before)

        # If terminated, send callback
        self.callbackEvent.set()

<commit_msg> Give each game_ticket_packet to the agent exactly once (#30)<commit_after>import bot_input_struct as bi
import ctypes
from ctypes import *
from datetime import datetime, timedelta
import game_data_struct as gd
import importlib
import mmap
import os
import rate_limiter
import sys
import imp
import traceback

OUTPUT_SHARED_MEMORY_TAG = 'Local\\RLBotOutput'
INPUT_SHARED_MEMORY_TAG = 'Local\\RLBotInput'
GAME_TICK_PACKET_REFRESHES_PER_SECOND = 120  # 2*60. https://en.wikipedia.org/wiki/Nyquist_rate
MAX_AGENT_CALL_PERIOD = timedelta(seconds=1.0/30)  # Minimum call rate when paused.
REFRESH_IN_PROGRESS = 1
REFRESH_NOT_IN_PROGRESS = 0
MAX_CARS = 10

class BotManager:

    def __init__(self, terminateEvent, callbackEvent, name, team, index, modulename):
        self.terminateEvent = terminateEvent
        self.callbackEvent = callbackEvent
        self.name = name
        self.team = team
        self.index = index
        self.module_name = modulename

    def run(self):
        # Set up shared memory map (offset makes it so bot only writes to its own input!) and map to buffer
        buff = mmap.mmap(-1, ctypes.sizeof(bi.GameInputPacket), INPUT_SHARED_MEMORY_TAG)
        bot_input = bi.GameInputPacket.from_buffer(buff)
        player_input = bot_input.sPlayerInput[self.index]
        player_input_lock = (ctypes.c_long).from_address(ctypes.addressof(player_input))

        # Set up shared memory for game data
        game_data_shared_memory = mmap.mmap(-1, ctypes.sizeof(gd.GameTickPacketWithLock), OUTPUT_SHARED_MEMORY_TAG)
        bot_output = gd.GameTickPacketWithLock.from_buffer(game_data_shared_memory)
        lock = ctypes.c_long(0)
        game_tick_packet = gd.GameTickPacket() # We want to do a deep copy for game inputs so people don't mess with em

        # Create Ratelimiter
        r = rate_limiter.RateLimiter(GAME_TICK_PACKET_REFRESHES_PER_SECOND)
        last_tick_game_time = None  # What the tick time of the last observed tick was
        last_call_real_time = datetime.now()  # When we last called the Agent

        # Find car with same name and assign index
        for i in range(MAX_CARS):
            if str(bot_output.gamecars[i].wName) == self.name:
                self.index = i
                continue

        # Get bot module
        agent_module = importlib.import_module(self.module_name)
        # Create bot from module
        agent = agent_module.Agent(self.name, self.team, self.index)
        last_module_modification_time = os.stat(agent_module.__file__).st_mtime

        # Run until main process tells to stop
        while not self.terminateEvent.is_set():
            before = datetime.now()
            # Read from game data shared memory
            game_data_shared_memory.seek(0)  # Move to beginning of shared memory
            ctypes.memmove(ctypes.addressof(lock), game_data_shared_memory.read(ctypes.sizeof(lock)), ctypes.sizeof(lock)) # dll uses InterlockedExchange so this read will return the correct value!

            if lock.value != REFRESH_IN_PROGRESS:
                game_data_shared_memory.seek(4, os.SEEK_CUR) # Move 4 bytes past error code
                ctypes.memmove(ctypes.addressof(game_tick_packet), game_data_shared_memory.read(ctypes.sizeof(gd.GameTickPacket)),ctypes.sizeof(gd.GameTickPacket))  # copy shared memory into struct

            # Run the Agent only if the gameInfo has updated.
            tick_game_time = game_tick_packet.gameInfo.TimeSeconds
            should_call_while_paused = datetime.now() - last_call_real_time >= MAX_AGENT_CALL_PERIOD
            if tick_game_time != last_tick_game_time or should_call_while_paused:
                last_tick_game_time = tick_game_time
                last_call_real_time = datetime.now()

                try:
                    # Reload the Agent if it has been modified.
                    new_module_modification_time = os.stat(agent_module.__file__).st_mtime
                    if new_module_modification_time != last_module_modification_time:
                        last_module_modification_time = new_module_modification_time
                        print('Reloading Agent: ' + agent_module.__file__)
                        imp.reload(agent_module)
                        agent = agent_module.Agent(self.name, self.team, self.index)

                    # Call agent
                    controller_input = agent.get_output_vector(game_tick_packet)

                    if not controller_input:
                        raise Exception('Agent "{}" did not return a player_input tuple.'.format(agent_module.__file__))

                    # Write all player inputs
                    player_input.fThrottle = controller_input[0]
                    player_input.fSteer = controller_input[1]
                    player_input.fPitch = controller_input[2]
                    player_input.fYaw = controller_input[3]
                    player_input.fRoll = controller_input[4]
                    player_input.bJump = controller_input[5]
                    player_input.bBoost = controller_input[6]
                    player_input.bHandbrake = controller_input[7]

                except Exception as e:
                    traceback.print_exc()

                # Workaround for windows streams behaving weirdly when not in command prompt
                sys.stdout.flush()
                sys.stderr.flush()

            # Ratelimit here
            after = datetime.now()
            # print('Latency of ' + self.name + ': ' + str(after - before))
            r.acquire(after-before)

        # If terminated, send callback
        self.callbackEvent.set()
<|endoftext|>


<commit_before>
{
  'targets': [
    {
      'target_name': 'pepper_test_plugin',
      'type': 'shared_library',
      'dependencies': [
        '../../../base/base.gyp:base',
        '../../../skia/skia.gyp:skia',
        '../../../third_party/npapi/npapi.gyp:npapi',
      ],
      'include_dirs': [
        '../../..',  # Root of Chrome Checkout
      ],
      'defines': [
        'PEPPER_APIS_ENABLED',
      ],
      'conditions': [
        ['OS=="win"', {
          'product_name': 'pepper_test_plugin',
          'msvs_guid': 'EE00E36E-9E8C-4DFB-925E-FBE32CEDB91A',
          'sources': [
            'pepper_test_plugin.def',
            'pepper_test_plugin.rc',
          ],
        }]
      ],
      'sources': [
        'main.cc',
        'plugin_object.cc',
        'plugin_object.h',
        'test_object.cc',
        'test_object.h',
      ],
      'run_as': {
        'working_directory': '.',
        'action': [
          '<(PRODUCT_DIR)/<(EXECUTABLE_PREFIX)chrome<(EXECUTABLE_SUFFIX)',
          '--no-sandbox',
          '--load-plugin=$(TargetPath)',
          'test_page.html',
        ],
      },
    }
  ],
}
<commit_msg>Fixed pepper plugin run as url. TEST=none BUG=none<commit_after>
{
  'targets': [
    {
      'target_name': 'pepper_test_plugin',
      'type': 'shared_library',
      'dependencies': [
        '../../../base/base.gyp:base',
        '../../../skia/skia.gyp:skia',
        '../../../third_party/npapi/npapi.gyp:npapi',
      ],
      'include_dirs': [
        '../../..',  # Root of Chrome Checkout
      ],
      'defines': [
        'PEPPER_APIS_ENABLED',
      ],
      'conditions': [
        ['OS=="win"', {
          'product_name': 'pepper_test_plugin',
          'msvs_guid': 'EE00E36E-9E8C-4DFB-925E-FBE32CEDB91A',
          'sources': [
            'pepper_test_plugin.def',
            'pepper_test_plugin.rc',
          ],
        }]
      ],
      'sources': [
        'main.cc',
        'plugin_object.cc',
        'plugin_object.h',
        'test_object.cc',
        'test_object.h',
      ],
      'run_as': {
        'working_directory': '.',
        'action': [
          '<(PRODUCT_DIR)/<(EXECUTABLE_PREFIX)chrome<(EXECUTABLE_SUFFIX)',
          '--no-sandbox',
          '--load-plugin=$(TargetPath)',
          'file://$(ProjectDir)test_page.html',
        ],
      },
    }
  ],
}
<|endoftext|>


<commit_before>#!/usr/bin/python
import sys,os
class AdbPaste:
	"Pass a long string as input to an android device/emulator"

	key_dict = {
		#key is the string, value is the keycode the emulator expects to generate that string
		"0":7,
		"1":8,
		"2":9,
		"3":10,
		"4":11,
		"5":12,
		"6":13,
		"7":14,
		"8":15,
		"9":16,
		"*":17,
		"#":18,
		"A":29,
		"B":30,
		"C":31,
		"D":32,
		"E":33,
		"F":34,
		"G":35,
		"H":36,
		"I":37,
		"J":38,
		"K":39,
		"L":40,
		"M":41,
		"N":42,
		"O":43,
		"P":44,
		"Q":45,
		"R":46,
		"S":47,
		"T":48,
		"U":49,
		"V":50,
		"W":51,
		"X":52,
		"Y":53,
		"Z":54,
		",":55,
		".":56,
		"	":61,
		" ":62,
		"\n":66,
		"`":68,
		"-":69,
		"=":70,
		"[":71,
		"]":72,
		"\\":73,
		";":74,
		"'":75,
		"/":76,
		"@":77,
		"+":81,
		"(":162,
		")":163,
		#// note how there's no colon or single/double quotes and others... sigh. can't standardize one solution for it all
	}

	#// charaters that must be sent as keyevent because as string sh will complain.
	#// there is nothing i can do when calling it on windows because adb will just
	#// pass it forward to sh and things break.
	trouble = [' ', '\n', '	'] # i think space is only needed in adb.exe->sh... when running directly in unix it may not be needed
	inconvenience = [';', ')' ,'(', "'", '\\', '&', '#', '<', '>']

	def __init__(self, input_string=""):
		self.addString( input_string )

	def addString(self, input_string):
		self.string_data = input_string

	def getKeys(self, fast=False):
		"thanks to some keys not being available, e.g. colon, we return an array of keycodes (int) or strings."
		r = []
		count = 0
		for c in self.string_data:
			count += 1
			# if char is in trouble list, create a new int element in the output
			if c in self.trouble:
				t = self.translate(c)
				r.append( t )
			# work around a bug in the emulator... if the browser starts to look on google
			#  while this script is 'typing' in the address bar, anything longer than 10 or so
			#  chars will fail on my box... so just make it slow here too... man, i hate the emulator.
			#if len(r) < 10: # or len(r[-1]) > 10:
			elif not fast and count > 7 and isinstance(r[-1], str) and len(r[-1]) > 7:
				r.append( c )
			else:
				#// if the last element is a safe string, continue to add to it
				# before anything, escape if needed
				if c == '"': # added this to CMD.exe issues, TODO: test on other platforms
					c = '\\\\\\"' # this will become \\\" to CMD when passing to adb.exe, which will become \" to sh, and finally " to the device

				elif c in self.inconvenience:
					c = '\\' + c
				#// here is something weird... $ does not need to be encoded (\$ results in \$ typed in the emulator) but it will
				#// also fail if it's not the last char in the string. proably sh at some point try to do variable subst
				if len(r) > 0 and isinstance(r[-1], str) and r[-1][-1] != '$':
					r[-1] += c
				else:
					#// otherwise, start a new safe string batch
					r.append( c )
		return r

	def sendKeys(self, key_list):
		for k in key_list:
			self.send( k );

	def send( self, key ):
		"sends a single key to the device/emulator"
		print('sending', key)
		if( isinstance(key, int) ):
			os.system('adb shell input keyevent %d'%key)
		else:
			os.system('adb shell input text "' + key + '"')

	def translate( self, char ):
		return self.key_dict[char] #// will fail on unkown values, so we can add them :)

if __name__=="__main__":
	arg = sys.argv[1:]
	#// --fast: must be 1st arg, i'm lazy. Will bypass the workaround of breaking longer strings
	#//         will mess up input in the browser or other input boxes that does network searchs
	#//         while you are typing. For sure!
	if arg[0] == "--fast":
		fast = True
		arg = arg[1:]
	else:
		fast = False

	#// --notab: Convert tabs into spaces. usefull for 'typing' a file into a textarea or field where tab would change focus
	if arg[0] == "--notab":
		notab = True
		arg = arg[1:]
	else:
		notab = False

	#// -- file: read the contents from a file, and not from stdin
	if arg[0] == "--file" and isinstance(arg[1], str):
		with open(arg[1], 'r') as content_file:
			arg = content_file.read()
			import re
			arg = re.sub('\t', ' ', arg)
	else:
		arg = " ".join(arg)

	paste = AdbPaste( arg )
	keys = paste.getKeys(fast)
	paste.sendKeys(keys)
<commit_msg>special case for > and ^<commit_after>#!/usr/bin/python
import sys,os
class AdbPaste:
	"Pass a long string as input to an android device/emulator"

	key_dict = {
		#key is the string, value is the keycode the emulator expects to generate that string
		"0":7,
		"1":8,
		"2":9,
		"3":10,
		"4":11,
		"5":12,
		"6":13,
		"7":14,
		"8":15,
		"9":16,
		"*":17,
		"#":18,
		"A":29,
		"B":30,
		"C":31,
		"D":32,
		"E":33,
		"F":34,
		"G":35,
		"H":36,
		"I":37,
		"J":38,
		"K":39,
		"L":40,
		"M":41,
		"N":42,
		"O":43,
		"P":44,
		"Q":45,
		"R":46,
		"S":47,
		"T":48,
		"U":49,
		"V":50,
		"W":51,
		"X":52,
		"Y":53,
		"Z":54,
		",":55,
		".":56,
		"	":61,
		" ":62,
		"\n":66,
		"`":68,
		"-":69,
		"=":70,
		"[":71,
		"]":72,
		"\\":73,
		";":74,
		"'":75,
		"/":76,
		"@":77,
		"+":81,
		"(":162,
		")":163,
		#// note how there's no colon or single/double quotes and others... sigh. can't standardize one solution for it all
	}

	#// charaters that must be sent as keyevent because as string sh will complain.
	#// there is nothing i can do when calling it on windows because adb will just
	#// pass it forward to sh and things break.
	trouble = [' ', '\n', '	'] # i think space is only needed in adb.exe->sh... when running directly in unix it may not be needed
	inconvenience = [';', ')' ,'(', "'", '\\', '&', '#', '<', '>']

	def __init__(self, input_string=""):
		self.addString( input_string )

	def addString(self, input_string):
		self.string_data = input_string

	def getKeys(self, fast=False):
		"thanks to some keys not being available, e.g. colon, we return an array of keycodes (int) or strings."
		r = []
		count = 0
		for c in self.string_data:
			count += 1
			# if char is in trouble list, create a new int element in the output
			if c in self.trouble:
				t = self.translate(c)
				r.append( t )
			# work around a bug in the emulator... if the browser starts to look on google
			#  while this script is 'typing' in the address bar, anything longer than 10 or so
			#  chars will fail on my box... so just make it slow here too... man, i hate the emulator.
			#if len(r) < 10: # or len(r[-1]) > 10:
			elif not fast and count > 7 and isinstance(r[-1], str) and len(r[-1]) > 7:
				r.append( c )
			else:
				#// if the last element is a safe string, continue to add to it
				# before anything, escape if needed
				if c == '"': # added this to CMD.exe issues, TODO: test on other platforms
					c = '\\\\\\"' # this will become \\\" to CMD when passing to adb.exe, which will become \" to sh, and finally " to the device
				# special case for >. only way to escape them in windows when it is in a double quote and followed by anything is with ^
				elif sys.platform == "win32" and c == ">":
					c = "\\^" + c
				# ^ is a escape char in windows. it will be ignored
				elif sys.platform == "win32" and c == "^":
					c = "^^"
				elif c in self.inconvenience:
					c = '\\' + c

				#// here is something weird... $ does not need to be encoded (\$ results in \$ typed in the emulator) but it will
				#// also fail if it's not the last char in the string. proably sh at some point try to do variable subst
				if len(r) > 0 and isinstance(r[-1], str) and r[-1][-1] != '$':
					r[-1] += c
				else:
					#// otherwise, start a new safe string batch
					r.append( c )
		return r

	def sendKeys(self, key_list):
		for k in key_list:
			self.send( k );

	def send( self, key ):
		"sends a single key to the device/emulator"
		print('sending', key)
		if( isinstance(key, int) ):
			os.system('adb shell input keyevent %d'%key)
		else:
			os.system('adb shell input text "' + key + '"')

	def translate( self, char ):
		return self.key_dict[char] #// will fail on unkown values, so we can add them :)

if __name__=="__main__":
	arg = sys.argv[1:]
	#// --fast: must be 1st arg, i'm lazy. Will bypass the workaround of breaking longer strings
	#//         will mess up input in the browser or other input boxes that does network searchs
	#//         while you are typing. For sure!
	if arg[0] == "--fast":
		fast = True
		arg = arg[1:]
	else:
		fast = False

	#// --notab: Convert tabs into spaces. usefull for 'typing' a file into a textarea or field where tab would change focus
	if arg[0] == "--notab":
		notab = True
		arg = arg[1:]
	else:
		notab = False

	#// -- file: read the contents from a file, and not from stdin
	if arg[0] == "--file" and isinstance(arg[1], str):
		with open(arg[1], 'r') as content_file:
			arg = content_file.read()
			import re
			arg = re.sub('\t', ' ', arg)
	else:
		arg = " ".join(arg)

	paste = AdbPaste( arg )
	keys = paste.getKeys(fast)
	paste.sendKeys(keys)
<|endoftext|>


<commit_before>#!/usr/bin/python

#
#   Copyright 2013 https://github.com/gcb
#
#   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.
#

import sys,os,itertools
class AdbPaste:
	"Pass a long string as input to an android device/emulator"

	key_dict = {
		#key is the string, value is the keycode the emulator expects to generate that string
		"0":7,
		"1":8,
		"2":9,
		"3":10,
		"4":11,
		"5":12,
		"6":13,
		"7":14,
		"8":15,
		"9":16,
		"*":17,
		"#":18,
		"A":29,
		"B":30,
		"C":31,
		"D":32,
		"E":33,
		"F":34,
		"G":35,
		"H":36,
		"I":37,
		"J":38,
		"K":39,
		"L":40,
		"M":41,
		"N":42,
		"O":43,
		"P":44,
		"Q":45,
		"R":46,
		"S":47,
		"T":48,
		"U":49,
		"V":50,
		"W":51,
		"X":52,
		"Y":53,
		"Z":54,
		",":55,
		".":56,
		"	":61,
		" ":62,
		"\n":66,
		"`":68,
		"-":69,
		"=":70,
		"[":71,
		"]":72,
		"\\":73,
		";":74,
		"'":75,
		"/":76,
		"@":77,
		"+":81,
		"(":162,
		")":163,
		#// note how there are no :'"? and others... sigh. can't standardize one solution for it all
	}

	#// charaters that must be sent as keyevent because as string sh will complain.
	#// there is nothing i can do when calling it on windows because adb will just
	#// pass it forward to sh and things break.
	trouble = [' ', '\n', '	'] # i think space is only needed in adb.exe->sh... when running directly in unix it may not be needed
	inconvenience = [';', ')' ,'(', "'", '\\', '&', '#', '<', '>', '|']

	def __init__(self, input_string=""):
		self.addString( input_string )

	def addString(self, input_string):
		self.string_data = input_string

	def getKeys(self, fast=False):
		"thanks to some keys not being available, e.g. colon, we return an array of keycodes (int) or strings."
		r = []
		count = 0
		for c in self.string_data:
			count += 1
			# if char is in trouble list, create a new int element in the output
			if c in self.trouble:
				t = self.translate(c)
				r.append( t )
			# work around a bug in the emulator... if the browser starts to look on google
			#  while this script is 'typing' in the address bar, anything longer than 10 or so
			#  chars will fail on my box... so just make it slow here too... man, i hate the emulator.
			#if len(r) < 10: # or len(r[-1]) > 10:
			elif not fast and count > 7 and isinstance(r[-1], str) and len(r[-1]) > 7:
				r.append( c )
			else:
				#// if the last element is a safe string, continue to add to it
				# before anything, escape if needed
				if c == '"': # added this to CMD.exe issues, TODO: test on other platforms
					c = '\\\\\\"' # this will become \\\" to CMD when passing to adb.exe, which will become \" to sh, and finally " to the device
				# special case for > ,only way to escape them in windows when it is in a double quote and followed by anything is with ^
				# but adding the ^ in front, if there's no double quote in the string, CMD will not treat ^ as a special char and send it along
				elif sys.platform == "win32" and c == ">":
					if len(r)>0 and isinstance(r[-1], str) and '"' in r[-1]:
						c = "\\^>"
					else:
						c = "\\>"
				# ^ is a escape char in windows. it will be ignored
				elif sys.platform == "win32" and c == "^":
					c = "^^"
				elif c in self.inconvenience:
					c = '\\' + c

				#// here is something weird... $ does not need to be encoded (\$ results in \$ typed in the emulator) but it will
				#// also fail if it's not the last char in the string. proably sh at some point try to do variable subst
				if len(r) > 0 and isinstance(r[-1], str) and r[-1][-1] != '$':
					r[-1] += c
				else:
					#// otherwise, start a new safe string batch
					r.append( c )

		# ? is a special case at least on win32. "asd?" and "?a" ok. "?" fail. "\?" shows "d".
		# so we can't escape it, but we can make it work by appending something when it is alone.
		# but then we have to delete that something... argh
		# also we only need to pad it if the string isn't already paddig it. but in the main loop we aren't looking forward.
		# so the solution here is to look at instances where it happens without any padding, and change to ?a<backspace>... sigh
		r = itertools.chain.from_iterable(("?a", 67) if item == "?" else (item, ) for item in r)

		return r

	def sendKeys(self, key_list, device = False):
		for k in key_list:
			self.send( k, device );

	def send( self, key, device = False ):
		"sends a single key to the device/emulator"
		print('sending', key)
		cmd = 'adb'
		if isinstance(device, str):
			cmd += ' -s ' + device
		if( isinstance(key, int) ):
			ret = os.system(cmd + ' shell input keyevent %d'%key)
		else:
			ret = os.system(cmd + ' shell input text "' + key + '"')
		if ret != 0:
			if isinstance(ret, int):
				sys.exit( ret )
			else:
				sys.exit( 1 )

	def translate( self, char ):
		return self.key_dict[char] #// will fail on unkown values, so we can add them :)

if __name__=="__main__":
	device = False
	arg = sys.argv[1:]
	#// --fast: must be 1st arg, i'm lazy. Will bypass the workaround of breaking longer strings
	#//         will mess up input in the browser or other input boxes that does network searchs
	#//         while you are typing. For sure!
	if arg[0] == "--fast":
		fast = True
		arg = arg[1:]
	else:
		fast = False

	#// --notab: Convert tabs into spaces. usefull for 'typing' a file into a textarea or field where tab would change focus
	if arg[0] == "--notab":
		notab = True
		arg = arg[1:]
	else:
		notab = False

	#// -s: pass the next value to -s flag on the adb command. For selecting which device to use when there's more than one present
	if arg[0] == "-s":
		device = arg[1]
		arg = arg[2:]

	#// -- file: read the contents from a file, and not from stdin
	if arg[0] == "--file" and isinstance(arg[1], str):
		with open(arg[1], 'r') as content_file:
			arg = content_file.read()
			import re
			arg = re.sub('\t', ' ', arg)
	else:
		arg = " ".join(arg)

	paste = AdbPaste( arg )
	keys = paste.getKeys(fast)
	paste.sendKeys(keys, device )
<commit_msg>Update AdbPaste.py<commit_after>#!/usr/bin/python

#
#   Copyright 2013 https://github.com/gcb
#
#   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.
#

import sys,os,itertools
class AdbPaste:
	"Pass a long string as input to an android device/emulator"

	key_dict = {
		#key is the string, value is the keycode the emulator expects to generate that string
		"0":7,
		"1":8,
		"2":9,
		"3":10,
		"4":11,
		"5":12,
		"6":13,
		"7":14,
		"8":15,
		"9":16,
		"*":17,
		"#":18,
		"A":29,
		"B":30,
		"C":31,
		"D":32,
		"E":33,
		"F":34,
		"G":35,
		"H":36,
		"I":37,
		"J":38,
		"K":39,
		"L":40,
		"M":41,
		"N":42,
		"O":43,
		"P":44,
		"Q":45,
		"R":46,
		"S":47,
		"T":48,
		"U":49,
		"V":50,
		"W":51,
		"X":52,
		"Y":53,
		"Z":54,
		",":55,
		".":56,
		"	":61,
		" ":62,
		"\n":66,
		"`":68,
		"-":69,
		"=":70,
		"[":71,
		"]":72,
		"\\":73,
		";":74,
		"'":75,
		"/":76,
		"@":77,
		"+":81,
		"(":162,
		")":163,
		#// note how there are no :'"? and others... sigh. can't standardize one solution for it all
	}

	#// charaters that must be sent as keyevent because as string sh will complain.
	#// there is nothing i can do when calling it on windows because adb will just
	#// pass it forward to sh and things break.
	trouble = [' ', '\n', '	'] # i think space is only needed in adb.exe->sh... when running directly in unix it may not be needed
	if sys.platform != "win32":
		trouble.append('`')
	inconvenience = [';', ')' ,'(', "'", '\\', '&', '#', '<', '>', '|']

	def __init__(self, input_string=""):
		self.addString( input_string )

	def addString(self, input_string):
		self.string_data = input_string

	def getKeys(self, fast=False):
		"thanks to some keys not being available, e.g. colon, we return an array of keycodes (int) or strings."
		r = []
		count = 0
		for c in self.string_data:
			count += 1
			# if char is in trouble list, create a new int element in the output
			if c in self.trouble:
				t = self.translate(c)
				r.append( t )
			# work around a bug in the emulator... if the browser starts to look on google
			#  while this script is 'typing' in the address bar, anything longer than 10 or so
			#  chars will fail on my box... so just make it slow here too... man, i hate the emulator.
			#if len(r) < 10: # or len(r[-1]) > 10:
			elif not fast and count > 7 and isinstance(r[-1], str) and len(r[-1]) > 7:
				r.append( c )
			else:
				#// if the last element is a safe string, continue to add to it
				# before anything, escape if needed
				if c == '"': # added this to CMD.exe issues, TODO: test on other platforms
					c = '\\\\\\"' # this will become \\\" to CMD when passing to adb.exe, which will become \" to sh, and finally " to the device
				# special case for > ,only way to escape them in windows when it is in a double quote and followed by anything is with ^
				# but adding the ^ in front, if there's no double quote in the string, CMD will not treat ^ as a special char and send it along
				elif sys.platform == "win32" and c == ">":
					if len(r)>0 and isinstance(r[-1], str) and '"' in r[-1]:
						c = "\\^>"
					else:
						c = "\\>"
				# ^ is a escape char in windows. it will be ignored
				elif sys.platform == "win32" and c == "^":
					c = "^^"
				elif c in self.inconvenience:
					c = '\\' + c

				#// here is something weird... $ does not need to be encoded (\$ results in \$ typed in the emulator) but it will
				#// also fail if it's not the last char in the string. proably sh at some point try to do variable subst
				if len(r) > 0 and isinstance(r[-1], str) and r[-1][-1] != '$':
					r[-1] += c
				else:
					#// otherwise, start a new safe string batch
					r.append( c )

		# ? is a special case at least on win32. "asd?" and "?a" ok. "?" fail. "\?" shows "d".
		# so we can't escape it, but we can make it work by appending something when it is alone.
		# but then we have to delete that something... argh
		# also we only need to pad it if the string isn't already paddig it. but in the main loop we aren't looking forward.
		# so the solution here is to look at instances where it happens without any padding, and change to ?a<backspace>... sigh
		r = itertools.chain.from_iterable(("?a", 67) if item == "?" else (item, ) for item in r)

		return r

	def sendKeys(self, key_list, device = False):
		for k in key_list:
			self.send( k, device );

	def send( self, key, device = False ):
		"sends a single key to the device/emulator"
		print('sending', key)
		cmd = 'adb'
		if isinstance(device, str):
			cmd += ' -s ' + device
		if( isinstance(key, int) ):
			ret = os.system(cmd + ' shell input keyevent %d'%key)
		else:
			ret = os.system(cmd + ' shell input text "' + key + '"')
		if ret != 0:
			if isinstance(ret, int):
				sys.exit( ret )
			else:
				sys.exit( 1 )

	def translate( self, char ):
		return self.key_dict[char] #// will fail on unkown values, so we can add them :)

if __name__=="__main__":
	device = False
	arg = sys.argv[1:]
	#// --fast: must be 1st arg, i'm lazy. Will bypass the workaround of breaking longer strings
	#//         will mess up input in the browser or other input boxes that does network searchs
	#//         while you are typing. For sure!
	if arg[0] == "--fast":
		fast = True
		arg = arg[1:]
	else:
		fast = False

	#// --notab: Convert tabs into spaces. usefull for 'typing' a file into a textarea or field where tab would change focus
	if arg[0] == "--notab":
		notab = True
		arg = arg[1:]
	else:
		notab = False

	#// -s: pass the next value to -s flag on the adb command. For selecting which device to use when there's more than one present
	if arg[0] == "-s":
		device = arg[1]
		arg = arg[2:]

	#// -- file: read the contents from a file, and not from stdin
	if arg[0] == "--file" and isinstance(arg[1], str):
		with open(arg[1], 'r') as content_file:
			arg = content_file.read()
			import re
			arg = re.sub('\t', ' ', arg)
	else:
		arg = " ".join(arg)

	paste = AdbPaste( arg )
	keys = paste.getKeys(fast)
	paste.sendKeys(keys, device )
<|endoftext|>


<commit_before>import ipywidgets as ipw

from .utils import update_widget
from .slot_wg import SlotWg
from .json_html import JsonHTML

debug_console = None  # ipw.Output()
"""
{"table": [{"output_name": "table", "output_module": "csv_loader_1", "input_name": "df", "input_module": "every_1"}, {"output_name": "table", "output_module": "csv_loader_1", "input_name": "table", "input_module": "histogram_index_1"}, {"output_name": "table", "output_module": "csv_loader_1", "input_name": "table", "input_module": "histogram_index_2"}, {"output_name": "table", "output_module": "csv_loader_1", "input_name": "table", "input_module": "histogram_index_3"}, {"output_name": "table", "output_module": "csv_loader_1", "input_name": "table", "input_module": "histogram_index_4"}], "_trace": null}
## range_query_2d
{"min": [{"output_name": "min", "output_module": "range_query2d_2", "input_name": "table.00.03", "input_module": "mc_histogram2_d_1"}, {"output_name": "min", "output_module": "range_query2d_2", "input_name": "table.00.03", "input_module": "mc_histogram2_d_2"}], "max": [{"output_name": "max", "output_module": "range_query2d_2", "input_name": "table.00.04", "input_module": "mc_histogram2_d_1"}, {"output_name": "max", "output_module": "range_query2d_2", "input_name": "table.00.04", "input_module": "mc_histogram2_d_2"}], "table": [{"output_name": "table", "output_module": "range_query2d_2", "input_name": "data", "input_module": "mc_histogram2_d_2"}, {"output_name": "table", "output_module": "range_query2d_2", "input_name": "table", "input_module": "sample_2"}], "_trace": null}

"""

class ModuleWg(ipw.Tab):  # pylint: disable=too-many-ancestors
    def __init__(self, board, dconsole=None):
        global debug_console  # pylint: disable=global-statement
        debug_console = dconsole
        self._index = board
        self._main = JsonHTML()
        self.module_name = None
        self.selection_changed = False
        self._output_slots = ipw.Tab()
        super().__init__([self._main, self._output_slots])
        self.set_title(0, 'Main')
        self.set_title(1, 'Output slots')

    async def refresh(self):
        _idx = self._index
        # pylint: disable=protected-access
        json_ = _idx._cache_js
        assert json_ is not None
        module_json = None
        m = None
        for i, m in enumerate(json_['modules']):
            if m['id'] == self.module_name:
                module_json = m
                break
        assert module_json is not None
        self.set_title(0, self.module_name)
        await update_widget(self._main, 'data', m)
        await update_widget(self._main, 'config',
                            dict(order=["classname",
                                        "speed",
                                        "debug",
                                        "state",
                                        "last_update",
                                        "default_step_size",
                                        "start_time",
                                        "end_time",
                                        "parameters",
                                        "input_slots"],
                                 sparkline=["speed"]))
        _selected_index = 0
        module = self._index.scheduler.modules()[self.module_name]
        if module is None:
            return
        if self.selection_changed or not self._output_slots.children:
            # first refresh
            self.selection_changed = False
            self.selected_index = 0
            slots = [SlotWg(module, sl)
                     for sl in m["output_slots"].keys()]+[SlotWg(module,
                                                                 '_params')]
            await update_widget(self._output_slots, 'children', slots)
            if module.name in self._index.vis_register:
                for wg, label in self._index.vis_register[module.name]:
                    self.children = (wg,) + self.children
                    self.set_title(0, label)
                    self.set_title(1, 'Main')
                    self.set_title(2, 'Output slots')
            elif len(self.children) > 2:
                self.children = self.children[:2]
        else:
            _selected_index = self._output_slots.selected_index
        for i, k in enumerate(m["output_slots"].keys()):
            self._output_slots.set_title(i, k)
            await self._output_slots.children[i].refresh()
        i += 1
        self._output_slots.set_title(i, '_params')
        await self._output_slots.children[i].refresh()
        self._output_slots.selected_index = _selected_index
<commit_msg>fixing tabs<commit_after>import ipywidgets as ipw

from .utils import update_widget
from .slot_wg import SlotWg
from .json_html import JsonHTML

debug_console = None  # ipw.Output()
"""
{"table": [{"output_name": "table", "output_module": "csv_loader_1", "input_name": "df", "input_module": "every_1"}, {"output_name": "table", "output_module": "csv_loader_1", "input_name": "table", "input_module": "histogram_index_1"}, {"output_name": "table", "output_module": "csv_loader_1", "input_name": "table", "input_module": "histogram_index_2"}, {"output_name": "table", "output_module": "csv_loader_1", "input_name": "table", "input_module": "histogram_index_3"}, {"output_name": "table", "output_module": "csv_loader_1", "input_name": "table", "input_module": "histogram_index_4"}], "_trace": null}
## range_query_2d
{"min": [{"output_name": "min", "output_module": "range_query2d_2", "input_name": "table.00.03", "input_module": "mc_histogram2_d_1"}, {"output_name": "min", "output_module": "range_query2d_2", "input_name": "table.00.03", "input_module": "mc_histogram2_d_2"}], "max": [{"output_name": "max", "output_module": "range_query2d_2", "input_name": "table.00.04", "input_module": "mc_histogram2_d_1"}, {"output_name": "max", "output_module": "range_query2d_2", "input_name": "table.00.04", "input_module": "mc_histogram2_d_2"}], "table": [{"output_name": "table", "output_module": "range_query2d_2", "input_name": "data", "input_module": "mc_histogram2_d_2"}, {"output_name": "table", "output_module": "range_query2d_2", "input_name": "table", "input_module": "sample_2"}], "_trace": null}

"""

class ModuleWg(ipw.Tab):  # pylint: disable=too-many-ancestors
    def __init__(self, board, dconsole=None):
        global debug_console  # pylint: disable=global-statement
        debug_console = dconsole
        self._index = board
        self._main = JsonHTML()
        self.module_name = None
        self.selection_changed = False
        self._output_slots = ipw.Tab()
        super().__init__([self._main, self._output_slots])
        self.set_title(0, 'Main')
        self.set_title(1, 'Output slots')

    async def refresh(self):
        _idx = self._index
        # pylint: disable=protected-access
        json_ = _idx._cache_js
        assert json_ is not None
        module_json = None
        m = None
        for i, m in enumerate(json_['modules']):
            if m['id'] == self.module_name:
                module_json = m
                break
        assert module_json is not None
        self.set_title(0, self.module_name)
        await update_widget(self._main, 'data', m)
        await update_widget(self._main, 'config',
                            dict(order=["classname",
                                        "speed",
                                        "debug",
                                        "state",
                                        "last_update",
                                        "default_step_size",
                                        "start_time",
                                        "end_time",
                                        "parameters",
                                        "input_slots"],
                                 sparkline=["speed"]))
        _selected_index = 0
        module = self._index.scheduler.modules()[self.module_name]
        if module is None:
            return
        if self.selection_changed or not self._output_slots.children:
            # first refresh
            self.selection_changed = False
            self.selected_index = 0
            slots = [SlotWg(module, sl)
                     for sl in m["output_slots"].keys()]+[SlotWg(module,
                                                                 '_params')]
            await update_widget(self._output_slots, 'children', slots)
            if module.name in self._index.vis_register:
                for wg, label in self._index.vis_register[module.name]:
                    self.children = (wg,) + self.children
                    self.set_title(0, label)
                    self.set_title(1, 'Main')
                    self.set_title(2, 'Output slots')
            elif len(self.children) > 2:
                self.children = self.children[1:]
                self.set_title(0, module.name)
                self.set_title(1, 'Output slots')
        else:
            _selected_index = self._output_slots.selected_index
        for i, k in enumerate(m["output_slots"].keys()):
            self._output_slots.set_title(i, k)
            await self._output_slots.children[i].refresh()
        i += 1
        self._output_slots.set_title(i, '_params')
        await self._output_slots.children[i].refresh()
        self._output_slots.selected_index = _selected_index
<|endoftext|>


<commit_before>import os
from dotenv import load_dotenv
load_dotenv('.env')

# General

TABULAR_EXTENSIONS = ['csv', 'xls', 'xlsx', 'ods']

# API

APP_PORT = os.environ.get('PORT', '5000')

# Database

DATABASE_URL = os.environ['DATABASE_URL']

# Celery

broker_url = os.environ['BROKER_URL']
result_backend = os.environ['RESULT_BACKEND']
task_serializer = 'json'
result_serializer = 'json'
timezone = 'Europe/London'
enable_utc = True
<commit_msg>added logging config<commit_after>import os
import logging
from dotenv import load_dotenv
load_dotenv('.env')

# General

TABULAR_EXTENSIONS = ['csv', 'xls', 'xlsx', 'ods']

# API

APP_PORT = os.environ.get('PORT', '5000')

# Database

DATABASE_URL = os.environ['DATABASE_URL']

# Celery

broker_url = os.environ['BROKER_URL']
result_backend = os.environ['RESULT_BACKEND']
task_serializer = 'json'
result_serializer = 'json'
timezone = 'Europe/London'
enable_utc = True

# Logging

logging.basicConfig(level=logging.DEBUG)
if os.environ.get('LOGGING_URL', None):
    root_logger = logging.getLogger()
    host, port = os.environ['LOGGING_URL'].split(':')
    syslog_handler = SysLogHandler(address=(host, int(port)))
    syslog_handler.setLevel(logging.INFO)
    root_logger.addHandler(syslog_handler)
<|endoftext|>


<commit_before>"""QSyntaxHighlighter implementation
Uses syntax module for doing the job
"""

from PyQt4.QtCore import Qt
from PyQt4.QtGui import QBrush, QColor, QFont, QSyntaxHighlighter, QTextCharFormat, QTextBlockUserData

class _TextBlockUserData(QTextBlockUserData):
    def __init__(self, data):
        QTextBlockUserData.__init__(self)
        self.data = data

class SyntaxHighlighter(QSyntaxHighlighter):
    def __init__(self, syntax, *args):
        QSyntaxHighlighter.__init__(self, *args)
        self._syntax = syntax
        self._quteparserToQtFormat = {}

    @staticmethod
    def formatConverterFunction(format):
        qtFormat = QTextCharFormat()
        qtFormat.setForeground(QBrush(QColor(format.color)))
        qtFormat.setBackground(QBrush(QColor(format.background)))
        qtFormat.setFontItalic(format.italic)
        qtFormat.setFontWeight(QFont.Bold if format.bold else QFont.Normal)
        qtFormat.setFontUnderline(format.underline)
        qtFormat.setFontStrikeOut(format.strikeOut)

        return qtFormat

    def _setFormat(self, start, length, format):
        if format is None:
            return
        self.setFormat(start, length, format)

    def highlightBlock(self, text):
        if False:
            lineData, highlightedSegments = self._syntax.highlightBlock(text, self._prevData())

            currentPos = 0
            for length, format in highlightedSegments:
                self._setFormat(currentPos, length, format)
                currentPos += length
        else:
            lineData = self._syntax.parseBlock(text, self._prevData())
        self.setCurrentBlockUserData(_TextBlockUserData(lineData))

    def _prevData(self):
        prevBlock = self.currentBlock().previous()
        if prevBlock.isValid():
            dataObject = prevBlock.userData()
            if dataObject is not None:
                return dataObject.data
        return None
<commit_msg>Do not use QSyntaxHighlighter. Highlight all on start<commit_after>"""QSyntaxHighlighter implementation
Uses syntax module for doing the job
"""

from PyQt4.QtCore import Qt, QObject
from PyQt4.QtGui import QBrush, QColor, QFont, \
                        QTextBlockUserData, QTextCharFormat, QTextDocument, QTextLayout

class _TextBlockUserData(QTextBlockUserData):
    def __init__(self, data):
        QTextBlockUserData.__init__(self)
        self.data = data

class SyntaxHighlighter(QObject):
    def __init__(self, syntax, object):
        if isinstance(object, QTextDocument):
            document = object
        elif isinstance(object, QTextEdit):
            document = object.document()
            assert document is not None
        else:
            raise TypeError("object must be QTextDocument or QTextEdit")

        QObject.__init__(self, document)
        self._syntax = syntax
        self._document = document

        self._parseAll()

    @staticmethod
    def formatConverterFunction(format):
        qtFormat = QTextCharFormat()
        qtFormat.setForeground(QBrush(QColor(format.color)))
        qtFormat.setBackground(QBrush(QColor(format.background)))
        qtFormat.setFontItalic(format.italic)
        qtFormat.setFontWeight(QFont.Bold if format.bold else QFont.Normal)
        qtFormat.setFontUnderline(format.underline)
        qtFormat.setFontStrikeOut(format.strikeOut)

        return qtFormat

    def _parseAll(self):
        syntax = self._syntax
        block = self._document.firstBlock()
        lineData = None
        while block.isValid():
            lineData = syntax.parseBlock(block.text(), lineData)
            block.setUserData(_TextBlockUserData(lineData))
            block = block.next()

    def _highlightAll(self):
        syntax = self._syntax
        block = self._document.firstBlock()
        lineData = None
        while block.isValid():
            lineData, highlightedSegments = syntax.highlightBlock(block.text(), lineData)
            block.setUserData(_TextBlockUserData(lineData))
            self._applyHighlightedSegments(block, highlightedSegments)
            block = block.next()

    def _highlightBlock(self, block):
        if True:
            lineData, highlightedSegments = self._syntax.highlightBlock(block.text(), self._prevData(block))
            self._applyHighlightedSegments(block, highlightedSegments)
        else:
            lineData = self._syntax.parseBlock(text, self._prevData(block))

        block.setUserData(_TextBlockUserData(lineData))

    def _prevData(self, block):
        prevBlock = block.previous()
        if prevBlock.isValid():
            dataObject = prevBlock.userData()
            if dataObject is not None:
                return dataObject.data
        return None

    def _applyHighlightedSegments(self, block, highlightedSegments):
        layout = block.layout()
        ranges = []
        currentPos = 0
        for length, format in highlightedSegments:
            range = QTextLayout.FormatRange()
            range.format = format
            range.start = currentPos
            range.length = length
            ranges.append(range)
            currentPos += length

        layout.setAdditionalFormats(ranges)
        self._document.markContentsDirty(block.position(), block.length())
<|endoftext|>


<commit_before># This file is part of QuTiP: Quantum Toolbox in Python.
#
#    Copyright (c) 2011 and later, Paul D. Nation and Robert J. Johansson.
#    All rights reserved.
#
#    Redistribution and use in source and binary forms, with or without
#    modification, are permitted provided that the following conditions are
#    met:
#
#    1. Redistributions of source code must retain the above copyright notice,
#       this list of conditions and the following disclaimer.
#
#    2. Redistributions in binary form must reproduce the above copyright
#       notice, this list of conditions and the following disclaimer in the
#       documentation and/or other materials provided with the distribution.
#
#    3. Neither the name of the QuTiP: Quantum Toolbox in Python nor the names
#       of its contributors may be used to endorse or promote products derived
#       from this software without specific prior written permission.
#
#    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
#    "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
#    LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
#    PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
#    HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
#    SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
#    LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
#    DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
#    THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
#    (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
#    OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
###############################################################################
import pytest
from copy import deepcopy

from qutip.qip.circuit import QubitCircuit
from qutip.qip.scheduler import Instruction, Scheduler
from qutip.qip.operations.gates import gate_sequence_product
from qutip import process_fidelity, qeye, tracedist
from qutip.qip.circuit import Gate

def _circuit1():
    circuit1 = QubitCircuit(6)
    circuit1.add_gate("SNOT", 2)
    circuit1.add_gate("CNOT", 4, 2)
    circuit1.add_gate("CNOT", 3, 2)
    circuit1.add_gate("CNOT", 1, 2)
    circuit1.add_gate("CNOT", 5, 4)
    circuit1.add_gate("CNOT", 1, 5)
    circuit1.add_gate("SWAP", [0, 1])
    return circuit1

def _circuit2():
    circuit2 = QubitCircuit(8)
    circuit2.add_gate("SNOT", 1)
    circuit2.add_gate("SNOT", 2)
    circuit2.add_gate("SNOT", 3)
    circuit2.add_gate("CNOT", 4, 5)
    circuit2.add_gate("CNOT", 4, 6)
    circuit2.add_gate("CNOT", 3, 4)
    circuit2.add_gate("CNOT", 3, 5)
    circuit2.add_gate("CNOT", 3, 7)
    circuit2.add_gate("CNOT", 2, 4)
    circuit2.add_gate("CNOT", 2, 6)
    circuit2.add_gate("CNOT", 2, 7)
    circuit2.add_gate("CNOT", 1, 5)
    circuit2.add_gate("CNOT", 1, 6)
    circuit2.add_gate("CNOT", 1, 7)
    return circuit2

def _instructions1():
    instruction_list = [
        Instruction("SNOT", [0], duration=1),
        Instruction("SNOT", [1], duration=1),
        Instruction("CNOT", [2], [3], duration=2),
        Instruction("CNOT", [1], [2], duration=2),
        Instruction("CNOT", [1], [0], duration=2),
        Instruction("SNOT", [3], duration=1),
        Instruction("CNOT", [1], [3], duration=2),
        Instruction("CNOT", [1], [3], duration=2)
    ]
    return instruction_list

@pytest.mark.parametrize(
    "circuit, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_circuit1()), "ASAP", 4, False, False, id="circuit1 ASAP)"),
        pytest.param(deepcopy(_circuit1()), "ALAP", 4, False, False, id="circuit1 ALAP)")
    ])
def test_scheduling_gates1(
        circuit, method, expected_length, random_shuffle, gates_schedule):
    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        circuit, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

# There is some problem with circuit2 on Mac.
# When I list all three tests together, a segment fault arise.
# I suspect it has something to do with pytest.
@pytest.mark.parametrize(
    "circuit, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_circuit2()), "ASAP", 4, False, False, id="circuit2 ASAP"),
    ])
def test_scheduling_gates2(
        circuit, method, expected_length, random_shuffle, gates_schedule):
    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        circuit, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

@pytest.mark.parametrize(
    "circuit, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_circuit2()), "ALAP", 5, False, False, id="circuit2 ALAP no shuffle")
    ])
def test_scheduling_gates3(
        circuit, method, expected_length, random_shuffle, gates_schedule):
    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        circuit, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

@pytest.mark.parametrize(
    "circuit, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_circuit2()), "ALAP", 4, True, False, id="circuit2 ALAP shuffle"),  # with random shuffling
    ])
def test_scheduling_gates4(
        circuit, method, expected_length, random_shuffle, gates_schedule):
    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        circuit, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

@pytest.mark.parametrize(
    "instructions, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_instructions1()), "ASAP", 7, False, False, id="circuit1 pulse ASAP)"),
        pytest.param(deepcopy(_instructions1()), "ALAP", 7, False, False, id="circuit1 pulse ALAP)"),
    ])
def test_scheduling_pulse(
        instructions, method, expected_length, random_shuffle, gates_schedule):
    circuit = QubitCircuit(4)
    for instruction in instructions:
        circuit.add_gate(
            Gate(instruction.name,
            instruction.targets,
            instruction.controls))

    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        instructions, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)<commit_msg>add an empty line at the end of a file<commit_after># This file is part of QuTiP: Quantum Toolbox in Python.
#
#    Copyright (c) 2011 and later, Paul D. Nation and Robert J. Johansson.
#    All rights reserved.
#
#    Redistribution and use in source and binary forms, with or without
#    modification, are permitted provided that the following conditions are
#    met:
#
#    1. Redistributions of source code must retain the above copyright notice,
#       this list of conditions and the following disclaimer.
#
#    2. Redistributions in binary form must reproduce the above copyright
#       notice, this list of conditions and the following disclaimer in the
#       documentation and/or other materials provided with the distribution.
#
#    3. Neither the name of the QuTiP: Quantum Toolbox in Python nor the names
#       of its contributors may be used to endorse or promote products derived
#       from this software without specific prior written permission.
#
#    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
#    "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
#    LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
#    PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
#    HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
#    SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
#    LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
#    DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
#    THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
#    (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
#    OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
###############################################################################
import pytest
from copy import deepcopy

from qutip.qip.circuit import QubitCircuit
from qutip.qip.scheduler import Instruction, Scheduler
from qutip.qip.operations.gates import gate_sequence_product
from qutip import process_fidelity, qeye, tracedist
from qutip.qip.circuit import Gate

def _circuit1():
    circuit1 = QubitCircuit(6)
    circuit1.add_gate("SNOT", 2)
    circuit1.add_gate("CNOT", 4, 2)
    circuit1.add_gate("CNOT", 3, 2)
    circuit1.add_gate("CNOT", 1, 2)
    circuit1.add_gate("CNOT", 5, 4)
    circuit1.add_gate("CNOT", 1, 5)
    circuit1.add_gate("SWAP", [0, 1])
    return circuit1

def _circuit2():
    circuit2 = QubitCircuit(8)
    circuit2.add_gate("SNOT", 1)
    circuit2.add_gate("SNOT", 2)
    circuit2.add_gate("SNOT", 3)
    circuit2.add_gate("CNOT", 4, 5)
    circuit2.add_gate("CNOT", 4, 6)
    circuit2.add_gate("CNOT", 3, 4)
    circuit2.add_gate("CNOT", 3, 5)
    circuit2.add_gate("CNOT", 3, 7)
    circuit2.add_gate("CNOT", 2, 4)
    circuit2.add_gate("CNOT", 2, 6)
    circuit2.add_gate("CNOT", 2, 7)
    circuit2.add_gate("CNOT", 1, 5)
    circuit2.add_gate("CNOT", 1, 6)
    circuit2.add_gate("CNOT", 1, 7)
    return circuit2

def _instructions1():
    instruction_list = [
        Instruction("SNOT", [0], duration=1),
        Instruction("SNOT", [1], duration=1),
        Instruction("CNOT", [2], [3], duration=2),
        Instruction("CNOT", [1], [2], duration=2),
        Instruction("CNOT", [1], [0], duration=2),
        Instruction("SNOT", [3], duration=1),
        Instruction("CNOT", [1], [3], duration=2),
        Instruction("CNOT", [1], [3], duration=2)
    ]
    return instruction_list

@pytest.mark.parametrize(
    "circuit, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_circuit1()), "ASAP", 4, False, False, id="circuit1 ASAP)"),
        pytest.param(deepcopy(_circuit1()), "ALAP", 4, False, False, id="circuit1 ALAP)")
    ])
def test_scheduling_gates1(
        circuit, method, expected_length, random_shuffle, gates_schedule):
    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        circuit, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

# There is some problem with circuit2 on Mac.
# When I list all three tests together, a segment fault arise.
# I suspect it has something to do with pytest.
@pytest.mark.parametrize(
    "circuit, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_circuit2()), "ASAP", 4, False, False, id="circuit2 ASAP"),
    ])
def test_scheduling_gates2(
        circuit, method, expected_length, random_shuffle, gates_schedule):
    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        circuit, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

@pytest.mark.parametrize(
    "circuit, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_circuit2()), "ALAP", 5, False, False, id="circuit2 ALAP no shuffle")
    ])
def test_scheduling_gates3(
        circuit, method, expected_length, random_shuffle, gates_schedule):
    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        circuit, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

@pytest.mark.parametrize(
    "circuit, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_circuit2()), "ALAP", 4, True, False, id="circuit2 ALAP shuffle"),  # with random shuffling
    ])
def test_scheduling_gates4(
        circuit, method, expected_length, random_shuffle, gates_schedule):
    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        circuit, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

@pytest.mark.parametrize(
    "instructions, method, expected_length, random_shuffle, gates_schedule",
    [
        pytest.param(deepcopy(_instructions1()), "ASAP", 7, False, False, id="circuit1 pulse ASAP)"),
        pytest.param(deepcopy(_instructions1()), "ALAP", 7, False, False, id="circuit1 pulse ALAP)"),
    ])
def test_scheduling_pulse(
        instructions, method, expected_length, random_shuffle, gates_schedule):
    circuit = QubitCircuit(4)
    for instruction in instructions:
        circuit.add_gate(
            Gate(instruction.name,
            instruction.targets,
            instruction.controls))

    if random_shuffle:
        repeat_num = 5
    else:
        repeat_num = 0
    result0 = gate_sequence_product(circuit.propagators())

    # run the scheduler
    scheduler = Scheduler(method)
    gate_cycle_indices = scheduler.schedule(
        instructions, gates_schedule=gates_schedule, repeat_num=repeat_num)

    # check if the scheduled length is expected
    assert(max(gate_cycle_indices) == expected_length)
    scheduled_gate = [[] for i in range(max(gate_cycle_indices)+1)]

    # check if the scheduled circuit is correct
    for i, cycles in enumerate(gate_cycle_indices):
        scheduled_gate[cycles].append(circuit.gates[i])
    circuit.gates = sum(scheduled_gate, [])
    result1 = gate_sequence_product(circuit.propagators())
    assert(tracedist(result0*result1.dag(), qeye(result0.dims[0])) < 1.0e-7)

<|endoftext|>