* BuildTupleFromCStrings - build a HeapTuple given user data in C string form. * values is an array of C strings, one for each attribute of the return tuple. * A NULL string pointer indicates we want to create a NULL field. */
| 2149 | * A NULL string pointer indicates we want to create a NULL field. |
| 2150 | */ |
| 2151 | HeapTuple |
| 2152 | BuildTupleFromCStrings(AttInMetadata *attinmeta, char **values) |
| 2153 | { |
| 2154 | TupleDesc tupdesc = attinmeta->tupdesc; |
| 2155 | int natts = tupdesc->natts; |
| 2156 | Datum *dvalues; |
| 2157 | bool *nulls; |
| 2158 | int i; |
| 2159 | HeapTuple tuple; |
| 2160 | |
| 2161 | dvalues = (Datum *) palloc(natts * sizeof(Datum)); |
| 2162 | nulls = (bool *) palloc(natts * sizeof(bool)); |
| 2163 | |
| 2164 | /* |
| 2165 | * Call the "in" function for each non-dropped attribute, even for nulls, |
| 2166 | * to support domains. |
| 2167 | */ |
| 2168 | for (i = 0; i < natts; i++) |
| 2169 | { |
| 2170 | if (!TupleDescAttr(tupdesc, i)->attisdropped) |
| 2171 | { |
| 2172 | /* Non-dropped attributes */ |
| 2173 | dvalues[i] = InputFunctionCall(&attinmeta->attinfuncs[i], |
| 2174 | values[i], |
| 2175 | attinmeta->attioparams[i], |
| 2176 | attinmeta->atttypmods[i]); |
| 2177 | if (values[i] != NULL) |
| 2178 | nulls[i] = false; |
| 2179 | else |
| 2180 | nulls[i] = true; |
| 2181 | } |
| 2182 | else |
| 2183 | { |
| 2184 | /* Handle dropped attributes by setting to NULL */ |
| 2185 | dvalues[i] = (Datum) 0; |
| 2186 | nulls[i] = true; |
| 2187 | } |
| 2188 | } |
| 2189 | |
| 2190 | /* |
| 2191 | * Form a tuple |
| 2192 | */ |
| 2193 | tuple = heap_form_tuple(tupdesc, dvalues, nulls); |
| 2194 | |
| 2195 | /* |
| 2196 | * Release locally palloc'd space. XXX would probably be good to pfree |
| 2197 | * values of pass-by-reference datums, as well. |
| 2198 | */ |
| 2199 | pfree(dvalues); |
| 2200 | pfree(nulls); |
| 2201 | |
| 2202 | return tuple; |
| 2203 | } |
| 2204 | |
| 2205 | /* |
| 2206 | * HeapTupleHeaderGetDatum - convert a HeapTupleHeader pointer to a Datum. |