From: Kyotaro Horiguchi Date: Tue, 2 Apr 2019 11:53:36 +0900 Subject: [PATCH 4/7] Add new interface to TableAmRoutine Add two interface functions to TableAmRoutine, which are related to WAL-skipping feature. --- src/backend/access/table/tableamapi.c | 4 ++ src/include/access/tableam.h | 79 +++++++++++++++++++++++------------ 2 files changed, 56 insertions(+), 27 deletions(-) diff --git a/src/backend/access/table/tableamapi.c b/src/backend/access/table/tableamapi.c index 51c0deaaf2..fef4e523e8 100644 --- a/src/backend/access/table/tableamapi.c +++ b/src/backend/access/table/tableamapi.c @@ -94,6 +94,10 @@ GetTableAmRoutine(Oid amhandler) (routine->scan_bitmap_next_tuple == NULL)); Assert(routine->scan_sample_next_block != NULL); Assert(routine->scan_sample_next_tuple != NULL); + Assert((routine->relation_register_walskip == NULL) == + (routine->relation_invalidate_walskip == NULL) && + (routine->relation_register_walskip == NULL) == + (routine->finish_bulk_insert == NULL)); return routine; } diff --git a/src/include/access/tableam.h b/src/include/access/tableam.h index 4efe178ed1..1a3a3c6711 100644 --- a/src/include/access/tableam.h +++ b/src/include/access/tableam.h @@ -382,19 +382,15 @@ typedef struct TableAmRoutine /* * Perform operations necessary to complete insertions made via - * tuple_insert and multi_insert with a BulkInsertState specified. This - * e.g. may e.g. used to flush the relation when inserting with - * TABLE_INSERT_SKIP_WAL specified. + * tuple_insert and multi_insert or page-level copying performed by ALTER + * TABLE rewrite. This is called at commit time if WAL-skipping is + * activated and the caller decided that any finish work is required to + * the file. * - * Typically callers of tuple_insert and multi_insert will just pass all - * the flags the apply to them, and each AM has to decide which of them - * make sense for it, and then only take actions in finish_bulk_insert - * that make sense for a specific AM. - * - * Optional callback. + * Optional callback. Must be provided when relation_register_walskip is + * provided. */ - void (*finish_bulk_insert) (Relation rel, int options); - + void (*finish_bulk_insert) (RelFileNode rnode, ForkNumber forkNum); /* ------------------------------------------------------------------------ * DDL related functionality. @@ -447,6 +443,26 @@ typedef struct TableAmRoutine double *tups_vacuumed, double *tups_recently_dead); + /* + * Register WAL-skipping on the current storage of rel. WAL-logging on the + * relation is skipped and the storage will be synced at commit. Returns + * true if successfully registered, and finish_bulk_insert() is called at + * commit. + * + * Optional callback. + */ + void (*relation_register_walskip) (Relation rel); + + /* + * Invalidate registered WAL skipping on the current storage of rel. The + * function is called when the storage of the relation is going to be + * out-of-use after commit. + * + * Optional callback. Must be provided when relation_register_walskip is + * provided. + */ + void (*relation_invalidate_walskip) (Relation rel); + /* * React to VACUUM command on the relation. The VACUUM might be user * triggered or by autovacuum. The specific actions performed by the AM @@ -1026,8 +1042,7 @@ table_compute_xid_horizon_for_tuples(Relation rel, * * * The BulkInsertState object (if any; bistate can be NULL for default - * behavior) is also just passed through to RelationGetBufferForTuple. If - * `bistate` is provided, table_finish_bulk_insert() needs to be called. + * behavior) is also just passed through to RelationGetBufferForTuple. * * On return the slot's tts_tid and tts_tableOid are updated to reflect the * insertion. But note that any toasting of fields within the slot is NOT @@ -1201,20 +1216,6 @@ table_lock_tuple(Relation rel, ItemPointer tid, Snapshot snapshot, flags, tmfd); } -/* - * Perform operations necessary to complete insertions made via - * tuple_insert and multi_insert with a BulkInsertState specified. This - * e.g. may e.g. used to flush the relation when inserting with - * TABLE_INSERT_SKIP_WAL specified. - */ -static inline void -table_finish_bulk_insert(Relation rel, int options) -{ - /* optional callback */ - if (rel->rd_tableam && rel->rd_tableam->finish_bulk_insert) - rel->rd_tableam->finish_bulk_insert(rel, options); -} - /* ------------------------------------------------------------------------ * DDL related functionality. @@ -1298,6 +1299,30 @@ table_relation_copy_for_cluster(Relation OldHeap, Relation NewHeap, tups_recently_dead); } +/* + * Register WAL-skipping to the relation. WAL-logging is skipped for the new + * pages after this call and the relation file is going to be synced at + * commit. + */ +static inline void +table_relation_register_walskip(Relation rel) +{ + if (rel->rd_tableam && rel->rd_tableam->relation_register_walskip) + rel->rd_tableam->relation_register_walskip(rel); +} + +/* + * Unregister WAL-skipping to the relation. Call this when the relation is + * going to be out-of-use after commit. WAL-skipping continues but the + * relation won't be synced at commit. + */ +static inline void +table_relation_invalidate_walskip(Relation rel) +{ + if (rel->rd_tableam && rel->rd_tableam->relation_invalidate_walskip) + rel->rd_tableam->relation_invalidate_walskip(rel); +} + /* * Perform VACUUM on the relation. The VACUUM can be user triggered or by * autovacuum. The specific actions performed by the AM will depend heavily on -- 2.16.3 ----Next_Part(Tue_Apr_02_19_54_06_2019_801)-- Content-Type: Text/X-Patch; charset=us-ascii Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="v10-0005-Add-infrastructure-to-WAL-logging-skip-feature.patch"