OSDN Git Service

Remove the mostly-stubbed-out-anyway support routines for WAL UNDO.
[pg-rex/syncrep.git] / src / include / access / tupmacs.h
1 /*-------------------------------------------------------------------------
2  *
3  * tupmacs.h
4  *        Tuple macros used by both index tuples and heap tuples.
5  *
6  *
7  * Portions Copyright (c) 1996-2005, PostgreSQL Global Development Group
8  * Portions Copyright (c) 1994, Regents of the University of California
9  *
10  * $PostgreSQL: pgsql/src/include/access/tupmacs.h,v 1.28 2005/05/06 17:24:55 tgl Exp $
11  *
12  *-------------------------------------------------------------------------
13  */
14 #ifndef TUPMACS_H
15 #define TUPMACS_H
16
17
18 /*
19  * check to see if the ATT'th bit of an array of 8-bit bytes is set.
20  */
21 #define att_isnull(ATT, BITS) (!((BITS)[(ATT) >> 3] & (1 << ((ATT) & 0x07))))
22
23 /*
24  * Given a Form_pg_attribute and a pointer into a tuple's data area,
25  * return the correct value or pointer.
26  *
27  * We return a Datum value in all cases.  If the attribute has "byval" false,
28  * we return the same pointer into the tuple data area that we're passed.
29  * Otherwise, we return the correct number of bytes fetched from the data
30  * area and extended to Datum form.
31  *
32  * On machines where Datum is 8 bytes, we support fetching 8-byte byval
33  * attributes; otherwise, only 1, 2, and 4-byte values are supported.
34  *
35  * Note that T must already be properly aligned for this to work correctly.
36  */
37 #define fetchatt(A,T) fetch_att(T, (A)->attbyval, (A)->attlen)
38
39 /*
40  * Same, but work from byval/len parameters rather than Form_pg_attribute.
41  */
42 #if SIZEOF_DATUM == 8
43
44 #define fetch_att(T,attbyval,attlen) \
45 ( \
46         (attbyval) ? \
47         ( \
48                 (attlen) == (int) sizeof(Datum) ? \
49                         *((Datum *)(T)) \
50                 : \
51           ( \
52                 (attlen) == (int) sizeof(int32) ? \
53                         Int32GetDatum(*((int32 *)(T))) \
54                 : \
55                 ( \
56                         (attlen) == (int) sizeof(int16) ? \
57                                 Int16GetDatum(*((int16 *)(T))) \
58                         : \
59                         ( \
60                                 AssertMacro((attlen) == 1), \
61                                 CharGetDatum(*((char *)(T))) \
62                         ) \
63                 ) \
64           ) \
65         ) \
66         : \
67         PointerGetDatum((char *) (T)) \
68 )
69
70 #else                                                   /* SIZEOF_DATUM != 8 */
71
72 #define fetch_att(T,attbyval,attlen) \
73 ( \
74         (attbyval) ? \
75         ( \
76                 (attlen) == (int) sizeof(int32) ? \
77                         Int32GetDatum(*((int32 *)(T))) \
78                 : \
79                 ( \
80                         (attlen) == (int) sizeof(int16) ? \
81                                 Int16GetDatum(*((int16 *)(T))) \
82                         : \
83                         ( \
84                                 AssertMacro((attlen) == 1), \
85                                 CharGetDatum(*((char *)(T))) \
86                         ) \
87                 ) \
88         ) \
89         : \
90         PointerGetDatum((char *) (T)) \
91 )
92 #endif   /* SIZEOF_DATUM == 8 */
93
94 /*
95  * att_align aligns the given offset as needed for a datum of alignment
96  * requirement attalign.  The cases are tested in what is hopefully something
97  * like their frequency of occurrence.
98  */
99 #define att_align(cur_offset, attalign) \
100 ( \
101         ((attalign) == 'i') ? INTALIGN(cur_offset) : \
102          (((attalign) == 'c') ? ((long)(cur_offset)) : \
103           (((attalign) == 'd') ? DOUBLEALIGN(cur_offset) : \
104                 ( \
105                         AssertMacro((attalign) == 's'), \
106                         SHORTALIGN(cur_offset) \
107                 ))) \
108 )
109
110 /*
111  * att_addlength increments the given offset by the length of the attribute.
112  * attval is only accessed if we are dealing with a variable-length attribute.
113  */
114 #define att_addlength(cur_offset, attlen, attval) \
115 ( \
116         ((attlen) > 0) ? \
117         ( \
118                 (cur_offset) + (attlen) \
119         ) \
120         : (((attlen) == -1) ? \
121         ( \
122                 (cur_offset) + VARATT_SIZE(DatumGetPointer(attval)) \
123         ) \
124         : \
125         ( \
126                 AssertMacro((attlen) == -2), \
127                 (cur_offset) + (strlen(DatumGetCString(attval)) + 1) \
128         )) \
129 )
130
131 /*
132  * store_att_byval is a partial inverse of fetch_att: store a given Datum
133  * value into a tuple data area at the specified address.  However, it only
134  * handles the byval case, because in typical usage the caller needs to
135  * distinguish by-val and by-ref cases anyway, and so a do-it-all macro
136  * wouldn't be convenient.
137  */
138 #if SIZEOF_DATUM == 8
139
140 #define store_att_byval(T,newdatum,attlen) \
141         do { \
142                 switch (attlen) \
143                 { \
144                         case sizeof(char): \
145                                 *(char *) (T) = DatumGetChar(newdatum); \
146                                 break; \
147                         case sizeof(int16): \
148                                 *(int16 *) (T) = DatumGetInt16(newdatum); \
149                                 break; \
150                         case sizeof(int32): \
151                                 *(int32 *) (T) = DatumGetInt32(newdatum); \
152                                 break; \
153                         case sizeof(Datum): \
154                                 *(Datum *) (T) = (newdatum); \
155                                 break; \
156                         default: \
157                                 elog(ERROR, "unsupported byval length: %d", \
158                                          (int) (attlen)); \
159                                 break; \
160                 } \
161         } while (0)
162
163 #else                                                   /* SIZEOF_DATUM != 8 */
164
165 #define store_att_byval(T,newdatum,attlen) \
166         do { \
167                 switch (attlen) \
168                 { \
169                         case sizeof(char): \
170                                 *(char *) (T) = DatumGetChar(newdatum); \
171                                 break; \
172                         case sizeof(int16): \
173                                 *(int16 *) (T) = DatumGetInt16(newdatum); \
174                                 break; \
175                         case sizeof(int32): \
176                                 *(int32 *) (T) = DatumGetInt32(newdatum); \
177                                 break; \
178                         default: \
179                                 elog(ERROR, "unsupported byval length: %d", \
180                                          (int) (attlen)); \
181                                 break; \
182                 } \
183         } while (0)
184 #endif   /* SIZEOF_DATUM == 8 */
185
186 #endif