Buffers

Usage

use Buffers;

or

import Buffers;

Support for buffers - regions of memory without a particular interpretation.

This module provides byteBuffer and buffer types which can be used to manage memory regions.

These types should be safe to use in a multi-locale context. These types should free their memory after the last user of that memory goes out of scope. They are currently reference counted but that may not always be the case.

Bytes Type

A byteBuffer is a contiguous memory region - really a data structure containing a pointer, length, and also the information necessary to free the memory region when it is no longer used.

Buffers

A buffer consists of a sequence of views into byteBuffer objects. A byteBuffer object might be shared by several buffer objects. It is efficient to go to a particular offset in a buffer, and to push or pop bytes objects from the beginning or end of a buffer.

record byteBuffer

This type represents a contiguous sequence of bytes. This sequence of bytes is represented with a C pointer and length and is currently reference counted. Note that this record contains private fields in addition to the home field.

var home: locale

The home locale storing the data

proc byteBuffer.init()

Initialize an empty bytes object

proc byteBuffer.init(len: int(64), out error: errorCode)

Initialize a bytes object by allocating zero-filled memory.

Arguments:
  • len – the number of bytes to allocate

  • error – (optional) capture an error that was encountered instead of halting on error

proc byteBuffer.ptr(): c_ptr(void)

Note

The pointer returned by this method is only valid for the lifetime of the byteBuffer object and will be invalid if this memory is freed.

Returns:

a c_ptr(void) to the internal byte array

proc byteBuffer.len: int(64)
Returns:

the number of bytes stored in a byteBuffer object

record buffer_iterator

This type represents a particular location with a buffer. Use buffer methods like buffer.start and buffer.advance to create and manipulate buffer_iterator s. Note that this record contains private fields in addition to the home field.

var home: locale

The home locale storing the data

record buffer_range

A region within a buffer (indicated by two buffer_iterator s )

var start: buffer_iterator
var end: buffer_iterator
proc buffer_range.len: int(64)
Returns:

the number of bytes stored in a buffer_range

record buffer

A buffer which can contain multiple memory regions (that is, multiple regions of byteBuffer objects). Note that this record contains private fields in addition to the home field.

var home: locale

The home locale storing the data

proc buffer.init(out error: errorCode)

Create an empty buffer.

Arguments:

error – (optional) capture an error that was encountered instead of halting on error

proc buffer.flatten(bufRange: buffer_range) throws

Flatten a buffer. Create a new byteBuffer object and copy the buffer into it. This function should work even if buffer is remote.

Arguments:

bufRange – the region of the buffer to copy, for example buffer.all()

Returns:

a newly initialized bytes object on the current locale

proc buffer.len
Returns:

the number of bytes stored in a buffer object

proc buffer.append(b: byteBuffer, skip_bytes: int(64) = 0, len_bytes: int(64) = b.len) throws

Append a byteBuffer object to a buffer. This function might store the passed bytes object by reference instead of copying it. The current implementation will always do so and will always increase the reference count of the bytes object. The version of this function called without the error argument will halt if an error is encountered.

Arguments:
  • b – the byteBuffer object to append

  • skip_bytes – how many bytes at the front of b to skip

  • len_bytes – how many bytes to append to the buffer

proc buffer.append(buf: buffer, part: buffer_range = buf.all()) throws

Append a buffer object to a buffer. This function might store a pointers to the bytes objects contained in buf instead of copying them. If that happens, the current implementation will increase their reference counts. The version of this function called without the error argument will halt if an error is encountered.

Arguments:
  • buf – the buffer object to append

  • part – a buffer_range indicating which section of the buffer to copy. Defaults to all of the buffer.

proc buffer.prepend(b: byteBuffer, skip_bytes: int(64) = 0, len_bytes: int(64) = b.len) throws

Prepend a byteBuffer object to a buffer. This function might store the passed bytes object by reference instead of copying it. The current implementation will always do so and will always increase the reference count of the bytes object. The version of this function called without the error argument will halt if an error is encountered.

Arguments:
  • b – the byteBuffer object to prepend

  • skip_bytes – how many bytes at the front of b to skip

  • len_bytes – how many bytes to append to the buffer

proc buffer.start(): buffer_iterator
Returns:

a buffer_iterator to the start of a buffer

proc buffer.end(): buffer_iterator
Returns:

a buffer_iterator to the end of a buffer

proc buffer.all(): buffer_range
Returns:

a buffer_range for the entirety of a buffer

proc buffer.next_part(ref it: buffer_iterator)

Advance a buffer_iterator to the next contiguous memory region stored therein

Arguments:

it – the buffer iterator to advance

proc buffer.prev_part(ref it: buffer_iterator)

Advance a buffer_iterator to the previous contiguous memory region stored therein

Arguments:

it – the buffer iterator to advance

proc buffer.advance(ref it: buffer_iterator, amount: int(64))

Advance a buffer_iterator by a particular number of bytes.

Arguments:
  • it – the buffer iterator to advance

  • amount – the number of bytes to advance

proc buffer.copyout(it: buffer_iterator, ref value: ?T): buffer_iterator throws  where isNumericType(T)

Read a basic type (integral or floating point value) or string from a buffer. For basic types, this method reads the value by copying from memory - so it reads a binary value in native endianness. For strings, this method reads a string encoded as the string length (as int) followed by that number of bytes (as uint(8)).

Arguments:
  • it – a buffer_iterator where reading will start

  • value – a basic type or string

Returns:

a buffer iterator storing the position immediately after the read value.

proc buffer.copyin(it: buffer_iterator, value: ?T): buffer_iterator throws  where isNumericType(T)

Write a basic type (integral or floating point value) or string to a buffer. For basic types, this method writes the value by copying to memory - so it writes a binary value in native endianness. For strings, this method writes a string encoded as the string length (as int) followed by that number of bytes (as uint(8)).

Arguments:
  • it – a buffer_iterator where reading will start

  • value – a basic type or string

Returns:

a buffer iterator storing the position immediately after the written value.