text: /* -------------------------------------------------------------------------
   *
   * pg_range.cpp
   *	  routines to support manipulation of the pg_range relation
   *
   * Portions Copyright (c) 1996-2012, PostgreSQL Global Development Group
   * Portions Copyright (c) 1994, Regents of the University of California
   *
   *
   * IDENTIFICATION
   *	  src/common/backend/catalog/pg_range.cpp
   *
   * -------------------------------------------------------------------------
   */
  #include "postgres.h"
  #include "knl/knl_variable.h"
  
  #include "access/genam.h"
  #include "access/heapam.h"
  #include "catalog/dependency.h"
  #include "catalog/indexing.h"
  #include "catalog/pg_collation.h"
  #include "catalog/pg_opclass.h"
  #include "catalog/pg_proc.h"
  #include "catalog/pg_range.h"
  #include "catalog/pg_type.h"
  #include "utils/fmgroids.h"
  #include "utils/rel.h"
  #include "utils/rel_gs.h"
  #include "utils/tqual.h"
  
  /*
   * RangeCreate
   *		Create an entry in pg_range.
   */
  void RangeCreate(Oid rangeTypeOid, Oid rangeSubType, Oid rangeCollation, Oid rangeSubOpclass,
      RegProcedure rangeCanonical, RegProcedure rangeSubDiff)
  {
      Relation pg_range;
      Datum values[Natts_pg_range];
      bool nulls[Natts_pg_range];
      HeapTuple tup;
      ObjectAddress myself;
      ObjectAddress referenced;
  
      pg_range = heap_open(RangeRelationId, RowExclusiveLock);
  
      errno_t rc = memset_s(nulls, sizeof(nulls), 0, sizeof(nulls));
      securec_check(rc, "", "");
  
      values[Anum_pg_range_rngtypid - 1] = ObjectIdGetDatum(rangeTypeOid);
      values[Anum_pg_range_rngsubtype - 1] = ObjectIdGetDatum(rangeSubType);
      values[Anum_pg_range_rngcollation - 1] = ObjectIdGetDatum(rangeCollation);
      values[Anum_pg_range_rngsubopc - 1] = ObjectIdGetDatum(rangeSubOpclass);
      values[Anum_pg_range_rngcanonical - 1] = ObjectIdGetDatum(rangeCanonical);
      values[Anum_pg_range_rngsubdiff - 1] = ObjectIdGetDatum(rangeSubDiff);
  
      tup = heap_form_tuple(RelationGetDescr(pg_range), values, nulls);
  
      (void)simple_heap_insert(pg_range, tup);
      CatalogUpdateIndexes(pg_range, tup);
      heap_freetuple_ext(tup);
  
      /* record type's dependencies on range-related items */
  
      myself.classId = TypeRelationId;
      myself.objectId = rangeTypeOid;
      myself.objectSubId = 0;
  
      referenced.classId = TypeRelationId;
      referenced.objectId = rangeSubType;
      referenced.objectSubId = 0;
      recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
  
      referenced.classId = OperatorClassRelationId;
      referenced.objectId = rangeSubOpclass;
      referenced.objectSubId = 0;
      recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
  
      if (OidIsValid(rangeCollation)) {
          referenced.classId = CollationRelationId;
          referenced.objectId = rangeCollation;
          referenced.objectSubId = 0;
          recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
      }
  
      if (OidIsValid(rangeCanonical)) {
          referenced.classId = ProcedureRelationId;
          referenced.objectId = rangeCanonical;
          referenced.objectSubId = 0;
          recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
      }
  
      if (OidIsValid(rangeSubDiff)) {
          referenced.classId = ProcedureRelationId;
          referenced.objectId = rangeSubDiff;
          referenced.objectSubId = 0;
          recordDependencyOn(&myself, &referenced, DEPENDENCY_NORMAL);
      }
  
      heap_close(pg_range, RowExclusiveLock);
  }
  
  /*
   * RangeDelete
   *		Remove the pg_range entry for the specified type.
   */
  void RangeDelete(Oid rangeTypeOid)
  {
      Relation pg_range;
      ScanKeyData key[1];
      SysScanDesc scan;
      HeapTuple tup;
  
      pg_range = heap_open(RangeRelationId, RowExclusiveLock);
  
      ScanKeyInit(&key[0], Anum_pg_range_rngtypid, BTEqualStrategyNumber, F_OIDEQ, ObjectIdGetDatum(rangeTypeOid));
  
      scan = systable_beginscan(pg_range, RangeTypidIndexId, true, SnapshotNow, 1, key);
  
      while (HeapTupleIsValid(tup = systable_getnext(scan))) {
          simple_heap_delete(pg_range, &tup->t_self);
      }
  
      systable_endscan(scan);
  
      heap_close(pg_range, RowExclusiveLock);
  }
  