MobilityDB 1.3
Loading...
Searching...
No Matches
postgres.h
Go to the documentation of this file.
1/*-------------------------------------------------------------------------
2 *
3 * postgres.h
4 * Primary include file for PostgreSQL server .c files
5 *
6 * This should be the first file included by PostgreSQL backend modules.
7 * Client-side code should include postgres_fe.h instead.
8 *
9 *
10 * Portions Copyright (c) 1996-2021, PostgreSQL Global Development Group
11 * Portions Copyright (c) 1995, Regents of the University of California
12 *
13 * src/include/postgres.h
14 *
15 *-------------------------------------------------------------------------
16 */
17/*
18 *----------------------------------------------------------------
19 * TABLE OF CONTENTS
20 *
21 * When adding stuff to this file, please try to put stuff
22 * into the relevant section, or add new sections as appropriate.
23 *
24 * section description
25 * ------- ------------------------------------------------
26 * 1) variable-length datatypes (TOAST support)
27 * 2) Datum type + support macros
28 *
29 * NOTES
30 *
31 * In general, this file should contain declarations that are widely needed
32 * in the backend environment, but are of no interest outside the backend.
33 *
34 * Simple type definitions live in c.h, where they are shared with
35 * postgres_fe.h. We do that since those type definitions are needed by
36 * frontend modules that want to deal with binary data transmission to or
37 * from the backend. Type definitions in this file should be for
38 * representations that never escape the backend, such as Datum or
39 * TOASTed varlena objects.
40 *
41 *----------------------------------------------------------------
42 */
43#ifndef POSTGRES_H
44#define POSTGRES_H
45
46#include "c.h"
47
48/*
49 * MEOS: redefining elog
50 * If WIN32 is set ERROR is defined in wingdi.h as #define ERROR 0
51 * and is imported through windows.h. Since in MEOS we do not use ERROR
52 * but keep it so elog(ERROR, "xxx") can be both used in MEOS and in PostgreSQL
53 * as soon as it is defined everything works fine.
54 */
55#define INFO 17 /* Messages specifically requested by user (eg
56 * VACUUM VERBOSE output); always sent to
57 * client regardless of client_min_messages,
58 * but by default not sent to server log. */
59#define NOTICE 18 /* Helpful messages to users about query
60 * operation; sent to client and not to server
61 * log by default. */
62#define WARNING 19 /* Warnings. NOTICE is for expected messages
63 * like implicit sequence creation by SERIAL.
64 * WARNING is for unexpected messages. */
65#ifndef ERROR
66#define ERROR 21 /* user error - abort transaction; return to known state */
67#endif
68#define EXIT_FAILURE 1
70/* MEOS: redefining palloc0, palloc, and pfree */
71#if MEOS
72#define palloc0(X) (calloc(1, X))
73#define palloc malloc
74#define repalloc realloc
75#define pfree free
76#define pstrdup strdup
77#endif /* MEOS */
78
79/* ----------------------------------------------------------------
80 * Section 1: variable-length datatypes (TOAST support)
81 * ----------------------------------------------------------------
82 */
83
84/*
85 * struct varatt_external is a traditional "TOAST pointer", that is, the
86 * information needed to fetch a Datum stored out-of-line in a TOAST table.
87 * The data is compressed if and only if the external size stored in
88 * va_extinfo is less than va_rawsize - VARHDRSZ.
89 *
90 * This struct must not contain any padding, because we sometimes compare
91 * these pointers using memcmp.
92 *
93 * Note that this information is stored unaligned within actual tuples, so
94 * you need to memcpy from the tuple into a local struct variable before
95 * you can look at these fields! (The reason we use memcmp is to avoid
96 * having to do that just to detect equality of two TOAST pointers...)
97 */
98typedef struct varatt_external
99{
100 int32 va_rawsize; /* Original data size (includes header) */
101 uint32 va_extinfo; /* External saved size (without header) and
102 * compression method */
103 Oid va_valueid; /* Unique ID of value within TOAST table */
104 Oid va_toastrelid; /* RelID of TOAST table containing it */
106
107/*
108 * These macros define the "saved size" portion of va_extinfo. Its remaining
109 * two high-order bits identify the compression method.
110 */
111#define VARLENA_EXTSIZE_BITS 30
112#define VARLENA_EXTSIZE_MASK ((1U << VARLENA_EXTSIZE_BITS) - 1)
113
114/*
115 * struct varatt_indirect is a "TOAST pointer" representing an out-of-line
116 * Datum that's stored in memory, not in an external toast relation.
117 * The creator of such a Datum is entirely responsible that the referenced
118 * storage survives for as long as referencing pointer Datums can exist.
120 * Note that just as for struct varatt_external, this struct is stored
121 * unaligned within any containing tuple.
122 */
123typedef struct varatt_indirect
124{
125 struct varlena *pointer; /* Pointer to in-memory varlena */
127
128/*
129 * struct varatt_expanded is a "TOAST pointer" representing an out-of-line
130 * Datum that is stored in memory, in some type-specific, not necessarily
131 * physically contiguous format that is convenient for computation not
132 * storage. APIs for this, in particular the definition of struct
133 * ExpandedObjectHeader, are in src/include/utils/expandeddatum.h.
134 *
135 * Note that just as for struct varatt_external, this struct is stored
136 * unaligned within any containing tuple.
137 */
139
140typedef struct varatt_expanded
141{
144
146 * Type tag for the various sorts of "TOAST pointer" datums. The peculiar
147 * value for VARTAG_ONDISK comes from a requirement for on-disk compatibility
148 * with a previous notion that the tag field was the pointer datum's length.
149 */
150typedef enum vartag_external
151{
157
158/* this test relies on the specific tag values above */
159#define VARTAG_IS_EXPANDED(tag) \
160 (((tag) & ~1) == VARTAG_EXPANDED_RO)
161
162#define VARTAG_SIZE(tag) \
163 ((tag) == VARTAG_INDIRECT ? sizeof(varatt_indirect) : \
164 VARTAG_IS_EXPANDED(tag) ? sizeof(varatt_expanded) : \
165 (tag) == VARTAG_ONDISK ? sizeof(varatt_external) : \
166 TrapMacro(true, "unrecognized TOAST vartag"))
167
168/*
169 * These structs describe the header of a varlena object that may have been
170 * TOASTed. Generally, don't reference these structs directly, but use the
171 * macros below.
172 *
173 * We use separate structs for the aligned and unaligned cases because the
174 * compiler might otherwise think it could generate code that assumes
175 * alignment while touching fields of a 1-byte-header varlena.
176 */
177typedef union
178{
179 struct /* Normal varlena (4-byte length) */
181 uint32 va_header;
182 char va_data[FLEXIBLE_ARRAY_MEMBER];
183 } va_4byte;
184 struct /* Compressed-in-line format */
185 {
186 uint32 va_header;
187 uint32 va_tcinfo; /* Original data size (excludes header) and
188 * compression method; see va_extinfo */
189 char va_data[FLEXIBLE_ARRAY_MEMBER]; /* Compressed data */
190 } va_compressed;
192
193typedef struct
194{
196 char va_data[FLEXIBLE_ARRAY_MEMBER]; /* Data begins here */
198
199/* TOAST pointers are a subset of varattrib_1b with an identifying tag byte */
200typedef struct
201{
202 uint8 va_header; /* Always 0x80 or 0x01 */
203 uint8 va_tag; /* Type of datum */
204 char va_data[FLEXIBLE_ARRAY_MEMBER]; /* Type-specific data */
206
207/*
208 * Bit layouts for varlena headers on big-endian machines:
209 *
210 * 00xxxxxx 4-byte length word, aligned, uncompressed data (up to 1G)
211 * 01xxxxxx 4-byte length word, aligned, *compressed* data (up to 1G)
212 * 10000000 1-byte length word, unaligned, TOAST pointer
213 * 1xxxxxxx 1-byte length word, unaligned, uncompressed data (up to 126b)
214 *
215 * Bit layouts for varlena headers on little-endian machines:
216 *
217 * xxxxxx00 4-byte length word, aligned, uncompressed data (up to 1G)
218 * xxxxxx10 4-byte length word, aligned, *compressed* data (up to 1G)
219 * 00000001 1-byte length word, unaligned, TOAST pointer
220 * xxxxxxx1 1-byte length word, unaligned, uncompressed data (up to 126b)
221 *
222 * The "xxx" bits are the length field (which includes itself in all cases).
223 * In the big-endian case we mask to extract the length, in the little-endian
224 * case we shift. Note that in both cases the flag bits are in the physically
225 * first byte. Also, it is not possible for a 1-byte length word to be zero;
226 * this lets us disambiguate alignment padding bytes from the start of an
227 * unaligned datum. (We now *require* pad bytes to be filled with zero!)
228 *
229 * In TOAST pointers the va_tag field (see varattrib_1b_e) is used to discern
230 * the specific type and length of the pointer datum.
231 */
232
233/*
234 * Endian-dependent macros. These are considered internal --- use the
235 * external macros below instead of using these directly.
236 *
237 * Note: IS_1B is true for external toast records but VARSIZE_1B will return 0
238 * for such records. Hence you should usually check for IS_EXTERNAL before
239 * checking for IS_1B.
240 */
241
242#ifdef WORDS_BIGENDIAN
243
244#define VARATT_IS_4B(PTR) \
245 ((((varattrib_1b *) (PTR))->va_header & 0x80) == 0x00)
246#define VARATT_IS_4B_U(PTR) \
247 ((((varattrib_1b *) (PTR))->va_header & 0xC0) == 0x00)
248#define VARATT_IS_4B_C(PTR) \
249 ((((varattrib_1b *) (PTR))->va_header & 0xC0) == 0x40)
250#define VARATT_IS_1B(PTR) \
251 ((((varattrib_1b *) (PTR))->va_header & 0x80) == 0x80)
252#define VARATT_IS_1B_E(PTR) \
253 ((((varattrib_1b *) (PTR))->va_header) == 0x80)
254#define VARATT_NOT_PAD_BYTE(PTR) \
255 (*((uint8 *) (PTR)) != 0)
256
257/* VARSIZE_4B() should only be used on known-aligned data */
258#define VARSIZE_4B(PTR) \
259 (((varattrib_4b *) (PTR))->va_4byte.va_header & 0x3FFFFFFF)
260#define VARSIZE_1B(PTR) \
261 (((varattrib_1b *) (PTR))->va_header & 0x7F)
262#define VARTAG_1B_E(PTR) \
263 (((varattrib_1b_e *) (PTR))->va_tag)
264
265#define SET_VARSIZE_4B(PTR,len) \
266 (((varattrib_4b *) (PTR))->va_4byte.va_header = (len) & 0x3FFFFFFF)
267#define SET_VARSIZE_4B_C(PTR,len) \
268 (((varattrib_4b *) (PTR))->va_4byte.va_header = ((len) & 0x3FFFFFFF) | 0x40000000)
269#define SET_VARSIZE_1B(PTR,len) \
270 (((varattrib_1b *) (PTR))->va_header = (len) | 0x80)
271#define SET_VARTAG_1B_E(PTR,tag) \
272 (((varattrib_1b_e *) (PTR))->va_header = 0x80, \
273 ((varattrib_1b_e *) (PTR))->va_tag = (tag))
275#else /* !WORDS_BIGENDIAN */
277#define VARATT_IS_4B(PTR) \
278 ((((varattrib_1b *) (PTR))->va_header & 0x01) == 0x00)
279#define VARATT_IS_4B_U(PTR) \
280 ((((varattrib_1b *) (PTR))->va_header & 0x03) == 0x00)
281#define VARATT_IS_4B_C(PTR) \
282 ((((varattrib_1b *) (PTR))->va_header & 0x03) == 0x02)
283#define VARATT_IS_1B(PTR) \
284 ((((varattrib_1b *) (PTR))->va_header & 0x01) == 0x01)
285#define VARATT_IS_1B_E(PTR) \
286 ((((varattrib_1b *) (PTR))->va_header) == 0x01)
287#define VARATT_NOT_PAD_BYTE(PTR) \
288 (*((uint8 *) (PTR)) != 0)
289
290/* VARSIZE_4B() should only be used on known-aligned data */
291#define VARSIZE_4B(PTR) \
292 ((((varattrib_4b *) (PTR))->va_4byte.va_header >> 2) & 0x3FFFFFFF)
293#define VARSIZE_1B(PTR) \
294 ((((varattrib_1b *) (PTR))->va_header >> 1) & 0x7F)
295#define VARTAG_1B_E(PTR) \
296 (((varattrib_1b_e *) (PTR))->va_tag)
298#define SET_VARSIZE_4B(PTR,len) \
299 (((varattrib_4b *) (PTR))->va_4byte.va_header = (((uint32) (len)) << 2))
300#define SET_VARSIZE_4B_C(PTR,len) \
301 (((varattrib_4b *) (PTR))->va_4byte.va_header = (((uint32) (len)) << 2) | 0x02)
302#define SET_VARSIZE_1B(PTR,len) \
303 (((varattrib_1b *) (PTR))->va_header = (((uint8) (len)) << 1) | 0x01)
304#define SET_VARTAG_1B_E(PTR,tag) \
305 (((varattrib_1b_e *) (PTR))->va_header = 0x01, \
306 ((varattrib_1b_e *) (PTR))->va_tag = (tag))
307
308#endif /* WORDS_BIGENDIAN */
309
310#define VARDATA_4B(PTR) (((varattrib_4b *) (PTR))->va_4byte.va_data)
311#define VARDATA_4B_C(PTR) (((varattrib_4b *) (PTR))->va_compressed.va_data)
312#define VARDATA_1B(PTR) (((varattrib_1b *) (PTR))->va_data)
313#define VARDATA_1B_E(PTR) (((varattrib_1b_e *) (PTR))->va_data)
315/*
316 * Externally visible TOAST macros begin here.
317 */
318
319#define VARHDRSZ_EXTERNAL offsetof(varattrib_1b_e, va_data)
320#define VARHDRSZ_COMPRESSED offsetof(varattrib_4b, va_compressed.va_data)
321#define VARHDRSZ_SHORT offsetof(varattrib_1b, va_data)
322
323#define VARATT_SHORT_MAX 0x7F
324#define VARATT_CAN_MAKE_SHORT(PTR) \
325 (VARATT_IS_4B_U(PTR) && \
326 (VARSIZE(PTR) - VARHDRSZ + VARHDRSZ_SHORT) <= VARATT_SHORT_MAX)
327#define VARATT_CONVERTED_SHORT_SIZE(PTR) \
328 (VARSIZE(PTR) - VARHDRSZ + VARHDRSZ_SHORT)
329
330/*
331 * In consumers oblivious to data alignment, call PG_DETOAST_DATUM_PACKED(),
332 * VARDATA_ANY(), VARSIZE_ANY() and VARSIZE_ANY_EXHDR(). Elsewhere, call
333 * PG_DETOAST_DATUM(), VARDATA() and VARSIZE(). Directly fetching an int16,
334 * int32 or wider field in the struct representing the datum layout requires
335 * aligned data. memcpy() is alignment-oblivious, as are most operations on
336 * datatypes, such as text, whose layout struct contains only char fields.
338 * Code assembling a new datum should call VARDATA() and SET_VARSIZE().
339 * (Datums begin life untoasted.)
341 * Other macros here should usually be used only by tuple assembly/disassembly
342 * code and code that specifically wants to work with still-toasted Datums.
343 */
344#define VARDATA(PTR) VARDATA_4B(PTR)
345#define VARSIZE(PTR) VARSIZE_4B(PTR)
346
347#define VARSIZE_SHORT(PTR) VARSIZE_1B(PTR)
348#define VARDATA_SHORT(PTR) VARDATA_1B(PTR)
350#define VARTAG_EXTERNAL(PTR) VARTAG_1B_E(PTR)
351#define VARSIZE_EXTERNAL(PTR) (VARHDRSZ_EXTERNAL + VARTAG_SIZE(VARTAG_EXTERNAL(PTR)))
352#define VARDATA_EXTERNAL(PTR) VARDATA_1B_E(PTR)
354#define VARATT_IS_COMPRESSED(PTR) VARATT_IS_4B_C(PTR)
355#define VARATT_IS_EXTERNAL(PTR) VARATT_IS_1B_E(PTR)
356#define VARATT_IS_EXTERNAL_ONDISK(PTR) \
357 (VARATT_IS_EXTERNAL(PTR) && VARTAG_EXTERNAL(PTR) == VARTAG_ONDISK)
358#define VARATT_IS_EXTERNAL_INDIRECT(PTR) \
359 (VARATT_IS_EXTERNAL(PTR) && VARTAG_EXTERNAL(PTR) == VARTAG_INDIRECT)
360#define VARATT_IS_EXTERNAL_EXPANDED_RO(PTR) \
361 (VARATT_IS_EXTERNAL(PTR) && VARTAG_EXTERNAL(PTR) == VARTAG_EXPANDED_RO)
362#define VARATT_IS_EXTERNAL_EXPANDED_RW(PTR) \
363 (VARATT_IS_EXTERNAL(PTR) && VARTAG_EXTERNAL(PTR) == VARTAG_EXPANDED_RW)
364#define VARATT_IS_EXTERNAL_EXPANDED(PTR) \
365 (VARATT_IS_EXTERNAL(PTR) && VARTAG_IS_EXPANDED(VARTAG_EXTERNAL(PTR)))
366#define VARATT_IS_EXTERNAL_NON_EXPANDED(PTR) \
367 (VARATT_IS_EXTERNAL(PTR) && !VARTAG_IS_EXPANDED(VARTAG_EXTERNAL(PTR)))
368#define VARATT_IS_SHORT(PTR) VARATT_IS_1B(PTR)
369#define VARATT_IS_EXTENDED(PTR) (!VARATT_IS_4B_U(PTR))
371#define SET_VARSIZE(PTR, len) SET_VARSIZE_4B(PTR, len)
372#define SET_VARSIZE_SHORT(PTR, len) SET_VARSIZE_1B(PTR, len)
373#define SET_VARSIZE_COMPRESSED(PTR, len) SET_VARSIZE_4B_C(PTR, len)
374
375#define SET_VARTAG_EXTERNAL(PTR, tag) SET_VARTAG_1B_E(PTR, tag)
377#define VARSIZE_ANY(PTR) \
378 (VARATT_IS_1B_E(PTR) ? VARSIZE_EXTERNAL(PTR) : \
379 (VARATT_IS_1B(PTR) ? VARSIZE_1B(PTR) : \
380 VARSIZE_4B(PTR)))
381
382/* Size of a varlena data, excluding header */
383#define VARSIZE_ANY_EXHDR(PTR) \
384 (VARATT_IS_1B_E(PTR) ? VARSIZE_EXTERNAL(PTR)-VARHDRSZ_EXTERNAL : \
385 (VARATT_IS_1B(PTR) ? VARSIZE_1B(PTR)-VARHDRSZ_SHORT : \
386 VARSIZE_4B(PTR)-VARHDRSZ))
388/* caution: this will not work on an external or compressed-in-line Datum */
389/* caution: this will return a possibly unaligned pointer */
390#define VARDATA_ANY(PTR) \
391 (VARATT_IS_1B(PTR) ? VARDATA_1B(PTR) : VARDATA_4B(PTR))
392
393/* Decompressed size and compression method of a compressed-in-line Datum */
394#define VARDATA_COMPRESSED_GET_EXTSIZE(PTR) \
395 (((varattrib_4b *) (PTR))->va_compressed.va_tcinfo & VARLENA_EXTSIZE_MASK)
396#define VARDATA_COMPRESSED_GET_COMPRESS_METHOD(PTR) \
397 (((varattrib_4b *) (PTR))->va_compressed.va_tcinfo >> VARLENA_EXTSIZE_BITS)
399/* Same for external Datums; but note argument is a struct varatt_external */
400#define VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer) \
401 ((toast_pointer).va_extinfo & VARLENA_EXTSIZE_MASK)
402#define VARATT_EXTERNAL_GET_COMPRESS_METHOD(toast_pointer) \
403 ((toast_pointer).va_extinfo >> VARLENA_EXTSIZE_BITS)
404
405#define VARATT_EXTERNAL_SET_SIZE_AND_COMPRESS_METHOD(toast_pointer, len, cm) \
406 do { \
407 Assert((cm) == TOAST_PGLZ_COMPRESSION_ID || \
408 (cm) == TOAST_LZ4_COMPRESSION_ID); \
409 ((toast_pointer).va_extinfo = \
410 (len) | ((uint32) (cm) << VARLENA_EXTSIZE_BITS)); \
411 } while (0)
412
414 * Testing whether an externally-stored value is compressed now requires
415 * comparing size stored in va_extinfo (the actual length of the external data)
416 * to rawsize (the original uncompressed datum's size). The latter includes
417 * VARHDRSZ overhead, the former doesn't. We never use compression unless it
418 * actually saves space, so we expect either equality or less-than.
419 */
420#define VARATT_EXTERNAL_IS_COMPRESSED(toast_pointer) \
421 (VARATT_EXTERNAL_GET_EXTSIZE(toast_pointer) < \
422 (toast_pointer).va_rawsize - VARHDRSZ)
423
424
425/* ----------------------------------------------------------------
426 * Section 2: Datum type + support macros
427 * ----------------------------------------------------------------
428 */
429
430/*
431 * A Datum contains either a value of a pass-by-value type or a pointer to a
432 * value of a pass-by-reference type. Therefore, we require:
434 * sizeof(Datum) == sizeof(void *) == 4 or 8
435 *
436 * The macros below and the analogous macros for other types should be used to
437 * convert between a Datum and the appropriate C type.
438 */
439
440typedef uintptr_t Datum;
442/*
443 * A NullableDatum is used in places where both a Datum and its nullness needs
444 * to be stored. This can be more efficient than storing datums and nullness
445 * in separate arrays, due to better spatial locality, even if more space may
446 * be wasted due to padding.
447 */
448typedef struct NullableDatum
449{
450#define FIELDNO_NULLABLE_DATUM_DATUM 0
451 Datum value;
452#define FIELDNO_NULLABLE_DATUM_ISNULL 1
453 bool isnull;
454 /* due to alignment padding this could be used for flags for free */
456
457#define SIZEOF_DATUM SIZEOF_VOID_P
458
460 * DatumGetBool
461 * Returns boolean value of a datum.
462 *
463 * Note: any nonzero value will be considered true.
464 */
465
466#define DatumGetBool(X) ((bool) ((X) != 0))
467
469 * BoolGetDatum
470 * Returns datum representation for a boolean.
471 *
472 * Note: any nonzero value will be considered true.
473 */
474
475#define BoolGetDatum(X) ((Datum) ((X) ? 1 : 0))
476
477/*
478 * DatumGetChar
479 * Returns character value of a datum.
480 */
481
482#define DatumGetChar(X) ((char) (X))
483
484/*
485 * CharGetDatum
486 * Returns datum representation for a character.
487 */
488
489#define CharGetDatum(X) ((Datum) (X))
490
491/*
492 * Int8GetDatum
493 * Returns datum representation for an 8-bit integer.
494 */
495
496#define Int8GetDatum(X) ((Datum) (X))
497
498/*
499 * DatumGetUInt8
500 * Returns 8-bit unsigned integer value of a datum.
501 */
502
503#define DatumGetUInt8(X) ((uint8) (X))
504
505/*
506 * UInt8GetDatum
507 * Returns datum representation for an 8-bit unsigned integer.
508 */
509
510#define UInt8GetDatum(X) ((Datum) (X))
511
512/*
513 * DatumGetInt16
514 * Returns 16-bit integer value of a datum.
515 */
516
517#define DatumGetInt16(X) ((int16) (X))
518
519/*
520 * Int16GetDatum
521 * Returns datum representation for a 16-bit integer.
522 */
523
524#define Int16GetDatum(X) ((Datum) (X))
525
526/*
527 * DatumGetUInt16
528 * Returns 16-bit unsigned integer value of a datum.
529 */
530
531#define DatumGetUInt16(X) ((uint16) (X))
532
533/*
534 * UInt16GetDatum
535 * Returns datum representation for a 16-bit unsigned integer.
536 */
537
538#define UInt16GetDatum(X) ((Datum) (X))
539
540/*
541 * DatumGetInt32
542 * Returns 32-bit integer value of a datum.
543 */
544
545#define DatumGetInt32(X) ((int32) (X))
546
547/*
548 * Int32GetDatum
549 * Returns datum representation for a 32-bit integer.
550 */
551
552#define Int32GetDatum(X) ((Datum) (X))
553
554/*
555 * DatumGetUInt32
556 * Returns 32-bit unsigned integer value of a datum.
557 */
558
559#define DatumGetUInt32(X) ((uint32) (X))
560
561/*
562 * UInt32GetDatum
563 * Returns datum representation for a 32-bit unsigned integer.
564 */
565
566#define UInt32GetDatum(X) ((Datum) (X))
567
568/*
569 * DatumGetObjectId
570 * Returns object identifier value of a datum.
571 */
572
573#define DatumGetObjectId(X) ((Oid) (X))
574
575/*
576 * ObjectIdGetDatum
577 * Returns datum representation for an object identifier.
578 */
579
580#define ObjectIdGetDatum(X) ((Datum) (X))
581
582/*
583 * DatumGetTransactionId
584 * Returns transaction identifier value of a datum.
585 */
586
587#define DatumGetTransactionId(X) ((TransactionId) (X))
588
589/*
590 * TransactionIdGetDatum
591 * Returns datum representation for a transaction identifier.
592 */
593
594#define TransactionIdGetDatum(X) ((Datum) (X))
595
596/*
597 * MultiXactIdGetDatum
598 * Returns datum representation for a multixact identifier.
599 */
600
601#define MultiXactIdGetDatum(X) ((Datum) (X))
602
603/*
604 * DatumGetCommandId
605 * Returns command identifier value of a datum.
606 */
607
608#define DatumGetCommandId(X) ((CommandId) (X))
609
610/*
611 * CommandIdGetDatum
612 * Returns datum representation for a command identifier.
613 */
614
615#define CommandIdGetDatum(X) ((Datum) (X))
616
617/*
618 * DatumGetPointer
619 * Returns pointer value of a datum.
620 */
621
622#define DatumGetPointer(X) ((Pointer) (X))
623
624/*
625 * PointerGetDatum
626 * Returns datum representation for a pointer.
627 */
628
629#define PointerGetDatum(X) ((Datum) (X))
630
631/*
632 * DatumGetCString
633 * Returns C string (null-terminated string) value of a datum.
634 *
635 * Note: C string is not a full-fledged Postgres type at present,
636 * but type input functions use this conversion for their inputs.
637 */
638
639#define DatumGetCString(X) ((char *) DatumGetPointer(X))
640
641/*
642 * CStringGetDatum
643 * Returns datum representation for a C string (null-terminated string).
645 * Note: C string is not a full-fledged Postgres type at present,
646 * but type output functions use this conversion for their outputs.
647 * Note: CString is pass-by-reference; caller must ensure the pointed-to
648 * value has adequate lifetime.
649 */
650
651#define CStringGetDatum(X) PointerGetDatum(X)
652
653/*
654 * DatumGetName
655 * Returns name value of a datum.
656 */
657
658#define DatumGetName(X) ((Name) DatumGetPointer(X))
659
660/*
661 * NameGetDatum
662 * Returns datum representation for a name.
663 *
664 * Note: Name is pass-by-reference; caller must ensure the pointed-to
665 * value has adequate lifetime.
666 */
667
668#define NameGetDatum(X) CStringGetDatum(NameStr(*(X)))
669
670/*
671 * DatumGetInt64
672 * Returns 64-bit integer value of a datum.
674 * Note: this macro hides whether int64 is pass by value or by reference.
675 */
676
677#ifdef USE_FLOAT8_BYVAL
678#define DatumGetInt64(X) ((int64) (X))
679#else
680#define DatumGetInt64(X) (* ((int64 *) DatumGetPointer(X)))
681#endif
682
683/*
684 * Int64GetDatum
685 * Returns datum representation for a 64-bit integer.
686 *
687 * Note: if int64 is pass by reference, this function returns a reference
688 * to palloc'd space.
689 */
690
691#ifdef USE_FLOAT8_BYVAL
692#define Int64GetDatum(X) ((Datum) (X))
693#else
694extern Datum Int64GetDatum(int64 X);
695#endif
696
697/*
698 * DatumGetUInt64
699 * Returns 64-bit unsigned integer value of a datum.
701 * Note: this macro hides whether int64 is pass by value or by reference.
702 */
703
704#ifdef USE_FLOAT8_BYVAL
705#define DatumGetUInt64(X) ((uint64) (X))
706#else
707#define DatumGetUInt64(X) (* ((uint64 *) DatumGetPointer(X)))
708#endif
709
710/*
711 * UInt64GetDatum
712 * Returns datum representation for a 64-bit unsigned integer.
713 *
714 * Note: if int64 is pass by reference, this function returns a reference
715 * to palloc'd space.
716 */
717
718#ifdef USE_FLOAT8_BYVAL
719#define UInt64GetDatum(X) ((Datum) (X))
720#else
721#define UInt64GetDatum(X) Int64GetDatum((int64) (X))
722#endif
723
724/*
725 * Float <-> Datum conversions
726 *
727 * These have to be implemented as inline functions rather than macros, when
728 * passing by value, because many machines pass int and float function
729 * parameters/results differently; so we need to play weird games with unions.
730 */
731
732/*
733 * DatumGetFloat4
734 * Returns 4-byte floating point value of a datum.
735 */
736static inline float4
738{
739 union
740 {
741 int32 value;
742 float4 retval;
743 } myunion;
744
745 myunion.value = DatumGetInt32(X);
746 return myunion.retval;
748
749/*
750 * Float4GetDatum
751 * Returns datum representation for a 4-byte floating point number.
752 */
753static inline Datum
755{
756 union
757 {
758 float4 value;
759 int32 retval;
760 } myunion;
761
762 myunion.value = X;
763 return Int32GetDatum(myunion.retval);
764}
765
766/*
767 * DatumGetFloat8
768 * Returns 8-byte floating point value of a datum.
769 *
770 * Note: this macro hides whether float8 is pass by value or by reference.
771 */
772
773#ifdef USE_FLOAT8_BYVAL
774static inline float8
776{
777 union
778 {
779 int64 value;
780 float8 retval;
781 } myunion;
782
783 myunion.value = DatumGetInt64(X);
784 return myunion.retval;
785}
786#else
787#define DatumGetFloat8(X) (* ((float8 *) DatumGetPointer(X)))
788#endif
789
790/*
791 * Float8GetDatum
792 * Returns datum representation for an 8-byte floating point number.
793 *
794 * Note: if float8 is pass by reference, this function returns a reference
795 * to palloc'd space.
796 */
797
798#ifdef USE_FLOAT8_BYVAL
799static inline Datum
801{
802 union
803 {
804 float8 value;
805 int64 retval;
806 } myunion;
807
808 myunion.value = X;
809 return Int64GetDatum(myunion.retval);
810}
811#else
812extern Datum Float8GetDatum(float8 X);
813#endif
814
815
816/*
817 * Int64GetDatumFast
818 * Float8GetDatumFast
819 *
820 * These macros are intended to allow writing code that does not depend on
821 * whether int64 and float8 are pass-by-reference types, while not
822 * sacrificing performance when they are. The argument must be a variable
823 * that will exist and have the same value for as long as the Datum is needed.
824 * In the pass-by-ref case, the address of the variable is taken to use as
825 * the Datum. In the pass-by-val case, these will be the same as the non-Fast
826 * macros.
827 */
828
829#ifdef USE_FLOAT8_BYVAL
830#define Int64GetDatumFast(X) Int64GetDatum(X)
831#define Float8GetDatumFast(X) Float8GetDatum(X)
832#else
833#define Int64GetDatumFast(X) PointerGetDatum(&(X))
834#define Float8GetDatumFast(X) PointerGetDatum(&(X))
835#endif
836
837#endif /* POSTGRES_H */
double float8
Definition: c.h:581
#define FLEXIBLE_ARRAY_MEMBER
Definition: c.h:362
float float4
Definition: c.h:580
static Datum Float4GetDatum(float4 X)
Definition: postgres.h:747
uintptr_t Datum
Definition: postgres.h:433
static float4 DatumGetFloat4(Datum X)
Definition: postgres.h:730
Datum Int64GetDatum(int64 X)
Datum Float8GetDatum(float8 X)
struct ExpandedObjectHeader ExpandedObjectHeader
Definition: postgres.h:131
#define DatumGetFloat8(X)
Definition: postgres.h:780
#define DatumGetInt32(X)
Definition: postgres.h:538
#define Int32GetDatum(X)
Definition: postgres.h:545
vartag_external
Definition: postgres.h:144
@ VARTAG_ONDISK
Definition: postgres.h:148
@ VARTAG_EXPANDED_RW
Definition: postgres.h:147
@ VARTAG_INDIRECT
Definition: postgres.h:145
@ VARTAG_EXPANDED_RO
Definition: postgres.h:146
#define DatumGetInt64(X)
Definition: postgres.h:673
unsigned int Oid
Definition: postgres_ext.h:31
unsigned int uint32
Definition: postgres_ext_defs.in.h:16
uintptr_t Datum
Definition: postgres_ext_defs.in.h:7
signed int int32
Definition: postgres_ext_defs.in.h:11
unsigned char uint8
Definition: postgres_ext_defs.in.h:14
long int int64
Definition: postgres_ext_defs.in.h:12
Datum value
Definition: postgres.h:444
bool isnull
Definition: postgres.h:446
Definition: postgres.h:442
ExpandedObjectHeader * eohptr
Definition: postgres.h:135
Definition: postgres.h:134
uint32 va_extinfo
Definition: postgres.h:94
int32 va_rawsize
Definition: postgres.h:93
Oid va_valueid
Definition: postgres.h:96
Oid va_toastrelid
Definition: postgres.h:97
Definition: postgres.h:92
struct varlena * pointer
Definition: postgres.h:118
Definition: postgres.h:117
uint8 va_header
Definition: postgres.h:195
Definition: postgres.h:194
Definition: postgres.h:187
Definition: postgres_ext_defs.in.h:34
Definition: postgres.h:171