xref: /titanic_50/usr/src/lib/libast/common/man/stak.3 (revision cb8a054b1ab30d5caa746e6c44f29d4c9d3071c1)
.fp 5 CW
STAK 3
NAME
stak - data stack storage library (obsolete: use stk instead)
SYNOPSIS

\f5
#include <stak.h>

Stak_t *stakcreate(int flags);
Stak_t *stakinstall(Stak_t *stack, char *(overflow)(int));
int stakdelete(Stak_t *stack);
void staklink(Stak_t *stack)

char *stakalloc(unsigned size);
char *stakcopy(const char *string);
char *stakset(char *address, unsigned offset);

char *stakseek(unsigned offset);
int stakputc(int c);
int stakputs(const char *string);
int stakwrite(const char *address, unsigned size);
int staktell(void);
char *stakptr(unsigned offset);
char *stakfreeze(unsigned extra);

DESCRIPTION

\f5stak is a package of routines designed to provide efficient stack oriented dynamic storage. A stack abstraction consists of an ordered list of contiguous memory regions, called stack frames, that can hold objects of arbitrary size. A stack is represented by the type \f5Stak_t defined in header \f5<stak.h>. At any instant there is one active stack. Variable size objects can be added to the active stack and programs can reference these objects directly with pointers. In addition, the last object on the stack (referred to here as the current object) can be built incrementally. The current object has an associated offset that determines its current size. While the current object is being built incrementally, its location might change so that it is necessary to reference the object with relative offsets ranging from zero to the current offset of the object.

There is a preset initial active stack. To use an additional stack, it is necessary to create it and to install it as the active stack. A stack is created with the \f5stakcreate() function. A flags argument of \f5STAK_SMALL indicates that unused space on the stack should be freed whenever this stack ceases to be the active stack. If successful, \f5stakcreate() returns a pointer to a stack whose reference count is 1. Otherwise, \f5stakcreate() returns a null pointer. The \f5staklink() function increases the reference count for the given stack. The \f5stakinstall() function makes the specified stack the active stack and returns a pointer to the previous active stack. When the overflow argument is not null, it specifies a function that will be called whenever \f5malloc(3) fails while trying to grow the stack. The overflow function will be called with the size that was passed to \f5malloc(3). The overflow function can call \f5exit(3), call \f5longjmp(3) or return. If the \f5overflow function returns, it must return a pointer to a memory region of the given size. The default action is to write an error to standard error and to call \f5exit(2) with a non-zero exit value. When stack is a null pointer, the active stack is not changed but the overflow function for the active stack can be changed and a pointer to the active stack is returned. The \f5stakdelete() function decrements the reference count and frees the memory associated with the specified stack when the reference count is zero. The effect of subsequent references to objects on the stack are undefined.

The \f5stakalloc() function returns an aligned pointer to space on the active stack that can be used to hold any object of the given size. \f5stakalloc() is similar to \f5malloc(3) except that individual items returned by \f5stakalloc() can not be freed. \f5stakalloc() causes the offset of the current object to be set to zero.

The \f5stakcopy() function copies the given string onto the stack and returns a pointer to the string on the stack. \f5stakcopy() causes the offset of the current object to be set to zero.

The \f5stakset() function finds the frame containing the given address, frees all frames that were created after the one containing the given address, and sets the current object to the given address. The top of the current object is set to offset bytes from current object. If address is not the address of an object on the stack the result is undefined.

The remaining functions are used to build the current object incrementally. An object that is built incrementally on the stack will always occupy contiguous memory within a stack frame but until \f5stakfreeze() is called, the location in memory for the object can change. There is a current offset associated with the current object that determines where subsequent operations apply. Initially, this offset is zero, and the offset changes as a result of the operations you specify. The \f5stakseek() function is used set the offset for the current object. The offset argument to \f5stakseek() specifies the new offset for the current object. The frame will be extended or moved if \f5offset causes the new current offset to extend beyond the current frame. \f5stakseek() returns a pointer to the beginning of the current object. The \f5staktell() function gives the offset of the current object.

The \f5stakputc() function adds a given character to the current object on the stack. The current offset is advanced by 1. The \f5stakputs() function appends the given string onto the current object in the stack and returns the length of the string. The current offset is advanced by the length of the string. The \f5stakwrite() function appends the given size byte memory region starting at address onto the current object in the stack and advances the current offset by size. The current offset is returned.

The \f5stakptr() function converts the given \f5offset for the current object into a memory address on the stack. This address is only valid until another stack operation is given. The result is not defined if offset exceeds the size of the current object. The \f5stakfreeze() function terminates the current object on the stack and returns a pointer to the beginning of this object. If extra is non-zero, extra bytes are added to the stack before the current object is terminated. The first added byte will contain zero and the contents of the remaining bytes are undefined.

HISTORY
The \f5stak interface was derived from similar routines in the KornShell code that is used for building parse trees and carrying out expansions. It provides an efficient mechanism for grouping dynamically allocated objects so that they can be freed all at once rather than individually.
AUTHOR
David Korn
SEE ALSO
\f5exit(2) \f5longjmp(3) \f5malloc(3)