Example #1
0
    def make_a_nonmoving_copy(self, obj, objsize):
        # NB. the object can have a finalizer or be a weakref, but
        # it's not an issue.
        totalsize = self.size_gc_header() + objsize
        tid = self.header(obj).tid
        if tid & GCFLAG_HASHMASK:
            totalsize_incl_hash = totalsize + llmemory.sizeof(lltype.Signed)
        else:
            totalsize_incl_hash = totalsize
        newaddr = self.allocate_external_object(totalsize_incl_hash)
        if not newaddr:
            return llmemory.NULL   # can't raise MemoryError during a collect()
        self._nonmoving_copy_count += 1
        self._nonmoving_copy_size += raw_malloc_usage(totalsize)

        llmemory.raw_memcopy(obj - self.size_gc_header(), newaddr, totalsize)
        if tid & GCFLAG_HASHMASK:
            hash = self._get_object_hash(obj, objsize, tid)
            (newaddr + totalsize).signed[0] = hash
            tid |= GC_HASH_HASFIELD
        #
        # GCFLAG_UNVISITED is not set
        # GCFLAG_NO_HEAP_PTRS is not set either, conservatively.  It may be
        # set by the next collection's collect_last_generation_roots().
        # This old object is immediately put at generation 3.
        newobj = newaddr + self.size_gc_header()
        hdr = self.header(newobj)
        hdr.tid = tid | self.GCFLAGS_FOR_NEW_EXTERNAL_OBJECTS
        ll_assert(self.is_last_generation(newobj),
                  "make_a_nonmoving_copy: object too young")
        self.gen3_rawmalloced_objects.append(newobj)
        self.last_generation_root_objects.append(newobj)
        self.rawmalloced_objects_to_trace.append(newobj)   # visit me
        return newobj
Example #2
0
File: rstr.py Project: soIu/rpython
 def copy_string_contents(src, dst, srcstart, dststart, length):
     """Copies 'length' characters from the 'src' string to the 'dst'
     string, starting at position 'srcstart' and 'dststart'."""
     # xxx Warning: don't try to do this at home.  It relies on a lot
     # of details to be sure that it works correctly in all cases.
     # Notably: no GC operation at all from the first cast_ptr_to_adr()
     # because it might move the strings.  The keepalive_until_here()
     # are obscurely essential to make sure that the strings stay alive
     # longer than the raw_memcopy().
     assert length >= 0
     ll_assert(srcstart >= 0, "copystrc: negative srcstart")
     ll_assert(srcstart + length <= len(src.chars), "copystrc: src ovf")
     ll_assert(dststart >= 0, "copystrc: negative dststart")
     ll_assert(dststart + length <= len(dst.chars), "copystrc: dst ovf")
     #
     # If the 'split_gc_address_space' option is set, we must copy
     # manually, character-by-character
     if rgc.must_split_gc_address_space():
         i = 0
         while i < length:
             dst.chars[dststart + i] = src.chars[srcstart + i]
             i += 1
         return
     #
     #
     # from here, no GC operations can happen
     asrc = _get_raw_buf(SRC_TP, src, srcstart)
     adst = _get_raw_buf(DST_TP, dst, dststart)
     llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(CHAR_TP) * length)
     # end of "no GC" section
     keepalive_until_here(src)
     keepalive_until_here(dst)
Example #3
0
File: rstr.py Project: soIu/rpython
 def ll_string2list(RESLIST, src):
     length = len(src.chars)
     lst = RESLIST.ll_newlist(length)
     dst = lst.ll_items()
     SRC = typeOf(src).TO  # STR or UNICODE
     DST = typeOf(dst).TO  # GcArray
     assert DST.OF is SRC.chars.OF
     #
     # If the 'split_gc_address_space' option is set, we must copy
     # manually, character-by-character
     if rgc.must_split_gc_address_space():
         i = 0
         while i < length:
             dst[i] = src.chars[i]
             i += 1
         return lst
     #
     # from here, no GC operations can happen
     asrc = llmemory.cast_ptr_to_adr(src) + (llmemory.offsetof(
         SRC, 'chars') + llmemory.itemoffsetof(SRC.chars, 0))
     adst = llmemory.cast_ptr_to_adr(dst) + llmemory.itemoffsetof(DST, 0)
     llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(DST.OF) * length)
     # end of "no GC" section
     keepalive_until_here(src)
     keepalive_until_here(dst)
     return lst
Example #4
0
File: rstr.py Project: soIu/rpython
 def copy_string_to_raw(src, ptrdst, srcstart, length):
     """
     Copies 'length' characters from the 'src' string to the 'ptrdst'
     buffer, starting at position 'srcstart'.
     'ptrdst' must be a non-gc Array of Char.
     """
     # xxx Warning: same note as above apply: don't do this at home
     assert length >= 0
     #
     # If the 'split_gc_address_space' option is set, we must copy
     # manually, character-by-character
     if rgc.must_split_gc_address_space():
         i = 0
         while i < length:
             ptrdst[i] = src.chars[srcstart + i]
             i += 1
         return
     #
     # from here, no GC operations can happen
     asrc = _get_raw_buf(SRC_TP, src, srcstart)
     adst = llmemory.cast_ptr_to_adr(ptrdst)
     adst = adst + llmemory.itemoffsetof(typeOf(ptrdst).TO, 0)
     llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(CHAR_TP) * length)
     # end of "no GC" section
     keepalive_until_here(src)
Example #5
0
 def ll_prepare_free_slot(_unused):
     """Free up a slot in the array of MAX entries, ready for storing
     a new shadowstackref.  Return the memory of the now-unused full
     shadowstack.
     """
     index = fullstack_cache[0]
     if index > 0:
         return llmemory.NULL     # there is already at least one free slot
     #
     # make a compact copy in one old entry and return the
     # original full-sized memory
     index = -index
     ll_assert(index > 0, "prepare_free_slot: cache[0] == 0")
     compacting = lltype.cast_int_to_ptr(SHADOWSTACKREFPTR,
                                         fullstack_cache[index])
     index += 1
     if index >= ShadowStackPool.MAX:
         index = 1
     fullstack_cache[0] = -index    # update to the next value in order
     #
     compacting.detach()
     original = compacting.base
     size = compacting.top - original
     new = llmemory.raw_malloc(size)
     if new == llmemory.NULL:
         return llmemory.NULL
     llmemory.raw_memcopy(original, new, size)
     compacting.base = new
     compacting.top = new + size
     return original
Example #6
0
def ll_shrink_array(p, smallerlength):
    from rpython.rtyper.lltypesystem.lloperation import llop
    from rpython.rlib.objectmodel import keepalive_until_here

    if llop.shrink_array(lltype.Bool, p, smallerlength):
        return p  # done by the GC
    # XXX we assume for now that the type of p is GcStruct containing a
    # variable array, with no further pointers anywhere, and exactly one
    # field in the fixed part -- like STR and UNICODE.

    TP = lltype.typeOf(p).TO
    newp = lltype.malloc(TP, smallerlength)

    assert len(TP._names) == 2
    field = getattr(p, TP._names[0])
    setattr(newp, TP._names[0], field)

    ARRAY = getattr(TP, TP._arrayfld)
    offset = (llmemory.offsetof(TP, TP._arrayfld) +
              llmemory.itemoffsetof(ARRAY, 0))
    source_addr = llmemory.cast_ptr_to_adr(p) + offset
    dest_addr = llmemory.cast_ptr_to_adr(newp) + offset
    llmemory.raw_memcopy(source_addr, dest_addr,
                         llmemory.sizeof(ARRAY.OF) * smallerlength)

    keepalive_until_here(p)
    keepalive_until_here(newp)
    return newp
Example #7
0
    def make_a_nonmoving_copy(self, obj, objsize):
        # NB. the object can have a finalizer or be a weakref, but
        # it's not an issue.
        totalsize = self.size_gc_header() + objsize
        tid = self.header(obj).tid
        if tid & GCFLAG_HASHMASK:
            totalsize_incl_hash = totalsize + llmemory.sizeof(lltype.Signed)
        else:
            totalsize_incl_hash = totalsize
        newaddr = self.allocate_external_object(totalsize_incl_hash)
        if not newaddr:
            return llmemory.NULL  # can't raise MemoryError during a collect()
        self._nonmoving_copy_count += 1
        self._nonmoving_copy_size += raw_malloc_usage(totalsize)

        llmemory.raw_memcopy(obj - self.size_gc_header(), newaddr, totalsize)
        if tid & GCFLAG_HASHMASK:
            hash = self._get_object_hash(obj, objsize, tid)
            (newaddr + totalsize).signed[0] = hash
            tid |= GC_HASH_HASFIELD
        #
        # GCFLAG_UNVISITED is not set
        # GCFLAG_NO_HEAP_PTRS is not set either, conservatively.  It may be
        # set by the next collection's collect_last_generation_roots().
        # This old object is immediately put at generation 3.
        newobj = newaddr + self.size_gc_header()
        hdr = self.header(newobj)
        hdr.tid = tid | self.GCFLAGS_FOR_NEW_EXTERNAL_OBJECTS
        ll_assert(self.is_last_generation(newobj),
                  "make_a_nonmoving_copy: object too young")
        self.gen3_rawmalloced_objects.append(newobj)
        self.last_generation_root_objects.append(newobj)
        self.rawmalloced_objects_to_trace.append(newobj)  # visit me
        return newobj
Example #8
0
def ll_shrink_array(p, smallerlength):
    from rpython.rtyper.lltypesystem.lloperation import llop
    from rpython.rlib.objectmodel import keepalive_until_here

    if llop.shrink_array(lltype.Bool, p, smallerlength):
        return p  # done by the GC
    # XXX we assume for now that the type of p is GcStruct containing a
    # variable array, with no further pointers anywhere, and exactly one
    # field in the fixed part -- like STR and UNICODE.

    TP = lltype.typeOf(p).TO
    newp = lltype.malloc(TP, smallerlength)

    assert len(TP._names) == 2
    field = getattr(p, TP._names[0])
    setattr(newp, TP._names[0], field)

    ARRAY = getattr(TP, TP._arrayfld)
    offset = llmemory.offsetof(TP, TP._arrayfld) + llmemory.itemoffsetof(ARRAY, 0)
    source_addr = llmemory.cast_ptr_to_adr(p) + offset
    dest_addr = llmemory.cast_ptr_to_adr(newp) + offset
    llmemory.raw_memcopy(source_addr, dest_addr, llmemory.sizeof(ARRAY.OF) * smallerlength)

    keepalive_until_here(p)
    keepalive_until_here(newp)
    return newp
Example #9
0
File: misc.py Project: kipras/pypy
def _raw_memcopy_opaque(source, dest, size):
    # push push push at the llmemory interface (with hacks that are all
    # removed after translation)
    zero = llmemory.itemoffsetof(rffi.CCHARP.TO, 0)
    llmemory.raw_memcopy(
        llmemory.cast_ptr_to_adr(source) + zero,
        llmemory.cast_ptr_to_adr(dest) + zero,
        size * llmemory.sizeof(lltype.Char))
Example #10
0
def ll_populate_list_from_raw_array(ll_list, src_ptr, length):
    ITEM = lltype.typeOf(src_ptr).TO.OF
    size = llmemory.sizeof(ITEM) * length
    ll_list._ll_resize(length)
    # start of no-GC section
    src_adr = get_raw_buf(src_ptr)
    dst_adr = get_raw_buf(ll_list.ll_items())
    llmemory.raw_memcopy(src_adr, dst_adr, size)
Example #11
0
def _raw_memcopy_opaque(source, dest, size):
    # push push push at the llmemory interface (with hacks that are all
    # removed after translation)
    zero = llmemory.itemoffsetof(rffi.CCHARP.TO, 0)
    llmemory.raw_memcopy(
        llmemory.cast_ptr_to_adr(source) + zero,
        llmemory.cast_ptr_to_adr(dest) + zero,
        size * llmemory.sizeof(lltype.Char))
Example #12
0
def ll_populate_list_from_raw_array(ll_list, src_ptr, length):
    ITEM = lltype.typeOf(src_ptr).TO.OF
    size = llmemory.sizeof(ITEM) * length
    ll_list._ll_resize(length)
    # start of no-GC section
    src_adr = get_raw_buf(src_ptr)
    dst_adr = get_raw_buf(ll_list.ll_items())
    llmemory.raw_memcopy(src_adr, dst_adr, size)
def sscopy_attach_shadow_stack(sscopy):
    base = llop.gc_adr_of_root_stack_base(llmemory.Address).address[0]
    ll_assert(llop.gc_adr_of_root_stack_top(llmemory.Address).address[0]==base,
              "attach_shadow_stack: ss is not empty?")
    length_bytes = sscopy.signed[0]
    llmemory.raw_memcopy(sscopy + SIZEADDR, base, length_bytes)
    llop.gc_adr_of_root_stack_top(llmemory.Address).address[0] = (
        base + length_bytes)
    llmemory.raw_free(sscopy)
Example #14
0
def ll_copy_list_to_raw_array(ll_list, dst_ptr):
    # this code is delicate: we must ensure that there are no GC operations
    # around the call to raw_memcopy
    #
    ITEM = lltype.typeOf(dst_ptr).TO.OF
    size = llmemory.sizeof(ITEM) * ll_list.ll_length()
    # start of no-GC section
    src_adr = get_raw_buf(ll_list.ll_items())
    dst_adr = get_raw_buf(dst_ptr)
    llmemory.raw_memcopy(src_adr, dst_adr, size)
Example #15
0
def sscopy_attach_shadow_stack(sscopy):
    base = llop.gc_adr_of_root_stack_base(llmemory.Address).address[0]
    ll_assert(
        llop.gc_adr_of_root_stack_top(llmemory.Address).address[0] == base,
        "attach_shadow_stack: ss is not empty?")
    length_bytes = sscopy.signed[0]
    llmemory.raw_memcopy(sscopy + SIZEADDR, base, length_bytes)
    llop.gc_adr_of_root_stack_top(llmemory.Address).address[0] = (base +
                                                                  length_bytes)
    llmemory.raw_free(sscopy)
def sscopy_detach_shadow_stack():
    base = llop.gc_adr_of_root_stack_base(llmemory.Address).address[0]
    top = llop.gc_adr_of_root_stack_top(llmemory.Address).address[0]
    length_bytes = top - base
    result = llmemory.raw_malloc(SIZEADDR + length_bytes)
    if result:
        result.signed[0] = length_bytes
        llmemory.raw_memcopy(base, result + SIZEADDR, length_bytes)
        llop.gc_adr_of_root_stack_top(llmemory.Address).address[0] = base
    return result
Example #17
0
def ll_copy_list_to_raw_array(ll_list, dst_ptr):
    # this code is delicate: we must ensure that there are no GC operations
    # around the call to raw_memcopy
    #
    ITEM = lltype.typeOf(dst_ptr).TO.OF
    size = llmemory.sizeof(ITEM) * ll_list.ll_length()
    # start of no-GC section
    src_adr = get_raw_buf(ll_list.ll_items())
    dst_adr = get_raw_buf(dst_ptr)
    llmemory.raw_memcopy(src_adr, dst_adr, size)
Example #18
0
def sscopy_detach_shadow_stack():
    base = llop.gc_adr_of_root_stack_base(llmemory.Address).address[0]
    top = llop.gc_adr_of_root_stack_top(llmemory.Address).address[0]
    length_bytes = top - base
    result = llmemory.raw_malloc(SIZEADDR + length_bytes)
    if result:
        result.signed[0] = length_bytes
        llmemory.raw_memcopy(base, result + SIZEADDR, length_bytes)
        llop.gc_adr_of_root_stack_top(llmemory.Address).address[0] = base
    return result
Example #19
0
def longername(a, b, size):
    if 1:
        baseofs = itemoffsetof(TP, 0)
        onesize = sizeof(TP.OF)
        size = baseofs + onesize * (size - 1)
        raw_memcopy(cast_ptr_to_adr(b) + baseofs, cast_ptr_to_adr(a) + baseofs, size)
    else:
        a = []
        for i in range(x):
            a.append(i)
    return 0
Example #20
0
    def copy_raw_to_string(ptrsrc, dst, dststart, length):
        # xxx Warning: same note as above apply: don't do this at home
        assert length >= 0
        # from here, no GC operations can happen
        adst = _get_raw_buf(SRC_TP, dst, dststart)
        asrc = llmemory.cast_ptr_to_adr(ptrsrc)

        asrc = asrc + llmemory.itemoffsetof(typeOf(ptrsrc).TO, 0)
        llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(CHAR_TP) * length)
        # end of "no GC" section
        keepalive_until_here(dst)
Example #21
0
    def copy_raw_to_string(ptrsrc, dst, dststart, length):
        # xxx Warning: same note as above apply: don't do this at home
        assert length >= 0
        # from here, no GC operations can happen
        adst = _get_raw_buf(SRC_TP, dst, dststart)
        asrc = llmemory.cast_ptr_to_adr(ptrsrc)

        asrc = asrc + llmemory.itemoffsetof(typeOf(ptrsrc).TO, 0)
        llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(CHAR_TP) * length)
        # end of "no GC" section
        keepalive_until_here(dst)
Example #22
0
def ll_populate_list_from_raw_array(ll_list, src_ptr, length):
    ll_list._ll_resize(length)
    if rgc.must_split_gc_address_space():
        for i in range(length):
            ll_list.ll_setitem_fast(i, src_ptr[i])
        return
    ITEM = lltype.typeOf(src_ptr).TO.OF
    size = llmemory.sizeof(ITEM) * length
    # start of no-GC section
    src_adr = get_raw_buf(src_ptr)
    dst_adr = get_raw_buf(ll_list.ll_items())
    llmemory.raw_memcopy(src_adr, dst_adr, size)
Example #23
0
def longername(a, b, size):
    if 1:
        baseofs = itemoffsetof(TP, 0)
        onesize = sizeof(TP.OF)
        size = baseofs + onesize * (size - 1)
        raw_memcopy(
            cast_ptr_to_adr(b) + baseofs,
            cast_ptr_to_adr(a) + baseofs, size)
    else:
        a = []
        for i in range(x):
            a.append(i)
    return 0
Example #24
0
def ll_copy_list_to_raw_array(ll_list, dst_ptr):
    if rgc.must_split_gc_address_space():
        for i in range(ll_list.ll_length()):
            dst_ptr[i] = ll_list.ll_getitem_fast(i)
        return
    # this code is delicate: we must ensure that there are no GC operations
    # around the call to raw_memcopy
    #
    ITEM = lltype.typeOf(dst_ptr).TO.OF
    size = llmemory.sizeof(ITEM) * ll_list.ll_length()
    # start of no-GC section
    src_adr = get_raw_buf(ll_list.ll_items())
    dst_adr = get_raw_buf(dst_ptr)
    llmemory.raw_memcopy(src_adr, dst_adr, size)
Example #25
0
 def ll_rebuild(shadowstackref, fullstack_base):
     if shadowstackref.fsindex > 0:
         shadowstackref.detach()
         return fullstack_base
     else:
         # make an expanded copy of the compact shadowstack stored in
         # 'shadowstackref' and free that
         compact = shadowstackref.base
         size = shadowstackref.top - compact
         shadowstackref.base = fullstack_base
         shadowstackref.top = fullstack_base + size
         llmemory.raw_memcopy(compact, fullstack_base, size)
         llmemory.raw_free(compact)
         return llmemory.NULL
Example #26
0
File: rgc.py Project: sota/pypy
def ll_arraycopy(source, dest, source_start, dest_start, length):
    from rpython.rtyper.lltypesystem.lloperation import llop
    from rpython.rlib.objectmodel import keepalive_until_here

    # XXX: Hack to ensure that we get a proper effectinfo.write_descrs_arrays
    # and also, maybe, speed up very small cases
    if length <= 1:
        if length == 1:
            copy_item(source, dest, source_start, dest_start)
        return

    # supports non-overlapping copies only
    if not we_are_translated():
        if source == dest:
            assert (source_start + length <= dest_start or
                    dest_start + length <= source_start)

    TP = lltype.typeOf(source).TO
    assert TP == lltype.typeOf(dest).TO

    slowpath = False
    if must_split_gc_address_space():
        slowpath = True
    elif _contains_gcptr(TP.OF):
        # perform a write barrier that copies necessary flags from
        # source to dest
        if not llop.gc_writebarrier_before_copy(lltype.Bool, source, dest,
                                                source_start, dest_start,
                                                length):
            slowpath = True
    if slowpath:
        # if the write barrier is not supported, or if we translate with
        # the option 'split_gc_address_space', then copy by hand
        i = 0
        while i < length:
            copy_item(source, dest, i + source_start, i + dest_start)
            i += 1
        return
    source_addr = llmemory.cast_ptr_to_adr(source)
    dest_addr   = llmemory.cast_ptr_to_adr(dest)
    cp_source_addr = (source_addr + llmemory.itemoffsetof(TP, 0) +
                      llmemory.sizeof(TP.OF) * source_start)
    cp_dest_addr = (dest_addr + llmemory.itemoffsetof(TP, 0) +
                    llmemory.sizeof(TP.OF) * dest_start)

    llmemory.raw_memcopy(cp_source_addr, cp_dest_addr,
                         llmemory.sizeof(TP.OF) * length)
    keepalive_until_here(source)
    keepalive_until_here(dest)
Example #27
0
 def copy_string_to_raw(src, ptrdst, srcstart, length):
     """
     Copies 'length' characters from the 'src' string to the 'ptrdst'
     buffer, starting at position 'srcstart'.
     'ptrdst' must be a non-gc Array of Char.
     """
     # xxx Warning: same note as above apply: don't do this at home
     assert length >= 0
     # from here, no GC operations can happen
     asrc = _get_raw_buf(SRC_TP, src, srcstart)
     adst = llmemory.cast_ptr_to_adr(ptrdst)
     adst = adst + llmemory.itemoffsetof(typeOf(ptrdst).TO, 0)
     llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(CHAR_TP) * length)
     # end of "no GC" section
     keepalive_until_here(src)
Example #28
0
 def copy_string_to_raw(src, ptrdst, srcstart, length):
     """
     Copies 'length' characters from the 'src' string to the 'ptrdst'
     buffer, starting at position 'srcstart'.
     'ptrdst' must be a non-gc Array of Char.
     """
     # xxx Warning: same note as above apply: don't do this at home
     assert length >= 0
     # from here, no GC operations can happen
     asrc = _get_raw_buf(SRC_TP, src, srcstart)
     adst = llmemory.cast_ptr_to_adr(ptrdst)
     adst = adst + llmemory.itemoffsetof(typeOf(ptrdst).TO, 0)
     llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(CHAR_TP) * length)
     # end of "no GC" section
     keepalive_until_here(src)
Example #29
0
 def ll_string2list(RESLIST, src):
     length = len(src.chars)
     lst = RESLIST.ll_newlist(length)
     dst = lst.ll_items()
     SRC = typeOf(src).TO  # STR or UNICODE
     DST = typeOf(dst).TO  # GcArray
     assert DST.OF is SRC.chars.OF
     # from here, no GC operations can happen
     asrc = llmemory.cast_ptr_to_adr(src) + (llmemory.offsetof(
         SRC, 'chars') + llmemory.itemoffsetof(SRC.chars, 0))
     adst = llmemory.cast_ptr_to_adr(dst) + llmemory.itemoffsetof(DST, 0)
     llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(DST.OF) * length)
     # end of "no GC" section
     keepalive_until_here(src)
     keepalive_until_here(dst)
     return lst
Example #30
0
 def _make_a_copy_with_tid(self, obj, objsize, tid):
     totalsize = self.size_gc_header() + objsize
     newaddr = self.free
     llarena.arena_reserve(newaddr, totalsize)
     raw_memcopy(obj - self.size_gc_header(), newaddr, totalsize)
     if tid & GCFLAG_HASHMASK:
         hash = self._get_object_hash(obj, objsize, tid)
         llarena.arena_reserve(newaddr + totalsize,
                               llmemory.sizeof(lltype.Signed))
         (newaddr + totalsize).signed[0] = hash
         tid |= GC_HASH_HASFIELD
         totalsize += llmemory.sizeof(lltype.Signed)
     self.free += totalsize
     newhdr = llmemory.cast_adr_to_ptr(newaddr, lltype.Ptr(self.HDR))
     newhdr.tid = tid
     newobj = newaddr + self.size_gc_header()
     return newobj
Example #31
0
 def copy_string_contents(src, dst, srcstart, dststart, length):
     """Copies 'length' characters from the 'src' string to the 'dst'
     string, starting at position 'srcstart' and 'dststart'."""
     # xxx Warning: don't try to do this at home.  It relies on a lot
     # of details to be sure that it works correctly in all cases.
     # Notably: no GC operation at all from the first cast_ptr_to_adr()
     # because it might move the strings.  The keepalive_until_here()
     # are obscurely essential to make sure that the strings stay alive
     # longer than the raw_memcopy().
     assert length >= 0
     # from here, no GC operations can happen
     src = _get_raw_buf(SRC_TP, src, srcstart)
     dst = _get_raw_buf(DST_TP, dst, dststart)
     llmemory.raw_memcopy(src, dst, llmemory.sizeof(CHAR_TP) * length)
     # end of "no GC" section
     keepalive_until_here(src)
     keepalive_until_here(dst)
Example #32
0
 def _make_a_copy_with_tid(self, obj, objsize, tid):
     totalsize = self.size_gc_header() + objsize
     newaddr = self.free
     llarena.arena_reserve(newaddr, totalsize)
     raw_memcopy(obj - self.size_gc_header(), newaddr, totalsize)
     if tid & GCFLAG_HASHMASK:
         hash = self._get_object_hash(obj, objsize, tid)
         llarena.arena_reserve(newaddr + totalsize,
                               llmemory.sizeof(lltype.Signed))
         (newaddr + totalsize).signed[0] = hash
         tid |= GC_HASH_HASFIELD
         totalsize += llmemory.sizeof(lltype.Signed)
     self.free += totalsize
     newhdr = llmemory.cast_adr_to_ptr(newaddr, lltype.Ptr(self.HDR))
     newhdr.tid = tid
     newobj = newaddr + self.size_gc_header()
     return newobj
Example #33
0
 def ll_string2list(RESLIST, src):
     length = len(src.chars)
     lst = RESLIST.ll_newlist(length)
     dst = lst.ll_items()
     SRC = typeOf(src).TO     # STR or UNICODE
     DST = typeOf(dst).TO     # GcArray
     assert DST.OF is SRC.chars.OF
     # from here, no GC operations can happen
     asrc = llmemory.cast_ptr_to_adr(src) + (
         llmemory.offsetof(SRC, 'chars') +
         llmemory.itemoffsetof(SRC.chars, 0))
     adst = llmemory.cast_ptr_to_adr(dst) + llmemory.itemoffsetof(DST, 0)
     llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(DST.OF) * length)
     # end of "no GC" section
     keepalive_until_here(src)
     keepalive_until_here(dst)
     return lst
Example #34
0
File: rgc.py Project: Qointum/pypy
def ll_arraycopy(source, dest, source_start, dest_start, length):
    from rpython.rtyper.lltypesystem.lloperation import llop
    from rpython.rlib.objectmodel import keepalive_until_here

    # XXX: Hack to ensure that we get a proper effectinfo.write_descrs_arrays
    # and also, maybe, speed up very small cases
    if length <= 1:
        if length == 1:
            copy_item(source, dest, source_start, dest_start)
        return

    # supports non-overlapping copies only
    if not we_are_translated():
        if source == dest:
            assert (source_start + length <= dest_start or
                    dest_start + length <= source_start)

    TP = lltype.typeOf(source).TO
    assert TP == lltype.typeOf(dest).TO
    if _contains_gcptr(TP.OF):
        # perform a write barrier that copies necessary flags from
        # source to dest
        if not llop.gc_writebarrier_before_copy(lltype.Bool, source, dest,
                                                source_start, dest_start,
                                                length):
            # if the write barrier is not supported, copy by hand
            i = 0
            while i < length:
                copy_item(source, dest, i + source_start, i + dest_start)
                i += 1
            return
    source_addr = llmemory.cast_ptr_to_adr(source)
    dest_addr   = llmemory.cast_ptr_to_adr(dest)
    cp_source_addr = (source_addr + llmemory.itemoffsetof(TP, 0) +
                      llmemory.sizeof(TP.OF) * source_start)
    cp_dest_addr = (dest_addr + llmemory.itemoffsetof(TP, 0) +
                    llmemory.sizeof(TP.OF) * dest_start)

    llmemory.raw_memcopy(cp_source_addr, cp_dest_addr,
                         llmemory.sizeof(TP.OF) * length)
    keepalive_until_here(source)
    keepalive_until_here(dest)
Example #35
0
File: rstr.py Project: soIu/rpython
    def copy_raw_to_string(ptrsrc, dst, dststart, length):
        # xxx Warning: same note as above apply: don't do this at home
        assert length >= 0
        #
        # If the 'split_gc_address_space' option is set, we must copy
        # manually, character-by-character
        if rgc.must_split_gc_address_space():
            i = 0
            while i < length:
                dst.chars[dststart + i] = ptrsrc[i]
                i += 1
            return
        #
        # from here, no GC operations can happen
        adst = _get_raw_buf(SRC_TP, dst, dststart)
        asrc = llmemory.cast_ptr_to_adr(ptrsrc)

        asrc = asrc + llmemory.itemoffsetof(typeOf(ptrsrc).TO, 0)
        llmemory.raw_memcopy(asrc, adst, llmemory.sizeof(CHAR_TP) * length)
        # end of "no GC" section
        keepalive_until_here(dst)
Example #36
0
File: rffi.py Project: charred/pypy
    def str_from_buffer(raw_buf, gc_buf, allocated_size, needed_size):
        """
        Converts from a pair returned by alloc_buffer to a high-level string.
        The returned string will be truncated to needed_size.
        """
        assert allocated_size >= needed_size

        if gc_buf and (allocated_size == needed_size):
            return hlstrtype(gc_buf)

        new_buf = lltype.malloc(STRTYPE, needed_size)
        str_chars_offset = (offsetof(STRTYPE, 'chars') + \
                            itemoffsetof(STRTYPE.chars, 0))
        if gc_buf:
            src = cast_ptr_to_adr(gc_buf) + str_chars_offset
        else:
            src = cast_ptr_to_adr(raw_buf) + itemoffsetof(TYPEP.TO, 0)
        dest = cast_ptr_to_adr(new_buf) + str_chars_offset
        raw_memcopy(src, dest,
                    llmemory.sizeof(ll_char_type) * needed_size)
        keepalive_until_here(gc_buf)
        keepalive_until_here(new_buf)
        return hlstrtype(new_buf)
Example #37
0
 def op_raw_memcopy(self, fromaddr, toaddr, size):
     checkadr(fromaddr)
     checkadr(toaddr)
     llmemory.raw_memcopy(fromaddr, toaddr, size)
Example #38
0
 def op_raw_memcopy(self, fromaddr, toaddr, size):
     checkadr(fromaddr)
     checkadr(toaddr)
     llmemory.raw_memcopy(fromaddr, toaddr, size)