#include <isc/string.h>
#include <isc/util.h>
-void
-isc__buffer_init(isc_buffer_t *b, void *base, unsigned int length) {
- /*
- * Make 'b' refer to the 'length'-byte region starting at 'base'.
- * XXXDCL see the comment in buffer.h about base being const.
- */
-
- REQUIRE(b != NULL);
-
- ISC__BUFFER_INIT(b, base, length);
-}
-
-void
-isc__buffer_initnull(isc_buffer_t *b) {
- /*
- * Initialize a new buffer which has no backing store. This can
- * later be grown as needed and swapped in place.
- */
-
- ISC__BUFFER_INIT(b, NULL, 0);
-}
-
void
isc_buffer_reinit(isc_buffer_t *b, void *base, unsigned int length) {
/*
b->length = length;
}
-void
-isc__buffer_invalidate(isc_buffer_t *b) {
- /*
- * Make 'b' an invalid buffer.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(!ISC_LINK_LINKED(b, link));
- REQUIRE(b->mctx == NULL);
-
- ISC__BUFFER_INVALIDATE(b);
-}
-
void
isc_buffer_setautorealloc(isc_buffer_t *b, bool enable) {
REQUIRE(ISC_BUFFER_VALID(b));
b->autore = enable;
}
-void
-isc__buffer_region(isc_buffer_t *b, isc_region_t *r) {
- /*
- * Make 'r' refer to the region of 'b'.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(r != NULL);
-
- ISC__BUFFER_REGION(b, r);
-}
-
-void
-isc__buffer_usedregion(const isc_buffer_t *b, isc_region_t *r) {
- /*
- * Make 'r' refer to the used region of 'b'.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(r != NULL);
-
- ISC__BUFFER_USEDREGION(b, r);
-}
-
-void
-isc__buffer_availableregion(isc_buffer_t *b, isc_region_t *r) {
- /*
- * Make 'r' refer to the available region of 'b'.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(r != NULL);
-
- ISC__BUFFER_AVAILABLEREGION(b, r);
-}
-
-void
-isc__buffer_add(isc_buffer_t *b, unsigned int n) {
- /*
- * Increase the 'used' region of 'b' by 'n' bytes.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(b->used + n <= b->length);
-
- ISC__BUFFER_ADD(b, n);
-}
-
-void
-isc__buffer_subtract(isc_buffer_t *b, unsigned int n) {
- /*
- * Decrease the 'used' region of 'b' by 'n' bytes.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(b->used >= n);
-
- ISC__BUFFER_SUBTRACT(b, n);
-}
-
-void
-isc__buffer_clear(isc_buffer_t *b) {
- /*
- * Make the used region empty.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
-
- ISC__BUFFER_CLEAR(b);
-}
-
-void
-isc__buffer_consumedregion(isc_buffer_t *b, isc_region_t *r) {
- /*
- * Make 'r' refer to the consumed region of 'b'.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(r != NULL);
-
- ISC__BUFFER_CONSUMEDREGION(b, r);
-}
-
-void
-isc__buffer_remainingregion(isc_buffer_t *b, isc_region_t *r) {
- /*
- * Make 'r' refer to the remaining region of 'b'.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(r != NULL);
-
- ISC__BUFFER_REMAININGREGION(b, r);
-}
-
-void
-isc__buffer_activeregion(isc_buffer_t *b, isc_region_t *r) {
- /*
- * Make 'r' refer to the active region of 'b'.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(r != NULL);
-
- ISC__BUFFER_ACTIVEREGION(b, r);
-}
-
-void
-isc__buffer_setactive(isc_buffer_t *b, unsigned int n) {
- /*
- * Sets the end of the active region 'n' bytes after current.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(b->current + n <= b->used);
-
- ISC__BUFFER_SETACTIVE(b, n);
-}
-
-void
-isc__buffer_first(isc_buffer_t *b) {
- /*
- * Make the consumed region empty.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
-
- ISC__BUFFER_FIRST(b);
-}
-
-void
-isc__buffer_forward(isc_buffer_t *b, unsigned int n) {
- /*
- * Increase the 'consumed' region of 'b' by 'n' bytes.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(b->current + n <= b->used);
-
- ISC__BUFFER_FORWARD(b, n);
-}
-
-void
-isc__buffer_back(isc_buffer_t *b, unsigned int n) {
- /*
- * Decrease the 'consumed' region of 'b' by 'n' bytes.
- */
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(n <= b->current);
-
- ISC__BUFFER_BACK(b, n);
-}
-
void
isc_buffer_compact(isc_buffer_t *b) {
unsigned int length;
return (result);
}
-void
-isc__buffer_putuint8(isc_buffer_t *b, uint8_t val) {
- isc_result_t result;
- REQUIRE(ISC_BUFFER_VALID(b));
- if (b->autore) {
- result = isc_buffer_reserve(&b, 1);
- REQUIRE(result == ISC_R_SUCCESS);
- }
- REQUIRE(isc_buffer_availablelength(b) >= 1);
-
- ISC__BUFFER_PUTUINT8(b, val);
-}
-
uint16_t
isc_buffer_getuint16(isc_buffer_t *b) {
unsigned char *cp;
return (result);
}
-void
-isc__buffer_putuint16(isc_buffer_t *b, uint16_t val) {
- isc_result_t result;
- REQUIRE(ISC_BUFFER_VALID(b));
- if (b->autore) {
- result = isc_buffer_reserve(&b, 2);
- REQUIRE(result == ISC_R_SUCCESS);
- }
- REQUIRE(isc_buffer_availablelength(b) >= 2);
-
- ISC__BUFFER_PUTUINT16(b, val);
-}
-
-void
-isc__buffer_putuint24(isc_buffer_t *b, uint32_t val) {
- isc_result_t result;
- REQUIRE(ISC_BUFFER_VALID(b));
- if (b->autore) {
- result = isc_buffer_reserve(&b, 3);
- REQUIRE(result == ISC_R_SUCCESS);
- }
- REQUIRE(isc_buffer_availablelength(b) >= 3);
-
- ISC__BUFFER_PUTUINT24(b, val);
-}
-
uint32_t
isc_buffer_getuint32(isc_buffer_t *b) {
unsigned char *cp;
return (result);
}
-void
-isc__buffer_putuint32(isc_buffer_t *b, uint32_t val) {
- isc_result_t result;
- REQUIRE(ISC_BUFFER_VALID(b));
- if (b->autore) {
- result = isc_buffer_reserve(&b, 4);
- REQUIRE(result == ISC_R_SUCCESS);
- }
- REQUIRE(isc_buffer_availablelength(b) >= 4);
-
- ISC__BUFFER_PUTUINT32(b, val);
-}
-
uint64_t
isc_buffer_getuint48(isc_buffer_t *b) {
unsigned char *cp;
return (result);
}
-void
-isc__buffer_putuint48(isc_buffer_t *b, uint64_t val) {
- isc_result_t result;
- uint16_t valhi;
- uint32_t vallo;
-
- REQUIRE(ISC_BUFFER_VALID(b));
- if (b->autore) {
- result = isc_buffer_reserve(&b, 6);
- REQUIRE(result == ISC_R_SUCCESS);
- }
- REQUIRE(isc_buffer_availablelength(b) >= 6);
-
- valhi = (uint16_t)(val >> 32);
- vallo = (uint32_t)(val & 0xFFFFFFFF);
- ISC__BUFFER_PUTUINT16(b, valhi);
- ISC__BUFFER_PUTUINT32(b, vallo);
-}
-
-void
-isc__buffer_putmem(isc_buffer_t *b, const unsigned char *base,
- unsigned int length) {
- isc_result_t result;
- REQUIRE(ISC_BUFFER_VALID(b));
- if (b->autore) {
- result = isc_buffer_reserve(&b, length);
- REQUIRE(result == ISC_R_SUCCESS);
- }
- REQUIRE(isc_buffer_availablelength(b) >= length);
-
- ISC__BUFFER_PUTMEM(b, base, length);
-}
-
-void
-isc__buffer_putstr(isc_buffer_t *b, const char *source) {
- unsigned int l;
- unsigned char *cp;
- isc_result_t result;
-
- REQUIRE(ISC_BUFFER_VALID(b));
- REQUIRE(source != NULL);
-
- /*
- * Do not use ISC__BUFFER_PUTSTR(), so strlen is only done once.
- */
- l = strlen(source);
- if (b->autore) {
- result = isc_buffer_reserve(&b, l);
- REQUIRE(result == ISC_R_SUCCESS);
- }
- REQUIRE(isc_buffer_availablelength(b) >= l);
-
- cp = isc_buffer_used(b);
- memmove(cp, source, l);
- b->used += l;
-}
-
void
isc_buffer_putdecint(isc_buffer_t *b, int64_t v) {
unsigned int l = 0;
#include <isc/assertions.h>
#include <isc/formatcheck.h>
#include <isc/lang.h>
+#include <isc/list.h>
#include <isc/magic.h>
+#include <isc/region.h>
+#include <isc/string.h>
#include <isc/types.h>
-/*!
- * To make many functions be inline macros (via \#define) define this.
- * If it is undefined, a function will be used.
- */
-/* #define ISC_BUFFER_USEINLINE */
-
ISC_LANG_BEGINDECLS
/*@{*/
* isc_buffer_allocate().
*/
-void
-isc__buffer_init(isc_buffer_t *b, void *base, unsigned int length);
-/*!<
- * \brief Make 'b' refer to the 'length'-byte region starting at base.
- *
- * Requires:
- *
- *\li 'length' > 0
- *
- *\li 'base' is a pointer to a sequence of 'length' bytes.
- *
- */
-
void
isc__buffer_initnull(isc_buffer_t *b);
-/*!<
- *\brief Initialize a buffer 'b' with a null data and zero length/
- */
void
isc_buffer_reinit(isc_buffer_t *b, void *base, unsigned int length);
*
*/
-void
-isc__buffer_invalidate(isc_buffer_t *b);
-/*!<
- * \brief Make 'b' an invalid buffer.
- *
- * Requires:
- *\li 'b' is a valid buffer.
- *
- * Ensures:
- *\li If assertion checking is enabled, future attempts to use 'b' without
- * calling isc_buffer_init() on it will cause an assertion failure.
- */
-
void
isc_buffer_setautorealloc(isc_buffer_t *b, bool enable);
/*!<
*
*/
-void
-isc__buffer_region(isc_buffer_t *b, isc_region_t *r);
-/*!<
- * \brief Make 'r' refer to the region of 'b'.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer.
- *
- *\li 'r' points to a region structure.
- */
-
-void
-isc__buffer_usedregion(const isc_buffer_t *b, isc_region_t *r);
-/*!<
- * \brief Make 'r' refer to the used region of 'b'.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer.
- *
- *\li 'r' points to a region structure.
- */
-
-void
-isc__buffer_availableregion(isc_buffer_t *b, isc_region_t *r);
-/*!<
- * \brief Make 'r' refer to the available region of 'b'.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer.
- *
- *\li 'r' points to a region structure.
- */
-
-void
-isc__buffer_add(isc_buffer_t *b, unsigned int n);
-/*!<
- * \brief Increase the 'used' region of 'b' by 'n' bytes.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer
- *
- *\li used + n <= length
- *
- */
-
-void
-isc__buffer_subtract(isc_buffer_t *b, unsigned int n);
-/*!<
- * \brief Decrease the 'used' region of 'b' by 'n' bytes.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer
- *
- *\li used >= n
- *
- */
-
-void
-isc__buffer_clear(isc_buffer_t *b);
-/*!<
- * \brief Make the used region empty.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer
- *
- * Ensures:
- *
- *\li used = 0
- *
- */
-
-void
-isc__buffer_consumedregion(isc_buffer_t *b, isc_region_t *r);
-/*!<
- * \brief Make 'r' refer to the consumed region of 'b'.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer.
- *
- *\li 'r' points to a region structure.
- */
-
-void
-isc__buffer_remainingregion(isc_buffer_t *b, isc_region_t *r);
-/*!<
- * \brief Make 'r' refer to the remaining region of 'b'.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer.
- *
- *\li 'r' points to a region structure.
- */
-
-void
-isc__buffer_activeregion(isc_buffer_t *b, isc_region_t *r);
-/*!<
- * \brief Make 'r' refer to the active region of 'b'.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer.
- *
- *\li 'r' points to a region structure.
- */
-
-void
-isc__buffer_setactive(isc_buffer_t *b, unsigned int n);
-/*!<
- * \brief Sets the end of the active region 'n' bytes after current.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer.
- *
- *\li current + n <= used
- */
-
-void
-isc__buffer_first(isc_buffer_t *b);
-/*!<
- * \brief Make the consumed region empty.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer
- *
- * Ensures:
- *
- *\li current == 0
- *
- */
-
-void
-isc__buffer_forward(isc_buffer_t *b, unsigned int n);
-/*!<
- * \brief Increase the 'consumed' region of 'b' by 'n' bytes.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer
- *
- *\li current + n <= used
- *
- */
-
-void
-isc__buffer_back(isc_buffer_t *b, unsigned int n);
-/*!<
- * \brief Decrease the 'consumed' region of 'b' by 'n' bytes.
- *
- * Requires:
- *
- *\li 'b' is a valid buffer
- *
- *\li n <= current
- *
- */
-
void
isc_buffer_compact(isc_buffer_t *b);
/*!<
*\li A 8-bit unsigned integer.
*/
-void
-isc__buffer_putuint8(isc_buffer_t *b, uint8_t val);
-/*!<
- * \brief Store an unsigned 8-bit integer from 'val' into 'b'.
- *
- * Requires:
- *\li 'b' is a valid buffer.
- *
- *\li The length of the available region of 'b' is at least 1
- * or the buffer has autoreallocation enabled.
- *
- * Ensures:
- *\li The used pointer in 'b' is advanced by 1.
- */
-
uint16_t
isc_buffer_getuint16(isc_buffer_t *b);
/*!<
*\li A 16-bit unsigned integer.
*/
-void
-isc__buffer_putuint16(isc_buffer_t *b, uint16_t val);
-/*!<
- * \brief Store an unsigned 16-bit integer in host byte order from 'val'
- * into 'b' in network byte order.
- *
- * Requires:
- *\li 'b' is a valid buffer.
- *
- *\li The length of the available region of 'b' is at least 2
- * or the buffer has autoreallocation enabled.
- *
- * Ensures:
- *\li The used pointer in 'b' is advanced by 2.
- */
-
uint32_t
isc_buffer_getuint32(isc_buffer_t *b);
/*!<
*\li A 32-bit unsigned integer.
*/
-void
-isc__buffer_putuint32(isc_buffer_t *b, uint32_t val);
-/*!<
- * \brief Store an unsigned 32-bit integer in host byte order from 'val'
- * into 'b' in network byte order.
- *
- * Requires:
- *\li 'b' is a valid buffer.
- *
- *\li The length of the available region of 'b' is at least 4
- * or the buffer has autoreallocation enabled.
- *
- * Ensures:
- *\li The used pointer in 'b' is advanced by 4.
- */
-
uint64_t
isc_buffer_getuint48(isc_buffer_t *b);
/*!<
*/
void
-isc__buffer_putuint48(isc_buffer_t *b, uint64_t val);
+isc_buffer_putdecint(isc_buffer_t *b, int64_t v);
/*!<
- * \brief Store an unsigned 48-bit integer in host byte order from 'val'
- * into 'b' in network byte order.
+ * \brief Put decimal representation of 'v' in b
*
* Requires:
*\li 'b' is a valid buffer.
*
- *\li The length of the available region of 'b' is at least 6
+ *\li The length of the available region of 'b' is at least strlen(dec('v'))
* or the buffer has autoreallocation enabled.
*
* Ensures:
- *\li The used pointer in 'b' is advanced by 6.
+ *\li The used pointer in 'b' is advanced by strlen(dec('v')).
*/
-void
-isc__buffer_putuint24(isc_buffer_t *b, uint32_t val);
+isc_result_t
+isc_buffer_copyregion(isc_buffer_t *b, const isc_region_t *r);
/*!<
- * Store an unsigned 24-bit integer in host byte order from 'val'
- * into 'b' in network byte order.
+ * \brief Copy the contents of 'r' into 'b'.
+ *
+ * Notes:
+ *\li If 'b' has autoreallocation enabled, and the length of 'r' is greater
+ * than the length of the available region of 'b', 'b' is reallocated.
*
* Requires:
*\li 'b' is a valid buffer.
*
- *\li The length of the available region of 'b' is at least 3
- * or the buffer has autoreallocation enabled.
+ *\li 'r' is a valid region.
*
- * Ensures:
- *\li The used pointer in 'b' is advanced by 3.
+ * Returns:
+ *\li ISC_R_SUCCESS
+ *\li ISC_R_NOSPACE The available region of 'b' is not
+ * big enough.
*/
-void
-isc__buffer_putmem(isc_buffer_t *b, const unsigned char *base,
- unsigned int length);
+isc_result_t
+isc_buffer_dup(isc_mem_t *mctx, isc_buffer_t **dstp, const isc_buffer_t *src);
/*!<
- * \brief Copy 'length' bytes of memory at 'base' into 'b'.
- *
- * Requires:
- *\li 'b' is a valid buffer.
- *
- *\li 'base' points to 'length' bytes of valid memory.
- *
- *\li The length of the available region of 'b' is at least 'length'
- * or the buffer has autoreallocation enabled.
- *
- * Ensures:
- *\li The used pointer in 'b' is advanced by 'length'.
- */
-
-void
-isc__buffer_putstr(isc_buffer_t *b, const char *source);
-/*!<
- * \brief Copy 'source' into 'b', not including terminating NUL.
- *
- * Requires:
- *\li 'b' is a valid buffer.
- *
- *\li 'source' is a valid NULL terminated string.
- *
- *\li The length of the available region of 'b' is at least strlen('source')
- * or the buffer has autoreallocation enabled.
- *
- * Ensures:
- *\li The used pointer in 'b' is advanced by strlen('source').
- */
-
-void
-isc_buffer_putdecint(isc_buffer_t *b, int64_t v);
-/*!<
- * \brief Put decimal representation of 'v' in b
- *
- * Requires:
- *\li 'b' is a valid buffer.
- *
- *\li The length of the available region of 'b' is at least strlen(dec('v'))
- * or the buffer has autoreallocation enabled.
- *
- * Ensures:
- *\li The used pointer in 'b' is advanced by strlen(dec('v')).
- */
-
-isc_result_t
-isc_buffer_copyregion(isc_buffer_t *b, const isc_region_t *r);
-/*!<
- * \brief Copy the contents of 'r' into 'b'.
- *
- * Notes:
- *\li If 'b' has autoreallocation enabled, and the length of 'r' is greater
- * than the length of the available region of 'b', 'b' is reallocated.
- *
- * Requires:
- *\li 'b' is a valid buffer.
- *
- *\li 'r' is a valid region.
- *
- * Returns:
- *\li ISC_R_SUCCESS
- *\li ISC_R_NOSPACE The available region of 'b' is not
- * big enough.
- */
-
-isc_result_t
-isc_buffer_dup(isc_mem_t *mctx, isc_buffer_t **dstp, const isc_buffer_t *src);
-/*!<
- * \brief Allocate 'dst' and copy used contents of 'src' into it.
+ * \brief Allocate 'dst' and copy used contents of 'src' into it.
*
* Requires:
*\li 'dstp' is not NULL and *dst is NULL.
*\li #ISC_R_FAILURE Other error occurred.
*/
-ISC_LANG_ENDDECLS
-
/*
- * Inline macro versions of the functions. These should never be called
- * directly by an application, but will be used by the functions within
- * buffer.c. The callers should always use "isc_buffer_*()" names, never
- * ones beginning with "isc__"
+ * Buffer functions implemented as inline.
*/
/*! \note
* XXXDCL Something more could be done with initializing buffers that
* point to const data. For example, isc_buffer_constinit() could
* set a new boolean flag in the buffer structure indicating whether
- * the buffer was initialized with that function. * Then if the
+ * the buffer was initialized with that function. Then if the
* boolean were true, the isc_buffer_put* functions could assert a
* contractual requirement for a non-const buffer.
*
- * One drawback is that the isc_buffer_* functions (macros) that return
+ * One drawback is that the isc_buffer_* functions that return
* pointers would still need to return non-const pointers to avoid compiler
* warnings, so it would be up to code that uses them to have to deal
* with the possibility that the buffer was initialized as const --
* true/false, they could at least assert a contractual requirement for
* non-const buffers when needed.
*/
-#define ISC__BUFFER_INIT(_b, _base, _length) \
- do { \
- (_b)->base = _base; \
- (_b)->length = (_length); \
- (_b)->used = 0; \
- (_b)->current = 0; \
- (_b)->active = 0; \
- (_b)->mctx = NULL; \
- ISC_LINK_INIT(_b, link); \
- (_b)->magic = ISC_BUFFER_MAGIC; \
- (_b)->autore = false; \
- } while (0)
-#define ISC__BUFFER_INITNULL(_b) ISC__BUFFER_INIT(_b, NULL, 0)
+/*!
+ * \brief Make 'b' refer to the 'length'-byte region starting at 'base'.
+ *
+ * Requires:
+ *
+ *\li 'length' > 0
+ *
+ *\li 'base' is a pointer to a sequence of 'length' bytes.
+ */
+static inline void
+isc_buffer_init(isc_buffer_t *b, void *base, unsigned int length) {
+ ISC_REQUIRE(b != NULL);
-#define ISC__BUFFER_INVALIDATE(_b) \
- do { \
- (_b)->magic = 0; \
- (_b)->base = NULL; \
- (_b)->length = 0; \
- (_b)->used = 0; \
- (_b)->current = 0; \
- (_b)->active = 0; \
- } while (0)
+ *b = (isc_buffer_t){ .base = base,
+ .length = length,
+ .magic = ISC_BUFFER_MAGIC };
+ ISC_LINK_INIT(b, link);
+}
-#define ISC__BUFFER_REGION(_b, _r) \
- do { \
- (_r)->base = (_b)->base; \
- (_r)->length = (_b)->length; \
- } while (0)
+/*!
+ *\brief Initialize a buffer 'b' with a null data field and zero length.
+ * This can later be grown as needed and swapped in place.
+ */
+static inline void
+isc_buffer_initnull(isc_buffer_t *b) {
+ *b = (isc_buffer_t){ .magic = ISC_BUFFER_MAGIC };
+ ISC_LINK_INIT(b, link);
+}
-#define ISC__BUFFER_USEDREGION(_b, _r) \
- do { \
- (_r)->base = (_b)->base; \
- (_r)->length = (_b)->used; \
+/*!
+ * \brief Make 'b' refer to the 'length'-byte constant region starting
+ * at 'base'.
+ *
+ * Requires:
+ *
+ *\li 'length' > 0
+ *\li 'base' is a pointer to a sequence of 'length' bytes.
+ */
+#define isc_buffer_constinit(_b, _d, _l) \
+ do { \
+ union { \
+ void *_var; \
+ const void *_const; \
+ } _deconst; \
+ _deconst._const = (_d); \
+ isc_buffer_init((_b), _deconst._var, (_l)); \
} while (0)
-#define ISC__BUFFER_AVAILABLEREGION(_b, _r) \
- do { \
- (_r)->base = isc_buffer_used(_b); \
- (_r)->length = isc_buffer_availablelength(_b); \
- } while (0)
+/*!
+ * \brief Make 'b' an invalid buffer.
+ *
+ * Requires:
+ *\li 'b' is a valid buffer.
+ *
+ * Ensures:
+ *\li Future attempts to use 'b' without calling isc_buffer_init() on
+ * it will cause an assertion failure.
+ */
+static inline void
+isc_buffer_invalidate(isc_buffer_t *b) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(!ISC_LINK_LINKED(b, link));
+ ISC_REQUIRE(b->mctx == NULL);
+
+ b->magic = 0;
+ b->base = NULL;
+ b->length = 0;
+ b->used = 0;
+ b->current = 0;
+ b->active = 0;
+}
-#define ISC__BUFFER_ADD(_b, _n) \
- do { \
- (_b)->used += (_n); \
- } while (0)
+/*!
+ * \brief Make 'r' refer to the region of 'b'.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer.
+ *
+ *\li 'r' points to a region structure.
+ */
+static inline void
+isc_buffer_region(isc_buffer_t *b, isc_region_t *r) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(r != NULL);
-#define ISC__BUFFER_SUBTRACT(_b, _n) \
- do { \
- (_b)->used -= (_n); \
- if ((_b)->current > (_b)->used) \
- (_b)->current = (_b)->used; \
- if ((_b)->active > (_b)->used) \
- (_b)->active = (_b)->used; \
- } while (0)
+ r->base = b->base;
+ r->length = b->length;
+}
-#define ISC__BUFFER_CLEAR(_b) \
- do { \
- (_b)->used = 0; \
- (_b)->current = 0; \
- (_b)->active = 0; \
- } while (0)
+/*!
+ * \brief Make 'r' refer to the used region of 'b'.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer.
+ *
+ *\li 'r' points to a region structure.
+ */
+static inline void
+isc_buffer_usedregion(const isc_buffer_t *b, isc_region_t *r) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(r != NULL);
-#define ISC__BUFFER_CONSUMEDREGION(_b, _r) \
- do { \
- (_r)->base = (_b)->base; \
- (_r)->length = (_b)->current; \
- } while (0)
+ r->base = b->base;
+ r->length = b->used;
+}
-#define ISC__BUFFER_REMAININGREGION(_b, _r) \
- do { \
- (_r)->base = isc_buffer_current(_b); \
- (_r)->length = isc_buffer_remaininglength(_b); \
- } while (0)
+/*!
+ * \brief Make 'r' refer to the available region of 'b'.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer.
+ *
+ *\li 'r' points to a region structure.
+ */
+static inline void
+isc_buffer_availableregion(isc_buffer_t *b, isc_region_t *r) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(r != NULL);
-#define ISC__BUFFER_ACTIVEREGION(_b, _r) \
- do { \
- if ((_b)->current < (_b)->active) { \
- (_r)->base = isc_buffer_current(_b); \
- (_r)->length = isc_buffer_activelength(_b); \
- } else { \
- (_r)->base = NULL; \
- (_r)->length = 0; \
- } \
- } while (0)
+ r->base = isc_buffer_used(b);
+ r->length = isc_buffer_availablelength(b);
+}
-#define ISC__BUFFER_SETACTIVE(_b, _n) \
- do { \
- (_b)->active = (_b)->current + (_n); \
- } while (0)
+/*!
+ * \brief Increase the 'used' region of 'b' by 'n' bytes.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer
+ *
+ *\li used + n <= length
+ */
+static inline void
+isc_buffer_add(isc_buffer_t *b, unsigned int n) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(b->used + n <= b->length);
-#define ISC__BUFFER_FIRST(_b) \
- do { \
- (_b)->current = 0; \
- } while (0)
+ b->used += n;
+}
-#define ISC__BUFFER_FORWARD(_b, _n) \
- do { \
- (_b)->current += (_n); \
- } while (0)
+/*!
+ * \brief Decrease the 'used' region of 'b' by 'n' bytes.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer
+ *
+ *\li used >= n
+ */
+static inline void
+isc_buffer_subtract(isc_buffer_t *b, unsigned int n) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(b->used >= n);
-#define ISC__BUFFER_BACK(_b, _n) \
- do { \
- (_b)->current -= (_n); \
- } while (0)
+ b->used -= n;
+ if (b->current > b->used) {
+ b->current = b->used;
+ }
+ if (b->active > b->used) {
+ b->active = b->used;
+ }
+}
-#define ISC__BUFFER_PUTMEM(_b, _base, _length) \
- do { \
- if ((_b)->autore) { \
- isc_buffer_t *_tmp = _b; \
- ISC_REQUIRE(isc_buffer_reserve(&_tmp, _length) == \
- ISC_R_SUCCESS); \
- } \
- ISC_REQUIRE(isc_buffer_availablelength(_b) >= \
- (unsigned int)_length); \
- if (_length > 0U) { \
- memmove(isc_buffer_used(_b), (_base), (_length)); \
- (_b)->used += (_length); \
- } \
- } while (0)
+/*!<
+ * \brief Make the used region empty.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer
+ *
+ * Ensures:
+ *
+ *\li used = 0
+ */
+static inline void
+isc_buffer_clear(isc_buffer_t *b) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
-#define ISC__BUFFER_PUTSTR(_b, _source) \
- do { \
- unsigned int _length; \
- unsigned char *_cp; \
- _length = (unsigned int)strlen(_source); \
- if ((_b)->autore) { \
- isc_buffer_t *_tmp = _b; \
- ISC_REQUIRE(isc_buffer_reserve(&_tmp, _length) == \
- ISC_R_SUCCESS); \
- } \
- ISC_REQUIRE(isc_buffer_availablelength(_b) >= _length); \
- _cp = isc_buffer_used(_b); \
- memmove(_cp, (_source), _length); \
- (_b)->used += (_length); \
- } while (0)
+ b->used = 0;
+ b->current = 0;
+ b->active = 0;
+}
-#define ISC__BUFFER_PUTUINT8(_b, _val) \
- do { \
- unsigned char *_cp; \
- /* evaluate (_val) only once */ \
- uint8_t _val2 = (_val); \
- if ((_b)->autore) { \
- isc_buffer_t *_tmp = _b; \
- ISC_REQUIRE(isc_buffer_reserve(&_tmp, 1) == \
- ISC_R_SUCCESS); \
- } \
- ISC_REQUIRE(isc_buffer_availablelength(_b) >= 1U); \
- _cp = isc_buffer_used(_b); \
- (_b)->used++; \
- _cp[0] = _val2; \
- } while (0)
+/*!
+ * \brief Make 'r' refer to the consumed region of 'b'.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer.
+ *
+ *\li 'r' points to a region structure.
+ */
+static inline void
+isc_buffer_consumedregion(isc_buffer_t *b, isc_region_t *r) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(r != NULL);
-#define ISC__BUFFER_PUTUINT16(_b, _val) \
- do { \
- unsigned char *_cp; \
- /* evaluate (_val) only once */ \
- uint16_t _val2 = (_val); \
- if ((_b)->autore) { \
- isc_buffer_t *_tmp = _b; \
- ISC_REQUIRE(isc_buffer_reserve(&_tmp, 2) == \
- ISC_R_SUCCESS); \
- } \
- ISC_REQUIRE(isc_buffer_availablelength(_b) >= 2U); \
- _cp = isc_buffer_used(_b); \
- (_b)->used += 2; \
- _cp[0] = (unsigned char)(_val2 >> 8); \
- _cp[1] = (unsigned char)_val2; \
- } while (0)
+ r->base = b->base;
+ r->length = b->current;
+}
-#define ISC__BUFFER_PUTUINT24(_b, _val) \
- do { \
- unsigned char *_cp; \
- /* evaluate (_val) only once */ \
- uint32_t _val2 = (_val); \
- if ((_b)->autore) { \
- isc_buffer_t *_tmp = _b; \
- ISC_REQUIRE(isc_buffer_reserve(&_tmp, 3) == \
- ISC_R_SUCCESS); \
- } \
- ISC_REQUIRE(isc_buffer_availablelength(_b) >= 3U); \
- _cp = isc_buffer_used(_b); \
- (_b)->used += 3; \
- _cp[0] = (unsigned char)(_val2 >> 16); \
- _cp[1] = (unsigned char)(_val2 >> 8); \
- _cp[2] = (unsigned char)_val2; \
- } while (0)
+/*!
+ * \brief Make 'r' refer to the remaining region of 'b'.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer.
+ *
+ *\li 'r' points to a region structure.
+ */
+static inline void
+isc_buffer_remainingregion(isc_buffer_t *b, isc_region_t *r) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(r != NULL);
-#define ISC__BUFFER_PUTUINT32(_b, _val) \
- do { \
- unsigned char *_cp; \
- /* evaluate (_val) only once */ \
- uint32_t _val2 = (_val); \
- if ((_b)->autore) { \
- isc_buffer_t *_tmp = _b; \
- ISC_REQUIRE(isc_buffer_reserve(&_tmp, 4) == \
- ISC_R_SUCCESS); \
- } \
- ISC_REQUIRE(isc_buffer_availablelength(_b) >= 4U); \
- _cp = isc_buffer_used(_b); \
- (_b)->used += 4; \
- _cp[0] = (unsigned char)(_val2 >> 24); \
- _cp[1] = (unsigned char)(_val2 >> 16); \
- _cp[2] = (unsigned char)(_val2 >> 8); \
- _cp[3] = (unsigned char)_val2; \
- } while (0)
+ r->base = isc_buffer_current(b);
+ r->length = isc_buffer_remaininglength(b);
+}
-#if defined(ISC_BUFFER_USEINLINE)
-#define isc_buffer_init ISC__BUFFER_INIT
-#define isc_buffer_initnull ISC__BUFFER_INITNULL
-#define isc_buffer_invalidate ISC__BUFFER_INVALIDATE
-#define isc_buffer_region ISC__BUFFER_REGION
-#define isc_buffer_usedregion ISC__BUFFER_USEDREGION
-#define isc_buffer_availableregion ISC__BUFFER_AVAILABLEREGION
-#define isc_buffer_add ISC__BUFFER_ADD
-#define isc_buffer_subtract ISC__BUFFER_SUBTRACT
-#define isc_buffer_clear ISC__BUFFER_CLEAR
-#define isc_buffer_consumedregion ISC__BUFFER_CONSUMEDREGION
-#define isc_buffer_remainingregion ISC__BUFFER_REMAININGREGION
-#define isc_buffer_activeregion ISC__BUFFER_ACTIVEREGION
-#define isc_buffer_setactive ISC__BUFFER_SETACTIVE
-#define isc_buffer_first ISC__BUFFER_FIRST
-#define isc_buffer_forward ISC__BUFFER_FORWARD
-#define isc_buffer_back ISC__BUFFER_BACK
-#define isc_buffer_putmem ISC__BUFFER_PUTMEM
-#define isc_buffer_putstr ISC__BUFFER_PUTSTR
-#define isc_buffer_putuint8 ISC__BUFFER_PUTUINT8
-#define isc_buffer_putuint16 ISC__BUFFER_PUTUINT16
-#define isc_buffer_putuint24 ISC__BUFFER_PUTUINT24
-#define isc_buffer_putuint32 ISC__BUFFER_PUTUINT32
-#else /* if defined(ISC_BUFFER_USEINLINE) */
-#define isc_buffer_init isc__buffer_init
-#define isc_buffer_initnull isc__buffer_initnull
-#define isc_buffer_invalidate isc__buffer_invalidate
-#define isc_buffer_region isc__buffer_region
-#define isc_buffer_usedregion isc__buffer_usedregion
-#define isc_buffer_availableregion isc__buffer_availableregion
-#define isc_buffer_add isc__buffer_add
-#define isc_buffer_subtract isc__buffer_subtract
-#define isc_buffer_clear isc__buffer_clear
-#define isc_buffer_consumedregion isc__buffer_consumedregion
-#define isc_buffer_remainingregion isc__buffer_remainingregion
-#define isc_buffer_activeregion isc__buffer_activeregion
-#define isc_buffer_setactive isc__buffer_setactive
-#define isc_buffer_first isc__buffer_first
-#define isc_buffer_forward isc__buffer_forward
-#define isc_buffer_back isc__buffer_back
-#define isc_buffer_putmem isc__buffer_putmem
-#define isc_buffer_putstr isc__buffer_putstr
-#define isc_buffer_putuint8 isc__buffer_putuint8
-#define isc_buffer_putuint16 isc__buffer_putuint16
-#define isc_buffer_putuint24 isc__buffer_putuint24
-#define isc_buffer_putuint32 isc__buffer_putuint32
-#endif /* if defined(ISC_BUFFER_USEINLINE) */
+/*!
+ * \brief Make 'r' refer to the active region of 'b'.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer.
+ *
+ *\li 'r' points to a region structure.
+ */
+static inline void
+isc_buffer_activeregion(isc_buffer_t *b, isc_region_t *r) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(r != NULL);
-#define isc_buffer_constinit(_b, _d, _l) \
- do { \
- union { \
- void *_var; \
- const void *_const; \
- } _deconst; \
- _deconst._const = (_d); \
- isc_buffer_init((_b), _deconst._var, (_l)); \
- } while (0)
+ if (b->current < b->active) {
+ r->base = isc_buffer_current(b);
+ r->length = isc_buffer_activelength(b);
+ } else {
+ r->base = NULL;
+ r->length = 0;
+ }
+}
-/*
- * No inline method for this one (yet).
+/*!
+ * \brief Sets the end of the active region 'n' bytes after current.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer.
+ *
+ *\li current + n <= used
+ */
+static inline void
+isc_buffer_setactive(isc_buffer_t *b, unsigned int n) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(b->current + n <= b->used);
+
+ b->active = b->current + n;
+}
+
+/*!<
+ * \brief Make the consumed region empty.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer
+ *
+ * Ensures:
+ *
+ *\li current == 0
+ */
+static inline void
+isc_buffer_first(isc_buffer_t *b) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+
+ b->current = 0;
+}
+
+/*!
+ * \brief Increase the 'consumed' region of 'b' by 'n' bytes.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer
+ *
+ *\li current + n <= used
+ */
+static inline void
+isc_buffer_forward(isc_buffer_t *b, unsigned int n) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(b->current + n <= b->used);
+
+ b->current += n;
+}
+
+/*!
+ * \brief Decrease the 'consumed' region of 'b' by 'n' bytes.
+ *
+ * Requires:
+ *
+ *\li 'b' is a valid buffer
+ *
+ *\li n <= current
+ */
+static inline void
+isc_buffer_back(isc_buffer_t *b, unsigned int n) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(n <= b->current);
+
+ b->current -= n;
+}
+
+/*!
+ * \brief Store an unsigned 8-bit integer from 'val' into 'b'.
+ *
+ * Requires:
+ *\li 'b' is a valid buffer.
+ *
+ *\li The length of the available region of 'b' is at least 1
+ * or the buffer has autoreallocation enabled.
+ *
+ * Ensures:
+ *\li The used pointer in 'b' is advanced by 1.
+ */
+static inline void
+isc_buffer_putuint8(isc_buffer_t *b, uint8_t val) {
+ unsigned char *cp;
+
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+
+ if (b->autore) {
+ isc_buffer_t *tmp = b;
+ ISC_REQUIRE(isc_buffer_reserve(&tmp, 1) == ISC_R_SUCCESS);
+ }
+
+ ISC_REQUIRE(isc_buffer_availablelength(b) >= 1U);
+
+ cp = isc_buffer_used(b);
+ b->used++;
+ cp[0] = val;
+}
+
+/*!
+ * \brief Store an unsigned 16-bit integer in host byte order from 'val'
+ * into 'b' in network byte order.
+ *
+ * Requires:
+ *\li 'b' is a valid buffer.
+ *
+ *\li The length of the available region of 'b' is at least 2
+ * or the buffer has autoreallocation enabled.
+ *
+ * Ensures:
+ *\li The used pointer in 'b' is advanced by 2.
*/
-#define isc_buffer_putuint48 isc__buffer_putuint48
+static inline void
+isc_buffer_putuint16(isc_buffer_t *b, uint16_t val) {
+ unsigned char *cp;
+
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+
+ if (b->autore) {
+ isc_buffer_t *tmp = b;
+ ISC_REQUIRE(isc_buffer_reserve(&tmp, 2) == ISC_R_SUCCESS);
+ }
+
+ ISC_REQUIRE(isc_buffer_availablelength(b) >= 2U);
+
+ cp = isc_buffer_used(b);
+ b->used += 2;
+ cp[0] = (unsigned char)(val >> 8);
+ cp[1] = (unsigned char)val;
+}
+
+/*!
+ * Store an unsigned 24-bit integer in host byte order from 'val'
+ * into 'b' in network byte order.
+ *
+ * Requires:
+ *\li 'b' is a valid buffer.
+ *
+ *\li The length of the available region of 'b' is at least 3
+ * or the buffer has autoreallocation enabled.
+ *
+ * Ensures:
+ *\li The used pointer in 'b' is advanced by 3.
+ */
+static inline void
+isc_buffer_putuint24(isc_buffer_t *b, uint32_t val) {
+ unsigned char *cp;
+
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+
+ if (b->autore) {
+ isc_buffer_t *tmp = b;
+ ISC_REQUIRE(isc_buffer_reserve(&tmp, 3) == ISC_R_SUCCESS);
+ }
+
+ ISC_REQUIRE(isc_buffer_availablelength(b) >= 3U);
+
+ cp = isc_buffer_used(b);
+ b->used += 3;
+ cp[0] = (unsigned char)(val >> 16);
+ cp[1] = (unsigned char)(val >> 8);
+ cp[2] = (unsigned char)val;
+}
+
+/*!
+ * \brief Store an unsigned 32-bit integer in host byte order from 'val'
+ * into 'b' in network byte order.
+ *
+ * Requires:
+ *\li 'b' is a valid buffer.
+ *
+ *\li The length of the available region of 'b' is at least 4
+ * or the buffer has autoreallocation enabled.
+ *
+ * Ensures:
+ *\li The used pointer in 'b' is advanced by 4.
+ */
+static inline void
+isc_buffer_putuint32(isc_buffer_t *b, uint32_t val) {
+ unsigned char *cp;
+
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+
+ if (b->autore) {
+ isc_buffer_t *tmp = b;
+ ISC_REQUIRE(isc_buffer_reserve(&tmp, 4) == ISC_R_SUCCESS);
+ }
+
+ ISC_REQUIRE(isc_buffer_availablelength(b) >= 4U);
+
+ cp = isc_buffer_used(b);
+ b->used += 4;
+ cp[0] = (unsigned char)(val >> 24);
+ cp[1] = (unsigned char)(val >> 16);
+ cp[2] = (unsigned char)(val >> 8);
+ cp[3] = (unsigned char)val;
+}
+
+/*!
+ * \brief Store an unsigned 48-bit integer in host byte order from 'val'
+ * into 'b' in network byte order.
+ *
+ * Requires:
+ *\li 'b' is a valid buffer.
+ *
+ *\li The length of the available region of 'b' is at least 6
+ * or the buffer has autoreallocation enabled.
+ *
+ * Ensures:
+ *\li The used pointer in 'b' is advanced by 6.
+ */
+static inline void
+isc_buffer_putuint48(isc_buffer_t *b, uint64_t val) {
+ unsigned char *cp = NULL;
+
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+
+ if (b->autore) {
+ isc_buffer_t *tmp = b;
+ ISC_REQUIRE(isc_buffer_reserve(&tmp, 6) == ISC_R_SUCCESS);
+ }
+
+ ISC_REQUIRE(isc_buffer_availablelength(b) >= 6U);
+
+ cp = isc_buffer_used(b);
+ b->used += 6;
+ cp[0] = (unsigned char)(val >> 40);
+ cp[1] = (unsigned char)(val >> 32);
+ cp[2] = (unsigned char)(val >> 24);
+ cp[3] = (unsigned char)(val >> 16);
+ cp[4] = (unsigned char)(val >> 8);
+ cp[5] = (unsigned char)val;
+}
+
+/*!
+ * \brief Copy 'length' bytes of memory at 'base' into 'b'.
+ *
+ * Requires:
+ *\li 'b' is a valid buffer.
+ *
+ *\li 'base' points to 'length' bytes of valid memory.
+ *
+ *\li The length of the available region of 'b' is at least 'length'
+ * or the buffer has autoreallocation enabled.
+ *
+ * Ensures:
+ *\li The used pointer in 'b' is advanced by 'length'.
+ */
+static inline void
+isc_buffer_putmem(isc_buffer_t *b, const unsigned char *base,
+ unsigned int length) {
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+
+ if (b->autore) {
+ isc_buffer_t *tmp = b;
+ ISC_REQUIRE(isc_buffer_reserve(&tmp, length) == ISC_R_SUCCESS);
+ }
+
+ ISC_REQUIRE(isc_buffer_availablelength(b) >= (unsigned int)length);
+
+ if (length > 0U) {
+ memmove(isc_buffer_used(b), base, length);
+ b->used += length;
+ }
+}
+
+/*!
+ * \brief Copy 'source' into 'b', not including terminating NUL.
+ *
+ * Requires:
+ *\li 'b' is a valid buffer.
+ *
+ *\li 'source' is a valid NULL terminated string.
+ *
+ *\li The length of the available region of 'b' is at least strlen('source')
+ * or the buffer has autoreallocation enabled.
+ *
+ * Ensures:
+ *\li The used pointer in 'b' is advanced by strlen('source').
+ */
+static inline void
+isc_buffer_putstr(isc_buffer_t *b, const char *source) {
+ unsigned int length;
+ unsigned char *cp;
+
+ ISC_REQUIRE(ISC_BUFFER_VALID(b));
+ ISC_REQUIRE(source != NULL);
+
+ length = (unsigned int)strlen(source);
+ if (b->autore) {
+ isc_buffer_t *tmp = b;
+ ISC_REQUIRE(isc_buffer_reserve(&tmp, length) == ISC_R_SUCCESS);
+ }
+
+ ISC_REQUIRE(isc_buffer_availablelength(b) >= length);
+
+ cp = isc_buffer_used(b);
+ memmove(cp, source, length);
+ b->used += length;
+}
+ISC_LANG_ENDDECLS