4747#define DELIM ','
4848#define NTIDARGS 2
4949
50+ static ItemPointer currtid_for_view (Relation viewrel , ItemPointer tid );
51+
5052/* ----------------------------------------------------------------
5153 * tidin
5254 * ----------------------------------------------------------------
@@ -275,20 +277,52 @@ hashtidextended(PG_FUNCTION_ARGS)
275277 * Maybe these implementations should be moved to another place
276278 */
277279
278- static ItemPointerData Current_last_tid = {{0 , 0 }, 0 };
279-
280- void
281- setLastTid (const ItemPointer tid )
280+ /*
281+ * Utility wrapper for current CTID functions.
282+ * Returns the latest version of a tuple pointing at "tid" for
283+ * relation "rel".
284+ */
285+ static ItemPointer
286+ currtid_internal (Relation rel , ItemPointer tid )
282287{
283- Current_last_tid = * tid ;
288+ ItemPointer result ;
289+ AclResult aclresult ;
290+ Snapshot snapshot ;
291+ TableScanDesc scan ;
292+
293+ result = (ItemPointer ) palloc (sizeof (ItemPointerData ));
294+
295+ aclresult = pg_class_aclcheck (RelationGetRelid (rel ), GetUserId (),
296+ ACL_SELECT );
297+ if (aclresult != ACLCHECK_OK )
298+ aclcheck_error (aclresult , get_relkind_objtype (rel -> rd_rel -> relkind ),
299+ RelationGetRelationName (rel ));
300+
301+ if (rel -> rd_rel -> relkind == RELKIND_VIEW )
302+ return currtid_for_view (rel , tid );
303+
304+ if (!RELKIND_HAS_STORAGE (rel -> rd_rel -> relkind ))
305+ elog (ERROR , "cannot look at latest visible tid for relation \"%s.%s\"" ,
306+ get_namespace_name (RelationGetNamespace (rel )),
307+ RelationGetRelationName (rel ));
308+
309+ ItemPointerCopy (tid , result );
310+
311+ snapshot = RegisterSnapshot (GetLatestSnapshot ());
312+ scan = table_beginscan_tid (rel , snapshot );
313+ table_tuple_get_latest_tid (scan , result );
314+ table_endscan (scan );
315+ UnregisterSnapshot (snapshot );
316+
317+ return result ;
284318}
285319
286320/*
287321 * Handle CTIDs of views.
288322 * CTID should be defined in the view and it must
289323 * correspond to the CTID of a base relation.
290324 */
291- static Datum
325+ static ItemPointer
292326currtid_for_view (Relation viewrel , ItemPointer tid )
293327{
294328 TupleDesc att = RelationGetDescr (viewrel );
@@ -338,12 +372,12 @@ currtid_for_view(Relation viewrel, ItemPointer tid)
338372 rte = rt_fetch (var -> varno , query -> rtable );
339373 if (rte )
340374 {
341- Datum result ;
375+ ItemPointer result ;
376+ Relation rel ;
342377
343- result = DirectFunctionCall2 (currtid_byreloid ,
344- ObjectIdGetDatum (rte -> relid ),
345- PointerGetDatum (tid ));
346- table_close (viewrel , AccessShareLock );
378+ rel = table_open (rte -> relid , AccessShareLock );
379+ result = currtid_internal (rel , tid );
380+ table_close (rel , AccessShareLock );
347381 return result ;
348382 }
349383 }
@@ -352,56 +386,14 @@ currtid_for_view(Relation viewrel, ItemPointer tid)
352386 }
353387 }
354388 elog (ERROR , "currtid cannot handle this view" );
355- return (Datum ) 0 ;
356- }
357-
358- Datum
359- currtid_byreloid (PG_FUNCTION_ARGS )
360- {
361- Oid reloid = PG_GETARG_OID (0 );
362- ItemPointer tid = PG_GETARG_ITEMPOINTER (1 );
363- ItemPointer result ;
364- Relation rel ;
365- AclResult aclresult ;
366- Snapshot snapshot ;
367- TableScanDesc scan ;
368-
369- result = (ItemPointer ) palloc (sizeof (ItemPointerData ));
370- if (!reloid )
371- {
372- * result = Current_last_tid ;
373- PG_RETURN_ITEMPOINTER (result );
374- }
375-
376- rel = table_open (reloid , AccessShareLock );
377-
378- aclresult = pg_class_aclcheck (RelationGetRelid (rel ), GetUserId (),
379- ACL_SELECT );
380- if (aclresult != ACLCHECK_OK )
381- aclcheck_error (aclresult , get_relkind_objtype (rel -> rd_rel -> relkind ),
382- RelationGetRelationName (rel ));
383-
384- if (rel -> rd_rel -> relkind == RELKIND_VIEW )
385- return currtid_for_view (rel , tid );
386-
387- if (!RELKIND_HAS_STORAGE (rel -> rd_rel -> relkind ))
388- elog (ERROR , "cannot look at latest visible tid for relation \"%s.%s\"" ,
389- get_namespace_name (RelationGetNamespace (rel )),
390- RelationGetRelationName (rel ));
391-
392- ItemPointerCopy (tid , result );
393-
394- snapshot = RegisterSnapshot (GetLatestSnapshot ());
395- scan = table_beginscan_tid (rel , snapshot );
396- table_tuple_get_latest_tid (scan , result );
397- table_endscan (scan );
398- UnregisterSnapshot (snapshot );
399-
400- table_close (rel , AccessShareLock );
401-
402- PG_RETURN_ITEMPOINTER (result );
389+ return NULL ;
403390}
404391
392+ /*
393+ * currtid_byrelname
394+ * Get the latest tuple version of the tuple pointing at a CTID, for a
395+ * given relation name.
396+ */
405397Datum
406398currtid_byrelname (PG_FUNCTION_ARGS )
407399{
@@ -410,35 +402,12 @@ currtid_byrelname(PG_FUNCTION_ARGS)
410402 ItemPointer result ;
411403 RangeVar * relrv ;
412404 Relation rel ;
413- AclResult aclresult ;
414- Snapshot snapshot ;
415- TableScanDesc scan ;
416405
417406 relrv = makeRangeVarFromNameList (textToQualifiedNameList (relname ));
418407 rel = table_openrv (relrv , AccessShareLock );
419408
420- aclresult = pg_class_aclcheck (RelationGetRelid (rel ), GetUserId (),
421- ACL_SELECT );
422- if (aclresult != ACLCHECK_OK )
423- aclcheck_error (aclresult , get_relkind_objtype (rel -> rd_rel -> relkind ),
424- RelationGetRelationName (rel ));
425-
426- if (rel -> rd_rel -> relkind == RELKIND_VIEW )
427- return currtid_for_view (rel , tid );
428-
429- if (!RELKIND_HAS_STORAGE (rel -> rd_rel -> relkind ))
430- elog (ERROR , "cannot look at latest visible tid for relation \"%s.%s\"" ,
431- get_namespace_name (RelationGetNamespace (rel )),
432- RelationGetRelationName (rel ));
433-
434- result = (ItemPointer ) palloc (sizeof (ItemPointerData ));
435- ItemPointerCopy (tid , result );
436-
437- snapshot = RegisterSnapshot (GetLatestSnapshot ());
438- scan = table_beginscan_tid (rel , snapshot );
439- table_tuple_get_latest_tid (scan , result );
440- table_endscan (scan );
441- UnregisterSnapshot (snapshot );
409+ /* grab the latest tuple version associated to this CTID */
410+ result = currtid_internal (rel , tid );
442411
443412 table_close (rel , AccessShareLock );
444413
0 commit comments