Next: Message Send, Previous: Exchanging Port Rights, Up: Messaging Interface
A message body can contain the address of a region in the sender's address space which should be transferred as part of the message. The message carries a logical copy of the memory, but the kernel uses VM techniques to defer any actual page copies. Unless the sender or the receiver modifies the data, the physical pages remain shared.
An out-of-line transfer occurs when the data's type descriptor specifies
msgt_inline
as FALSE
. The address of the memory region (a
vm_offset_t
or vm_address_t
) should follow the type
descriptor in the message body. The type descriptor and the address
contribute to the message's size (send_size
, msgh_size
).
The out-of-line data does not contribute to the message's size.
The name, size, and number fields in the type descriptor describe the
type and length of the out-of-line data, not the in-line address.
Out-of-line memory frequently requires long type descriptors
(mach_msg_type_long_t
), because the msgt_number
field is
too small to describe a page of 4K bytes.
Out-of-line memory arrives somewhere in the receiver's address space as
new memory. It has the same inheritance and protection attributes as
newly vm_allocate
'd memory. The receiver has the responsibility
of deallocating (with vm_deallocate
) the memory when it is no
longer needed. Security-conscious receivers should exercise caution
when using out-of-line memory from untrustworthy sources, because the
memory may be backed by an unreliable memory manager.
Null out-of-line memory is legal. If the out-of-line region size is
zero (for example, because msgtl_number
is zero), then the
region's specified address is ignored. A received null out-of-line
memory region always has a zero address.
Unaligned addresses and region sizes that are not page multiples are
legal. A received message can also contain memory with unaligned
addresses and funny sizes. In the general case, the first and last
pages in the new memory region in the receiver do not contain only data
from the sender, but are partly zero.1 The received address points to the
start of the data in the first page. This possibility doesn't
complicate deallocation, because vm_deallocate
does the right
thing, rounding the start address down and the end address up to
deallocate all arrived pages.
Out-of-line memory has a deallocate option, controlled by the
msgt_deallocate
bit. If it is TRUE
and the out-of-line
memory region is not null, then the region is implicitly deallocated
from the sender, as if by vm_deallocate
. In particular, the
start and end addresses are rounded so that every page overlapped by the
memory region is deallocated. The use of msgt_deallocate
effectively changes the memory copy into a memory movement. In a
received message, msgt_deallocate
is TRUE
in type
descriptors for out-of-line memory.
Out-of-line memory can carry port rights.
[1] Sending out-of-line memory with a non-page-aligned address, or a size which is not a page multiple, works but with a caveat. The extra bytes in the first and last page of the received memory are not zeroed, so the receiver can peek at more data than the sender intended to transfer. This might be a security problem for the sender.