1
0
mirror of https://git.FreeBSD.org/src.git synced 2025-01-25 16:13:17 +00:00

Rewrite of the buf code:

- convert Buf_AddByte from a macro to a function
- move #define's into the header file
- remove unused field in struct Buffer
- remove size fields - they can be easily computed
- inline Buf_OvAddByte

Submitted by:	Max Okumoto <okumoto@ucsd.edu>
This commit is contained in:
Hartmut Brandt 2005-02-04 16:48:35 +00:00
parent 0ed0329f9c
commit f4dd241033
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=141290
2 changed files with 98 additions and 172 deletions

View File

@ -1,4 +1,5 @@
/*-
* Copyright (c) 2005 Max Okumoto
* Copyright (c) 1988, 1989, 1990, 1993
* The Regents of the University of California. All rights reserved.
* Copyright (c) 1988, 1989 by Adam de Boor
@ -42,8 +43,8 @@
#include <sys/cdefs.h>
__FBSDID("$FreeBSD$");
/*-
* buf.c --
/*
* buf.c
* Functions for automatically-expanded buffers.
*/
@ -54,220 +55,151 @@ __FBSDID("$FreeBSD$");
#include "sprite.h"
#include "util.h"
#ifndef max
#define max(a,b) ((a) > (b) ? (a) : (b))
#ifndef MAX
#define MAX(a,b) ((a) > (b) ? (a) : (b))
#endif
/*
* BufExpand --
* Expand the given buffer to hold the given number of additional
* bytes.
* Makes sure there's room for an extra NULL byte at the end of the
* buffer in case it holds a string.
/**
* Returns the number of bytes in the buffer. Doesn't include the
* null-terminating byte.
*/
#define BufExpand(bp, nb) do { \
if ((bp)->left < (nb) + 1) { \
int newSize = (bp)->size + max((nb) + 1, BUF_ADD_INC); \
Byte *newBuf = erealloc((bp)->buffer, newSize); \
\
(bp)->inPtr = newBuf + ((bp)->inPtr - (bp)->buffer); \
(bp)->outPtr = newBuf + ((bp)->outPtr - (bp)->buffer); \
(bp)->buffer = newBuf; \
(bp)->size = newSize; \
(bp)->left = newSize - ((bp)->inPtr - (bp)->buffer); \
} \
} while (0)
#define BUF_DEF_SIZE 256 /* Default buffer size */
#define BUF_ADD_INC 256 /* Expansion increment when Adding */
#define BUF_UNGET_INC 16 /* Expansion increment when Ungetting */
/*-
*-----------------------------------------------------------------------
* Buf_OvAddByte --
* Add a single byte to the buffer. left is zero or negative.
*
* Results:
* None.
*
* Side Effects:
* The buffer may be expanded.
*
*-----------------------------------------------------------------------
*/
void
Buf_OvAddByte(Buffer *bp, Byte byte)
inline size_t
Buf_Size(const Buffer *buf)
{
return (buf->end - buf->buf);
}
/**
* Expand the buffer to hold the number of additional bytes, plus
* space to store a terminating NULL byte.
*/
static inline void
BufExpand(Buffer *bp, size_t nb)
{
size_t len = Buf_Size(bp);
size_t size;
if (bp->size < len + nb + 1) {
size = bp->size + MAX(nb + 1, BUF_ADD_INC);
bp->size = size;
bp->buf = erealloc(bp->buf, size);
bp->end = bp->buf + len;
}
}
/**
* Add a single byte to the buffer.
*/
inline void
Buf_AddByte(Buffer *bp, Byte byte)
{
bp->left = 0;
BufExpand(bp, 1);
*bp->inPtr++ = byte;
bp->left--;
/*
* Null-terminate
*/
*bp->inPtr = 0;
*bp->end = byte;
bp->end++;
*bp->end = '\0';
}
/*-
*-----------------------------------------------------------------------
* Buf_AddBytes --
* Add a number of bytes to the buffer.
*
* Results:
* None.
*
* Side Effects:
* Guess what?
*
*-----------------------------------------------------------------------
/**
* Add bytes to the buffer.
*/
void
Buf_AddBytes(Buffer *bp, size_t numBytes, const Byte *bytesPtr)
Buf_AddBytes(Buffer *bp, size_t len, const Byte *bytes)
{
BufExpand(bp, numBytes);
BufExpand(bp, len);
memcpy(bp->inPtr, bytesPtr, numBytes);
bp->inPtr += numBytes;
bp->left -= numBytes;
/*
* Null-terminate
*/
*bp->inPtr = 0;
memcpy(bp->end, bytes, len);
bp->end += len;
*bp->end = '\0';
}
/*-
*-----------------------------------------------------------------------
* Buf_GetAll --
* Get all the available data at once.
/**
* Get a reference to the internal buffer.
*
* Results:
* A pointer to the data and the number of bytes available.
* len:
* Pointer to where we return the number of bytes in the internal buffer.
*
* Side Effects:
* None.
*
*-----------------------------------------------------------------------
* Returns:
* return A pointer to the data.
*/
Byte *
Buf_GetAll(Buffer *bp, size_t *numBytesPtr)
Buf_GetAll(Buffer *bp, size_t *len)
{
if (numBytesPtr != NULL)
*numBytesPtr = bp->inPtr - bp->outPtr;
if (len != NULL)
*len = Buf_Size(bp);
return (bp->outPtr);
return (bp->buf);
}
/*-
*-----------------------------------------------------------------------
* Buf_Size --
* Returns the number of bytes in the given buffer. Doesn't include
* the null-terminating byte.
/**
* Initialize a buffer. If no initial size is given, a reasonable
* default is used.
*
* Results:
* The number of bytes.
* Returns:
* A buffer object to be given to other functions in this library.
*
* Side Effects:
* None.
*
*-----------------------------------------------------------------------
*/
size_t
Buf_Size(Buffer *buf)
{
return (buf->inPtr - buf->outPtr);
}
/*-
*-----------------------------------------------------------------------
* Buf_Init --
* Initialize a buffer. If no initial size is given, a reasonable
* default is used.
*
* Results:
* A buffer to be given to other functions in this library.
*
* Side Effects:
* The buffer is created, the space allocated and pointers
* initialized.
*
*-----------------------------------------------------------------------
* Space is allocated for the Buffer object and a internal buffer.
*/
Buffer *
Buf_Init(size_t size)
{
Buffer *bp; /* New Buffer */
bp = emalloc(sizeof(*bp));
Buffer *bp; /* New Buffer */
if (size <= 0)
size = BUF_DEF_SIZE;
bp->left = bp->size = size;
bp->buffer = emalloc(size);
bp->inPtr = bp->outPtr = bp->buffer;
*bp->inPtr = 0;
bp = emalloc(sizeof(*bp));
bp->size = size;
bp->buf = emalloc(size);
bp->end = bp->buf;
*bp->end = '\0';
return (bp);
}
/*-
*-----------------------------------------------------------------------
* Buf_Destroy --
* Destroy a buffer, and optionally free its data, too.
*
* Results:
* None.
/**
* Destroy a buffer, and optionally free its data, too.
*
* Side Effects:
* The buffer is freed.
*
*-----------------------------------------------------------------------
* Space for the Buffer object and possibly the internal buffer
* is de-allocated.
*/
void
Buf_Destroy(Buffer *buf, Boolean freeData)
{
if (freeData)
free(buf->buffer);
free(buf->buf);
free(buf);
}
/*-
*-----------------------------------------------------------------------
* Buf_ReplaceLastByte --
* Replace the last byte in a buffer.
*
* Results:
* None.
*
* Side Effects:
* If the buffer was empty intially, then a new byte will be added.
* Otherwise, the last byte is overwritten.
*
*-----------------------------------------------------------------------
/**
* Replace the last byte in a buffer. If the buffer was empty
* intially, then a new byte will be added.
*/
void
Buf_ReplaceLastByte(Buffer *buf, Byte byte)
Buf_ReplaceLastByte(Buffer *bp, Byte byte)
{
if (buf->inPtr == buf->outPtr)
Buf_AddByte(buf, byte);
else
*(buf->inPtr - 1) = byte;
if (bp->end == bp->buf) {
Buf_AddByte(bp, byte);
} else {
*(bp->end - 1) = byte;
}
}
/**
* Clear the contents of the buffer.
*/
void
Buf_Clear(Buffer *bp)
{
bp->inPtr = bp->buffer;
bp->outPtr = bp->buffer;
bp->left = bp->size;
bp->inPtr[0] = '\0';
}
bp->end = bp->buf;
*bp->end = '\0';
}

View File

@ -63,28 +63,22 @@
*/
#define MAKE_BSIZE 256 /* starting size for expandable buffers */
#define BUF_ERROR 256
#define BUF_DEF_SIZE 256 /* Default buffer size */
#define BUF_ADD_INC 256 /* Expansion increment when Adding */
typedef char Byte;
typedef struct Buffer {
size_t size; /* Current size of the buffer */
size_t left; /* Space left (== size - (inPtr - buffer)) */
Byte *buffer; /* The buffer itself */
Byte *inPtr; /* Place to write to */
Byte *outPtr; /* Place to read from */
size_t size; /* Current size of the buffer */
Byte *buf; /* The buffer itself */
Byte *end; /* Place to write to */
} Buffer;
/* Buf_AddByte adds a single byte to a buffer. */
#define Buf_AddByte(bp, byte) \
(void)(--(bp)->left <= 0 ? Buf_OvAddByte((bp), (byte)), 1 : \
(*(bp)->inPtr++ = (byte), *(bp)->inPtr = 0), 1)
void Buf_OvAddByte(Buffer *, Byte);
void Buf_AddByte(Buffer *, Byte);
void Buf_AddBytes(Buffer *, size_t, const Byte *);
Byte *Buf_GetAll(Buffer *, size_t *);
void Buf_Clear(Buffer *);
size_t Buf_Size(Buffer *);
size_t Buf_Size(const Buffer *);
Buffer *Buf_Init(size_t);
void Buf_Destroy(Buffer *, Boolean);
void Buf_ReplaceLastByte(Buffer *, Byte);