PostgreSQL Source Code git master
Loading...
Searching...
No Matches
bufpage.h File Reference
#include "access/xlogdefs.h"
#include "storage/block.h"
#include "storage/off.h"
Include dependency graph for bufpage.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  PageXLogRecPtr
 
struct  PageHeaderData
 

Macros

#define PD_HAS_FREE_LINES   0x0001 /* are there any unused line pointers? */
 
#define PD_PAGE_FULL   0x0002 /* not enough free space for new tuple? */
 
#define PD_ALL_VISIBLE
 
#define PD_VALID_FLAG_BITS   0x0007 /* OR of all valid pd_flags bits */
 
#define PG_PAGE_LAYOUT_VERSION   4
 
#define SizeOfPageHeaderData   (offsetof(PageHeaderData, pd_linp))
 
#define PageGetSpecialPointer(page)
 
#define PageSetPrunable(page, xid)
 
#define PageClearPrunable(page)    (((PageHeader) (page))->pd_prune_xid = InvalidTransactionId)
 
#define PAI_OVERWRITE   (1 << 0)
 
#define PAI_IS_HEAP   (1 << 1)
 
#define PIV_LOG_WARNING   (1 << 0)
 
#define PIV_LOG_LOG   (1 << 1)
 
#define PIV_IGNORE_CHECKSUM_FAILURE   (1 << 2)
 
#define PIV_ZERO_BUFFERS_ON_ERROR   (1 << 3)
 
#define PageAddItem(page, item, size, offsetNumber, overwrite, is_heap)
 

Typedefs

typedef char PageData
 
typedef PageDataPage
 
typedef uint16 LocationIndex
 
typedef struct PageHeaderData PageHeaderData
 
typedef PageHeaderDataPageHeader
 

Functions

static XLogRecPtr PageXLogRecPtrGet (const volatile PageXLogRecPtr *val)
 
static void PageXLogRecPtrSet (volatile PageXLogRecPtr *ptr, XLogRecPtr lsn)
 
static bool PageIsEmpty (const PageData *page)
 
static bool PageIsNew (const PageData *page)
 
static ItemId PageGetItemId (Page page, OffsetNumber offsetNumber)
 
static charPageGetContents (Page page)
 
static Size PageGetPageSize (const PageData *page)
 
static uint8 PageGetPageLayoutVersion (const PageData *page)
 
static void PageSetPageSizeAndVersion (Page page, Size size, uint8 version)
 
static uint16 PageGetSpecialSize (const PageData *page)
 
static void PageValidateSpecialPointer (const PageData *page)
 
static voidPageGetItem (PageData *page, const ItemIdData *itemId)
 
static OffsetNumber PageGetMaxOffsetNumber (const PageData *page)
 
static XLogRecPtr PageGetLSN (const PageData *page)
 
static void PageSetLSN (Page page, XLogRecPtr lsn)
 
static bool PageHasFreeLinePointers (const PageData *page)
 
static void PageSetHasFreeLinePointers (Page page)
 
static void PageClearHasFreeLinePointers (Page page)
 
static bool PageIsFull (const PageData *page)
 
static void PageSetFull (Page page)
 
static void PageClearFull (Page page)
 
static bool PageIsAllVisible (const PageData *page)
 
static void PageSetAllVisible (Page page)
 
static void PageClearAllVisible (Page page)
 
static TransactionId PageGetPruneXid (const PageData *page)
 
 StaticAssertDecl (BLCKSZ==((BLCKSZ/sizeof(size_t)) *sizeof(size_t)), "BLCKSZ has to be a multiple of sizeof(size_t)")
 
void PageInit (Page page, Size pageSize, Size specialSize)
 
bool PageIsVerified (PageData *page, BlockNumber blkno, int flags, bool *checksum_failure_p)
 
OffsetNumber PageAddItemExtended (Page page, const void *item, Size size, OffsetNumber offsetNumber, int flags)
 
Page PageGetTempPage (const PageData *page)
 
Page PageGetTempPageCopy (const PageData *page)
 
Page PageGetTempPageCopySpecial (const PageData *page)
 
void PageRestoreTempPage (Page tempPage, Page oldPage)
 
void PageRepairFragmentation (Page page)
 
void PageTruncateLinePointerArray (Page page)
 
Size PageGetFreeSpace (const PageData *page)
 
Size PageGetFreeSpaceForMultipleTuples (const PageData *page, int ntups)
 
Size PageGetExactFreeSpace (const PageData *page)
 
Size PageGetHeapFreeSpace (const PageData *page)
 
void PageIndexTupleDelete (Page page, OffsetNumber offnum)
 
void PageIndexMultiDelete (Page page, OffsetNumber *itemnos, int nitems)
 
void PageIndexTupleDeleteNoCompact (Page page, OffsetNumber offnum)
 
bool PageIndexTupleOverwrite (Page page, OffsetNumber offnum, const void *newtup, Size newsize)
 
void PageSetChecksum (Page page, BlockNumber blkno)
 

Variables

PGDLLIMPORT bool ignore_checksum_failure
 

Macro Definition Documentation

◆ PageAddItem

#define PageAddItem (   page,
  item,
  size,
  offsetNumber,
  overwrite,
  is_heap 
)
Value:
PageAddItemExtended(page, item, size, offsetNumber, \
((overwrite) ? PAI_OVERWRITE : 0) | \
((is_heap) ? PAI_IS_HEAP : 0))
OffsetNumber PageAddItemExtended(Page page, const void *item, Size size, OffsetNumber offsetNumber, int flags)
Definition bufpage.c:203
#define PAI_IS_HEAP
Definition bufpage.h:496
#define PAI_OVERWRITE
Definition bufpage.h:495
static int fb(int x)
static void overwrite(PGconn *conn, Oid lobjId, int start, int len)
Definition testlo.c:108

Definition at line 504 of file bufpage.h.

507 : 0) | \

◆ PageClearPrunable

#define PageClearPrunable (   page)     (((PageHeader) (page))->pd_prune_xid = InvalidTransactionId)

Definition at line 485 of file bufpage.h.

◆ PageGetSpecialPointer

#define PageGetSpecialPointer (   page)
Value:
( \
((page) + ((PageHeader) (page))->pd_special) \
)

Definition at line 363 of file bufpage.h.

◆ PageSetPrunable

#define PageSetPrunable (   page,
  xid 
)
Value:
do { \
if (!TransactionIdIsValid(((PageHeader) (page))->pd_prune_xid) || \
TransactionIdPrecedes(xid, ((PageHeader) (page))->pd_prune_xid)) \
((PageHeader) (page))->pd_prune_xid = (xid); \
} while (0)
PageHeaderData * PageHeader
Definition bufpage.h:199
#define TransactionIdIsValid(xid)
Definition transam.h:41
#define TransactionIdIsNormal(xid)
Definition transam.h:42
static bool TransactionIdPrecedes(TransactionId id1, TransactionId id2)
Definition transam.h:263

Definition at line 478 of file bufpage.h.

480 { \
482 if (!TransactionIdIsValid(((PageHeader) (page))->pd_prune_xid) || \
483 TransactionIdPrecedes(xid, ((PageHeader) (page))->pd_prune_xid)) \
484 ((PageHeader) (page))->pd_prune_xid = (xid); \

◆ PAI_IS_HEAP

#define PAI_IS_HEAP   (1 << 1)

Definition at line 496 of file bufpage.h.

◆ PAI_OVERWRITE

#define PAI_OVERWRITE   (1 << 0)

Definition at line 495 of file bufpage.h.

◆ PD_ALL_VISIBLE

#define PD_ALL_VISIBLE
Value:
0x0004 /* all tuples on page are visible to
* everyone */

Definition at line 215 of file bufpage.h.

◆ PD_HAS_FREE_LINES

#define PD_HAS_FREE_LINES   0x0001 /* are there any unused line pointers? */

Definition at line 213 of file bufpage.h.

◆ PD_PAGE_FULL

#define PD_PAGE_FULL   0x0002 /* not enough free space for new tuple? */

Definition at line 214 of file bufpage.h.

◆ PD_VALID_FLAG_BITS

#define PD_VALID_FLAG_BITS   0x0007 /* OR of all valid pd_flags bits */

Definition at line 217 of file bufpage.h.

◆ PG_PAGE_LAYOUT_VERSION

#define PG_PAGE_LAYOUT_VERSION   4

Definition at line 231 of file bufpage.h.

◆ PIV_IGNORE_CHECKSUM_FAILURE

#define PIV_IGNORE_CHECKSUM_FAILURE   (1 << 2)

Definition at line 501 of file bufpage.h.

◆ PIV_LOG_LOG

#define PIV_LOG_LOG   (1 << 1)

Definition at line 500 of file bufpage.h.

◆ PIV_LOG_WARNING

#define PIV_LOG_WARNING   (1 << 0)

Definition at line 499 of file bufpage.h.

◆ PIV_ZERO_BUFFERS_ON_ERROR

#define PIV_ZERO_BUFFERS_ON_ERROR   (1 << 3)

Definition at line 502 of file bufpage.h.

◆ SizeOfPageHeaderData

#define SizeOfPageHeaderData   (offsetof(PageHeaderData, pd_linp))

Definition at line 241 of file bufpage.h.

Typedef Documentation

◆ LocationIndex

Definition at line 90 of file bufpage.h.

◆ Page

Definition at line 81 of file bufpage.h.

◆ PageData

Definition at line 80 of file bufpage.h.

◆ PageHeader

Definition at line 199 of file bufpage.h.

◆ PageHeaderData

Function Documentation

◆ PageAddItemExtended()

OffsetNumber PageAddItemExtended ( Page  page,
const void item,
Size  size,
OffsetNumber  offsetNumber,
int  flags 
)
extern

Definition at line 203 of file bufpage.c.

208{
209 PageHeader phdr = (PageHeader) page;
211 int lower;
212 int upper;
214 OffsetNumber limit;
215 bool needshuffle = false;
216
217 /*
218 * Be wary about corrupted page pointers
219 */
220 if (phdr->pd_lower < SizeOfPageHeaderData ||
221 phdr->pd_lower > phdr->pd_upper ||
222 phdr->pd_upper > phdr->pd_special ||
223 phdr->pd_special > BLCKSZ)
226 errmsg("corrupted page pointers: lower = %u, upper = %u, special = %u",
227 phdr->pd_lower, phdr->pd_upper, phdr->pd_special)));
228
229 /*
230 * Select offsetNumber to place the new item at
231 */
233
234 /* was offsetNumber passed in? */
236 {
237 /* yes, check it */
238 if ((flags & PAI_OVERWRITE) != 0)
239 {
240 if (offsetNumber < limit)
241 {
244 {
245 elog(WARNING, "will not overwrite a used ItemId");
246 return InvalidOffsetNumber;
247 }
248 }
249 }
250 else
251 {
252 if (offsetNumber < limit)
253 needshuffle = true; /* need to move existing linp's */
254 }
255 }
256 else
257 {
258 /* offsetNumber was not passed in, so find a free slot */
259 /* if no free slot, we'll put it at limit (1st open slot) */
260 if (PageHasFreeLinePointers(page))
261 {
262 /*
263 * Scan line pointer array to locate a "recyclable" (unused)
264 * ItemId.
265 *
266 * Always use earlier items first. PageTruncateLinePointerArray
267 * can only truncate unused items when they appear as a contiguous
268 * group at the end of the line pointer array.
269 */
271 offsetNumber < limit; /* limit is maxoff+1 */
272 offsetNumber++)
273 {
275
276 /*
277 * We check for no storage as well, just to be paranoid;
278 * unused items should never have storage. Assert() that the
279 * invariant is respected too.
280 */
282
284 break;
285 }
286 if (offsetNumber >= limit)
287 {
288 /* the hint is wrong, so reset it */
290 }
291 }
292 else
293 {
294 /* don't bother searching if hint says there's no free slot */
295 offsetNumber = limit;
296 }
297 }
298
299 /* Reject placing items beyond the first unused line pointer */
300 if (offsetNumber > limit)
301 {
302 elog(WARNING, "specified item offset is too large");
303 return InvalidOffsetNumber;
304 }
305
306 /* Reject placing items beyond heap boundary, if heap */
307 if ((flags & PAI_IS_HEAP) != 0 && offsetNumber > MaxHeapTuplesPerPage)
308 {
309 elog(WARNING, "can't put more than MaxHeapTuplesPerPage items in a heap page");
310 return InvalidOffsetNumber;
311 }
312
313 /*
314 * Compute new lower and upper pointers for page, see if it'll fit.
315 *
316 * Note: do arithmetic as signed ints, to avoid mistakes if, say,
317 * alignedSize > pd_upper.
318 */
319 if (offsetNumber == limit || needshuffle)
320 lower = phdr->pd_lower + sizeof(ItemIdData);
321 else
322 lower = phdr->pd_lower;
323
324 alignedSize = MAXALIGN(size);
325
326 upper = (int) phdr->pd_upper - (int) alignedSize;
327
328 if (lower > upper)
329 return InvalidOffsetNumber;
330
331 /*
332 * OK to insert the item. First, shuffle the existing pointers if needed.
333 */
335
336 if (needshuffle)
337 memmove(itemId + 1, itemId,
338 (limit - offsetNumber) * sizeof(ItemIdData));
339
340 /* set the line pointer */
342
343 /*
344 * Items normally contain no uninitialized bytes. Core bufpage consumers
345 * conform, but this is not a necessary coding rule; a new index AM could
346 * opt to depart from it. However, data type input functions and other
347 * C-language functions that synthesize datums should initialize all
348 * bytes; datumIsEqual() relies on this. Testing here, along with the
349 * similar check in printtup(), helps to catch such mistakes.
350 *
351 * Values of the "name" type retrieved via index-only scans may contain
352 * uninitialized bytes; see comment in btrescan(). Valgrind will report
353 * this as an error, but it is safe to ignore.
354 */
356
357 /* copy the item's data onto the page */
358 memcpy((char *) page + upper, item, size);
359
360 /* adjust page header */
361 phdr->pd_lower = (LocationIndex) lower;
362 phdr->pd_upper = (LocationIndex) upper;
363
364 return offsetNumber;
365}
#define SizeOfPageHeaderData
Definition bufpage.h:241
static ItemId PageGetItemId(Page page, OffsetNumber offsetNumber)
Definition bufpage.h:268
static bool PageHasFreeLinePointers(const PageData *page)
Definition bufpage.h:422
static void PageClearHasFreeLinePointers(Page page)
Definition bufpage.h:432
uint16 LocationIndex
Definition bufpage.h:90
static OffsetNumber PageGetMaxOffsetNumber(const PageData *page)
Definition bufpage.h:396
#define MAXALIGN(LEN)
Definition c.h:896
#define Assert(condition)
Definition c.h:943
size_t Size
Definition c.h:689
memcpy(sums, checksumBaseOffsets, sizeof(checksumBaseOffsets))
int errcode(int sqlerrcode)
Definition elog.c:874
#define WARNING
Definition elog.h:37
#define PANIC
Definition elog.h:44
#define elog(elevel,...)
Definition elog.h:228
#define ereport(elevel,...)
Definition elog.h:152
#define MaxHeapTuplesPerPage
#define ItemIdSetNormal(itemId, off, len)
Definition itemid.h:140
#define ItemIdIsUsed(itemId)
Definition itemid.h:92
#define ItemIdHasStorage(itemId)
Definition itemid.h:120
#define VALGRIND_CHECK_MEM_IS_DEFINED(addr, size)
Definition memdebug.h:23
static char * errmsg
#define InvalidOffsetNumber
Definition off.h:26
#define OffsetNumberIsValid(offsetNumber)
Definition off.h:39
#define OffsetNumberNext(offsetNumber)
Definition off.h:52
uint16 OffsetNumber
Definition off.h:24
#define FirstOffsetNumber
Definition off.h:27
Datum lower(PG_FUNCTION_ARGS)
Datum upper(PG_FUNCTION_ARGS)
#define ERRCODE_DATA_CORRUPTED
LocationIndex pd_special
Definition bufpage.h:193
LocationIndex pd_upper
Definition bufpage.h:192
LocationIndex pd_lower
Definition bufpage.h:191

References Assert, elog, ereport, errcode(), ERRCODE_DATA_CORRUPTED, errmsg, fb(), FirstOffsetNumber, InvalidOffsetNumber, ItemIdHasStorage, ItemIdIsUsed, ItemIdSetNormal, lower(), MAXALIGN, MaxHeapTuplesPerPage, memcpy(), OffsetNumberIsValid, OffsetNumberNext, PageClearHasFreeLinePointers(), PageGetItemId(), PageGetMaxOffsetNumber(), PageHasFreeLinePointers(), PAI_IS_HEAP, PAI_OVERWRITE, PANIC, PageHeaderData::pd_lower, PageHeaderData::pd_special, PageHeaderData::pd_upper, SizeOfPageHeaderData, upper(), VALGRIND_CHECK_MEM_IS_DEFINED, and WARNING.

◆ PageClearAllVisible()

◆ PageClearFull()

static void PageClearFull ( Page  page)
inlinestatic

Definition at line 448 of file bufpage.h.

450{
451 ((PageHeader) page)->pd_flags &= ~PD_PAGE_FULL;

References fb().

Referenced by heap_page_prune_and_freeze(), and mask_page_hint_bits().

◆ PageClearHasFreeLinePointers()

static void PageClearHasFreeLinePointers ( Page  page)
inlinestatic

Definition at line 432 of file bufpage.h.

434{
435 ((PageHeader) page)->pd_flags &= ~PD_HAS_FREE_LINES;

References fb().

Referenced by mask_page_hint_bits(), PageAddItemExtended(), PageRepairFragmentation(), and PageTruncateLinePointerArray().

◆ PageGetContents()

◆ PageGetExactFreeSpace()

Size PageGetExactFreeSpace ( const PageData page)
extern

Definition at line 967 of file bufpage.c.

968{
969 const PageHeaderData *phdr = (const PageHeaderData *) page;
970 int space;
971
972 /*
973 * Use signed arithmetic here so that we behave sensibly if pd_lower >
974 * pd_upper.
975 */
976 space = (int) phdr->pd_upper - (int) phdr->pd_lower;
977
978 if (space < 0)
979 return 0;
980
981 return (Size) space;
982}

References fb(), PageHeaderData::pd_lower, and PageHeaderData::pd_upper.

Referenced by _bt_bottomupdel_pass(), _bt_dedup_pass(), _bt_findsplitloc(), allocNewBuffer(), brin_can_do_samepage_update(), doPickSplit(), GetHashPageStats(), ginHeapTupleFastInsert(), pgstat_heap(), pgstat_index_page(), pgstatindex_impl(), spgAddNodeAction(), SpGistGetBuffer(), SpGistPageAddNewItem(), SpGistSetLastUsedPage(), statapprox_heap(), and writeListPage().

◆ PageGetFreeSpace()

Size PageGetFreeSpace ( const PageData page)
extern

Definition at line 916 of file bufpage.c.

917{
918 const PageHeaderData *phdr = (const PageHeaderData *) page;
919 int space;
920
921 /*
922 * Use signed arithmetic here so that we behave sensibly if pd_lower >
923 * pd_upper.
924 */
925 space = (int) phdr->pd_upper - (int) phdr->pd_lower;
926
927 if (space < (int) sizeof(ItemIdData))
928 return 0;
929 space -= sizeof(ItemIdData);
930
931 return (Size) space;
932}

References fb(), PageHeaderData::pd_lower, and PageHeaderData::pd_upper.

Referenced by _bt_buildadd(), _bt_delete_or_dedup_one_page(), _bt_findinsertloc(), _bt_insertonpg(), _bt_search_insert(), _hash_doinsert(), br_page_get_freespace(), entryIsEnoughSpace(), GetBTPageStatistics(), GetHashPageStatistics(), gist_indexsortbuild_levelstate_add(), gistnospace(), PageGetHeapFreeSpace(), and terminate_brin_buildstate().

◆ PageGetFreeSpaceForMultipleTuples()

Size PageGetFreeSpaceForMultipleTuples ( const PageData page,
int  ntups 
)
extern

Definition at line 943 of file bufpage.c.

944{
945 const PageHeaderData *phdr = (const PageHeaderData *) page;
946 int space;
947
948 /*
949 * Use signed arithmetic here so that we behave sensibly if pd_lower >
950 * pd_upper.
951 */
952 space = (int) phdr->pd_upper - (int) phdr->pd_lower;
953
954 if (space < (int) (ntups * sizeof(ItemIdData)))
955 return 0;
956 space -= ntups * sizeof(ItemIdData);
957
958 return (Size) space;
959}

References fb(), PageHeaderData::pd_lower, and PageHeaderData::pd_upper.

Referenced by _hash_splitbucket(), and _hash_squeezebucket().

◆ PageGetHeapFreeSpace()

Size PageGetHeapFreeSpace ( const PageData page)
extern

Definition at line 1000 of file bufpage.c.

1001{
1002 Size space;
1003
1004 space = PageGetFreeSpace(page);
1005 if (space > 0)
1006 {
1007 OffsetNumber offnum,
1008 nline;
1009
1010 /*
1011 * Are there already MaxHeapTuplesPerPage line pointers in the page?
1012 */
1015 {
1016 if (PageHasFreeLinePointers(page))
1017 {
1018 /*
1019 * Since this is just a hint, we must confirm that there is
1020 * indeed a free line pointer
1021 */
1022 for (offnum = FirstOffsetNumber; offnum <= nline; offnum = OffsetNumberNext(offnum))
1023 {
1024 ItemId lp = PageGetItemId(unconstify(PageData *, page), offnum);
1025
1026 if (!ItemIdIsUsed(lp))
1027 break;
1028 }
1029
1030 if (offnum > nline)
1031 {
1032 /*
1033 * The hint is wrong, but we can't clear it here since we
1034 * don't have the ability to mark the page dirty.
1035 */
1036 space = 0;
1037 }
1038 }
1039 else
1040 {
1041 /*
1042 * Although the hint might be wrong, PageAddItem will believe
1043 * it anyway, so we must believe it too.
1044 */
1045 space = 0;
1046 }
1047 }
1048 }
1049 return space;
1050}
Size PageGetFreeSpace(const PageData *page)
Definition bufpage.c:916
char PageData
Definition bufpage.h:80
#define unconstify(underlying_type, expr)
Definition c.h:1325

References fb(), FirstOffsetNumber, ItemIdIsUsed, MaxHeapTuplesPerPage, OffsetNumberNext, PageGetFreeSpace(), PageGetItemId(), PageGetMaxOffsetNumber(), PageHasFreeLinePointers(), and unconstify.

Referenced by heap_multi_insert(), heap_page_prune_opt(), heap_update(), heap_xlog_insert(), heap_xlog_multi_insert(), heap_xlog_prune_freeze(), heap_xlog_update(), lazy_scan_heap(), lazy_scan_new_or_empty(), lazy_vacuum_heap_rel(), raw_heap_insert(), and RelationGetBufferForTuple().

◆ PageGetItem()

static void * PageGetItem ( PageData page,
const ItemIdData itemId 
)
inlinestatic

Definition at line 378 of file bufpage.h.

380{
381 Assert(page);
383
384 return (char *) page + ItemIdGetOffset(itemId);
#define ItemIdGetOffset(itemId)
Definition itemid.h:65

References Assert, fb(), ItemIdGetOffset, and ItemIdHasStorage.

Referenced by _bt_afternewitemoff(), _bt_binsrch_posting(), _bt_bottomupdel_finish_pending(), _bt_bottomupdel_pass(), _bt_buildadd(), _bt_check_natts(), _bt_check_unique(), _bt_checkkeys_look_ahead(), _bt_compare(), _bt_deadblocks(), _bt_dedup_pass(), _bt_delitems_delete_check(), _bt_do_singleval(), _bt_get_endpoint(), _bt_getstackbuf(), _bt_insert_parent(), _bt_insertonpg(), _bt_killitems(), _bt_mark_page_halfdead(), _bt_newlevel(), _bt_pagedel(), _bt_readpage(), _bt_recsplitloc(), _bt_search(), _bt_set_startikey(), _bt_simpledel_pass(), _bt_split(), _bt_split_firstright(), _bt_split_lastleft(), _bt_strategy(), _bt_unlink_halfdead_page(), _hash_binsearch(), _hash_binsearch_last(), _hash_finish_split(), _hash_kill_items(), _hash_load_qualified_items(), _hash_pgaddtup(), _hash_splitbucket(), _hash_squeezebucket(), addLeafTuple(), addOrReplaceTuple(), BitmapHeapScanNextBlock(), brin_doupdate(), brin_evacuate_page(), brin_page_items(), brinGetTupleForHeapBlock(), bt_check_level_from_leftmost(), bt_child_check(), bt_child_highkey_check(), bt_downlink_missing_check(), bt_page_print_tuples(), bt_right_page_check_scankey(), bt_target_page_check(), btree_xlog_dedup(), btree_xlog_insert(), btree_xlog_mark_page_halfdead(), btree_xlog_split(), btree_xlog_updates(), btvacuumpage(), checkSplitConditions(), collect_corrupt_items(), collectMatchBitmap(), collectMatchesForHeapRow(), doPickSplit(), entryFindChildPtr(), entryGetLeftMostPage(), entryIsEnoughSpace(), entryLocateEntry(), entryLocateLeafEntry(), entryPreparePage(), entrySplitPage(), GetBTPageStatistics(), getRightMostTuple(), gin_check_parent_keys_consistency(), gin_refind_parent(), ginbulkdelete(), ginEntryInsert(), ginRedoInsertEntry(), ginVacuumEntryPage(), gist_page_items(), gist_page_items_bytea(), gistBufferingFindCorrectParent(), gistbufferinginserttuples(), gistchoose(), gistdeletepage(), gistdoinsert(), gistextractpage(), gistFindCorrectParent(), gistFindPath(), gistformdownlink(), gistGetMaxLevel(), gistMemorizeAllDownlinks(), gistnospace(), gistProcessItup(), gistScanPage(), gistvacuum_delete_empty_pages(), gistvacuumpage(), hash_page_items(), hashbucketcleanup(), heap_abort_speculative(), heap_delete(), heap_fetch(), heap_finish_speculative(), heap_force_common(), heap_freeze_prepared_tuples(), heap_get_latest_tid(), heap_get_root_tuples(), heap_hot_search_buffer(), heap_index_delete_tuples(), heap_lock_tuple(), heap_page_items(), heap_page_prune_execute(), heap_page_would_be_all_visible(), heap_pre_freeze_checks(), heap_prune_chain(), heap_prune_record_unchanged_lp_normal(), heap_update(), heap_xlog_confirm(), heap_xlog_delete(), heap_xlog_inplace(), heap_xlog_lock(), heap_xlog_lock_updated(), heap_xlog_prune_freeze(), heap_xlog_update(), heapam_scan_analyze_next_tuple(), heapam_scan_bitmap_next_tuple(), heapam_scan_sample_next_tuple(), heapgettup(), heapgettup_pagemode(), index_compute_xid_horizon_for_tuples(), index_delete_check_htid(), invariant_l_nontarget_offset(), invariant_l_offset(), lazy_scan_noprune(), matchPartialInPendingList(), moveLeafs(), page_collect_tuples(), page_verify_redirects(), PageIndexTupleOverwrite(), processPendingPage(), prune_freeze_plan(), raw_heap_insert(), read_seq_tuple(), RelationPutHeapTuple(), saveNodeLink(), scanGetCandidate(), ScanSourceDatabasePgClassPage(), setRedirectionTuple(), spgdoinsert(), SpGistPageAddNewItem(), spgprocesspending(), spgRedoAddLeaf(), spgRedoAddNode(), spgRedoMoveLeafs(), spgRedoPickSplit(), spgRedoVacuumLeaf(), spgRedoVacuumRedirect(), spgSplitNodeAction(), spgTestLeafTuple(), spgWalk(), startScanEntry(), statapprox_heap(), vacuumLeafPage(), vacuumLeafRoot(), vacuumRedirectAndPlaceholder(), and verify_heapam().

◆ PageGetItemId()

static ItemId PageGetItemId ( Page  page,
OffsetNumber  offsetNumber 
)
inlinestatic

Definition at line 268 of file bufpage.h.

270{
271 return &((PageHeader) page)->pd_linp[offsetNumber - 1];

References fb().

Referenced by _bt_afternewitemoff(), _bt_binsrch_posting(), _bt_bottomupdel_finish_pending(), _bt_bottomupdel_pass(), _bt_buildadd(), _bt_check_natts(), _bt_check_unique(), _bt_checkkeys_look_ahead(), _bt_compare(), _bt_deadblocks(), _bt_dedup_pass(), _bt_delete_or_dedup_one_page(), _bt_delitems_delete_check(), _bt_do_singleval(), _bt_findsplitloc(), _bt_get_endpoint(), _bt_getstackbuf(), _bt_insert_parent(), _bt_insertonpg(), _bt_killitems(), _bt_mark_page_halfdead(), _bt_newlevel(), _bt_pagedel(), _bt_readpage(), _bt_recsplitloc(), _bt_search(), _bt_set_startikey(), _bt_simpledel_pass(), _bt_slideleft(), _bt_split(), _bt_split_firstright(), _bt_split_lastleft(), _bt_split_penalty(), _bt_strategy(), _bt_unlink_halfdead_page(), _hash_binsearch(), _hash_binsearch_last(), _hash_finish_split(), _hash_kill_items(), _hash_load_qualified_items(), _hash_pgaddtup(), _hash_splitbucket(), _hash_squeezebucket(), _hash_vacuum_one_page(), addLeafTuple(), addOrReplaceTuple(), BitmapHeapScanNextBlock(), brin_doupdate(), brin_evacuate_page(), brin_page_items(), brin_start_evacuating_page(), brinGetTupleForHeapBlock(), brininsert(), brinRevmapDesummarizeRange(), bt_page_print_tuples(), btree_xlog_dedup(), btree_xlog_insert(), btree_xlog_mark_page_halfdead(), btree_xlog_split(), btree_xlog_updates(), btvacuumpage(), checkSplitConditions(), collect_corrupt_items(), collectMatchBitmap(), collectMatchesForHeapRow(), compactify_tuples(), count_nondeletable_pages(), doPickSplit(), entryFindChildPtr(), entryGetLeftMostPage(), entryIsEnoughSpace(), entryLocateEntry(), entryLocateLeafEntry(), entryPreparePage(), entrySplitPage(), GetBTPageStatistics(), GetHashPageStatistics(), GetHashPageStats(), getRightMostTuple(), ginbulkdelete(), ginEntryInsert(), ginRedoInsertEntry(), ginVacuumEntryPage(), gist_page_items(), gist_page_items_bytea(), gistBufferingFindCorrectParent(), gistbufferinginserttuples(), gistchoose(), gistdeletepage(), gistdoinsert(), gistextractpage(), gistFindCorrectParent(), gistFindPath(), gistformdownlink(), gistGetMaxLevel(), gistkillitems(), gistMemorizeAllDownlinks(), gistnospace(), gistProcessItup(), gistprunepage(), gistScanPage(), gistvacuum_delete_empty_pages(), gistvacuumpage(), hash_page_items(), hashbucketcleanup(), heap_abort_speculative(), heap_delete(), heap_fetch(), heap_finish_speculative(), heap_force_common(), heap_freeze_prepared_tuples(), heap_get_latest_tid(), heap_get_root_tuples(), heap_hot_search_buffer(), heap_index_delete_tuples(), heap_lock_tuple(), heap_mask(), heap_page_items(), heap_page_prune_execute(), heap_page_would_be_all_visible(), heap_pre_freeze_checks(), heap_prune_chain(), heap_prune_record_unchanged_lp_normal(), heap_update(), heap_xlog_confirm(), heap_xlog_delete(), heap_xlog_inplace(), heap_xlog_lock(), heap_xlog_lock_updated(), heap_xlog_prune_freeze(), heap_xlog_update(), heapam_scan_analyze_next_tuple(), heapam_scan_bitmap_next_tuple(), heapam_scan_sample_next_tuple(), heapgettup(), heapgettup_pagemode(), index_compute_xid_horizon_for_tuples(), index_delete_check_htid(), lazy_scan_noprune(), lazy_vacuum_heap_page(), mask_lp_flags(), matchPartialInPendingList(), moveLeafs(), page_collect_tuples(), page_verify_redirects(), PageAddItemExtended(), PageGetHeapFreeSpace(), PageGetItemIdCareful(), PageGetItemIdCareful(), PageIndexMultiDelete(), PageIndexTupleDelete(), PageIndexTupleDeleteNoCompact(), PageIndexTupleOverwrite(), PageRepairFragmentation(), PageTruncateLinePointerArray(), pgstat_index_page(), processPendingPage(), prune_freeze_fast_path(), prune_freeze_plan(), raw_heap_insert(), read_seq_tuple(), RelationPutHeapTuple(), saveNodeLink(), scanGetCandidate(), ScanSourceDatabasePgClassPage(), setRedirectionTuple(), spgdoinsert(), SpGistPageAddNewItem(), spgprocesspending(), spgRedoAddLeaf(), spgRedoAddNode(), spgRedoMoveLeafs(), spgRedoPickSplit(), spgRedoVacuumLeaf(), spgRedoVacuumRedirect(), spgSplitNodeAction(), spgTestLeafTuple(), spgWalk(), startScanEntry(), statapprox_heap(), vacuumLeafPage(), vacuumLeafRoot(), vacuumRedirectAndPlaceholder(), and verify_heapam().

◆ PageGetLSN()

◆ PageGetMaxOffsetNumber()

static OffsetNumber PageGetMaxOffsetNumber ( const PageData page)
inlinestatic

Definition at line 396 of file bufpage.h.

398{
399 const PageHeaderData *pageheader = (const PageHeaderData *) page;
400
401 if (pageheader->pd_lower <= SizeOfPageHeaderData)
402 return 0;
403 else
404 return (pageheader->pd_lower - SizeOfPageHeaderData) / sizeof(ItemIdData);

References fb(), and SizeOfPageHeaderData.

Referenced by _bt_binsrch(), _bt_binsrch_insert(), _bt_bottomupdel_pass(), _bt_check_natts(), _bt_check_unique(), _bt_dedup_finish_pending(), _bt_dedup_pass(), _bt_delete_or_dedup_one_page(), _bt_do_singleval(), _bt_endpoint(), _bt_findinsertloc(), _bt_findsplitloc(), _bt_get_endpoint(), _bt_getstackbuf(), _bt_killitems(), _bt_lock_subtree_parent(), _bt_mark_page_halfdead(), _bt_pagedel(), _bt_readnextpage(), _bt_readpage(), _bt_search_insert(), _bt_slideleft(), _bt_split(), _bt_unlink_halfdead_page(), _hash_binsearch(), _hash_binsearch_last(), _hash_finish_split(), _hash_kill_items(), _hash_load_qualified_items(), _hash_pgaddtup(), _hash_splitbucket(), _hash_squeezebucket(), _hash_vacuum_one_page(), addOrReplaceTuple(), BitmapHeapScanNextBlock(), brin_doupdate(), brin_evacuate_page(), brin_page_items(), brin_start_evacuating_page(), brin_xlog_insert_update(), brinGetTupleForHeapBlock(), brinRevmapDesummarizeRange(), bt_child_check(), bt_child_highkey_check(), bt_page_items_bytea(), bt_page_items_internal(), bt_right_page_check_scankey(), bt_rootdescend(), bt_target_page_check(), btree_xlog_dedup(), btvacuumpage(), check_index_page(), checkSplitConditions(), collect_corrupt_items(), compactify_tuples(), count_nondeletable_pages(), doPickSplit(), entryFindChildPtr(), entryGetLeftMostPage(), entryLocateEntry(), entryLocateLeafEntry(), entrySplitPage(), GetBTPageStatistics(), GetHashPageStatistics(), GetHashPageStats(), getRightMostTuple(), gin_check_parent_keys_consistency(), gin_refind_parent(), ginbulkdelete(), ginHeapTupleFastInsert(), ginInsertCleanup(), ginRedoInsertEntry(), ginRedoUpdateMetapage(), ginvacuumcleanup(), ginVacuumEntryPage(), ginVacuumPostingTreeLeaves(), gist_page_items(), gist_page_items_bytea(), gistBufferingFindCorrectParent(), gistbufferinginserttuples(), gistchoose(), gistdeletepage(), gistextractpage(), gistfillbuffer(), gistFindCorrectParent(), gistFindPath(), gistformdownlink(), gistMemorizeAllDownlinks(), gistprunepage(), gistRedoPageUpdateRecord(), gistScanPage(), gistvacuum_delete_empty_pages(), gistvacuumpage(), hash_page_items(), hashbucketcleanup(), heap_fetch(), heap_finish_speculative(), heap_force_common(), heap_get_latest_tid(), heap_get_root_tuples(), heap_hot_search_buffer(), heap_index_delete_tuples(), heap_insert(), heap_mask(), heap_multi_insert(), heap_page_items(), heap_page_would_be_all_visible(), heap_prepare_pagescan(), heap_xlog_confirm(), heap_xlog_delete(), heap_xlog_inplace(), heap_xlog_insert(), heap_xlog_lock(), heap_xlog_lock_updated(), heap_xlog_multi_insert(), heap_xlog_update(), heapam_scan_analyze_next_tuple(), heapam_scan_sample_next_tuple(), heapgettup_continue_page(), heapgettup_start_page(), lazy_scan_noprune(), log_heap_update(), mask_lp_flags(), moveLeafs(), moveRightIfItNeeded(), page_verify_redirects(), PageAddItemExtended(), PageGetHeapFreeSpace(), PageIndexMultiDelete(), PageIndexTupleDelete(), PageIndexTupleDeleteNoCompact(), PageIndexTupleOverwrite(), PageRepairFragmentation(), PageTruncateLinePointerArray(), palloc_btree_page(), pgstat_btree_page(), pgstat_gist_page(), pgstat_hash_page(), processPendingPage(), prune_freeze_fast_path(), prune_freeze_plan(), RelationGetBufferForTuple(), scanGetCandidate(), ScanSourceDatabasePgClassPage(), SpGistPageAddNewItem(), spgRedoVacuumRedirect(), spgWalk(), statapprox_heap(), vacuumLeafPage(), vacuumLeafRoot(), vacuumRedirectAndPlaceholder(), and verify_heapam().

◆ PageGetPageLayoutVersion()

static uint8 PageGetPageLayoutVersion ( const PageData page)
inlinestatic

Definition at line 311 of file bufpage.h.

313{
314 return (((const PageHeaderData *) page)->pd_pagesize_version & 0x00FF);

Referenced by page_header().

◆ PageGetPageSize()

static Size PageGetPageSize ( const PageData page)
inlinestatic

◆ PageGetPruneXid()

static TransactionId PageGetPruneXid ( const PageData page)
inlinestatic

Definition at line 470 of file bufpage.h.

472{
473 return ((const PageHeaderData *) page)->pd_prune_xid;

Referenced by heap_page_prune_and_freeze(), heap_page_prune_opt(), and prune_freeze_fast_path().

◆ PageGetSpecialSize()

◆ PageGetTempPage()

Page PageGetTempPage ( const PageData page)
extern

Definition at line 374 of file bufpage.c.

375{
377 Page temp;
378
381
382 return temp;
383}
PageData * Page
Definition bufpage.h:81
void * palloc(Size size)
Definition mcxt.c:1387

References fb(), PageGetPageSize(), and palloc().

Referenced by dataSplitPageInternal(), and ginPlaceToPage().

◆ PageGetTempPageCopy()

Page PageGetTempPageCopy ( const PageData page)
extern

Definition at line 391 of file bufpage.c.

392{
394 Page temp;
395
398
399 memcpy(temp, page, pageSize);
400
401 return temp;
402}

References fb(), memcpy(), PageGetPageSize(), and palloc().

Referenced by entrySplitPage(), and ginVacuumEntryPage().

◆ PageGetTempPageCopySpecial()

Page PageGetTempPageCopySpecial ( const PageData page)
extern

Definition at line 411 of file bufpage.c.

412{
414 Page temp;
415
418
422 PageGetSpecialSize(page));
423
424 return temp;
425}
void PageInit(Page page, Size pageSize, Size specialSize)
Definition bufpage.c:42
static uint16 PageGetSpecialSize(const PageData *page)
Definition bufpage.h:341
#define PageGetSpecialPointer(page)
Definition bufpage.h:363

References fb(), memcpy(), PageGetPageSize(), PageGetSpecialPointer, PageGetSpecialSize(), PageInit(), and palloc().

Referenced by _bt_dedup_pass(), btree_xlog_dedup(), btree_xlog_split(), and gistplacetopage().

◆ PageHasFreeLinePointers()

static bool PageHasFreeLinePointers ( const PageData page)
inlinestatic

Definition at line 422 of file bufpage.h.

424{
425 return ((const PageHeaderData *) page)->pd_flags & PD_HAS_FREE_LINES;
#define PD_HAS_FREE_LINES
Definition bufpage.h:213

References PD_HAS_FREE_LINES.

Referenced by PageAddItemExtended(), and PageGetHeapFreeSpace().

◆ PageIndexMultiDelete()

void PageIndexMultiDelete ( Page  page,
OffsetNumber itemnos,
int  nitems 
)
extern

Definition at line 1170 of file bufpage.c.

1171{
1172 PageHeader phdr = (PageHeader) page;
1173 Offset pd_lower = phdr->pd_lower;
1174 Offset pd_upper = phdr->pd_upper;
1175 Offset pd_special = phdr->pd_special;
1180 ItemId lp;
1181 int nline,
1182 nused;
1183 Size totallen;
1184 Size size;
1185 unsigned offset;
1186 int nextitm;
1187 OffsetNumber offnum;
1188 bool presorted = true; /* For now */
1189
1191
1192 /*
1193 * If there aren't very many items to delete, then retail
1194 * PageIndexTupleDelete is the best way. Delete the items in reverse
1195 * order so we don't have to think about adjusting item numbers for
1196 * previous deletions.
1197 *
1198 * TODO: tune the magic number here
1199 */
1200 if (nitems <= 2)
1201 {
1202 while (--nitems >= 0)
1204 return;
1205 }
1206
1207 /*
1208 * As with PageRepairFragmentation, paranoia seems justified.
1209 */
1210 if (pd_lower < SizeOfPageHeaderData ||
1211 pd_lower > pd_upper ||
1212 pd_upper > pd_special ||
1213 pd_special > BLCKSZ ||
1214 pd_special != MAXALIGN(pd_special))
1215 ereport(ERROR,
1217 errmsg("corrupted page pointers: lower = %u, upper = %u, special = %u",
1218 pd_lower, pd_upper, pd_special)));
1219
1220 /*
1221 * Scan the line pointer array and build a list of just the ones we are
1222 * going to keep. Notice we do not modify the page yet, since we are
1223 * still validity-checking.
1224 */
1227 totallen = 0;
1228 nused = 0;
1229 nextitm = 0;
1230 last_offset = pd_special;
1231 for (offnum = FirstOffsetNumber; offnum <= nline; offnum = OffsetNumberNext(offnum))
1232 {
1233 lp = PageGetItemId(page, offnum);
1235 size = ItemIdGetLength(lp);
1236 offset = ItemIdGetOffset(lp);
1237 if (offset < pd_upper ||
1238 (offset + size) > pd_special ||
1239 offset != MAXALIGN(offset))
1240 ereport(ERROR,
1242 errmsg("corrupted line pointer: offset = %u, size = %zu",
1243 offset, size)));
1244
1245 if (nextitm < nitems && offnum == itemnos[nextitm])
1246 {
1247 /* skip item to be deleted */
1248 nextitm++;
1249 }
1250 else
1251 {
1252 itemidptr->offsetindex = nused; /* where it will go */
1253 itemidptr->itemoff = offset;
1254
1255 if (last_offset > itemidptr->itemoff)
1256 last_offset = itemidptr->itemoff;
1257 else
1258 presorted = false;
1259
1260 itemidptr->alignedlen = MAXALIGN(size);
1261 totallen += itemidptr->alignedlen;
1262 newitemids[nused] = *lp;
1263 itemidptr++;
1264 nused++;
1265 }
1266 }
1267
1268 /* this will catch invalid or out-of-order itemnos[] */
1269 if (nextitm != nitems)
1270 elog(ERROR, "incorrect index offsets supplied");
1271
1272 if (totallen > (Size) (pd_special - pd_lower))
1273 ereport(ERROR,
1275 errmsg("corrupted item lengths: total %zu, available space %u",
1276 totallen, pd_special - pd_lower)));
1277
1278 /*
1279 * Looks good. Overwrite the line pointers with the copy, from which we've
1280 * removed all the unused items.
1281 */
1282 memcpy(phdr->pd_linp, newitemids, nused * sizeof(ItemIdData));
1283 phdr->pd_lower = SizeOfPageHeaderData + nused * sizeof(ItemIdData);
1284
1285 /* and compactify the tuple data */
1286 if (nused > 0)
1287 compactify_tuples(itemidbase, nused, page, presorted);
1288 else
1289 phdr->pd_upper = pd_special;
1290}
static void compactify_tuples(itemIdCompact itemidbase, int nitems, Page page, bool presorted)
Definition bufpage.c:483
void PageIndexTupleDelete(Page page, OffsetNumber offnum)
Definition bufpage.c:1061
signed int Offset
Definition c.h:708
#define ERROR
Definition elog.h:40
#define nitems(x)
Definition indent.h:31
#define ItemIdGetLength(itemId)
Definition itemid.h:59
#define MaxIndexTuplesPerPage
Definition itup.h:181
ItemIdData pd_linp[FLEXIBLE_ARRAY_MEMBER]
Definition bufpage.h:196

References Assert, compactify_tuples(), elog, ereport, errcode(), ERRCODE_DATA_CORRUPTED, errmsg, ERROR, fb(), FirstOffsetNumber, ItemIdGetLength, ItemIdGetOffset, ItemIdHasStorage, MAXALIGN, MaxIndexTuplesPerPage, memcpy(), nitems, OffsetNumberNext, PageGetItemId(), PageGetMaxOffsetNumber(), PageIndexTupleDelete(), PageHeaderData::pd_linp, PageHeaderData::pd_lower, PageHeaderData::pd_special, PageHeaderData::pd_upper, and SizeOfPageHeaderData.

Referenced by _bt_delitems_delete(), _bt_delitems_vacuum(), _hash_squeezebucket(), _hash_vacuum_one_page(), btree_xlog_delete(), btree_xlog_vacuum(), gistprunepage(), gistRedoDeleteRecord(), gistRedoPageUpdateRecord(), gistvacuumpage(), hash_xlog_delete(), hash_xlog_move_page_contents(), hash_xlog_vacuum_one_page(), hashbucketcleanup(), spgPageIndexMultiDelete(), spgRedoVacuumRedirect(), spgRedoVacuumRoot(), vacuumLeafRoot(), and vacuumRedirectAndPlaceholder().

◆ PageIndexTupleDelete()

void PageIndexTupleDelete ( Page  page,
OffsetNumber  offnum 
)
extern

Definition at line 1061 of file bufpage.c.

1062{
1063 PageHeader phdr = (PageHeader) page;
1064 char *addr;
1065 ItemId tup;
1066 Size size;
1067 unsigned offset;
1068 int nbytes;
1069 int offidx;
1070 int nline;
1071
1072 /*
1073 * As with PageRepairFragmentation, paranoia seems justified.
1074 */
1075 if (phdr->pd_lower < SizeOfPageHeaderData ||
1076 phdr->pd_lower > phdr->pd_upper ||
1077 phdr->pd_upper > phdr->pd_special ||
1078 phdr->pd_special > BLCKSZ ||
1079 phdr->pd_special != MAXALIGN(phdr->pd_special))
1080 ereport(ERROR,
1082 errmsg("corrupted page pointers: lower = %u, upper = %u, special = %u",
1083 phdr->pd_lower, phdr->pd_upper, phdr->pd_special)));
1084
1086 if ((int) offnum <= 0 || (int) offnum > nline)
1087 elog(ERROR, "invalid index offnum: %u", offnum);
1088
1089 /* change offset number to offset index */
1090 offidx = offnum - 1;
1091
1092 tup = PageGetItemId(page, offnum);
1094 size = ItemIdGetLength(tup);
1095 offset = ItemIdGetOffset(tup);
1096
1097 if (offset < phdr->pd_upper || (offset + size) > phdr->pd_special ||
1098 offset != MAXALIGN(offset))
1099 ereport(ERROR,
1101 errmsg("corrupted line pointer: offset = %u, size = %zu",
1102 offset, size)));
1103
1104 /* Amount of space to actually be deleted */
1105 size = MAXALIGN(size);
1106
1107 /*
1108 * First, we want to get rid of the pd_linp entry for the index tuple. We
1109 * copy all subsequent linp's back one slot in the array. We don't use
1110 * PageGetItemId, because we are manipulating the _array_, not individual
1111 * linp's.
1112 */
1113 nbytes = phdr->pd_lower -
1114 ((char *) &phdr->pd_linp[offidx + 1] - (char *) phdr);
1115
1116 if (nbytes > 0)
1117 memmove(&(phdr->pd_linp[offidx]),
1118 &(phdr->pd_linp[offidx + 1]),
1119 nbytes);
1120
1121 /*
1122 * Now move everything between the old upper bound (beginning of tuple
1123 * space) and the beginning of the deleted tuple forward, so that space in
1124 * the middle of the page is left free. If we've just deleted the tuple
1125 * at the beginning of tuple space, then there's no need to do the copy.
1126 */
1127
1128 /* beginning of tuple space */
1129 addr = (char *) page + phdr->pd_upper;
1130
1131 if (offset > phdr->pd_upper)
1132 memmove(addr + size, addr, offset - phdr->pd_upper);
1133
1134 /* adjust free space boundary pointers */
1135 phdr->pd_upper += size;
1136 phdr->pd_lower -= sizeof(ItemIdData);
1137
1138 /*
1139 * Finally, we need to adjust the linp entries that remain.
1140 *
1141 * Anything that used to be before the deleted tuple's data was moved
1142 * forward by the size of the deleted tuple.
1143 */
1144 if (!PageIsEmpty(page))
1145 {
1146 int i;
1147
1148 nline--; /* there's one less than when we started */
1149 for (i = 1; i <= nline; i++)
1150 {
1151 ItemId ii = PageGetItemId(page, i);
1152
1154 if (ItemIdGetOffset(ii) <= offset)
1155 ii->lp_off += size;
1156 }
1157 }
1158}
static bool PageIsEmpty(const PageData *page)
Definition bufpage.h:248
int i
Definition isn.c:77
unsigned lp_off
Definition itemid.h:27

References Assert, elog, ereport, errcode(), ERRCODE_DATA_CORRUPTED, errmsg, ERROR, fb(), i, ItemIdGetLength, ItemIdGetOffset, ItemIdHasStorage, ItemIdData::lp_off, MAXALIGN, PageGetItemId(), PageGetMaxOffsetNumber(), PageIsEmpty(), PageHeaderData::pd_linp, PageHeaderData::pd_lower, PageHeaderData::pd_special, PageHeaderData::pd_upper, and SizeOfPageHeaderData.

Referenced by _bt_mark_page_halfdead(), addLeafTuple(), addOrReplaceTuple(), btree_xlog_mark_page_halfdead(), entryPreparePage(), ginRedoInsertEntry(), ginVacuumEntryPage(), gistdeletepage(), gistplacetopage(), gistRedoPageDelete(), PageIndexMultiDelete(), spgAddNodeAction(), SpGistPageAddNewItem(), spgRedoAddLeaf(), spgRedoAddNode(), spgRedoSplitTuple(), and spgSplitNodeAction().

◆ PageIndexTupleDeleteNoCompact()

void PageIndexTupleDeleteNoCompact ( Page  page,
OffsetNumber  offnum 
)
extern

Definition at line 1304 of file bufpage.c.

1305{
1306 PageHeader phdr = (PageHeader) page;
1307 char *addr;
1308 ItemId tup;
1309 Size size;
1310 unsigned offset;
1311 int nline;
1312
1313 /*
1314 * As with PageRepairFragmentation, paranoia seems justified.
1315 */
1316 if (phdr->pd_lower < SizeOfPageHeaderData ||
1317 phdr->pd_lower > phdr->pd_upper ||
1318 phdr->pd_upper > phdr->pd_special ||
1319 phdr->pd_special > BLCKSZ ||
1320 phdr->pd_special != MAXALIGN(phdr->pd_special))
1321 ereport(ERROR,
1323 errmsg("corrupted page pointers: lower = %u, upper = %u, special = %u",
1324 phdr->pd_lower, phdr->pd_upper, phdr->pd_special)));
1325
1327 if ((int) offnum <= 0 || (int) offnum > nline)
1328 elog(ERROR, "invalid index offnum: %u", offnum);
1329
1330 tup = PageGetItemId(page, offnum);
1332 size = ItemIdGetLength(tup);
1333 offset = ItemIdGetOffset(tup);
1334
1335 if (offset < phdr->pd_upper || (offset + size) > phdr->pd_special ||
1336 offset != MAXALIGN(offset))
1337 ereport(ERROR,
1339 errmsg("corrupted line pointer: offset = %u, size = %zu",
1340 offset, size)));
1341
1342 /* Amount of space to actually be deleted */
1343 size = MAXALIGN(size);
1344
1345 /*
1346 * Either set the line pointer to "unused", or zap it if it's the last
1347 * one. (Note: it's possible that the next-to-last one(s) are already
1348 * unused, but we do not trouble to try to compact them out if so.)
1349 */
1350 if ((int) offnum < nline)
1352 else
1353 {
1354 phdr->pd_lower -= sizeof(ItemIdData);
1355 nline--; /* there's one less than when we started */
1356 }
1357
1358 /*
1359 * Now move everything between the old upper bound (beginning of tuple
1360 * space) and the beginning of the deleted tuple forward, so that space in
1361 * the middle of the page is left free. If we've just deleted the tuple
1362 * at the beginning of tuple space, then there's no need to do the copy.
1363 */
1364
1365 /* beginning of tuple space */
1366 addr = (char *) page + phdr->pd_upper;
1367
1368 if (offset > phdr->pd_upper)
1369 memmove(addr + size, addr, offset - phdr->pd_upper);
1370
1371 /* adjust free space boundary pointer */
1372 phdr->pd_upper += size;
1373
1374 /*
1375 * Finally, we need to adjust the linp entries that remain.
1376 *
1377 * Anything that used to be before the deleted tuple's data was moved
1378 * forward by the size of the deleted tuple.
1379 */
1380 if (!PageIsEmpty(page))
1381 {
1382 int i;
1383
1384 for (i = 1; i <= nline; i++)
1385 {
1386 ItemId ii = PageGetItemId(page, i);
1387
1388 if (ItemIdHasStorage(ii) && ItemIdGetOffset(ii) <= offset)
1389 ii->lp_off += size;
1390 }
1391 }
1392}
#define ItemIdSetUnused(itemId)
Definition itemid.h:128

References Assert, elog, ereport, errcode(), ERRCODE_DATA_CORRUPTED, errmsg, ERROR, fb(), i, ItemIdGetLength, ItemIdGetOffset, ItemIdHasStorage, ItemIdSetUnused, ItemIdData::lp_off, MAXALIGN, PageGetItemId(), PageGetMaxOffsetNumber(), PageIsEmpty(), PageHeaderData::pd_lower, PageHeaderData::pd_special, PageHeaderData::pd_upper, and SizeOfPageHeaderData.

Referenced by brin_doupdate(), brin_xlog_desummarize_page(), brin_xlog_update(), and brinRevmapDesummarizeRange().

◆ PageIndexTupleOverwrite()

bool PageIndexTupleOverwrite ( Page  page,
OffsetNumber  offnum,
const void newtup,
Size  newsize 
)
extern

Definition at line 1414 of file bufpage.c.

1416{
1417 PageHeader phdr = (PageHeader) page;
1418 ItemId tupid;
1419 int oldsize;
1420 unsigned offset;
1422 int size_diff;
1423 int itemcount;
1424
1425 /*
1426 * As with PageRepairFragmentation, paranoia seems justified.
1427 */
1428 if (phdr->pd_lower < SizeOfPageHeaderData ||
1429 phdr->pd_lower > phdr->pd_upper ||
1430 phdr->pd_upper > phdr->pd_special ||
1431 phdr->pd_special > BLCKSZ ||
1432 phdr->pd_special != MAXALIGN(phdr->pd_special))
1433 ereport(ERROR,
1435 errmsg("corrupted page pointers: lower = %u, upper = %u, special = %u",
1436 phdr->pd_lower, phdr->pd_upper, phdr->pd_special)));
1437
1439 if ((int) offnum <= 0 || (int) offnum > itemcount)
1440 elog(ERROR, "invalid index offnum: %u", offnum);
1441
1442 tupid = PageGetItemId(page, offnum);
1445 offset = ItemIdGetOffset(tupid);
1446
1447 if (offset < phdr->pd_upper || (offset + oldsize) > phdr->pd_special ||
1448 offset != MAXALIGN(offset))
1449 ereport(ERROR,
1451 errmsg("corrupted line pointer: offset = %u, size = %d",
1452 offset, oldsize)));
1453
1454 /*
1455 * Determine actual change in space requirement, check for page overflow.
1456 */
1459 if (alignednewsize > oldsize + (phdr->pd_upper - phdr->pd_lower))
1460 return false;
1461
1462 /*
1463 * Relocate existing data and update line pointers, unless the new tuple
1464 * is the same size as the old (after alignment), in which case there's
1465 * nothing to do. Notice that what we have to relocate is data before the
1466 * target tuple, not data after, so it's convenient to express size_diff
1467 * as the amount by which the tuple's size is decreasing, making it the
1468 * delta to add to pd_upper and affected line pointers.
1469 */
1471 if (size_diff != 0)
1472 {
1473 char *addr = (char *) page + phdr->pd_upper;
1474 int i;
1475
1476 /* relocate all tuple data before the target tuple */
1477 memmove(addr + size_diff, addr, offset - phdr->pd_upper);
1478
1479 /* adjust free space boundary pointer */
1480 phdr->pd_upper += size_diff;
1481
1482 /* adjust affected line pointers too */
1483 for (i = FirstOffsetNumber; i <= itemcount; i++)
1484 {
1485 ItemId ii = PageGetItemId(page, i);
1486
1487 /* Allow items without storage; currently only BRIN needs that */
1488 if (ItemIdHasStorage(ii) && ItemIdGetOffset(ii) <= offset)
1489 ii->lp_off += size_diff;
1490 }
1491 }
1492
1493 /* Update the item's tuple length without changing its lp_flags field */
1494 tupid->lp_off = offset + size_diff;
1495 tupid->lp_len = newsize;
1496
1497 /* Copy new tuple data onto page */
1499
1500 return true;
1501}
static void * PageGetItem(PageData *page, const ItemIdData *itemId)
Definition bufpage.h:378

References Assert, elog, ereport, errcode(), ERRCODE_DATA_CORRUPTED, errmsg, ERROR, fb(), FirstOffsetNumber, i, ItemIdGetLength, ItemIdGetOffset, ItemIdHasStorage, ItemIdData::lp_off, MAXALIGN, memcpy(), PageGetItem(), PageGetItemId(), PageGetMaxOffsetNumber(), PageHeaderData::pd_lower, PageHeaderData::pd_special, PageHeaderData::pd_upper, and SizeOfPageHeaderData.

Referenced by _bt_buildadd(), _bt_delitems_delete(), _bt_delitems_vacuum(), _bt_mark_page_halfdead(), brin_doupdate(), brin_xlog_samepage_update(), btree_xlog_updates(), gistplacetopage(), and gistRedoPageUpdateRecord().

◆ PageInit()

void PageInit ( Page  page,
Size  pageSize,
Size  specialSize 
)
extern

Definition at line 42 of file bufpage.c.

43{
44 PageHeader p = (PageHeader) page;
45
47
50
51 /* Make sure all fields of page are zero, as well as unused space */
52 MemSet(p, 0, pageSize);
53
54 p->pd_flags = 0;
59 /* p->pd_prune_xid = InvalidTransactionId; done by above MemSet */
60}
#define PG_PAGE_LAYOUT_VERSION
Definition bufpage.h:231
static void PageSetPageSizeAndVersion(Page page, Size size, uint8 version)
Definition bufpage.h:324
#define MemSet(start, val, len)
Definition c.h:1107
uint16 pd_flags
Definition bufpage.h:190

References Assert, fb(), MAXALIGN, MemSet, PageSetPageSizeAndVersion(), PageHeaderData::pd_flags, PageHeaderData::pd_lower, PageHeaderData::pd_special, PageHeaderData::pd_upper, PG_PAGE_LAYOUT_VERSION, and SizeOfPageHeaderData.

Referenced by _bt_pageinit(), _hash_pageinit(), BloomInitPage(), brin_page_init(), fill_seq_fork_with_data(), fsm_readbuf(), GinInitPage(), gistinitpage(), heap_xlog_insert(), heap_xlog_multi_insert(), heap_xlog_prune_freeze(), heap_xlog_update(), modify_rel_block(), PageGetTempPageCopySpecial(), raw_heap_insert(), RelationAddBlocks(), RelationGetBufferForTuple(), seq_redo(), SpGistInitPage(), vm_readbuf(), and XLogRecordPageWithFreeSpace().

◆ PageIsAllVisible()

◆ PageIsEmpty()

◆ PageIsFull()

static bool PageIsFull ( const PageData page)
inlinestatic

Definition at line 438 of file bufpage.h.

440{
441 return ((const PageHeaderData *) page)->pd_flags & PD_PAGE_FULL;
#define PD_PAGE_FULL
Definition bufpage.h:214

References PD_PAGE_FULL.

Referenced by heap_page_prune_and_freeze(), and heap_page_prune_opt().

◆ PageIsNew()

static bool PageIsNew ( const PageData page)
inlinestatic

Definition at line 258 of file bufpage.h.

260{
261 return ((const PageHeaderData *) page)->pd_upper == 0;

Referenced by _bt_allocbuf(), _bt_checkpage(), _hash_checkpage(), blbulkdelete(), blgetbitmap(), blinsert(), BloomNewBuffer(), BloomPageAddItem(), blvacuumcleanup(), brin_metapage_info(), brin_page_cleanup(), brin_page_items(), brin_page_type(), brin_revmap_data(), brin_start_evacuating_page(), bt_page_items_bytea(), BTPageGetDeleteXid(), BTPageIsRecyclable(), btvacuumpage(), check_index_page(), count_nondeletable_pages(), ExtendBufferedRelShared(), fsm_page_contents(), fsm_readbuf(), gin_leafpage_items(), gin_metapage_info(), gin_page_opaque_info(), GinPageIsRecyclable(), gist_page_items(), gist_page_items_bytea(), gist_page_opaque_info(), gistcheckpage(), gistdeletepage(), gistNewBuffer(), gistPageRecyclable(), gistvacuum_delete_empty_pages(), hash_page_type(), heap_xlog_multi_insert(), heap_xlog_prune_freeze(), lazy_scan_new_or_empty(), log_newpage(), log_newpage_range(), log_newpages(), page_checksum_internal(), PageIsVerified(), PageSetChecksum(), pg_checksum_page(), pgstat_btree_page(), pgstat_gist_page(), pgstat_hash_page(), pgstathashindex(), RelationAddBlocks(), RelationGetBufferForTuple(), revmap_physical_extend(), scan_file(), ScanSourceDatabasePgClass(), SpGistGetBuffer(), SpGistNewBuffer(), spgprocesspending(), spgvacuumpage(), statapprox_heap(), verify_brin_page(), verify_gist_page(), verify_hash_page(), verify_page_checksum(), vm_readbuf(), XLogReadBufferExtended(), XLogReadBufferForRedoExtended(), and XLogRecordPageWithFreeSpace().

◆ PageIsVerified()

bool PageIsVerified ( PageData page,
BlockNumber  blkno,
int  flags,
bool checksum_failure_p 
)
extern

Definition at line 94 of file bufpage.c.

95{
96 const PageHeaderData *p = (const PageHeaderData *) page;
97 size_t *pagebytes;
98 bool checksum_failure = false;
99 bool header_sane = false;
100 uint16 checksum = 0;
101
103 *checksum_failure_p = false;
104
105 /*
106 * Don't verify page data unless the page passes basic non-zero test
107 */
108 if (!PageIsNew(page))
109 {
110 /*
111 * There shouldn't be any check for interrupt calls happening in this
112 * codepath, but just to be on the safe side we hold interrupts since
113 * if they did happen the data checksum state could change during
114 * verifying checksums, which could lead to incorrect verification
115 * results.
116 */
119 {
120 checksum = pg_checksum_page(page, blkno);
121
122 if (checksum != p->pd_checksum)
123 {
124 checksum_failure = true;
126 *checksum_failure_p = true;
127 }
128 }
130
131 /*
132 * The following checks don't prove the header is correct, only that
133 * it looks sane enough to allow into the buffer pool. Later usage of
134 * the block can still reveal problems, which is why we offer the
135 * checksum option.
136 */
137 if ((p->pd_flags & ~PD_VALID_FLAG_BITS) == 0 &&
138 p->pd_lower <= p->pd_upper &&
139 p->pd_upper <= p->pd_special &&
140 p->pd_special <= BLCKSZ &&
142 header_sane = true;
143
145 return true;
146 }
147
148 /* Check all-zeroes case */
149 pagebytes = (size_t *) page;
150
152 return true;
153
154 /*
155 * Throw a WARNING/LOG, as instructed by PIV_LOG_*, if the checksum fails,
156 * but only after we've checked for the all-zeroes case.
157 */
159 {
160 if ((flags & (PIV_LOG_WARNING | PIV_LOG_LOG)) != 0)
163 errmsg("page verification failed, calculated checksum %u but expected %u%s",
164 checksum, p->pd_checksum,
165 (flags & PIV_ZERO_BUFFERS_ON_ERROR ? ", buffer will be zeroed" : ""))));
166
168 return true;
169 }
170
171 return false;
172}
#define PD_VALID_FLAG_BITS
Definition bufpage.h:217
#define PIV_LOG_LOG
Definition bufpage.h:500
#define PIV_ZERO_BUFFERS_ON_ERROR
Definition bufpage.h:502
#define PIV_LOG_WARNING
Definition bufpage.h:499
static bool PageIsNew(const PageData *page)
Definition bufpage.h:258
#define PIV_IGNORE_CHECKSUM_FAILURE
Definition bufpage.h:501
uint16 pg_checksum_page(char *page, BlockNumber blkno)
#define LOG
Definition elog.h:32
static bool pg_memory_is_all_zeros(const void *ptr, size_t len)
Definition memutils.h:219
#define RESUME_INTERRUPTS()
Definition miscadmin.h:138
#define HOLD_INTERRUPTS()
Definition miscadmin.h:136
static bool checksum_failure
uint16 pd_checksum
Definition bufpage.h:189
bool DataChecksumsNeedVerify(void)
Definition xlog.c:4706

References checksum_failure, DataChecksumsNeedVerify(), ereport, errcode(), ERRCODE_DATA_CORRUPTED, errmsg, fb(), HOLD_INTERRUPTS, LOG, MAXALIGN, PageIsNew(), PageHeaderData::pd_checksum, PageHeaderData::pd_flags, PageHeaderData::pd_lower, PageHeaderData::pd_special, PageHeaderData::pd_upper, PD_VALID_FLAG_BITS, pg_checksum_page(), pg_memory_is_all_zeros(), PIV_IGNORE_CHECKSUM_FAILURE, PIV_LOG_LOG, PIV_LOG_WARNING, PIV_ZERO_BUFFERS_ON_ERROR, RESUME_INTERRUPTS, and WARNING.

Referenced by buffer_readv_complete_one(), and RelationCopyStorage().

◆ PageRepairFragmentation()

void PageRepairFragmentation ( Page  page)
extern

Definition at line 708 of file bufpage.c.

709{
710 Offset pd_lower = ((PageHeader) page)->pd_lower;
711 Offset pd_upper = ((PageHeader) page)->pd_upper;
712 Offset pd_special = ((PageHeader) page)->pd_special;
716 ItemId lp;
717 int nline,
718 nstorage,
719 nunused;
721 int i;
722 Size totallen;
723 bool presorted = true; /* For now */
724
725 /*
726 * It's worth the trouble to be more paranoid here than in most places,
727 * because we are about to reshuffle data in (what is usually) a shared
728 * disk buffer. If we aren't careful then corrupted pointers, lengths,
729 * etc could cause us to clobber adjacent disk buffers, spreading the data
730 * loss further. So, check everything.
731 */
732 if (pd_lower < SizeOfPageHeaderData ||
733 pd_lower > pd_upper ||
734 pd_upper > pd_special ||
735 pd_special > BLCKSZ ||
736 pd_special != MAXALIGN(pd_special))
739 errmsg("corrupted page pointers: lower = %u, upper = %u, special = %u",
740 pd_lower, pd_upper, pd_special)));
741
742 /*
743 * Run through the line pointer array and collect data about live items.
744 */
747 nunused = totallen = 0;
748 last_offset = pd_special;
749 for (i = FirstOffsetNumber; i <= nline; i++)
750 {
751 lp = PageGetItemId(page, i);
752 if (ItemIdIsUsed(lp))
753 {
754 if (ItemIdHasStorage(lp))
755 {
756 itemidptr->offsetindex = i - 1;
757 itemidptr->itemoff = ItemIdGetOffset(lp);
758
759 if (last_offset > itemidptr->itemoff)
760 last_offset = itemidptr->itemoff;
761 else
762 presorted = false;
763
764 if (unlikely(itemidptr->itemoff < (int) pd_upper ||
765 itemidptr->itemoff >= (int) pd_special))
768 errmsg("corrupted line pointer: %u",
769 itemidptr->itemoff)));
770 itemidptr->alignedlen = MAXALIGN(ItemIdGetLength(lp));
771 totallen += itemidptr->alignedlen;
772 itemidptr++;
773 }
774
775 finalusedlp = i; /* Could be the final non-LP_UNUSED item */
776 }
777 else
778 {
779 /* Unused entries should have lp_len = 0, but make sure */
782 nunused++;
783 }
784 }
785
787 if (nstorage == 0)
788 {
789 /* Page is completely empty, so just reset it quickly */
790 ((PageHeader) page)->pd_upper = pd_special;
791 }
792 else
793 {
794 /* Need to compact the page the hard way */
795 if (totallen > (Size) (pd_special - pd_lower))
798 errmsg("corrupted item lengths: total %zu, available space %u",
799 totallen, pd_special - pd_lower)));
800
802 }
803
804 if (finalusedlp != nline)
805 {
806 /* The last line pointer is not the last used line pointer */
808
809 Assert(nunused >= nunusedend && nunusedend > 0);
810
811 /* remove trailing unused line pointers from the count */
812 nunused -= nunusedend;
813 /* truncate the line pointer array */
814 ((PageHeader) page)->pd_lower -= (sizeof(ItemIdData) * nunusedend);
815 }
816
817 /* Set hint bit for PageAddItemExtended */
818 if (nunused > 0)
820 else
822}
static void PageSetHasFreeLinePointers(Page page)
Definition bufpage.h:427
#define unlikely(x)
Definition c.h:438

References Assert, compactify_tuples(), ereport, errcode(), ERRCODE_DATA_CORRUPTED, errmsg, ERROR, fb(), FirstOffsetNumber, i, InvalidOffsetNumber, ItemIdGetLength, ItemIdGetOffset, ItemIdHasStorage, ItemIdIsUsed, ItemIdSetUnused, MAXALIGN, MaxHeapTuplesPerPage, PageClearHasFreeLinePointers(), PageGetItemId(), PageGetMaxOffsetNumber(), PageSetHasFreeLinePointers(), SizeOfPageHeaderData, and unlikely.

Referenced by heap_page_prune_execute().

◆ PageRestoreTempPage()

void PageRestoreTempPage ( Page  tempPage,
Page  oldPage 
)
extern

Definition at line 433 of file bufpage.c.

434{
436
439
441}
void pfree(void *pointer)
Definition mcxt.c:1616

References fb(), memcpy(), PageGetPageSize(), and pfree().

Referenced by _bt_dedup_pass(), btree_xlog_dedup(), btree_xlog_split(), createPostingTree(), ginbulkdelete(), and gistplacetopage().

◆ PageSetAllVisible()

static void PageSetAllVisible ( Page  page)
inlinestatic

◆ PageSetChecksum()

void PageSetChecksum ( Page  page,
BlockNumber  blkno 
)
extern

Definition at line 1518 of file bufpage.c.

1519{
1521 /* If we don't need a checksum, just return */
1522 if (PageIsNew(page) || !DataChecksumsNeedWrite())
1523 {
1525 return;
1526 }
1527
1528 ((PageHeader) page)->pd_checksum = pg_checksum_page(page, blkno);
1530}
bool DataChecksumsNeedWrite(void)
Definition xlog.c:4678

References DataChecksumsNeedWrite(), HOLD_INTERRUPTS, PageIsNew(), pg_checksum_page(), and RESUME_INTERRUPTS.

Referenced by _hash_alloc_buckets(), FlushBuffer(), FlushLocalBuffer(), modify_rel_block(), and smgr_bulk_flush().

◆ PageSetFull()

static void PageSetFull ( Page  page)
inlinestatic

Definition at line 443 of file bufpage.h.

445{
446 ((PageHeader) page)->pd_flags |= PD_PAGE_FULL;

References PD_PAGE_FULL.

Referenced by heap_update().

◆ PageSetHasFreeLinePointers()

static void PageSetHasFreeLinePointers ( Page  page)
inlinestatic

Definition at line 427 of file bufpage.h.

429{
430 ((PageHeader) page)->pd_flags |= PD_HAS_FREE_LINES;

References PD_HAS_FREE_LINES.

Referenced by PageRepairFragmentation(), and PageTruncateLinePointerArray().

◆ PageSetLSN()

static void PageSetLSN ( Page  page,
XLogRecPtr  lsn 
)
inlinestatic

Definition at line 416 of file bufpage.h.

418{
419 PageXLogRecPtrSet(&((PageHeader) page)->pd_lsn, lsn);
static void PageXLogRecPtrSet(volatile PageXLogRecPtr *ptr, XLogRecPtr lsn)
Definition bufpage.h:131

References PageXLogRecPtrSet().

Referenced by _bt_clear_incomplete_split(), _bt_dedup_pass(), _bt_delitems_delete(), _bt_delitems_vacuum(), _bt_getroot(), _bt_insertonpg(), _bt_mark_page_halfdead(), _bt_newlevel(), _bt_restore_meta(), _bt_set_cleanup_info(), _bt_split(), _bt_unlink_halfdead_page(), _hash_addovflpage(), _hash_doinsert(), _hash_expandtable(), _hash_freeovflpage(), _hash_init(), _hash_splitbucket(), _hash_squeezebucket(), _hash_vacuum_one_page(), addLeafTuple(), brin_doinsert(), brin_doupdate(), brin_xlog_createidx(), brin_xlog_desummarize_page(), brin_xlog_insert_update(), brin_xlog_revmap_extend(), brin_xlog_samepage_update(), brin_xlog_update(), brinbuild(), brinRevmapDesummarizeRange(), btree_xlog_dedup(), btree_xlog_delete(), btree_xlog_insert(), btree_xlog_mark_page_halfdead(), btree_xlog_newroot(), btree_xlog_split(), btree_xlog_unlink_page(), btree_xlog_vacuum(), createPostingTree(), doPickSplit(), fill_seq_fork_with_data(), generic_redo(), GenericXLogFinish(), ginDeletePostingPage(), ginHeapTupleFastInsert(), ginPlaceToPage(), ginRedoClearIncompleteSplit(), ginRedoCreatePTree(), ginRedoDeleteListPages(), ginRedoDeletePage(), ginRedoInsert(), ginRedoInsertListPage(), ginRedoUpdateMetapage(), ginRedoVacuumDataLeafPage(), ginUpdateStats(), ginVacuumPostingTreeLeaf(), gist_indexsortbuild(), gist_indexsortbuild_levelstate_flush(), gistbuild(), gistdeletepage(), gistplacetopage(), gistprunepage(), gistRedoClearFollowRight(), gistRedoDeleteRecord(), gistRedoPageDelete(), gistRedoPageSplitRecord(), gistRedoPageUpdateRecord(), gistvacuumpage(), hash_xlog_add_ovfl_page(), hash_xlog_delete(), hash_xlog_init_bitmap_page(), hash_xlog_init_meta_page(), hash_xlog_insert(), hash_xlog_move_page_contents(), hash_xlog_split_allocate_page(), hash_xlog_split_cleanup(), hash_xlog_split_complete(), hash_xlog_squeeze_page(), hash_xlog_update_meta_page(), hash_xlog_vacuum_one_page(), hashbucketcleanup(), hashbulkdelete(), heap_abort_speculative(), heap_delete(), heap_finish_speculative(), heap_inplace_update_and_unlock(), heap_insert(), heap_lock_tuple(), heap_lock_updated_tuple_rec(), heap_multi_insert(), heap_update(), heap_xlog_confirm(), heap_xlog_delete(), heap_xlog_inplace(), heap_xlog_insert(), heap_xlog_lock(), heap_xlog_lock_updated(), heap_xlog_multi_insert(), heap_xlog_prune_freeze(), heap_xlog_update(), log_heap_prune_and_freeze(), log_newpage(), log_newpage_range(), log_newpages(), log_split_page(), MarkSharedBufferDirtyHint(), moveLeafs(), nextval_internal(), revmap_physical_extend(), seq_redo(), SetSequence(), shiftList(), spgAddNodeAction(), spgRedoAddLeaf(), spgRedoAddNode(), spgRedoMoveLeafs(), spgRedoPickSplit(), spgRedoSplitTuple(), spgRedoVacuumLeaf(), spgRedoVacuumRedirect(), spgRedoVacuumRoot(), spgSplitNodeAction(), vacuumLeafPage(), vacuumLeafRoot(), vacuumRedirectAndPlaceholder(), writeListPage(), XLogReadBufferForRedoExtended(), and xlogVacuumPage().

◆ PageSetPageSizeAndVersion()

static void PageSetPageSizeAndVersion ( Page  page,
Size  size,
uint8  version 
)
inlinestatic

Definition at line 324 of file bufpage.h.

326{
327 Assert((size & 0xFF00) == size);
328 Assert((version & 0x00FF) == version);
329
330 ((PageHeader) page)->pd_pagesize_version = size | version;

References Assert.

Referenced by PageInit().

◆ PageTruncateLinePointerArray()

void PageTruncateLinePointerArray ( Page  page)
extern

Definition at line 844 of file bufpage.c.

845{
846 PageHeader phdr = (PageHeader) page;
847 bool countdone = false,
848 sethint = false;
849 int nunusedend = 0;
850
851 /* Scan line pointer array back-to-front */
852 for (int i = PageGetMaxOffsetNumber(page); i >= FirstOffsetNumber; i--)
853 {
854 ItemId lp = PageGetItemId(page, i);
855
856 if (!countdone && i > FirstOffsetNumber)
857 {
858 /*
859 * Still determining which line pointers from the end of the array
860 * will be truncated away. Either count another line pointer as
861 * safe to truncate, or notice that it's not safe to truncate
862 * additional line pointers (stop counting line pointers).
863 */
864 if (!ItemIdIsUsed(lp))
865 nunusedend++;
866 else
867 countdone = true;
868 }
869 else
870 {
871 /*
872 * Once we've stopped counting we still need to figure out if
873 * there are any remaining LP_UNUSED line pointers somewhere more
874 * towards the front of the array.
875 */
876 if (!ItemIdIsUsed(lp))
877 {
878 /*
879 * This is an unused line pointer that we won't be truncating
880 * away -- so there is at least one. Set hint on page.
881 */
882 sethint = true;
883 break;
884 }
885 }
886 }
887
888 if (nunusedend > 0)
889 {
890 phdr->pd_lower -= sizeof(ItemIdData) * nunusedend;
891
892#ifdef CLOBBER_FREED_MEMORY
893 memset((char *) page + phdr->pd_lower, 0x7F,
894 sizeof(ItemIdData) * nunusedend);
895#endif
896 }
897 else
899
900 /* Set hint bit for PageAddItemExtended */
901 if (sethint)
903 else
905}

References Assert, fb(), FirstOffsetNumber, i, ItemIdIsUsed, PageClearHasFreeLinePointers(), PageGetItemId(), PageGetMaxOffsetNumber(), PageSetHasFreeLinePointers(), and PageHeaderData::pd_lower.

Referenced by heap_page_prune_execute(), and lazy_vacuum_heap_page().

◆ PageValidateSpecialPointer()

static void PageValidateSpecialPointer ( const PageData page)
inlinestatic

Definition at line 352 of file bufpage.h.

354{
355 Assert(page);
356 Assert(((const PageHeaderData *) page)->pd_special <= BLCKSZ);
357 Assert(((const PageHeaderData *) page)->pd_special >= SizeOfPageHeaderData);

References Assert, fb(), and SizeOfPageHeaderData.

◆ PageXLogRecPtrGet()

static XLogRecPtr PageXLogRecPtrGet ( const volatile PageXLogRecPtr val)
inlinestatic

Definition at line 123 of file bufpage.h.

124{
125 PageXLogRecPtr tmp = {val->lsn};
126
127 return (tmp.lsn << 32) | (tmp.lsn >> 32);
128}
long val
Definition informix.c:689

References PageXLogRecPtr::lsn, and val.

Referenced by PageGetLSN().

◆ PageXLogRecPtrSet()

static void PageXLogRecPtrSet ( volatile PageXLogRecPtr ptr,
XLogRecPtr  lsn 
)
inlinestatic

Definition at line 131 of file bufpage.h.

132{
133 ptr->lsn = (lsn << 32) | (lsn >> 32);
134}

References PageXLogRecPtr::lsn.

Referenced by mask_page_lsn_and_checksum(), and PageSetLSN().

◆ StaticAssertDecl()

StaticAssertDecl ( BLCKSZ  = =((BLCKSZ/sizeof(size_t)) *sizeof(size_t)),
"BLCKSZ has to be a multiple of sizeof(size_t)"   
)

Variable Documentation

◆ ignore_checksum_failure

PGDLLIMPORT bool ignore_checksum_failure
extern

Definition at line 27 of file bufpage.c.

Referenced by AsyncReadBuffers(), read_rel_block_ll(), and RelationCopyStorage().