[Integrated] [foreign-memaccess] RFR: Move MemoryAddress::copy

John Rose john.r.rose at oracle.com
Sat May 16 01:19:45 UTC 2020

Nice work; thank you.

When working with an address a, you often want to copy
memory to or from that address, and (independently)
before or after that address.  In C the corresponding
pointer operations would be of form like this:

   *p = *q;  // copy element at (= just after) pointer
   p[0] = q[0];  // ditto
   p[i] = q[j];  // copy indexed elements near p and q
   *p++ = *q++;  // same, with auto-increment
   *--p = *--q;  // copy element just before pointer + auto-incr.

I guess the Panama code for such operations would contain
expressions like this:

   p.segment().asSlice(a.segmentOffset(), (some size)).copyFrom(q…)

What are the natural idioms that might benefit the user,
who wants to get smoothly from a MA p to a copyFrom operation?

It seems to me that one possible primitive would be sized slice

    MemoryAddress sliceAfter(long size) {
        return segment().asSlice(segmentOffset(), size);

That is good for source operands, since the “size” value needs to
be attached to the MA in order to get the right slice, and copyFrom
takes the size from the source, not the destination.

For sources of the form *--q, maybe this also:

    MemoryAddress sliceBefore(long size) {
        return segment().asSlice(segmentOffset() - size, size);

Or maybe this combo:

    MemoryAddress sliceAt(int index, long size) {
        return segment().asSlice(segmentOffset() + (size * index), size);

Then sliceAt(0,s) == sliceAfter(s) and sliceAt(-1,s) == sliceBefore(s).
That suggests that the latter forms (sliceAfter(s)) are redundant,
and that sliceAt is the interesting primitive.

Another use case is an *unsized* slice creator for destination operands.
This allows the sizing information to flow naturally (without redundancy)
from the data source through copyFrom:

    MemoryAddress sliceAfter() {
        return segment().asSlice(segmentOffset(), segment().byteSize() - segmentOffset());

Maybe for symmetry, and for cutting off buffers after a fill pointer, this too:

    MemoryAddress sliceBefore() {
        return segment().asSlice(0, segmentOffset());

Anyway, I like the way MS is shaping up, as a small bounded location of
state, and MA as a working pointer therein.  You all have probably had
similar thoughts about “what sort of sugary methods we might eventually
place on MA”.  The placement of MS::copyOf unlocked some of those ideas
for me, and the above is what I came up with, FWIW.

— John

More information about the panama-dev mailing list