1515#include "postgres.h"
1616
1717#include "access/heapam_xlog.h"
18+ #include "access/rmgrdesc_utils.h"
1819
1920static void
2021out_infobits (StringInfo buf ,uint8 infobits )
2122{
23+ if ((infobits & XLHL_XMAX_IS_MULTI )== 0 &&
24+ (infobits & XLHL_XMAX_LOCK_ONLY )== 0 &&
25+ (infobits & XLHL_XMAX_EXCL_LOCK )== 0 &&
26+ (infobits & XLHL_XMAX_KEYSHR_LOCK )== 0 &&
27+ (infobits & XLHL_KEYS_UPDATED )== 0 )
28+ return ;
29+
30+ appendStringInfoString (buf ,", infobits: [" );
31+
2232if (infobits & XLHL_XMAX_IS_MULTI )
23- appendStringInfoString (buf ,"IS_MULTI " );
33+ appendStringInfoString (buf ," IS_MULTI " );
2434if (infobits & XLHL_XMAX_LOCK_ONLY )
25- appendStringInfoString (buf ,"LOCK_ONLY " );
35+ appendStringInfoString (buf ,", LOCK_ONLY " );
2636if (infobits & XLHL_XMAX_EXCL_LOCK )
27- appendStringInfoString (buf ,"EXCL_LOCK " );
37+ appendStringInfoString (buf ,", EXCL_LOCK " );
2838if (infobits & XLHL_XMAX_KEYSHR_LOCK )
29- appendStringInfoString (buf ,"KEYSHR_LOCK " );
39+ appendStringInfoString (buf ,", KEYSHR_LOCK " );
3040if (infobits & XLHL_KEYS_UPDATED )
31- appendStringInfoString (buf ,"KEYS_UPDATED " );
41+ appendStringInfoString (buf ,", KEYS_UPDATED" );
42+
43+ appendStringInfoString (buf ," ]" );
44+ }
45+
46+ static void
47+ plan_elem_desc (StringInfo buf ,void * plan ,void * data )
48+ {
49+ xl_heap_freeze_plan * new_plan = (xl_heap_freeze_plan * )plan ;
50+ OffsetNumber * * offsets = data ;
51+
52+ appendStringInfo (buf ,"{ xmax: %u, infomask: %u, infomask2: %u, ntuples: %u" ,
53+ new_plan -> xmax ,
54+ new_plan -> t_infomask ,new_plan -> t_infomask2 ,
55+ new_plan -> ntuples );
56+
57+ appendStringInfoString (buf ,", offsets:" );
58+ array_desc (buf ,* offsets ,sizeof (OffsetNumber ),new_plan -> ntuples ,
59+ & offset_elem_desc ,NULL );
60+
61+ * offsets += new_plan -> ntuples ;
62+
63+ appendStringInfo (buf ," }" );
3264}
3365
3466void
@@ -42,14 +74,15 @@ heap_desc(StringInfo buf, XLogReaderState *record)
4274{
4375xl_heap_insert * xlrec = (xl_heap_insert * )rec ;
4476
45- appendStringInfo (buf ,"off %u flags 0x%02X" ,xlrec -> offnum ,
77+ appendStringInfo (buf ,"off: %u, flags: 0x%02X" ,
78+ xlrec -> offnum ,
4679xlrec -> flags );
4780}
4881else if (info == XLOG_HEAP_DELETE )
4982{
5083xl_heap_delete * xlrec = (xl_heap_delete * )rec ;
5184
52- appendStringInfo (buf ,"off %u flags 0x%02X " ,
85+ appendStringInfo (buf ,"off: %u, flags: 0x%02X" ,
5386xlrec -> offnum ,
5487xlrec -> flags );
5588out_infobits (buf ,xlrec -> infobits_set );
@@ -58,62 +91,66 @@ heap_desc(StringInfo buf, XLogReaderState *record)
5891{
5992xl_heap_update * xlrec = (xl_heap_update * )rec ;
6093
61- appendStringInfo (buf ,"off %u xmax %u flags 0x%02X " ,
94+ appendStringInfo (buf ,"off: %u, xmax: %u, flags: 0x%02X" ,
6295xlrec -> old_offnum ,
6396xlrec -> old_xmax ,
6497xlrec -> flags );
6598out_infobits (buf ,xlrec -> old_infobits_set );
66- appendStringInfo (buf ,"; new off %u xmax %u" ,
99+ appendStringInfo (buf ,", new off: %u, xmax %u" ,
67100xlrec -> new_offnum ,
68101xlrec -> new_xmax );
69102}
70103else if (info == XLOG_HEAP_HOT_UPDATE )
71104{
72105xl_heap_update * xlrec = (xl_heap_update * )rec ;
73106
74- appendStringInfo (buf ,"off %u xmax %u flags 0x%02X " ,
107+ appendStringInfo (buf ,"off: %u, xmax: %u, flags: 0x%02X" ,
75108xlrec -> old_offnum ,
76109xlrec -> old_xmax ,
77110xlrec -> flags );
78111out_infobits (buf ,xlrec -> old_infobits_set );
79- appendStringInfo (buf ,"; new off %u xmax %u" ,
112+ appendStringInfo (buf ,", new off: %u, xmax: %u" ,
80113xlrec -> new_offnum ,
81114xlrec -> new_xmax );
82115}
83116else if (info == XLOG_HEAP_TRUNCATE )
84117{
85118xl_heap_truncate * xlrec = (xl_heap_truncate * )rec ;
86- int i ;
87119
120+ appendStringInfoString (buf ,"flags: [" );
88121if (xlrec -> flags & XLH_TRUNCATE_CASCADE )
89- appendStringInfoString (buf ,"cascade " );
122+ appendStringInfoString (buf ," CASCADE " );
90123if (xlrec -> flags & XLH_TRUNCATE_RESTART_SEQS )
91- appendStringInfoString (buf ,"restart_seqs " );
92- appendStringInfo (buf ,"nrelids %u relids" ,xlrec -> nrelids );
93- for (i = 0 ;i < xlrec -> nrelids ;i ++ )
94- appendStringInfo (buf ," %u" ,xlrec -> relids [i ]);
124+ appendStringInfoString (buf ,", RESTART_SEQS" );
125+ appendStringInfoString (buf ," ]" );
126+
127+ appendStringInfo (buf ,", nrelids: %u" ,xlrec -> nrelids );
128+ appendStringInfoString (buf ,", relids:" );
129+ array_desc (buf ,xlrec -> relids ,sizeof (Oid ),xlrec -> nrelids ,
130+ & relid_desc ,NULL );
95131}
96132else if (info == XLOG_HEAP_CONFIRM )
97133{
98134xl_heap_confirm * xlrec = (xl_heap_confirm * )rec ;
99135
100- appendStringInfo (buf ,"off %u" ,xlrec -> offnum );
136+ appendStringInfo (buf ,"off: %u" ,xlrec -> offnum );
101137}
102138else if (info == XLOG_HEAP_LOCK )
103139{
104140xl_heap_lock * xlrec = (xl_heap_lock * )rec ;
105141
106- appendStringInfo (buf ,"off %u: xid %u: flags 0x%02X " ,
142+ appendStringInfo (buf ,"off: %u, xid: %u, flags: 0x%02X" ,
107143xlrec -> offnum ,xlrec -> locking_xid ,xlrec -> flags );
108144out_infobits (buf ,xlrec -> infobits_set );
109145}
110146else if (info == XLOG_HEAP_INPLACE )
111147{
112148xl_heap_inplace * xlrec = (xl_heap_inplace * )rec ;
113149
114- appendStringInfo (buf ,"off %u" ,xlrec -> offnum );
150+ appendStringInfo (buf ,"off: %u" ,xlrec -> offnum );
115151}
116152}
153+
117154void
118155heap2_desc (StringInfo buf ,XLogReaderState * record )
119156{
@@ -125,57 +162,119 @@ heap2_desc(StringInfo buf, XLogReaderState *record)
125162{
126163xl_heap_prune * xlrec = (xl_heap_prune * )rec ;
127164
128- appendStringInfo (buf ,"snapshotConflictHorizon %u nredirected %u ndead %u" ,
165+ appendStringInfo (buf ,"snapshotConflictHorizon: %u, nredirected: %u, ndead: %u" ,
129166xlrec -> snapshotConflictHorizon ,
130167xlrec -> nredirected ,
131168xlrec -> ndead );
169+
170+ if (!XLogRecHasBlockImage (record ,0 ))
171+ {
172+ OffsetNumber * end ;
173+ OffsetNumber * redirected ;
174+ OffsetNumber * nowdead ;
175+ OffsetNumber * nowunused ;
176+ int nredirected ;
177+ int nunused ;
178+ Size datalen ;
179+
180+ redirected = (OffsetNumber * )XLogRecGetBlockData (record ,0 ,
181+ & datalen );
182+
183+ nredirected = xlrec -> nredirected ;
184+ end = (OffsetNumber * ) ((char * )redirected + datalen );
185+ nowdead = redirected + (nredirected * 2 );
186+ nowunused = nowdead + xlrec -> ndead ;
187+ nunused = (end - nowunused );
188+ Assert (nunused >=0 );
189+
190+ appendStringInfo (buf ,", nunused: %u" ,nunused );
191+
192+ appendStringInfoString (buf ,", redirected:" );
193+ array_desc (buf ,redirected ,sizeof (OffsetNumber )* 2 ,
194+ nredirected ,& redirect_elem_desc ,NULL );
195+ appendStringInfoString (buf ,", dead:" );
196+ array_desc (buf ,nowdead ,sizeof (OffsetNumber ),xlrec -> ndead ,
197+ & offset_elem_desc ,NULL );
198+ appendStringInfoString (buf ,", unused:" );
199+ array_desc (buf ,nowunused ,sizeof (OffsetNumber ),nunused ,
200+ & offset_elem_desc ,NULL );
201+ }
132202}
133203else if (info == XLOG_HEAP2_VACUUM )
134204{
135205xl_heap_vacuum * xlrec = (xl_heap_vacuum * )rec ;
136206
137- appendStringInfo (buf ,"nunused %u" ,xlrec -> nunused );
207+ appendStringInfo (buf ,"nunused: %u" ,xlrec -> nunused );
208+
209+ if (!XLogRecHasBlockImage (record ,0 ))
210+ {
211+ OffsetNumber * nowunused ;
212+
213+ nowunused = (OffsetNumber * )XLogRecGetBlockData (record ,0 ,NULL );
214+
215+ appendStringInfoString (buf ,", unused:" );
216+ array_desc (buf ,nowunused ,sizeof (OffsetNumber ),xlrec -> nunused ,
217+ & offset_elem_desc ,NULL );
218+ }
138219}
139220else if (info == XLOG_HEAP2_FREEZE_PAGE )
140221{
141222xl_heap_freeze_page * xlrec = (xl_heap_freeze_page * )rec ;
142223
143- appendStringInfo (buf ,"snapshotConflictHorizon %u nplans %u" ,
224+ appendStringInfo (buf ,"snapshotConflictHorizon: %u, nplans: %u" ,
144225xlrec -> snapshotConflictHorizon ,xlrec -> nplans );
226+
227+ if (!XLogRecHasBlockImage (record ,0 ))
228+ {
229+ xl_heap_freeze_plan * plans ;
230+ OffsetNumber * offsets ;
231+
232+ plans = (xl_heap_freeze_plan * )XLogRecGetBlockData (record ,0 ,NULL );
233+ offsets = (OffsetNumber * )& plans [xlrec -> nplans ];
234+ appendStringInfoString (buf ,", plans:" );
235+ array_desc (buf ,plans ,sizeof (xl_heap_freeze_plan ),xlrec -> nplans ,
236+ & plan_elem_desc ,& offsets );
237+ }
145238}
146239else if (info == XLOG_HEAP2_VISIBLE )
147240{
148241xl_heap_visible * xlrec = (xl_heap_visible * )rec ;
149242
150- appendStringInfo (buf ,"snapshotConflictHorizon %u flags 0x%02X" ,
243+ appendStringInfo (buf ,"snapshotConflictHorizon: %u, flags: 0x%02X" ,
151244xlrec -> snapshotConflictHorizon ,xlrec -> flags );
152245}
153246else if (info == XLOG_HEAP2_MULTI_INSERT )
154247{
155248xl_heap_multi_insert * xlrec = (xl_heap_multi_insert * )rec ;
249+ bool isinit = (XLogRecGetInfo (record )& XLOG_HEAP_INIT_PAGE )!= 0 ;
156250
157- appendStringInfo (buf ,"%d tuples flags 0x%02X" ,xlrec -> ntuples ,
251+ appendStringInfo (buf ,"ntuples: %d, flags: 0x%02X" ,xlrec -> ntuples ,
158252xlrec -> flags );
253+
254+ appendStringInfoString (buf ,", offsets:" );
255+ if (!XLogRecHasBlockImage (record ,0 )&& !isinit )
256+ array_desc (buf ,xlrec -> offsets ,sizeof (OffsetNumber ),
257+ xlrec -> ntuples ,& offset_elem_desc ,NULL );
159258}
160259else if (info == XLOG_HEAP2_LOCK_UPDATED )
161260{
162261xl_heap_lock_updated * xlrec = (xl_heap_lock_updated * )rec ;
163262
164- appendStringInfo (buf ,"off %u: xmax %u: flags 0x%02X " ,
263+ appendStringInfo (buf ,"off: %u, xmax: %u, flags: 0x%02X" ,
165264xlrec -> offnum ,xlrec -> xmax ,xlrec -> flags );
166265out_infobits (buf ,xlrec -> infobits_set );
167266}
168267else if (info == XLOG_HEAP2_NEW_CID )
169268{
170269xl_heap_new_cid * xlrec = (xl_heap_new_cid * )rec ;
171270
172- appendStringInfo (buf ,"rel %u/%u/%u; tid %u/%u" ,
271+ appendStringInfo (buf ,"rel: %u/%u/%u, tid: %u/%u" ,
173272xlrec -> target_locator .spcOid ,
174273xlrec -> target_locator .dbOid ,
175274xlrec -> target_locator .relNumber ,
176275ItemPointerGetBlockNumber (& (xlrec -> target_tid )),
177276ItemPointerGetOffsetNumber (& (xlrec -> target_tid )));
178- appendStringInfo (buf ,"; cmin: %u, cmax: %u, combo: %u" ,
277+ appendStringInfo (buf ,", cmin: %u, cmax: %u, combo: %u" ,
179278xlrec -> cmin ,xlrec -> cmax ,xlrec -> combocid );
180279}
181280}