PostgreSQL Source Code git master
Loading...
Searching...
No Matches
tupmacs.h File Reference
#include "catalog/pg_type_d.h"
#include "port/pg_bitutils.h"
#include "port/pg_bswap.h"
#include "varatt.h"
Include dependency graph for tupmacs.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Macros

#define SPREAD_BITS_MULTIPLIER_32   0x204081U
 
#define fetchatt(A, T)   fetch_att(T, (A)->attbyval, (A)->attlen)
 
#define att_align_datum(cur_offset, attalign, attlen, attdatum)
 
#define att_datum_alignby(cur_offset, attalignby, attlen, attdatum)
 
#define att_align_pointer(cur_offset, attalign, attlen, attptr)
 
#define att_pointer_alignby(cur_offset, attalignby, attlen, attptr)
 
#define att_align_nominal(cur_offset, attalign)    att_nominal_alignby(cur_offset, typalign_to_alignby(attalign))
 
#define att_nominal_alignby(cur_offset, attalignby)    TYPEALIGN(attalignby, cur_offset)
 
#define att_addlength_datum(cur_offset, attlen, attdatum)    att_addlength_pointer(cur_offset, attlen, DatumGetPointer(attdatum))
 
#define att_addlength_pointer(cur_offset, attlen, attptr)
 

Functions

static bool att_isnull (int ATT, const bits8 *BITS)
 
static void populate_isnull_array (const bits8 *bits, int natts, bool *isnull)
 
static Datum fetch_att (const void *T, bool attbyval, int attlen)
 
static Datum fetch_att_noerr (const void *T, bool attbyval, int attlen)
 
static Datum align_fetch_then_add (const char *tupptr, uint32 *off, bool attbyval, int attlen, uint8 attalignby)
 
static int first_null_attr (const bits8 *bits, int natts)
 
static uint8 typalign_to_alignby (char typalign)
 
static void store_att_byval (void *T, Datum newdatum, int attlen)
 

Macro Definition Documentation

◆ att_addlength_datum

Definition at line 419 of file tupmacs.h.

436 : (((attlen) == -1) ? \
437 ( \
439 ) \
440 : \
441 ( \
442 AssertMacro((attlen) == -2), \
443 (cur_offset) + (strlen((const char *) (attptr)) + 1) \
444 )) \
445)
446
448/*
449 * store_att_byval is a partial inverse of fetch_att: store a given Datum
450 * value into a tuple data area at the specified address. However, it only
451 * handles the byval case, because in typical usage the caller needs to
452 * distinguish by-val and by-ref cases anyway, and so a do-it-all function
453 * wouldn't be convenient.
454 */
457{
458 switch (attlen)
459 {
460 case sizeof(char):
461 *(char *) T = DatumGetChar(newdatum);
462 break;
463 case sizeof(int16):
465 break;
466 case sizeof(int32):
468 break;
469 case sizeof(int64):
471 break;
472 default:
473 elog(ERROR, "unsupported byval length: %d", attlen);
474 }
475}
476#endif /* FRONTEND */
477
478#endif /* TUPMACS_H */
#define FRONTEND
#define AssertMacro(condition)
Definition c.h:946
int64_t int64
Definition c.h:615
int16_t int16
Definition c.h:613
int32_t int32
Definition c.h:614
#define ERROR
Definition elog.h:39
#define elog(elevel,...)
Definition elog.h:226
static const uint32 T[65]
Definition md5.c:119
int16 attlen
static int64 DatumGetInt64(Datum X)
Definition postgres.h:403
uint64_t Datum
Definition postgres.h:70
static char DatumGetChar(Datum X)
Definition postgres.h:122
static int16 DatumGetInt16(Datum X)
Definition postgres.h:162
static int32 DatumGetInt32(Datum X)
Definition postgres.h:202
static int fb(int x)
static void store_att_byval(void *T, Datum newdatum, int attlen)
Definition tupmacs.h:457
static Size VARSIZE_ANY(const void *PTR)
Definition varatt.h:460

◆ att_addlength_pointer

#define att_addlength_pointer (   cur_offset,
  attlen,
  attptr 
)
Value:
( \
((attlen) > 0) ? \
( \
) \
: (((attlen) == -1) ? \
( \
) \
: \
( \
AssertMacro((attlen) == -2), \
(cur_offset) + (strlen((const char *) (attptr)) + 1) \
)) \
)

Definition at line 431 of file tupmacs.h.

437 : (((attlen) == -1) ? \
438 ( \
440 ) \
441 : \
442 ( \
443 AssertMacro((attlen) == -2), \
444 (cur_offset) + (strlen((const char *) (attptr)) + 1) \
445 )) \
446)

◆ att_align_datum

#define att_align_datum (   cur_offset,
  attalign,
  attlen,
  attdatum 
)
Value:
( \
)
char attalign
static Pointer DatumGetPointer(Datum X)
Definition postgres.h:332
static bool VARATT_IS_SHORT(const void *PTR)
Definition varatt.h:403

Definition at line 341 of file tupmacs.h.

◆ att_align_nominal

Definition at line 404 of file tupmacs.h.

◆ att_align_pointer

#define att_align_pointer (   cur_offset,
  attalign,
  attlen,
  attptr 
)
Value:
( \
((attlen) == -1 && VARATT_NOT_PAD_BYTE(attptr)) ? \
)
#define att_align_nominal(cur_offset, attalign)
Definition tupmacs.h:404
#define VARATT_NOT_PAD_BYTE(PTR)
Definition varatt.h:238

Definition at line 372 of file tupmacs.h.

◆ att_datum_alignby

#define att_datum_alignby (   cur_offset,
  attalignby,
  attlen,
  attdatum 
)
Value:

Definition at line 352 of file tupmacs.h.

355 : \
356 TYPEALIGN(attalignby, cur_offset))

◆ att_nominal_alignby

#define att_nominal_alignby (   cur_offset,
  attalignby 
)     TYPEALIGN(attalignby, cur_offset)

Definition at line 411 of file tupmacs.h.

◆ att_pointer_alignby

#define att_pointer_alignby (   cur_offset,
  attalignby,
  attlen,
  attptr 
)
Value:
( \
((attlen) == -1 && VARATT_NOT_PAD_BYTE(attptr)) ? \
TYPEALIGN(attalignby, cur_offset))
#define TYPEALIGN(ALIGNVAL, LEN)
Definition c.h:891

Definition at line 383 of file tupmacs.h.

386 : \
387 TYPEALIGN(attalignby, cur_offset))

◆ fetchatt

#define fetchatt (   A,
  T 
)    fetch_att(T, (A)->attbyval, (A)->attlen)

Definition at line 102 of file tupmacs.h.

◆ SPREAD_BITS_MULTIPLIER_32

#define SPREAD_BITS_MULTIPLIER_32   0x204081U

Function Documentation

◆ align_fetch_then_add()

static Datum align_fetch_then_add ( const char tupptr,
uint32 off,
bool  attbyval,
int  attlen,
uint8  attalignby 
)
inlinestatic

Definition at line 172 of file tupmacs.h.

174{
175 Datum res;
176
177 if (attlen > 0)
178 {
179 const char *offset_ptr;
180
181 *off = TYPEALIGN(attalignby, *off);
182 offset_ptr = tupptr + *off;
183 *off += attlen;
184 if (attbyval)
185 {
186 switch (attlen)
187 {
188 case sizeof(char):
190 case sizeof(int16):
192 case sizeof(int32):
194 default:
195
196 /*
197 * populate_compact_attribute_internal() should have
198 * checked
199 */
200 Assert(attlen == sizeof(int64));
201 return Int64GetDatum(*((const int64 *) offset_ptr));
202 }
203 }
205 }
206 else if (attlen == -1)
207 {
208 if (!VARATT_IS_SHORT(tupptr + *off))
209 *off = TYPEALIGN(attalignby, *off);
210
211 res = PointerGetDatum(tupptr + *off);
212 *off += VARSIZE_ANY(DatumGetPointer(res));
213 return res;
214 }
215 else
216 {
217 Assert(attlen == -2);
218 *off = TYPEALIGN(attalignby, *off);
219 res = PointerGetDatum(tupptr + *off);
220 *off += strlen(tupptr + *off) + 1;
221 return res;
222 }
223}
#define Assert(condition)
Definition c.h:945
bool attbyval
static Datum Int64GetDatum(int64 X)
Definition postgres.h:413
static Datum PointerGetDatum(const void *X)
Definition postgres.h:342
static Datum Int16GetDatum(int16 X)
Definition postgres.h:172
static Datum Int32GetDatum(int32 X)
Definition postgres.h:212
static Datum CharGetDatum(char X)
Definition postgres.h:132

References Assert, attbyval, attlen, CharGetDatum(), DatumGetPointer(), fb(), Int16GetDatum(), Int32GetDatum(), Int64GetDatum(), PointerGetDatum(), TYPEALIGN, VARATT_IS_SHORT(), and VARSIZE_ANY().

Referenced by heap_deform_tuple(), index_deform_tuple_internal(), and slot_deform_heap_tuple().

◆ att_isnull()

static bool att_isnull ( int  ATT,
const bits8 BITS 
)
inlinestatic

◆ fetch_att()

static Datum fetch_att ( const void T,
bool  attbyval,
int  attlen 
)
inlinestatic

◆ fetch_att_noerr()

static Datum fetch_att_noerr ( const void T,
bool  attbyval,
int  attlen 
)
inlinestatic

Definition at line 137 of file tupmacs.h.

138{
139 if (attbyval)
140 {
141 switch (attlen)
142 {
143 case sizeof(int32):
145 case sizeof(int16):
147 case sizeof(char):
149 default:
150 Assert(attlen == sizeof(int64));
151 return Int64GetDatum(*((const int64 *) T));
152 }
153 }
154 else
155 return PointerGetDatum(T);
156}

References Assert, attbyval, attlen, CharGetDatum(), fb(), Int16GetDatum(), Int32GetDatum(), Int64GetDatum(), PointerGetDatum(), and T.

Referenced by heap_deform_tuple(), index_deform_tuple_internal(), and slot_deform_heap_tuple().

◆ first_null_attr()

static int first_null_attr ( const bits8 bits,
int  natts 
)
inlinestatic

Definition at line 244 of file tupmacs.h.

245{
246 int nattByte = natts >> 3;
247 int bytenum;
248 int res;
249
250#ifdef USE_ASSERT_CHECKING
251 int firstnull_check = natts;
252
253 /* Do it the slow way and check we get the same answer. */
254 for (int i = 0; i < natts; i++)
255 {
256 if (att_isnull(i, bits))
257 {
259 break;
260 }
261 }
262#endif
263
264 /* Process all bytes up to just before the byte for the natts attribute */
265 for (bytenum = 0; bytenum < nattByte; bytenum++)
266 {
267 /* break if there's any NULL attrs (a 0 bit) */
268 if (bits[bytenum] != 0xFF)
269 break;
270 }
271
272 /*
273 * Look for the highest 0-bit in the 'bytenum' element. To do this, we
274 * promote the uint8 to uint32 before performing the bitwise NOT and
275 * looking for the first 1-bit. This works even when the byte is 0xFF, as
276 * the bitwise NOT of 0xFF in 32 bits is 0xFFFFFF00, in which case
277 * pg_rightmost_one_pos32() will return 8. We may end up with a value
278 * higher than natts here, but we'll fix that with the Min() below.
279 */
280 res = bytenum << 3;
281 res += pg_rightmost_one_pos32(~((uint32) bits[bytenum]));
282
283 /*
284 * Since we did no masking to mask out bits beyond the natts'th bit, we
285 * may have found a bit higher than natts, so we must cap res to natts
286 */
287 res = Min(res, natts);
288
289 /* Ensure we got the same answer as the att_isnull() loop got */
290 Assert(res == firstnull_check);
291
292 return res;
293}
#define Min(x, y)
Definition c.h:1093
uint32_t uint32
Definition c.h:618
int i
Definition isn.c:77
static int pg_rightmost_one_pos32(uint32 word)
static bool att_isnull(int ATT, const bits8 *BITS)
Definition tupmacs.h:28

References Assert, att_isnull(), fb(), i, Min, and pg_rightmost_one_pos32().

Referenced by heap_deform_tuple(), index_deform_tuple_internal(), nocache_index_getattr(), nocachegetattr(), and slot_deform_heap_tuple().

◆ populate_isnull_array()

static void populate_isnull_array ( const bits8 bits,
int  natts,
bool isnull 
)
inlinestatic

Definition at line 43 of file tupmacs.h.

44{
45 int nbytes = (natts + 7) >> 3;
46
47 /*
48 * Multiplying the inverted NULL bitmap byte by this value results in the
49 * lowest bit in each byte being set the same as each bit of the inverted
50 * byte. We perform this as 2 32-bit operations rather than a single
51 * 64-bit operation as multiplying by the required value to do this in
52 * 64-bits would result in overflowing a uint64 in some cases.
53 *
54 * XXX if we ever require BMI2 (-march=x86-64-v3), then this could be done
55 * more efficiently on most X86-64 CPUs with the PDEP instruction. Beware
56 * that some chips (e.g. AMD's Zen2) are horribly inefficient at PDEP.
57 */
58#define SPREAD_BITS_MULTIPLIER_32 0x204081U
59
60 for (int i = 0; i < nbytes; i++, isnull += 8)
61 {
64
65 /* Convert the lower 4 bits of NULL bitmap word into a 64 bit int */
67
68 /*
69 * Convert the upper 4 bits of NULL bitmap word into a 64 bit int,
70 * shift into the upper 32 bit and bitwise-OR with the result of the
71 * lower 4 bits.
72 */
73 isnull_8 |= ((uint64) ((nullbyte >> 4) * SPREAD_BITS_MULTIPLIER_32)) << 32;
74
75 /* Mask out all other bits apart from the lowest bit of each byte. */
76 isnull_8 &= UINT64CONST(0x0101010101010101);
77
78#ifdef WORDS_BIGENDIAN
79
80 /*
81 * Fix byte order on big-endian machines before copying to the array.
82 */
84#endif
85 memcpy(isnull, &isnull_8, sizeof(uint64));
86 }
87}
uint8 bits8
Definition c.h:625
uint64_t uint64
Definition c.h:619
#define UINT64CONST(x)
Definition c.h:633
static uint64 pg_bswap64(uint64 x)
Definition pg_bswap.h:89
#define SPREAD_BITS_MULTIPLIER_32

References fb(), i, pg_bswap64(), SPREAD_BITS_MULTIPLIER_32, and UINT64CONST.

Referenced by slot_deform_heap_tuple().

◆ store_att_byval()

static void store_att_byval ( void T,
Datum  newdatum,
int  attlen 
)
inlinestatic

Definition at line 457 of file tupmacs.h.

458{
459 switch (attlen)
460 {
461 case sizeof(char):
462 *(char *) T = DatumGetChar(newdatum);
463 break;
464 case sizeof(int16):
466 break;
467 case sizeof(int32):
469 break;
470 case sizeof(int64):
472 break;
473 default:
474 elog(ERROR, "unsupported byval length: %d", attlen);
475 }
476}

References attlen, DatumGetChar(), DatumGetInt16(), DatumGetInt32(), DatumGetInt64(), elog, ERROR, fb(), and T.

Referenced by ArrayCastAndSet(), brin_range_serialize(), datum_write(), fill_val(), and statext_mcv_serialize().

◆ typalign_to_alignby()

static uint8 typalign_to_alignby ( char  typalign)
inlinestatic

Definition at line 302 of file tupmacs.h.

303{
305
306 switch (typalign)
307 {
308 case TYPALIGN_CHAR:
309 alignby = sizeof(char);
310 break;
311 case TYPALIGN_SHORT:
313 break;
314 case TYPALIGN_INT:
316 break;
317 case TYPALIGN_DOUBLE:
319 break;
320 default:
321#ifndef FRONTEND
322 elog(ERROR, "invalid typalign value: %c", typalign);
323#else
324 fprintf(stderr, "invalid typalign value: %c\n", typalign);
325 exit(1);
326#endif
327 alignby = 0;
328 break;
329 }
330 return alignby;
331}
uint8_t uint8
Definition c.h:616
#define fprintf(file, fmt, msg)
Definition cubescan.l:21
char typalign
Definition pg_type.h:178

References elog, ERROR, fb(), fprintf, and typalign.

Referenced by array_create_iterator(), array_fill_internal(), array_in(), array_iter_setup(), array_map(), array_replace_internal(), array_seek(), array_set_element(), array_slice_size(), array_to_text_internal(), construct_md_array(), CopyArrayEls(), deconstruct_array(), EA_get_flat_size(), ExecEvalHashedScalarArrayOp(), ExecEvalScalarArrayOp(), get_text_array_contents(), multirange_size_estimate(), PLyList_FromArray_recurse(), populate_compact_attribute_internal(), ReadArrayBinary(), width_bucket_array_variable(), and write_multirange_data().