Пример #1
0
def prep_string(s):
    """Takes a Pixie string and returns a VoidP to that string. The string should be freed via dispose!, otherwise
    memory leaks could result."""
    affirm(isinstance(s, String), u"Can only prep strings with prep-string")
    utf8 = unicode_to_utf8(rt.name(s))
    raw = rffi.str2charp(utf8)
    return VoidP(rffi.cast(rffi.VOIDP, raw))
Пример #2
0
def unpack(ptr, offset, tp):
    """(unpack ptr offset tp)
       Reads a value of type tp from offset of ptr."""
    affirm(isinstance(ptr, VoidP) or isinstance(ptr, Buffer) or isinstance(ptr, CStruct), u"Type is not unpackable")
    affirm(isinstance(tp, CType), u"Packing type must be a CType")
    ptr = rffi.ptradd(ptr.raw_data(), offset.int_val())
    return tp.ffi_get_value(ptr)
Пример #3
0
def ffi_prep_callback(tp, f):
    """(ffi-prep-callback callback-tp fn)
       Prepares a Pixie function for use as a c callback. callback-tp is a ffi callback type,
       fn is a pixie function (can be a closure, native fn or any object that implements -invoke.
       Returns a function pointer that can be passed to c and invoked as a callback."""
    affirm(isinstance(tp, CFunctionType),
           u"First argument to ffi-prep-callback must be a CFunctionType")
    raw_closure = rffi.cast(rffi.VOIDP, clibffi.closureHeap.alloc())

    if not we_are_translated():
        unique_id = id_generator.get_next()
    else:
        unique_id = rffi.cast(lltype.Signed, raw_closure)

    res = clibffi.c_ffi_prep_closure(
        rffi.cast(clibffi.FFI_CLOSUREP, raw_closure),
        tp.get_cd().cif, invoke_callback, rffi.cast(rffi.VOIDP, unique_id))

    if rffi.cast(lltype.Signed, res) != clibffi.FFI_OK:
        registered_callbacks[unique_id] = None
        runtime_error(u"libffi failed to build this callback")

    cb = CCallback(tp, raw_closure, unique_id, f)
    registered_callbacks[unique_id] = cb

    return cb
Пример #4
0
Файл: ffi.py Проект: kidaa/pixie
def unpack(ptr, offset, tp):
    """(unpack ptr offset tp)
       Reads a value of type tp from offset of ptr."""
    affirm(isinstance(ptr, VoidP) or isinstance(ptr, Buffer) or isinstance(ptr, CStruct), u"Type is not unpackable")
    affirm(isinstance(tp, CType), u"Packing type must be a CType")
    ptr = rffi.ptradd(ptr.raw_data(), offset.int_val())
    return tp.ffi_get_value(ptr)
Пример #5
0
Файл: ffi.py Проект: kidaa/pixie
def prep_string(s):
    """Takes a Pixie string and returns a VoidP to that string. The string should be freed via dispose!, otherwise
    memory leaks could result."""
    affirm(isinstance(s, String), u"Can only prep strings with prep-string")
    utf8 = unicode_to_utf8(rt.name(s))
    raw = rffi.str2charp(utf8)
    return VoidP(rffi.cast(rffi.VOIDP, raw))
Пример #6
0
Файл: ffi.py Проект: kidaa/pixie
def ffi_prep_callback(tp, f):
    """(ffi-prep-callback callback-tp fn)
       Prepares a Pixie function for use as a c callback. callback-tp is a ffi callback type,
       fn is a pixie function (can be a closure, native fn or any object that implements -invoke.
       Returns a function pointer that can be passed to c and invoked as a callback."""
    affirm(isinstance(tp, CFunctionType), u"First argument to ffi-prep-callback must be a CFunctionType")
    raw_closure = rffi.cast(rffi.VOIDP, clibffi.closureHeap.alloc())

    if not we_are_translated():
        unique_id = id_generator.get_next()
    else:
        unique_id = rffi.cast(lltype.Signed, raw_closure)

    res = clibffi.c_ffi_prep_closure(rffi.cast(clibffi.FFI_CLOSUREP, raw_closure), tp.get_cd().cif,
                             invoke_callback,
                             rffi.cast(rffi.VOIDP, unique_id))


    if rffi.cast(lltype.Signed, res) != clibffi.FFI_OK:
        registered_callbacks[unique_id] = None
        runtime_error(u"libffi failed to build this callback")

    cb = CCallback(tp, raw_closure, unique_id, f)
    registered_callbacks[unique_id] = cb

    return cb
Пример #7
0
    def ffi_set_value(self, ptr, val):
        affirm(isinstance(val, CCallback), u"Can only encode CCallbacks as function pointers")


        casted = rffi.cast(rffi.VOIDPP, ptr)
        casted[0] = val.get_raw_closure()

        return None
Пример #8
0
Файл: ffi.py Проект: kidaa/pixie
def pack(ptr, offset, tp, val):
    """(pack! ptr offset tp val)
       Writes val at offset of ptr with the format tp"""
    affirm(isinstance(ptr, VoidP) or isinstance(ptr, Buffer) or isinstance(ptr, CStruct), u"Type is not unpackable")
    affirm(isinstance(tp, CType), u"Packing type must be a CType")
    ptr = rffi.ptradd(ptr.raw_data(), offset.int_val())
    tp.ffi_set_value(ptr, val)
    return nil
Пример #9
0
Файл: ffi.py Проект: kgann/pixie
    def ffi_set_value(self, ptr, val):
        affirm(isinstance(val, CCallback),
               u"Can only encode CCallbacks as function pointers")

        casted = rffi.cast(rffi.VOIDPP, ptr)
        casted[0] = val.get_raw_closure()

        return None
Пример #10
0
def pack(ptr, offset, tp, val):
    """(pack! ptr offset tp val)
       Writes val at offset of ptr with the format tp"""
    affirm(isinstance(ptr, VoidP) or isinstance(ptr, Buffer) or isinstance(ptr, CStruct), u"Type is not unpackable")
    affirm(isinstance(tp, CType), u"Packing type must be a CType")
    ptr = rffi.ptradd(ptr.raw_data(), offset.int_val())
    tp.ffi_set_value(ptr, val)
    return nil
Пример #11
0
 def ffi_set_value(self, ptr, val):
     pnt = rffi.cast(rffi.VOIDPP, ptr)
     if isinstance(val, Buffer):
         pnt[0] = val.buffer()
     elif isinstance(val, VoidP):
         pnt[0] = val.raw_data()
     else:
         print val
         affirm(False, u"Cannot encode this type")
Пример #12
0
 def ffi_set_value(self, ptr, val):
     pnt = rffi.cast(rffi.VOIDPP, ptr)
     if isinstance(val, Buffer):
         pnt[0] = val.buffer()
     elif isinstance(val, VoidP):
         pnt[0] = val.raw_data()
     else:
         print val
         affirm(False, u"Cannot encode this type")
Пример #13
0
Файл: ffi.py Проект: kidaa/pixie
    def ffi_set_value(self, ptr, val):
        if isinstance(val, CCallback):
            casted = rffi.cast(rffi.VOIDPP, ptr)
            casted[0] = val.get_raw_closure()
        elif val is nil:
            casted = rffi.cast(rffi.VOIDPP, ptr)
            casted[0] = rffi.cast(rffi.VOIDP, 0)
        else:
            frm_name = rt.name(rt.str(val.type()))
            to_name = rt.name(rt.str(self))
            affirm(False, u"Cannot encode " + frm_name + u" as " + to_name)

        return None
Пример #14
0
    def ffi_set_value(self, ptr, val):
        if isinstance(val, CCallback):
            casted = rffi.cast(rffi.VOIDPP, ptr)
            casted[0] = val.get_raw_closure()
        elif val is nil:
            casted = rffi.cast(rffi.VOIDPP, ptr)
            casted[0] = rffi.cast(rffi.VOIDP, 0)
        else:
            frm_name = rt.name(rt.str(val.type()))
            to_name = rt.name(rt.str(self))
            affirm(False, u"Cannot encode " + frm_name + u" as " + to_name)

        return None
Пример #15
0
def c_struct(name, size, spec):
    d = {}
    for x in range(rt.count(spec)):
        row = rt.nth(spec, rt.wrap(x))
        nm = rt.nth(row, rt.wrap(0))
        tp = rt.nth(row, rt.wrap(1))
        offset = rt.nth(row, rt.wrap(2))

        affirm(isinstance(nm, Keyword), u"c-struct field names must be keywords")
        if not isinstance(tp, CType):
            runtime_error(u"c-struct field types must be c types, got: " + rt.name(rt.str(tp)))

        d[nm] = (tp, offset.int_val())

    return CStructType(rt.name(name), size.int_val(), d)
Пример #16
0
def c_struct(name, size, spec):
    """(c-struct name size spec)
       Creates a CStruct named name, of size size, with the given spec. Spec is a vector
       of vectors. Each row of the format [field-name type offset]"""
    d = {}
    for x in range(rt.count(spec)):
        row = rt.nth(spec, rt.wrap(x))
        nm = rt.nth(row, rt.wrap(0))
        tp = rt.nth(row, rt.wrap(1))
        offset = rt.nth(row, rt.wrap(2))

        affirm(isinstance(nm, Keyword), u"c-struct field names must be keywords")
        #if not isinstance(tp, CType):
        #    runtime_error(u"c-struct field types must be c types, got: " + rt.name(rt.str(tp)))

        d[nm] = (tp, offset.int_val())

    tp = CStructType(rt.name(name), size.int_val(), d)
    proto._dispose_BANG_.extend(tp, _dispose_cstruct)
    return tp
Пример #17
0
Файл: ffi.py Проект: kidaa/pixie
 def ffi_set_value(self, ptr, val):
     pnt = rffi.cast(rffi.VOIDPP, ptr)
     if isinstance(val, String):
         pnt = rffi.cast(rffi.CCHARPP, ptr)
         utf8 = unicode_to_utf8(rt.name(val))
         raw = rffi.str2charp(utf8)
         pnt[0] = raw
         return CCharPToken(raw)
     elif isinstance(val, Buffer):
         pnt[0] = val.buffer()
     elif isinstance(val, VoidP):
         pnt[0] = val.raw_data()
     elif val is nil:
         pnt[0] = rffi.cast(rffi.VOIDP, 0)
     elif isinstance(val, CStruct):
         pnt[0] = rffi.cast(rffi.VOIDP, val.raw_data())
     else:
         frm_name = rt.name(rt.str(val.type()))
         to_name = rt.name(rt.str(self))
         affirm(False, u"Cannot encode " + frm_name + u" as " + to_name)
Пример #18
0
Файл: ffi.py Проект: kidaa/pixie
def c_struct(name, size, spec):
    """(c-struct name size spec)
       Creates a CStruct named name, of size size, with the given spec. Spec is a vector
       of vectors. Each row of the format [field-name type offset]"""
    d = {}
    for x in range(rt.count(spec)):
        row = rt.nth(spec, rt.wrap(x))
        nm = rt.nth(row, rt.wrap(0))
        tp = rt.nth(row, rt.wrap(1))
        offset = rt.nth(row, rt.wrap(2))

        affirm(isinstance(nm, Keyword), u"c-struct field names must be keywords")
        #if not isinstance(tp, CType):
        #    runtime_error(u"c-struct field types must be c types, got: " + rt.name(rt.str(tp)))

        d[nm] = (tp, offset.int_val())

    tp = CStructType(rt.name(name), size.int_val(), d)
    proto._dispose_BANG_.extend(tp, _dispose_cstruct)
    return tp
Пример #19
0
 def ffi_set_value(self, ptr, val):
     pnt = rffi.cast(rffi.VOIDPP, ptr)
     if isinstance(val, String):
         pnt = rffi.cast(rffi.CCHARPP, ptr)
         utf8 = unicode_to_utf8(rt.name(val))
         raw = rffi.str2charp(utf8)
         pnt[0] = raw
         return CCharPToken(raw)
     elif isinstance(val, Buffer):
         pnt[0] = val.buffer()
     elif isinstance(val, VoidP):
         pnt[0] = val.raw_data()
     elif val is nil:
         pnt[0] = rffi.cast(rffi.VOIDP, 0)
     elif isinstance(val, CStruct):
         pnt[0] = rffi.cast(rffi.VOIDP, val.raw_data())
     else:
         frm_name = rt.name(rt.str(val.type()))
         to_name = rt.name(rt.str(self))
         affirm(False, u"Cannot encode " + frm_name + u" as " + to_name)
Пример #20
0
def _ffi_fn(lib, nm, args, ret_type):
    affirm(isinstance(lib, ExternalLib), u"First argument must be an ExternalLib")
    affirm(isinstance(ret_type, object.Type), u"Ret type must be a type")
    affirm(rt.namespace(nm) is None, u"Name must not be namespaced")

    cnt = rt.count(args)
    new_args = [None] * cnt
    for x in range(cnt):
        t = rt.nth(args, rt.wrap(x))
        affirm(isinstance(t, object.Type), u"Arg defs must be types")
        new_args[x] = t

    f = FFIFn(lib, rt.name(nm), new_args, ret_type)
    return f
Пример #21
0
Файл: ffi.py Проект: kgann/pixie
 def ffi_set_value(self, ptr, val):
     if isinstance(val, String):
         pnt = rffi.cast(rffi.CCHARPP, ptr)
         utf8 = unicode_to_utf8(rt.name(val))
         raw = rffi.str2charp(utf8)
         pnt[0] = raw
         return CCharPToken(raw)
     elif isinstance(val, Buffer):
         vpnt = rffi.cast(rffi.VOIDPP, ptr)
         vpnt[0] = val.buffer()
     elif isinstance(val, VoidP):
         vpnt = rffi.cast(rffi.VOIDPP, ptr)
         vpnt[0] = val.raw_data()
     elif val is nil:
         vpnt = rffi.cast(rffi.VOIDPP, ptr)
         vpnt[0] = rffi.cast(rffi.VOIDP, 0)
     elif isinstance(val, CStruct):
         vpnt = rffi.cast(rffi.VOIDPP, ptr)
         vpnt[0] = rffi.cast(rffi.VOIDP, val.raw_data())
     else:
         print val
         affirm(False, u"Cannot encode this type")
Пример #22
0
def _ffi_fn(lib, nm, args, ret_type):
    affirm(isinstance(lib, ExternalLib),
           u"First argument must be an ExternalLib")
    affirm(isinstance(ret_type, object.Type), u"Ret type must be a type")
    affirm(rt.namespace(nm) is None, u"Name must not be namespaced")

    cnt = rt.count(args)
    new_args = [None] * cnt
    for x in range(cnt):
        t = rt.nth(args, rt.wrap(x))
        affirm(isinstance(t, object.Type), u"Arg defs must be types")
        new_args[x] = t

    f = FFIFn(lib, rt.name(nm), new_args, ret_type)
    return f
Пример #23
0
Файл: ffi.py Проект: kidaa/pixie
def pack(ptr, offset):
    affirm(isinstance(ptr, VoidP) or isinstance(ptr, Buffer) or isinstance(ptr, CStruct), u"Type is not unpackable")
    ptr = rffi.ptradd(ptr.raw_data(), offset.int_val())
    return VoidP(ptr)
Пример #24
0
Файл: ffi.py Проект: kidaa/pixie
def _ffi_voidp(lib, nm):
    affirm(isinstance(lib, ExternalLib), u"First argument to ffi-voidp should be an external library")
    name = rt.name(nm)
    return VoidP(lib.get_fn_ptr(name))
Пример #25
0
Файл: ffi.py Проект: kidaa/pixie
def _ffi_fn__args(args):
    affirm(len(args) >= 4, u"ffi-fn requires at least 4 arguments")
    lib, nm, arg_types, ret_type = args[:4]

    affirm(isinstance(lib, ExternalLib), u"First argument must be an ExternalLib")
    affirm(isinstance(ret_type, object.Type), u"Ret type must be a type")
    affirm(rt.namespace(nm) is None, u"Name must not be namespaced")

    cnt = rt.count(arg_types)
    new_args = [None] * cnt
    for x in range(cnt):
        t = rt.nth(arg_types, rt.wrap(x))
        affirm(isinstance(t, object.Type), u"Arg defs must be types")
        new_args[x] = t

    kwargs = args[4:]
    affirm(len(kwargs) & 0x1 == 0, u"ffi-fn requires even number of options")

    is_variadic = False
    for i in range(0, len(kwargs)/2, 2):
        key = kwargs[i]
        val = kwargs[i+1]
        
        affirm(isinstance(key, Keyword), u"ffi-fn options should be keyword/bool pairs")
        affirm(val is true or val is false, u"ffi-fn options should be keyword/bool pairs")

        k = rt.name(key)
        if k == u"variadic?":
            is_variadic = True if val is true else False
        else:
            affirm(False, u"unknown ffi-fn option: :" + k)

    tp = CFunctionType(new_args, ret_type, is_variadic)
    nm = rt.name(nm)
    f = FFIFn(nm, lib.get_fn_ptr(nm), tp)
    return f
Пример #26
0
def prep_ffi_call__args(args):
    fn = args[0]
    affirm(isinstance(fn, CFunctionType), u"First arg must be a FFI function")
Пример #27
0
def _ffi_fn__args(args):
    affirm(len(args) >= 4, u"ffi-fn requires at least 4 arguments")
    lib, nm, arg_types, ret_type = args[:4]

    affirm(isinstance(lib, ExternalLib),
           u"First argument must be an ExternalLib")
    affirm(isinstance(ret_type, object.Type), u"Ret type must be a type")
    affirm(rt.namespace(nm) is None, u"Name must not be namespaced")

    cnt = rt.count(arg_types)
    new_args = [None] * cnt
    for x in range(cnt):
        t = rt.nth(arg_types, rt.wrap(x))
        affirm(isinstance(t, object.Type), u"Arg defs must be types")
        new_args[x] = t

    kwargs = args[4:]
    affirm(len(kwargs) & 0x1 == 0, u"ffi-fn requires even number of options")

    is_variadic = False
    for i in range(0, len(kwargs) / 2, 2):
        key = kwargs[i]
        val = kwargs[i + 1]

        affirm(isinstance(key, Keyword),
               u"ffi-fn options should be keyword/bool pairs")
        affirm(val is true or val is false,
               u"ffi-fn options should be keyword/bool pairs")

        k = rt.name(key)
        if k == u"variadic?":
            is_variadic = True if val is true else False
        else:
            affirm(False, u"unknown ffi-fn option: :" + k)

    tp = CFunctionType(new_args, ret_type, is_variadic)
    nm = rt.name(nm)
    f = FFIFn(nm, lib.get_fn_ptr(nm), tp)
    return f
Пример #28
0
def _ffi_voidp(lib, nm):
    affirm(isinstance(lib, ExternalLib),
           u"First argument to ffi-voidp should be an external library")
    name = rt.name(nm)
    return VoidP(lib.get_fn_ptr(name))
Пример #29
0
Файл: ffi.py Проект: kidaa/pixie
def prep_ffi_call__args(args):
    fn = args[0]
    affirm(isinstance(fn, CFunctionType), u"First arg must be a FFI function")
Пример #30
0
def pack(ptr, offset):
    affirm(
        isinstance(ptr, VoidP) or isinstance(ptr, Buffer)
        or isinstance(ptr, CStruct), u"Type is not unpackable")
    ptr = rffi.ptradd(ptr.raw_data(), offset.int_val())
    return VoidP(ptr)