PostgreSQL Source Code: src/backend/access/index/indexam.c Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

25

26

27

28

29

30

31

32

33

34

35

36

37

38

39

40

41

42

43

45

60

61

62

63

64

65

66

67

68

69

70

71

72

73

74

75#define RELATION_CHECKS \

76do { \

77 Assert(RelationIsValid(indexRelation)); \

78 Assert(PointerIsValid(indexRelation->rd_indam)); \

79 if (unlikely(ReindexIsProcessingIndex(RelationGetRelid(indexRelation)))) \

80 ereport(ERROR, \

81 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), \

82 errmsg("cannot access index \"%s\" while it is being reindexed", \

83 RelationGetRelationName(indexRelation)))); \

84} while(0)

85

86#define SCAN_CHECKS \

87( \

88 AssertMacro(IndexScanIsValid(scan)), \

89 AssertMacro(RelationIsValid(scan->indexRelation)), \

90 AssertMacro(PointerIsValid(scan->indexRelation->rd_indam)) \

92

93#define CHECK_REL_PROCEDURE(pname) \

94do { \

95 if (indexRelation->rd_indam->pname == NULL) \

96 elog(ERROR, "function \"%s\" is not defined for index \"%s\"", \

97 CppAsString(pname), RelationGetRelationName(indexRelation)); \

98} while(0)

99

100#define CHECK_SCAN_PROCEDURE(pname) \

101do { \

102 if (scan->indexRelation->rd_indam->pname == NULL) \

103 elog(ERROR, "function \"%s\" is not defined for index \"%s\"", \

104 CppAsString(pname), RelationGetRelationName(scan->indexRelation)); \

105} while(0)

106

108 int nkeys, int norderbys, Snapshot snapshot,

111

112

113

114

115

116

117

118

119

120

121

122

123

124

125

126

127

128

129

130

131

134{

136

138

140

141 return r;

142}

143

144

145

146

147

148

149

150

153{

155

157

158

159 if (!r)

160 return NULL;

161

163

164 return r;

165}

166

167

168

169

170

171

172

173

174

175

176void

178{

180

182

183

185

186 if (lockmode != NoLock)

188}

189

190

191

192

193

194

195

196static inline void

198{

199 if (r->rd_rel->relkind != RELKIND_INDEX &&

200 r->rd_rel->relkind != RELKIND_PARTITIONED_INDEX)

202 (errcode(ERRCODE_WRONG_OBJECT_TYPE),

203 errmsg("\"%s\" is not an index",

205}

206

207

208

209

210

211

212bool

215 bool *isnull,

219 bool indexUnchanged,

221{

224

229

231 heap_t_ctid, heapRelation,

232 checkUnique, indexUnchanged,

233 indexInfo);

234}

235

236

237

238

239

240void

243{

245

248}

249

250

251

252

253

254

260 int nkeys, int norderbys)

261{

263

265

267

268

269

270

271

275

276

278

279 return scan;

280}

281

282

283

284

285

286

287

292 int nkeys)

293{

295

297

299

300

301

302

303

306

307 return scan;

308}

309

310

311

312

315 int nkeys, int norderbys, Snapshot snapshot,

317{

319

322

325

326

327

328

330

331

332

333

335 norderbys);

336

339

340 return scan;

341}

342

343

344

345

346

347

348

349

350

351

352

353

354

355void

358 ScanKey orderbys, int norderbys)

359{

362

365

366

369

372

374 orderbys, norderbys);

375}

376

377

378

379

380

381void

383{

386

387

389 {

392 }

393

394

396

397

399

402

403

405}

406

407

408

409

410

411void

413{

416

418}

419

420

421

422

423

424

425

426

427

428

429

430

431

432

433

434

435void

437{

439

442

443

446

449

451}

452

453

454

455

456

457

458

459

462 Snapshot snapshot, bool instrument,

463 bool parallel_aware, int nworkers)

464{

466

467 Assert(instrument || parallel_aware);

468

470

474

475 if (instrument)

476 {

477 Size sharedinfosz;

478

481 nbytes = add_size(nbytes, sharedinfosz);

483 }

484

485

486

487

488

489 if (parallel_aware &&

493 nkeys,

494 norderbys));

495

496 return nbytes;

497}

498

499

500

501

502

503

504

505

506

507

508

509void

511 Snapshot snapshot, bool instrument,

512 bool parallel_aware, int nworkers,

515{

517

518 Assert(instrument || parallel_aware);

519

521

525

531

532 if (instrument)

533 {

534 Size sharedinfosz;

535

539 offset = add_size(offset, sharedinfosz);

541

542

545 memset(*sharedinfo, 0, sharedinfosz);

546 (*sharedinfo)->num_workers = nworkers;

547 }

548

549

551 {

552 void *amtarget;

553

557 }

558}

559

560

561

562

563

564void

566{

568

571

572

575}

576

577

578

579

580

581

585 int nkeys, int norderbys,

587{

590

593

597 pscan, true);

598

599

600

601

602

606

607

609

610 return scan;

611}

612

613

614

615

616

617

618

619

622{

623 bool found;

624

627

628

630

631

632

633

634

635

636

638

639

642

643

644 if (!found)

645 {

646

649

650 return NULL;

651 }

653

655

656

658}

659

660

661

662

663

664

665

666

667

668

669

670

671

672

673

674

675

676

677

678bool

680{

681 bool all_dead = false;

682 bool found;

683

687

688 if (found)

690

691

692

693

694

695

696

697

700

701 return found;

702}

703

704

705

706

707

708

709

710

711

712

713

714

715

716

717

718

719bool

721{

722 for (;;)

723 {

725 {

727

728

730

731

732 if (tid == NULL)

733 break;

734

736 }

737

738

739

740

741

742

745 return true;

746 }

747

748 return false;

749}

750

751

752

753

754

755

756

757

758

759

760

761

762

763

766{

768

771

772

774

775

776

777

779

781

782 return ntids;

783}

784

785

786

787

788

789

790

791

792

793

798 void *callback_state)

799{

801

804

807}

808

809

810

811

812

813

814

818{

820

823

825}

826

827

828

829

830

831

832

833

834bool

836{

838

839

841 return false;

842

844}

845

846

847

848

849

850

851

852

853

854

855

856

857

858

859

860

861

862

863

864

865

866

867

868

869

870

871

876{

878 int nproc;

879 int procindex;

880

882

883 Assert(procnum > 0 && procnum <= (uint16) nproc);

884

885 procindex = (nproc * (attnum - 1)) + (procnum - 1);

886

888

890

891 return loc[procindex];

892}

893

894

895

896

897

898

899

900

901

902

903

904

905

910{

912 int nproc;

913 int optsproc;

914 int procindex;

915

918

919 Assert(procnum > 0 && procnum <= (uint16) nproc);

920

921 procindex = (nproc * (attnum - 1)) + (procnum - 1);

922

924

925 Assert(locinfo != NULL);

926

927 locinfo += procindex;

928

929

931 {

934

936

937 procId = loc[procindex];

938

939

940

941

942

943

944

946 elog(ERROR, "missing support function %d for attribute %d of index \"%s\"",

948

950

951 if (procnum != optsproc)

952 {

953

956

958

960 }

961 }

962

963 return locinfo;

964}

965

966

967

968

969

970

971

972

973

974void

977 bool recheckOrderBy)

978{

979 int i;

980

981 Assert(distances || !recheckOrderBy);

982

984

986 {

987 if (orderByTypes[i] == FLOAT8OID)

988 {

989#ifndef USE_FLOAT8_BYVAL

990

993#endif

994 if (distances && !distances[i].isnull)

995 {

998 }

999 else

1000 {

1003 }

1004 }

1005 else if (orderByTypes[i] == FLOAT4OID)

1006 {

1007

1008 if (distances && !distances[i].isnull)

1009 {

1012 }

1013 else

1014 {

1017 }

1018 }

1019 else

1020 {

1021

1022

1023

1024

1025

1026

1027

1028

1030 elog(ERROR, "ORDER BY operator must return float8 or float4 if the distance function is lossy");

1032 }

1033 }

1034}

1035

1036

1037

1038

1039

1040

1041

1045{

1050

1051

1052 if (amoptsprocnum != 0)

1054

1056 {

1057 Oid opclass;

1058 Datum indclassDatum;

1060

1062 return NULL;

1063

1064

1065

1066

1067

1069 Anum_pg_index_indclass);

1072

1074 (errcode(ERRCODE_INVALID_PARAMETER_VALUE),

1075 errmsg("operator class %s has no options",

1077 }

1078

1080

1082

1084

1086}

static bool validate(Port *port, const char *auth)

#define InvalidBlockNumber

static Datum values[MAXATTR]

#define OffsetToPointer(base, offset)

#define RegProcedureIsValid(p)

#define OidIsValid(objectId)

int errcode(int sqlerrcode)

int errmsg(const char *fmt,...)

#define ereport(elevel,...)

void set_fn_opclass_options(FmgrInfo *flinfo, bytea *options)

void fmgr_info_cxt(Oid functionId, FmgrInfo *finfo, MemoryContext mcxt)

Datum Float8GetDatum(float8 X)

#define FunctionCall1(flinfo, arg1)

void IndexScanEnd(IndexScanDesc scan)

bool(* IndexBulkDeleteCallback)(ItemPointer itemptr, void *state)

struct IndexScanInstrumentation IndexScanInstrumentation

Assert(PointerIsAligned(start, uint64))

void index_parallelscan_initialize(Relation heapRelation, Relation indexRelation, Snapshot snapshot, bool instrument, bool parallel_aware, int nworkers, SharedIndexScanInstrumentation **sharedinfo, ParallelIndexScanDesc target)

bool index_getnext_slot(IndexScanDesc scan, ScanDirection direction, TupleTableSlot *slot)

#define CHECK_REL_PROCEDURE(pname)

static void validate_relation_kind(Relation r)

bool index_insert(Relation indexRelation, Datum *values, bool *isnull, ItemPointer heap_t_ctid, Relation heapRelation, IndexUniqueCheck checkUnique, bool indexUnchanged, IndexInfo *indexInfo)

IndexScanDesc index_beginscan_parallel(Relation heaprel, Relation indexrel, IndexScanInstrumentation *instrument, int nkeys, int norderbys, ParallelIndexScanDesc pscan)

FmgrInfo * index_getprocinfo(Relation irel, AttrNumber attnum, uint16 procnum)

void index_restrpos(IndexScanDesc scan)

IndexBulkDeleteResult * index_vacuum_cleanup(IndexVacuumInfo *info, IndexBulkDeleteResult *istat)

bytea * index_opclass_options(Relation indrel, AttrNumber attnum, Datum attoptions, bool validate)

static IndexScanDesc index_beginscan_internal(Relation indexRelation, int nkeys, int norderbys, Snapshot snapshot, ParallelIndexScanDesc pscan, bool temp_snap)

IndexScanDesc index_beginscan(Relation heapRelation, Relation indexRelation, Snapshot snapshot, IndexScanInstrumentation *instrument, int nkeys, int norderbys)

IndexBulkDeleteResult * index_bulk_delete(IndexVacuumInfo *info, IndexBulkDeleteResult *istat, IndexBulkDeleteCallback callback, void *callback_state)

void index_insert_cleanup(Relation indexRelation, IndexInfo *indexInfo)

void index_close(Relation relation, LOCKMODE lockmode)

bool index_can_return(Relation indexRelation, int attno)

ItemPointer index_getnext_tid(IndexScanDesc scan, ScanDirection direction)

RegProcedure index_getprocid(Relation irel, AttrNumber attnum, uint16 procnum)

bool index_fetch_heap(IndexScanDesc scan, TupleTableSlot *slot)

void index_markpos(IndexScanDesc scan)

Relation try_index_open(Oid relationId, LOCKMODE lockmode)

void index_endscan(IndexScanDesc scan)

IndexScanDesc index_beginscan_bitmap(Relation indexRelation, Snapshot snapshot, IndexScanInstrumentation *instrument, int nkeys)

Size index_parallelscan_estimate(Relation indexRelation, int nkeys, int norderbys, Snapshot snapshot, bool instrument, bool parallel_aware, int nworkers)

Relation index_open(Oid relationId, LOCKMODE lockmode)

int64 index_getbitmap(IndexScanDesc scan, TIDBitmap *bitmap)

void index_parallelrescan(IndexScanDesc scan)

void index_rescan(IndexScanDesc scan, ScanKey keys, int nkeys, ScanKey orderbys, int norderbys)

#define CHECK_SCAN_PROCEDURE(pname)

void index_store_float8_orderby_distances(IndexScanDesc scan, Oid *orderByTypes, IndexOrderByDistance *distances, bool recheckOrderBy)

bool ItemPointerEquals(ItemPointer pointer1, ItemPointer pointer2)

static bool ItemPointerIsValid(const ItemPointerData *pointer)

void UnlockRelationId(LockRelId *relid, LOCKMODE lockmode)

void pfree(void *pointer)

static MemoryContext MemoryContextSwitchTo(MemoryContext context)

#define pgstat_count_index_tuples(rel, n)

#define pgstat_count_heap_fetch(rel)

static Datum PointerGetDatum(const void *X)

static Datum Float4GetDatum(float4 X)

static Pointer DatumGetPointer(Datum X)

void CheckForSerializableConflictIn(Relation relation, ItemPointer tid, BlockNumber blkno)

void PredicateLockRelation(Relation relation, Snapshot snapshot)

#define RelationGetRelationName(relation)

void RelationDecrementReferenceCount(Relation rel)

void RelationIncrementReferenceCount(Relation rel)

bytea ** RelationGetIndexAttOptions(Relation relation, bool copy)

void RelationClose(Relation relation)

#define RelFileLocatorEquals(locator1, locator2)

void init_local_reloptions(local_relopts *relopts, Size relopt_struct_size)

void * build_local_reloptions(local_relopts *relopts, Datum options, bool validate)

char * generate_opclass_name(Oid opclass)

Size add_size(Size s1, Size s2)

void SerializeSnapshot(Snapshot snapshot, char *start_address)

void UnregisterSnapshot(Snapshot snapshot)

Snapshot RestoreSnapshot(char *start_address)

Snapshot RegisterSnapshot(Snapshot snapshot)

Size EstimateSnapshotSpace(Snapshot snapshot)

#define IsMVCCSnapshot(snapshot)

Relation try_relation_open(Oid relationId, LOCKMODE lockmode)

Relation relation_open(Oid relationId, LOCKMODE lockmode)

amvacuumcleanup_function amvacuumcleanup

amestimateparallelscan_function amestimateparallelscan

amrestrpos_function amrestrpos

aminsert_function aminsert

amendscan_function amendscan

amparallelrescan_function amparallelrescan

amgettuple_function amgettuple

amcanreturn_function amcanreturn

amgetbitmap_function amgetbitmap

ambulkdelete_function ambulkdelete

ammarkpos_function ammarkpos

ambeginscan_function ambeginscan

amrescan_function amrescan

aminitparallelscan_function aminitparallelscan

aminsertcleanup_function aminsertcleanup

struct ParallelIndexScanDescData * parallel_scan

IndexFetchTableData * xs_heapfetch

bool xactStartedInRecovery

struct IndexScanInstrumentation * instrument

ItemPointerData xs_heaptid

struct SnapshotData * xs_snapshot

RelFileLocator ps_indexlocator

RelFileLocator ps_locator

char ps_snapshot_data[FLEXIBLE_ARRAY_MEMBER]

struct IndexAmRoutine * rd_indam

RegProcedure * rd_support

struct HeapTupleData * rd_indextuple

MemoryContext rd_indexcxt

RelFileLocator rd_locator

struct FmgrInfo * rd_supportinfo

Oid values[FLEXIBLE_ARRAY_MEMBER]

Datum SysCacheGetAttrNotNull(int cacheId, HeapTuple tup, AttrNumber attributeNumber)

static void table_index_fetch_reset(struct IndexFetchTableData *scan)

static IndexFetchTableData * table_index_fetch_begin(Relation rel)

static void table_index_fetch_end(struct IndexFetchTableData *scan)

static bool table_index_fetch_tuple(struct IndexFetchTableData *scan, ItemPointer tid, Snapshot snapshot, TupleTableSlot *slot, bool *call_again, bool *all_dead)

static void callback(struct sockaddr *addr, struct sockaddr *mask, void *unused)

#define TransactionIdIsValid(xid)