00001 /*------------------------------------------------------------------------- 00002 * 00003 * stringinfo.h 00004 * Declarations/definitions for "StringInfo" functions. 00005 * 00006 * StringInfo provides an indefinitely-extensible string data type. 00007 * It can be used to buffer either ordinary C strings (null-terminated text) 00008 * or arbitrary binary data. All storage is allocated with palloc(). 00009 * 00010 * Portions Copyright (c) 1996-2013, PostgreSQL Global Development Group 00011 * Portions Copyright (c) 1994, Regents of the University of California 00012 * 00013 * src/include/lib/stringinfo.h 00014 * 00015 *------------------------------------------------------------------------- 00016 */ 00017 #ifndef STRINGINFO_H 00018 #define STRINGINFO_H 00019 00020 /*------------------------- 00021 * StringInfoData holds information about an extensible string. 00022 * data is the current buffer for the string (allocated with palloc). 00023 * len is the current string length. There is guaranteed to be 00024 * a terminating '\0' at data[len], although this is not very 00025 * useful when the string holds binary data rather than text. 00026 * maxlen is the allocated size in bytes of 'data', i.e. the maximum 00027 * string size (including the terminating '\0' char) that we can 00028 * currently store in 'data' without having to reallocate 00029 * more space. We must always have maxlen > len. 00030 * cursor is initialized to zero by makeStringInfo or initStringInfo, 00031 * but is not otherwise touched by the stringinfo.c routines. 00032 * Some routines use it to scan through a StringInfo. 00033 *------------------------- 00034 */ 00035 typedef struct StringInfoData 00036 { 00037 char *data; 00038 int len; 00039 int maxlen; 00040 int cursor; 00041 } StringInfoData; 00042 00043 typedef StringInfoData *StringInfo; 00044 00045 00046 /*------------------------ 00047 * There are two ways to create a StringInfo object initially: 00048 * 00049 * StringInfo stringptr = makeStringInfo(); 00050 * Both the StringInfoData and the data buffer are palloc'd. 00051 * 00052 * StringInfoData string; 00053 * initStringInfo(&string); 00054 * The data buffer is palloc'd but the StringInfoData is just local. 00055 * This is the easiest approach for a StringInfo object that will 00056 * only live as long as the current routine. 00057 * 00058 * To destroy a StringInfo, pfree() the data buffer, and then pfree() the 00059 * StringInfoData if it was palloc'd. There's no special support for this. 00060 * 00061 * NOTE: some routines build up a string using StringInfo, and then 00062 * release the StringInfoData but return the data string itself to their 00063 * caller. At that point the data string looks like a plain palloc'd 00064 * string. 00065 *------------------------- 00066 */ 00067 00068 /*------------------------ 00069 * makeStringInfo 00070 * Create an empty 'StringInfoData' & return a pointer to it. 00071 */ 00072 extern StringInfo makeStringInfo(void); 00073 00074 /*------------------------ 00075 * initStringInfo 00076 * Initialize a StringInfoData struct (with previously undefined contents) 00077 * to describe an empty string. 00078 */ 00079 extern void initStringInfo(StringInfo str); 00080 00081 /*------------------------ 00082 * resetStringInfo 00083 * Clears the current content of the StringInfo, if any. The 00084 * StringInfo remains valid. 00085 */ 00086 extern void resetStringInfo(StringInfo str); 00087 00088 /*------------------------ 00089 * appendStringInfo 00090 * Format text data under the control of fmt (an sprintf-style format string) 00091 * and append it to whatever is already in str. More space is allocated 00092 * to str if necessary. This is sort of like a combination of sprintf and 00093 * strcat. 00094 */ 00095 extern void 00096 appendStringInfo(StringInfo str, const char *fmt,...) 00097 /* This extension allows gcc to check the format string */ 00098 __attribute__((format(PG_PRINTF_ATTRIBUTE, 2, 3))); 00099 00100 /*------------------------ 00101 * appendStringInfoVA 00102 * Attempt to format text data under the control of fmt (an sprintf-style 00103 * format string) and append it to whatever is already in str. If successful 00104 * return true; if not (because there's not enough space), return false 00105 * without modifying str. Typically the caller would enlarge str and retry 00106 * on false return --- see appendStringInfo for standard usage pattern. 00107 */ 00108 extern bool 00109 appendStringInfoVA(StringInfo str, const char *fmt, va_list args) 00110 __attribute__((format(PG_PRINTF_ATTRIBUTE, 2, 0))); 00111 00112 /*------------------------ 00113 * appendStringInfoString 00114 * Append a null-terminated string to str. 00115 * Like appendStringInfo(str, "%s", s) but faster. 00116 */ 00117 extern void appendStringInfoString(StringInfo str, const char *s); 00118 00119 /*------------------------ 00120 * appendStringInfoChar 00121 * Append a single byte to str. 00122 * Like appendStringInfo(str, "%c", ch) but much faster. 00123 */ 00124 extern void appendStringInfoChar(StringInfo str, char ch); 00125 00126 /*------------------------ 00127 * appendStringInfoCharMacro 00128 * As above, but a macro for even more speed where it matters. 00129 * Caution: str argument will be evaluated multiple times. 00130 */ 00131 #define appendStringInfoCharMacro(str,ch) \ 00132 (((str)->len + 1 >= (str)->maxlen) ? \ 00133 appendStringInfoChar(str, ch) : \ 00134 (void)((str)->data[(str)->len] = (ch), (str)->data[++(str)->len] = '\0')) 00135 00136 /*------------------------ 00137 * appendStringInfoSpaces 00138 * Append a given number of spaces to str. 00139 */ 00140 extern void appendStringInfoSpaces(StringInfo str, int count); 00141 00142 /*------------------------ 00143 * appendBinaryStringInfo 00144 * Append arbitrary binary data to a StringInfo, allocating more space 00145 * if necessary. 00146 */ 00147 extern void appendBinaryStringInfo(StringInfo str, 00148 const char *data, int datalen); 00149 00150 /*------------------------ 00151 * enlargeStringInfo 00152 * Make sure a StringInfo's buffer can hold at least 'needed' more bytes. 00153 */ 00154 extern void enlargeStringInfo(StringInfo str, int needed); 00155 00156 #endif /* STRINGINFO_H */