Age Owner Branch data TLA Line data Source code
1 : : /*-------------------------------------------------------------------------
2 : : *
3 : : * rangetypes.h
4 : : * Declarations for Postgres range types.
5 : : *
6 : : *
7 : : * Portions Copyright (c) 1996-2024, PostgreSQL Global Development Group
8 : : * Portions Copyright (c) 1994, Regents of the University of California
9 : : *
10 : : * src/include/utils/rangetypes.h
11 : : *
12 : : *-------------------------------------------------------------------------
13 : : */
14 : : #ifndef RANGETYPES_H
15 : : #define RANGETYPES_H
16 : :
17 : : #include "utils/typcache.h"
18 : :
19 : :
20 : : /*
21 : : * Ranges are varlena objects, so must meet the varlena convention that
22 : : * 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 : : */
25 : : typedef struct
26 : : {
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 whose
46 : : * 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) */
62 : : typedef struct
63 : : {
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 objects
72 : : */
73 : : static inline RangeType *
565 peter@eisentraut.org 74 :CBC 5179585 : DatumGetRangeTypeP(Datum X)
75 : : {
76 : 5179585 : return (RangeType *) PG_DETOAST_DATUM(X);
77 : : }
78 : :
79 : : static inline RangeType *
80 : : DatumGetRangeTypePCopy(Datum X)
81 : : {
82 : : return (RangeType *) PG_DETOAST_DATUM_COPY(X);
83 : : }
84 : :
85 : : static inline Datum
86 : 975554 : RangeTypePGetDatum(const RangeType *X)
87 : : {
88 : 975554 : 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 RTLeftStrategyNumber
98 : : #define RANGESTRAT_OVERLEFT RTOverLeftStrategyNumber
99 : : #define RANGESTRAT_OVERLAPS RTOverlapStrategyNumber
100 : : #define RANGESTRAT_OVERRIGHT RTOverRightStrategyNumber
101 : : #define RANGESTRAT_AFTER RTRightStrategyNumber
102 : : #define RANGESTRAT_ADJACENT RTSameStrategyNumber
103 : : #define RANGESTRAT_CONTAINS RTContainsStrategyNumber
104 : : #define RANGESTRAT_CONTAINED_BY RTContainedByStrategyNumber
105 : : #define RANGESTRAT_CONTAINS_ELEM RTContainsElemStrategyNumber
106 : : #define RANGESTRAT_EQ RTEqualStrategyNumber
107 : :
108 : : /*
109 : : * prototypes for functions defined in rangetypes.c
110 : : */
111 : :
112 : : extern bool range_contains_elem_internal(TypeCacheEntry *typcache, const RangeType *r, Datum val);
113 : :
114 : : /* internal versions of the above */
115 : : extern bool range_eq_internal(TypeCacheEntry *typcache, const RangeType *r1,
116 : : const RangeType *r2);
117 : : extern bool range_ne_internal(TypeCacheEntry *typcache, const RangeType *r1,
118 : : const RangeType *r2);
119 : : extern bool range_contains_internal(TypeCacheEntry *typcache, const RangeType *r1,
120 : : const RangeType *r2);
121 : : extern bool range_contained_by_internal(TypeCacheEntry *typcache, const RangeType *r1,
122 : : const RangeType *r2);
123 : : extern bool range_before_internal(TypeCacheEntry *typcache, const RangeType *r1,
124 : : const RangeType *r2);
125 : : extern bool range_after_internal(TypeCacheEntry *typcache, const RangeType *r1,
126 : : const RangeType *r2);
127 : : extern bool range_adjacent_internal(TypeCacheEntry *typcache, const RangeType *r1,
128 : : const RangeType *r2);
129 : : extern bool range_overlaps_internal(TypeCacheEntry *typcache, const RangeType *r1,
130 : : const RangeType *r2);
131 : : extern bool range_overleft_internal(TypeCacheEntry *typcache, const RangeType *r1,
132 : : const RangeType *r2);
133 : : extern bool range_overright_internal(TypeCacheEntry *typcache, const RangeType *r1,
134 : : const RangeType *r2);
135 : : extern RangeType *range_union_internal(TypeCacheEntry *typcache, RangeType *r1,
136 : : RangeType *r2, bool strict);
137 : : extern RangeType *range_minus_internal(TypeCacheEntry *typcache, RangeType *r1,
138 : : RangeType *r2);
139 : : extern RangeType *range_intersect_internal(TypeCacheEntry *typcache, const RangeType *r1,
140 : : const RangeType *r2);
141 : :
142 : : /* assorted support functions */
143 : : extern TypeCacheEntry *range_get_typcache(FunctionCallInfo fcinfo,
144 : : Oid rngtypid);
145 : : extern RangeType *range_serialize(TypeCacheEntry *typcache, RangeBound *lower,
146 : : RangeBound *upper, bool empty,
147 : : struct Node *escontext);
148 : : extern void range_deserialize(TypeCacheEntry *typcache, const RangeType *range,
149 : : RangeBound *lower, RangeBound *upper,
150 : : bool *empty);
151 : : extern char range_get_flags(const RangeType *range);
152 : : extern void range_set_contain_empty(RangeType *range);
153 : : extern RangeType *make_range(TypeCacheEntry *typcache, RangeBound *lower,
154 : : RangeBound *upper, bool empty,
155 : : struct Node *escontext);
156 : : extern int range_cmp_bounds(TypeCacheEntry *typcache, const RangeBound *b1,
157 : : const RangeBound *b2);
158 : : extern int range_cmp_bound_values(TypeCacheEntry *typcache, const RangeBound *b1,
159 : : const RangeBound *b2);
160 : : extern int range_compare(const void *key1, const void *key2, void *arg);
161 : : extern bool bounds_adjacent(TypeCacheEntry *typcache, RangeBound boundA,
162 : : RangeBound boundB);
163 : : extern RangeType *make_empty_range(TypeCacheEntry *typcache);
164 : : extern bool range_split_internal(TypeCacheEntry *typcache, const RangeType *r1,
165 : : const RangeType *r2, RangeType **output1,
166 : : RangeType **output2);
167 : :
168 : : #endif /* RANGETYPES_H */
|