codekingpro/portable-devtools
114k
1/*-------------------------------------------------------------------------2 *3 * rangetypes.h4 * Declarations for Postgres range types.5 *6 *7 * Portions Copyright (c) 1996-2023, PostgreSQL Global Development Group8 * Portions Copyright (c) 1994, Regents of the University of California9 *10 * src/include/utils/rangetypes.h11 *12 *-------------------------------------------------------------------------13 */14#ifndef RANGETYPES_H15#define RANGETYPES_H16 17#include "utils/typcache.h"18 19 20/*21 * Ranges are varlena objects, so must meet the varlena convention that22 * the first int32 of the object contains the total object size in bytes.23 * Be sure to use VARSIZE() and SET_VARSIZE() to access it, though!24 */25typedef struct26{27 int32 vl_len_; /* varlena header (do not touch directly!) */28 Oid rangetypid; /* range type's own OID */29 /* Following the OID are zero to two bound values, then a flags byte */30} RangeType;31 32#define RANGE_EMPTY_LITERAL "empty"33 34/* Use this macro in preference to fetching rangetypid field directly */35#define RangeTypeGetOid(r) ((r)->rangetypid)36 37/* A range's flags byte contains these bits: */38#define RANGE_EMPTY 0x01 /* range is empty */39#define RANGE_LB_INC 0x02 /* lower bound is inclusive */40#define RANGE_UB_INC 0x04 /* upper bound is inclusive */41#define RANGE_LB_INF 0x08 /* lower bound is -infinity */42#define RANGE_UB_INF 0x10 /* upper bound is +infinity */43#define RANGE_LB_NULL 0x20 /* lower bound is null (NOT USED) */44#define RANGE_UB_NULL 0x40 /* upper bound is null (NOT USED) */45#define RANGE_CONTAIN_EMPTY 0x80 /* marks a GiST internal-page entry whose46 * subtree contains some empty ranges */47 48#define RANGE_HAS_LBOUND(flags) (!((flags) & (RANGE_EMPTY | \49 RANGE_LB_NULL | \50 RANGE_LB_INF)))51 52#define RANGE_HAS_UBOUND(flags) (!((flags) & (RANGE_EMPTY | \53 RANGE_UB_NULL | \54 RANGE_UB_INF)))55 56#define RangeIsEmpty(r) ((range_get_flags(r) & RANGE_EMPTY) != 0)57#define RangeIsOrContainsEmpty(r) \58 ((range_get_flags(r) & (RANGE_EMPTY | RANGE_CONTAIN_EMPTY)) != 0)59 60 61/* Internal representation of either bound of a range (not what's on disk) */62typedef struct63{64 Datum val; /* the bound value, if any */65 bool infinite; /* bound is +/- infinity */66 bool inclusive; /* bound is inclusive (vs exclusive) */67 bool lower; /* this is the lower (vs upper) bound */68} RangeBound;69 70/*71 * fmgr functions for range type objects72 */73static inline RangeType *74DatumGetRangeTypeP(Datum X)75{76 return (RangeType *) PG_DETOAST_DATUM(X);77}78 79static inline RangeType *80DatumGetRangeTypePCopy(Datum X)81{82 return (RangeType *) PG_DETOAST_DATUM_COPY(X);83}84 85static inline Datum86RangeTypePGetDatum(const RangeType *X)87{88 return PointerGetDatum(X);89}90 91#define PG_GETARG_RANGE_P(n) DatumGetRangeTypeP(PG_GETARG_DATUM(n))92#define PG_GETARG_RANGE_P_COPY(n) DatumGetRangeTypePCopy(PG_GETARG_DATUM(n))93#define PG_RETURN_RANGE_P(x) return RangeTypePGetDatum(x)94 95/* Operator strategy numbers used in the GiST and SP-GiST range opclasses */96/* Numbers are chosen to match up operator names with existing usages */97#define RANGESTRAT_BEFORE RTLeftStrategyNumber98#define RANGESTRAT_OVERLEFT RTOverLeftStrategyNumber99#define RANGESTRAT_OVERLAPS RTOverlapStrategyNumber100#define RANGESTRAT_OVERRIGHT RTOverRightStrategyNumber101#define RANGESTRAT_AFTER RTRightStrategyNumber102#define RANGESTRAT_ADJACENT RTSameStrategyNumber103#define RANGESTRAT_CONTAINS RTContainsStrategyNumber104#define RANGESTRAT_CONTAINED_BY RTContainedByStrategyNumber105#define RANGESTRAT_CONTAINS_ELEM RTContainsElemStrategyNumber106#define RANGESTRAT_EQ RTEqualStrategyNumber107 108/*109 * prototypes for functions defined in rangetypes.c110 */111 112extern bool range_contains_elem_internal(TypeCacheEntry *typcache, const RangeType *r, Datum val);113 114/* internal versions of the above */115extern bool range_eq_internal(TypeCacheEntry *typcache, const RangeType *r1,116 const RangeType *r2);117extern bool range_ne_internal(TypeCacheEntry *typcache, const RangeType *r1,118 const RangeType *r2);119extern bool range_contains_internal(TypeCacheEntry *typcache, const RangeType *r1,120 const RangeType *r2);121extern bool range_contained_by_internal(TypeCacheEntry *typcache, const RangeType *r1,122 const RangeType *r2);123extern bool range_before_internal(TypeCacheEntry *typcache, const RangeType *r1,124 const RangeType *r2);125extern bool range_after_internal(TypeCacheEntry *typcache, const RangeType *r1,126 const RangeType *r2);127extern bool range_adjacent_internal(TypeCacheEntry *typcache, const RangeType *r1,128 const RangeType *r2);129extern bool range_overlaps_internal(TypeCacheEntry *typcache, const RangeType *r1,130 const RangeType *r2);131extern bool range_overleft_internal(TypeCacheEntry *typcache, const RangeType *r1,132 const RangeType *r2);133extern bool range_overright_internal(TypeCacheEntry *typcache, const RangeType *r1,134 const RangeType *r2);135extern RangeType *range_union_internal(TypeCacheEntry *typcache, RangeType *r1,136 RangeType *r2, bool strict);137extern RangeType *range_minus_internal(TypeCacheEntry *typcache, RangeType *r1,138 RangeType *r2);139extern RangeType *range_intersect_internal(TypeCacheEntry *typcache, const RangeType *r1,140 const RangeType *r2);141 142/* assorted support functions */143extern TypeCacheEntry *range_get_typcache(FunctionCallInfo fcinfo,144 Oid rngtypid);145extern RangeType *range_serialize(TypeCacheEntry *typcache, RangeBound *lower,146 RangeBound *upper, bool empty,147 struct Node *escontext);148extern void range_deserialize(TypeCacheEntry *typcache, const RangeType *range,149 RangeBound *lower, RangeBound *upper,150 bool *empty);151extern char range_get_flags(const RangeType *range);152extern void range_set_contain_empty(RangeType *range);153extern RangeType *make_range(TypeCacheEntry *typcache, RangeBound *lower,154 RangeBound *upper, bool empty,155 struct Node *escontext);156extern int range_cmp_bounds(TypeCacheEntry *typcache, const RangeBound *b1,157 const RangeBound *b2);158extern int range_cmp_bound_values(TypeCacheEntry *typcache, const RangeBound *b1,159 const RangeBound *b2);160extern int range_compare(const void *key1, const void *key2, void *arg);161extern bool bounds_adjacent(TypeCacheEntry *typcache, RangeBound boundA,162 RangeBound boundB);163extern RangeType *make_empty_range(TypeCacheEntry *typcache);164extern bool range_split_internal(TypeCacheEntry *typcache, const RangeType *r1,165 const RangeType *r2, RangeType **output1,166 RangeType **output2);167 168#endif /* RANGETYPES_H */169 