Esempio n. 1
0
def int_binary_op(op: str, c_func_name: str, result_type: RType = int_rprimitive) -> None:
    binary_op(op=op,
              arg_types=[int_rprimitive, int_rprimitive],
              result_type=result_type,
              error_kind=ERR_NEVER,
              format_str='{dest} = {args[0]} %s {args[1]} :: int' % op,
              emit=simple_emit('{dest} = %s({args[0]}, {args[1]});' % c_func_name))
Esempio n. 2
0
def int_binary_op(op: str,
                  c_func_name: str,
                  result_type: RType = int_rprimitive,
                  error_kind: int = ERR_NEVER) -> None:
    binary_op(op=op,
              arg_types=[int_rprimitive, int_rprimitive],
              result_type=result_type,
              error_kind=error_kind,
              format_str='{dest} = {args[0]} %s {args[1]} :: int' % op,
              emit=call_emit(c_func_name))
Esempio n. 3
0
def int_compare_op(op: str, c_func_name: str) -> None:
    int_binary_op(op, c_func_name, bool_rprimitive)
    # Generate a straight compare if we know both sides are short
    binary_op(
        op=op,
        arg_types=[short_int_rprimitive, short_int_rprimitive],
        result_type=bool_rprimitive,
        error_kind=ERR_NEVER,
        format_str='{dest} = {args[0]} %s {args[1]} :: short_int' % op,
        emit=simple_emit(
            '{dest} = (Py_ssize_t){args[0]} %s (Py_ssize_t){args[1]};' % op),
        priority=2)
Esempio n. 4
0
                          arg_types=[],
                          result_type=object_rprimitive,
                          error_kind=ERR_MAGIC,
                          emit=call_emit('CPy_FetchStopIterationValue'))

#
# Fallback primitive operations that operate on 'object' operands
#

for op, opid in [('==', 'Py_EQ'), ('!=', 'Py_NE'), ('<', 'Py_LT'),
                 ('<=', 'Py_LE'), ('>', 'Py_GT'), ('>=', 'Py_GE')]:
    # The result type is 'object' since that's what PyObject_RichCompare returns.
    binary_op(
        op=op,
        arg_types=[object_rprimitive, object_rprimitive],
        result_type=object_rprimitive,
        error_kind=ERR_MAGIC,
        emit=simple_emit(
            '{dest} = PyObject_RichCompare({args[0]}, {args[1]}, %s);' % opid),
        priority=0)

for op, funcname in [('+', 'PyNumber_Add'), ('-', 'PyNumber_Subtract'),
                     ('*', 'PyNumber_Multiply'),
                     ('//', 'PyNumber_FloorDivide'),
                     ('/', 'PyNumber_TrueDivide'), ('%', 'PyNumber_Remainder'),
                     ('<<', 'PyNumber_Lshift'), ('>>', 'PyNumber_Rshift'),
                     ('&', 'PyNumber_And'), ('^', 'PyNumber_Xor'),
                     ('|', 'PyNumber_Or')]:
    binary_op(op=op,
              arg_types=[object_rprimitive, object_rprimitive],
              result_type=object_rprimitive,
              error_kind=ERR_MAGIC,
Esempio n. 5
0
                             result_type=object_rprimitive,
                             error_kind=ERR_MAGIC,
                             emit=emit_get_item)

dict_set_item_op = method_op(
    name='__setitem__',
    arg_types=[dict_rprimitive, object_rprimitive, object_rprimitive],
    result_type=bool_rprimitive,
    error_kind=ERR_FALSE,
    emit=simple_emit(
        '{dest} = PyDict_SetItem({args[0]}, {args[1]}, {args[2]}) >= 0;'))

binary_op(
    op='in',
    arg_types=[object_rprimitive, dict_rprimitive],
    result_type=bool_rprimitive,
    error_kind=ERR_MAGIC,
    format_str='{dest} = {args[0]} in {args[1]} :: dict',
    emit=negative_int_emit('{dest} = PyDict_Contains({args[1]}, {args[0]});'))

# NOTE: PyDict_Update is technically not equivalent to update, but the cases where it
# differs (when the second argument has no keys) should never typecheck for us, so the
# difference is irrelevant.
dict_update_op = method_op(
    name='update',
    arg_types=[dict_rprimitive, object_rprimitive],
    result_type=bool_rprimitive,
    error_kind=ERR_FALSE,
    emit=simple_emit('{dest} = PyDict_Update({args[0]}, {args[1]}) != -1;'))

new_dict_op = func_op(name='builtins.dict',
Esempio n. 6
0
                       "%s = PySequence_Repeat(%s, %s);" % (dest, lst, temp))


def emit_multiply(emitter: EmitterInterface, args: List[str],
                  dest: str) -> None:
    emit_multiply_helper(emitter, dest, args[0], args[1])


def emit_multiply_reversed(emitter: EmitterInterface, args: List[str],
                           dest: str) -> None:
    emit_multiply_helper(emitter, dest, args[1], args[0])


binary_op(op='*',
          arg_types=[list_rprimitive, int_rprimitive],
          result_type=list_rprimitive,
          error_kind=ERR_MAGIC,
          format_str='{dest} = {args[0]} * {args[1]} :: list',
          emit=emit_multiply)

binary_op(op='*',
          arg_types=[int_rprimitive, list_rprimitive],
          result_type=list_rprimitive,
          error_kind=ERR_MAGIC,
          format_str='{dest} = {args[0]} * {args[1]} :: list',
          emit=emit_multiply_reversed)


def emit_len(emitter: EmitterInterface, args: List[str], dest: str) -> None:
    temp = emitter.temp_name()
    emitter.emit_declaration('long long %s;' % temp)
    emitter.emit_line('%s = PyList_GET_SIZE(%s);' % (temp, args[0]))
Esempio n. 7
0
from typing import List, Callable

from mypyc.ops import (object_rprimitive, str_rprimitive, bool_rprimitive,
                       ERR_MAGIC, EmitterInterface)
from mypyc.ops_primitive import func_op, binary_op, simple_emit

func_op(name='builtins.str',
        arg_types=[object_rprimitive],
        result_type=str_rprimitive,
        error_kind=ERR_MAGIC,
        emit=simple_emit('{dest} = PyObject_Str({args[0]});'))

binary_op(op='+',
          arg_types=[str_rprimitive, str_rprimitive],
          result_type=str_rprimitive,
          error_kind=ERR_MAGIC,
          emit=simple_emit('{dest} = PyUnicode_Concat({args[0]}, {args[1]});'))


def emit_str_compare(
        comparison: str) -> Callable[[EmitterInterface, List[str], str], None]:
    def emit(emitter: EmitterInterface, args: List[str], dest: str) -> None:
        temp = emitter.temp_name()
        emitter.emit_declaration('int %s;' % temp)
        emitter.emit_lines(
            '%s = PyUnicode_Compare(%s, %s);' % (temp, args[0], args[1]),
            'if (%s == -1 && PyErr_Occurred())' % temp, '    %s = 2;' % dest,
            'else', '    %s = (%s %s);' % (dest, temp, comparison))

    return emit