|
11 | 11 | * Portions Copyright (c) 1996-2009, PostgreSQL Global Development Group
|
12 | 12 | * Portions Copyright (c) 1994, Regents of the University of California
|
13 | 13 | *
|
14 |
| - * $PostgreSQL: pgsql/src/include/access/reloptions.h,v 1.7 2009/01/05 17:14:28 alvherre Exp $ |
| 14 | + * $PostgreSQL: pgsql/src/include/access/reloptions.h,v 1.8 2009/01/06 14:47:37 alvherre Exp $ |
15 | 15 | *
|
16 | 16 | *-------------------------------------------------------------------------
|
17 | 17 | */
|
@@ -106,58 +106,86 @@ typedef struct relopt_string
|
106 | 106 | * Most of the time there's no need to call HAVE_RELOPTION manually, but it's
|
107 | 107 | * possible that an amoptions routine needs to walk the array with a different
|
108 | 108 | * purpose (say, to compute the size of a struct to allocate beforehand.)
|
| 109 | + * |
| 110 | + * The last argument in the HANDLE_*_RELOPTION macros allows the caller to |
| 111 | + * determine whether the option was set (true), or its value acquired from |
| 112 | + * defaults (false); it can be passed as (char *) NULL if the caller does not |
| 113 | + * need this information. |
109 | 114 | */
|
110 | 115 | #define HAVE_RELOPTION(optname, option) \
|
111 | 116 | (pg_strncasecmp(option.gen->name, optname, option.gen->namelen) == 0)
|
112 | 117 |
|
113 |
| -#define HANDLE_INT_RELOPTION(optname, var, option) \ |
| 118 | +#define HANDLE_INT_RELOPTION(optname, var, option, wasset) \ |
114 | 119 | do { \
|
115 | 120 | if (HAVE_RELOPTION(optname, option)) \
|
116 | 121 | { \
|
117 | 122 | if (option.isset) \
|
118 | 123 | var = option.values.int_val; \
|
119 | 124 | else \
|
120 | 125 | var = ((relopt_int *) option.gen)->default_val; \
|
| 126 | + (wasset) != NULL ? *(wasset) = option.isset : (dummyret)NULL; \ |
121 | 127 | continue; \
|
122 | 128 | } \
|
123 | 129 | } while (0)
|
124 | 130 |
|
125 |
| -#define HANDLE_BOOL_RELOPTION(optname, var, option) \ |
| 131 | +#define HANDLE_BOOL_RELOPTION(optname, var, option, wasset) \ |
126 | 132 | do { \
|
127 | 133 | if (HAVE_RELOPTION(optname, option)) \
|
128 | 134 | { \
|
129 | 135 | if (option.isset) \
|
130 | 136 | var = option.values.bool_val; \
|
131 | 137 | else \
|
132 | 138 | var = ((relopt_bool *) option.gen)->default_val; \
|
| 139 | + (wasset) != NULL ? *(wasset) = option.isset : (dummyret) NULL; \ |
133 | 140 | continue; \
|
134 | 141 | } \
|
135 | 142 | } while (0)
|
136 | 143 |
|
137 |
| -#define HANDLE_REAL_RELOPTION(optname, var, option) \ |
| 144 | +#define HANDLE_REAL_RELOPTION(optname, var, option, wasset) \ |
138 | 145 | do { \
|
139 | 146 | if (HAVE_RELOPTION(optname, option)) \
|
140 | 147 | { \
|
141 | 148 | if (option.isset) \
|
142 | 149 | var = option.values.real_val; \
|
143 | 150 | else \
|
144 | 151 | var = ((relopt_real *) option.gen)->default_val; \
|
| 152 | + (wasset) != NULL ? *(wasset) = option.isset : (dummyret) NULL; \ |
145 | 153 | continue; \
|
146 | 154 | } \
|
147 | 155 | } while (0)
|
148 | 156 |
|
149 |
| -/* Note that this assumes that the variable is already allocated! */ |
150 |
| -#define HANDLE_STRING_RELOPTION(optname, var, option) \ |
| 157 | +/* |
| 158 | + * Note that this assumes that the variable is already allocated at the tail of |
| 159 | + * reloptions structure (StdRdOptions or other). |
| 160 | + * |
| 161 | + * "base" is a pointer to the reloptions structure, and "offset" is an integer |
| 162 | + * variable that must be initialized to sizeof(reloptions structure). This |
| 163 | + * struct must have been allocated with enough space to hold any string option |
| 164 | + * present, including terminating \0 for every option. SET_VARSIZE() must be |
| 165 | + * called on the struct with this offset as the second argument, after all the |
| 166 | + * string options have been processed. |
| 167 | + */ |
| 168 | +#define HANDLE_STRING_RELOPTION(optname, var, option, base, offset, wasset) \ |
151 | 169 | do { \
|
152 | 170 | if (HAVE_RELOPTION(optname, option)) \
|
153 | 171 | { \
|
154 | 172 | relopt_string *optstring = (relopt_string *) option.gen;\
|
155 |
| - if (optstring->default_isnull) \ |
156 |
| - var[0] = '\0'; \ |
| 173 | + char *string_val = NULL; \ |
| 174 | + \ |
| 175 | + if (option.isset) \ |
| 176 | + string_val = option.values.string_val; \ |
| 177 | + else if (!optstring->default_isnull) \ |
| 178 | + string_val = optstring->default_val; \ |
| 179 | + (wasset) != NULL ? *(wasset) = option.isset : (dummyret) NULL; \ |
| 180 | + \ |
| 181 | + if (!string_val) \ |
| 182 | + var = 0; \ |
157 | 183 | else \
|
158 |
| - strcpy(var, \ |
159 |
| - option.isset ? option.values.string_val : \ |
160 |
| - optstring->default_val); \ |
| 184 | + { \ |
| 185 | + strcpy((char *)(base) + (offset), string_val); \ |
| 186 | + var = (offset); \ |
| 187 | + (offset) += strlen(string_val) + 1; \ |
| 188 | + } \ |
161 | 189 | continue; \
|
162 | 190 | } \
|
163 | 191 | } while (0)
|
|
0 commit comments