RFC: static bulk copy methods

Radosław Smogura mail at smogura.eu
Thu Jun 10 19:05:07 UTC 2021


Hi all,

Let me add my two cents, I wonder if some transformations with bulk copy can’t be achieved by vector operations on memory segments?

What do you think?

Kind regards,
Rado

> On Jun 10, 2021, at 4:30 PM, Maurizio Cimadamore <maurizio.cimadamore at oracle.com> wrote:
> 
> Hi
> I've create a draft PR which adds the new MemorySegment method to do the bulk copy (with swap if needed), plus the code that Lee posted in this thread [1]:
> 
> https://github.com/openjdk/panama-foreign/pull/555
> 
> There are a couple of points which deserve a discussion.
> 
> First, array indices are always expressed as logical indices (e.g. to access the second long in a long[], we use "1", not "16"). This creates some tension when adding the static methods for doing the bulk copy between arrays and segments, as the more natural index to be used with a segment is not a logical index, but just a raw byte offset. In this PR the static methods in MemoryCopy simply accept logical indices for arrays and raw offsets for segments, w/o any further attempt to reconcile the mismatch. In a separate thread [2] we have discussed few options to ameliorate the situation, should this become an issue in real code.
> 
> Second, to do a "swappy" bulk copy we need to know the size of the elements we're copying. That's because the byte swap will be applied on a per-element basis (of course). There are several options to provide such an API in MemorySegment, listed below:
> 
> ```
> MemorySegment.copyFrom(MemorySegment src, int elemSize, boolean swap) // 1
> MemorySegment.copyFrom(MemorySegment src, ValueLayout elemLayout, ByteOrder order) // 2
> MemorySegment.copyFrom(MemorySegment src, ValueLayout srcElementLayout, ValueLayout dstElementLayout) // 3
> ```
> 
> The first is merely a wrapper around unsafe. It's a good fallback, but seems very low level, even for our API; specifically, it seems we could do something to avoid that "swap" parameter.
> 
> The second option takes a step towards layouts - e.g. if we model elements with a layout, then we can compare the endianness of the layout with the provided order. What I find confusing about this API is that it's not clear to which segment (source or target) does the layout or order arguments apply to.
> 
> The third option fully embrace layouts and is what is implemented in the PR. We now have a layout for the source elements, and a layout for the destination elements. If their order is different a byte swap occurs. The simpler one-argument copyFrom can be expressed as:
> 
> ```
> copyFrom(src) == copyFrom(src, JAVA_BYTE, JAVA_BYTE)
> ```
> 
> To perform a swappy copy between short elements, a client would probably do:
> 
> ```
> copyFrom(src, BITS_16_LE, BITS_16_BE)
> ```
> 
> The method will also check alignment constraints in the source and target segments, so if clients want to use this enhanced copyFrom to copy elements at unaligned addresses, the alignment constraints should be removed from the target layout:
> 
> ```
> copyFrom(src, BITS_16_LE, BITS_16_BE.withBitAlignment(8))
> ```
> 
> This check adds extra safety belts, and does not affect expressiveness, since we can always create "unaligned" layouts to bulk copy at arbitrary addresses --- and I imagine that the routines in MemoryCopy will want to do something along these lines.
> 
> Comments welcome.
> 
> Maurizio
> 
> [1] - https://mail.openjdk.java.net/pipermail/panama-dev/2021-April/013518.html
> [2] - https://mail.openjdk.java.net/pipermail/panama-dev/2021-June/014047.html


More information about the panama-dev mailing list