macLib.h

Text macro substitution routines.

This general purpose macro substitution library is used for all macro substitutions in EPICS Base.

Author

William Lupton, W. M. Keck Observatory

Most routines return 0 (OK) on success, -1 (ERROR) on failure, or small positive values for extra info. The macGetValue() and macExpandString() routines depart from this and return information both on success / failure and on value length. Errors and warnings are reported using errlogPrintf().

Core Library

The core library provides a minimal set of basic operations.

long macCreateHandle(MAC_HANDLE **handle, const char *pairs[])

Creates a new macro substitution context.

Parameters:
  • handle – pointer to variable to receive pointer to new macro substitution context

  • pairs – pointer to NULL-terminated array of {name,value} pair strings. A NULL value implies undefined; a NULL pairs argument implies no macros.

Returns:

0 = OK; <0 = ERROR

void macSuppressWarning(MAC_HANDLE *handle, int falseTrue)

Disable or enable warning messages.

The macExpandString() routine prints warnings when it cant expand a macro. This routine can be used to silence those warnings. A non zero value will suppress the warning messages from subsequent library routines given the same handle.

Parameters:
  • handle – opaque handle

  • falseTrue – 0 means issue, 1 means suppress

long macExpandString(MAC_HANDLE *handle, const char *src, char *dest, long capacity)

Expand a string which may contain macro references.

This routine parses the src string looking for macro references and passes any it finds to macGetValue() for translation.

Note

The return value is similar to that of macGetValue(). Its absolute value is the number of characters copied to dest. If the return value is negative, at least one undefined macro was left unexpanded.

Parameters:
  • handle – opaque handle

  • src – source string

  • dest – destination string

  • capacity – capacity of destination buffer (dest)

Returns:

Returns the length of the expanded string, <0 if any macro are undefined

long macPutValue(MAC_HANDLE *handle, const char *name, const char *value)

Sets the value of a specific macro.

Note

If value is NULL, all instances of name are undefined at all scoping levels (the named macro doesn’t have to exist in this case). Macros referenced in value need not be defined at this point.

Parameters:
  • handle – opaque handle

  • name – macro name

  • value – macro value

Returns:

Returns the length of the value string.

long macGetValue(MAC_HANDLE *handle, const char *name, char *value, long capacity)

Returns the value of a macro.

value will be zero-terminated if the length of the value is less than capacity. The return value is the number of characters copied to value (see below for behavior if the macro is undefined). If capacity is zero, no characters will be copied to value (which may be NULL) and the call can be used to check whether the macro is defined.

If the macro is undefined, the macro reference will be returned in the value string (if permitted by maxlen) and the function value will be minus the number of characters copied. Note that treatment of capacity is intended to be consistent with the strncpy() routine.

If the value contains macro references, these references will be expanded recursively. This expansion will detect a direct or indirect self reference.

Macro references begin with a “$” immediately followed by either a “(” or a “{” character. The macro name comes next, and may optionally be succeeded by an “=” and a default value, which will be returned if the named macro is undefined at the moment of expansion. A reference is terminated by the matching “)” or “}” character.

Note

Truncation of the value is not reported, applications should assume that truncation has occurred if the return value is equal to capacity.

Parameters:
  • handle – opaque handle

  • name – macro name or reference

  • value – string to receive macro value or name argument if macro is undefined

  • capacity – capacity of destination buffer (value)

Returns:

Returns the length of the value string, <0 if undefined

long macDeleteHandle(MAC_HANDLE *handle)

Marks a handle invalid, and frees all storage associated with it.

Note

Note that this does not free any strings into which macro values have been returned. Macro values are always returned into strings which were pre-allocated by the caller.

Parameters:

handle – opaque handle

Returns:

0 = OK; <0 = ERROR

long macPushScope(MAC_HANDLE *handle)

Marks the start of a new scoping level.

Marks all macro definitions added after this call as belonging to another scope. These macros will be lost on a macPopScope() call and those at the current scope will be re-instated.

Parameters:

handle – opaque handle

Returns:

0 = OK; <0 = ERROR

long macPopScope(MAC_HANDLE *handle)

Retrieve the last pushed scope (like stack operations)

See macPushScope()

Parameters:

handle – opaque handle

Returns:

0 = OK; <0 = ERROR

long macReportMacros(MAC_HANDLE *handle)

Reports details of current definitions.

Parameters:

handle – opaque handle

Returns:

0 = OK; <0 = ERROR This sends details of current definitions to standard output, and is intended purely for debugging purposes.

Utility Library

These convenience functions are intended for applications to use and provide a more convenient interface for some purposes.

long macParseDefns(MAC_HANDLE *handle, const char *defns, char **pairs[])

Parse macro definitions into an array of {name, value} pairs.

This takes a set of macro definitions in “a=xxx,b=yyy” format and converts them into an array of pointers to character strings which are, in order, “first name”, “first value”, “second name”, “second

value” etc. The array is terminated with two NULL pointers and all storage is allocated contiguously so that it can be freed with a single call to free().

This routine is independent of any handle and provides a generally useful service which may be used elsewhere. Any macro references in values are not expanded at this point since the referenced macros may be defined or redefined before the macro actually has to be translated.

Shell-style escapes and quotes are supported, as are things like “A=B,B=$(C$(A)),CA=CA,CB=CB” (sets B to “CB”). White space is significant within values but ignored elsewhere (i.e. surrounding “=” and “,” characters).

The function returns the number of definitions encountered, or -1 if the supplied string is invalid.

Parameters:
  • handle – opaque handle; may be NULL if debug messages are not required.

  • defns – macro definitions in “a=xxx,b=yyy” format

  • pairs – address of variable to receive pointer to NULL-terminated array of {name, value} pair strings; all storage is allocated contiguously

Returns:

Number of macros found; <0 = ERROR

long macInstallMacros(MAC_HANDLE *handle, char *pairs[])

Install set of {name, value} pairs as definitions.

This takes an array of pairs as defined above and installs them as definitions by calling macPutValue(). The pairs array is terminated by a NULL pointer.

Parameters:
  • handle – opaque handle

  • pairs – pointer to NULL-terminated array of {name,value} pair strings; a NULL value implies undefined; a NULL argument implies no macros

Returns:

Number of macros defined; <0 = ERROR

char *macEnvExpand(const char *str)

Expand environment variables in a string.

This routine expands a string which may contain macros that are environment variables. It parses the string looking for such references and passes them to macGetValue() for translation. It uses malloc() to allocate space for the expanded string and returns a pointer to this null-terminated string. It returns NULL if the source string contains any undefined references.

Parameters:

str – string to be expanded

Returns:

Expanded string; NULL if any undefined macros were used.

char *macDefExpand(const char *str, MAC_HANDLE *macros)

Expands macros and environment variables in a string.

This routine is similar to macEnvExpand() but allows an optional handle to be passed in that may contain additional macro definitions. These macros are appended to the set of macros from environment variables when expanding the string.

Parameters:
  • str – string to be expanded

  • macros – opaque handle; may be NULL if only environment variables are to be used

Returns:

Expanded string; NULL if any undefined macros were used.

Defines

MAC_SIZE

Maximum size of a macro name or value.

struct MAC_HANDLE
#include <macLib.h>

Macro substitution context, for use by macLib routines only.

An application may have multiple active contexts if desired.

Public Members

long magic

magic number (used for authentication)

int dirty

values need expanding from raw values?

int level

scoping level

int debug

debugging level

ELLLIST list

macro name / value list

int flags

operating mode flags