static void placeOne(Relation r, GISTSTATE *giststate, GistSplitVector *v, IndexTuple itup, OffsetNumber off, int attno) { GISTENTRY identry[INDEX_MAX_KEYS]; bool isnull[INDEX_MAX_KEYS]; bool toLeft = true; gistDeCompressAtt(giststate, r, itup, NULL, (OffsetNumber) 0, identry, isnull); for (; attno < giststate->tupdesc->natts; attno++) { float lpenalty, rpenalty; GISTENTRY entry; gistentryinit(entry, v->spl_lattr[attno], r, NULL, 0, FALSE); lpenalty = gistpenalty(giststate, attno, &entry, v->spl_lisnull[attno], identry + attno, isnull[attno]); gistentryinit(entry, v->spl_rattr[attno], r, NULL, 0, FALSE); rpenalty = gistpenalty(giststate, attno, &entry, v->spl_risnull[attno], identry + attno, isnull[attno]); if (lpenalty != rpenalty) { if (lpenalty > rpenalty) toLeft = false; break; } } if (toLeft) v->splitVector.spl_left[v->splitVector.spl_nleft++] = off; else v->splitVector.spl_right[v->splitVector.spl_nright++] = off; }
/* * initialize a GiST entry with a decompressed version of key */ void gistdentryinit(GISTSTATE *giststate, int nkey, GISTENTRY *e, Datum k, Relation r, Page pg, OffsetNumber o, bool l, bool isNull) { if (!isNull) { GISTENTRY *dep; gistentryinit(*e, k, r, pg, o, l); /* there may not be a decompress function in opclass */ if (!OidIsValid(giststate->decompressFn[nkey].fn_oid)) return; dep = (GISTENTRY *) DatumGetPointer(FunctionCall1Coll(&giststate->decompressFn[nkey], giststate->supportCollation[nkey], PointerGetDatum(e))); /* decompressFn may just return the given pointer */ if (dep != e) gistentryinit(*e, dep->key, dep->rel, dep->page, dep->offset, dep->leafkey); } else gistentryinit(*e, (Datum) 0, r, pg, o, l); }
Datum ghstore_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval = entry; if (entry->leafkey) { GISTTYPE *res = (GISTTYPE *) palloc0(CALCGTSIZE(0)); HStore *val = DatumGetHStoreP(entry->key); HEntry *hsent = ARRPTR(val); char *ptr = STRPTR(val); int count = HS_COUNT(val); int i; SET_VARSIZE(res, CALCGTSIZE(0)); for (i = 0; i < count; ++i) { int h; h = crc32_sz((char *) HSTORE_KEY(hsent, ptr, i), HSTORE_KEYLEN(hsent, i)); HASH(GETSIGN(res), h); if (!HSTORE_VALISNULL(hsent, i)) { h = crc32_sz((char *) HSTORE_VAL(hsent, ptr, i), HSTORE_VALLEN(hsent, i)); HASH(GETSIGN(res), h); } } retval = (GISTENTRY *) palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(res), entry->rel, entry->page, entry->offset, FALSE); } else if (!ISALLTRUE(DatumGetPointer(entry->key))) { int32 i; GISTTYPE *res; BITVECP sign = GETSIGN(DatumGetPointer(entry->key)); LOOPBYTE { if ((sign[i] & 0xff) != 0xff) PG_RETURN_POINTER(retval); } res = (GISTTYPE *) palloc(CALCGTSIZE(ALLISTRUE)); SET_VARSIZE(res, CALCGTSIZE(ALLISTRUE)); res->flag = ALLISTRUE; retval = (GISTENTRY *) palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(res), entry->rel, entry->page, entry->offset, FALSE); }
/* * GiST compress for polygons: represent a polygon by its bounding box */ datum_t gist_poly_compress(PG_FUNC_ARGS) { struct gist_entry *entry = (struct gist_entry *)ARG_POINTER(0); struct gist_entry *retval; if (entry->leafkey) { retval = palloc(sizeof(struct gist_entry)); if (D_TO_PTR(entry->key) != NULL) { POLYGON *in = D_TO_POLYGON_P(entry->key); BOX *r; r = (BOX *) palloc(sizeof(BOX)); memcpy((void *)r, (void *)&(in->boundbox), sizeof(BOX)); gistentryinit(*retval, PTR_TO_D(r), entry->rel, entry->page, entry->offset, FALSE); } else { gistentryinit(*retval, (datum_t) 0, entry->rel, entry->page, entry->offset, FALSE); } } else { retval = entry; } RET_POINTER(retval); }
/* * GiST compress for circles: represent a circle by its bounding box */ datum_t gist_circle_compress(PG_FUNC_ARGS) { struct gist_entry *entry = (struct gist_entry *)ARG_POINTER(0); struct gist_entry *retval; if (entry->leafkey) { retval = palloc(sizeof(struct gist_entry)); if (D_TO_CIRCLE_P(entry->key) != NULL) { CIRCLE *in = D_TO_CIRCLE_P(entry->key); BOX *r; r = (BOX *) palloc(sizeof(BOX)); r->high.x = in->center.x + in->radius; r->low.x = in->center.x - in->radius; r->high.y = in->center.y + in->radius; r->low.y = in->center.y - in->radius; gistentryinit(*retval, PTR_TO_D(r), entry->rel, entry->page, entry->offset, FALSE); } else { gistentryinit(*retval, (datum_t) 0, entry->rel, entry->page, entry->offset, FALSE); } } else retval = entry; RET_POINTER(retval); }
/* * GiST compress for polygons: represent a polygon by its bounding box */ Datum gist_poly_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval; if (entry->leafkey) { retval = palloc(sizeof(GISTENTRY)); if (DatumGetPointer(entry->key) != NULL) { POLYGON *in = DatumGetPolygonP(entry->key); BOX *r; r = (BOX *) palloc(sizeof(BOX)); memcpy((void *) r, (void *) &(in->boundbox), sizeof(BOX)); gistentryinit(*retval, PointerGetDatum(r), entry->rel, entry->page, entry->offset, FALSE); } else { gistentryinit(*retval, (Datum) 0, entry->rel, entry->page, entry->offset, FALSE); } } else retval = entry; PG_RETURN_POINTER(retval); }
/* * GiST compress for circles: represent a circle by its bounding box */ Datum gist_circle_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval; if (entry->leafkey) { retval = palloc(sizeof(GISTENTRY)); if (DatumGetCircleP(entry->key) != NULL) { CIRCLE *in = DatumGetCircleP(entry->key); BOX *r; r = (BOX *) palloc(sizeof(BOX)); r->high.x = in->center.x + in->radius; r->low.x = in->center.x - in->radius; r->high.y = in->center.y + in->radius; r->low.y = in->center.y - in->radius; gistentryinit(*retval, PointerGetDatum(r), entry->rel, entry->page, entry->offset, FALSE); } else { gistentryinit(*retval, (Datum) 0, entry->rel, entry->page, entry->offset, FALSE); } } else retval = entry; PG_RETURN_POINTER(retval); }
Datum g_int_decompress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval; ArrayType *r; int *dr, lenr; ArrayType *in; int lenin; int *din; int i, j; in = (ArrayType *) PG_DETOAST_DATUM(entry->key); if (ARRISVOID(in)) PG_RETURN_POINTER(entry); lenin = ARRNELEMS(in); if (lenin < 2 * MAXNUMRANGE || ISLEAFKEY(in)) { /* not compressed value */ if (in != (ArrayType *) DatumGetPointer(entry->key)) { retval = palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(in), entry->rel, entry->page, entry->offset, VARSIZE(in), FALSE); PG_RETURN_POINTER(retval); } PG_RETURN_POINTER(entry); } din = ARRPTR(in); lenr = internal_size(din, lenin); r = new_intArrayType(lenr); dr = ARRPTR(r); for (i = 0; i < lenin; i += 2) for (j = din[i]; j <= din[i + 1]; j++) if ((!i) || *(dr - 1) != j) *dr++ = j; if (in != (ArrayType *) DatumGetPointer(entry->key)) pfree(in); retval = palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(r), entry->rel, entry->page, entry->offset, VARSIZE(r), FALSE); PG_RETURN_POINTER(retval); }
/* * Compress a molecule of type molecule into an index entry of type molfp. * This is the conversion that makes index entries out of table entries. */ Datum molfp_compress (PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER (0); GISTENTRY *retval; if (entry->leafkey) { MOLECULE *mol = (MOLECULE *) DatumGetPointer (PG_DETOAST_DATUM (entry->key)); MOLFP *fp = new_molfp(); memcpy (fp->bytes, mol->fp.bytes, sizeof(MOLFP)); retval = (GISTENTRY *) palloc (sizeof (GISTENTRY)); gistentryinit (*retval, PointerGetDatum (fp), entry->rel, entry->page, entry->offset, FALSE); } else { retval = entry; } PG_RETURN_POINTER (retval); }
Datum gbt_bpchar_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval; if (tinfo.eml == 0) { tinfo.eml = pg_database_encoding_max_length(); } if (entry->leafkey) { Datum d = DirectFunctionCall1(rtrim1, entry->key); GISTENTRY trim; gistentryinit(trim, d, entry->rel, entry->page, entry->offset, VARSIZE(DatumGetPointer(d)), TRUE); retval = gbt_var_compress(&trim, &tinfo); } else retval = entry; PG_RETURN_POINTER(retval); }
Datum gbt_tstz_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval; if (entry->leafkey) { tsKEY *r = (tsKEY *) palloc(sizeof(tsKEY)); TimestampTz ts = DatumGetTimestampTz(entry->key); Timestamp gmt; gmt = tstz_to_ts_gmt(ts); retval = palloc(sizeof(GISTENTRY)); r->lower = r->upper = gmt; gistentryinit(*retval, PointerGetDatum(r), entry->rel, entry->page, entry->offset, FALSE); } else retval = entry; PG_RETURN_POINTER(retval); }
Datum gbt_timetz_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval; if (entry->leafkey) { timeKEY *r = (timeKEY *) palloc(sizeof(timeKEY)); TimeTzADT *tz = DatumGetTimeTzADTP(entry->key); TimeADT tmp; retval = palloc(sizeof(GISTENTRY)); /* We are using the time + zone only to compress */ #ifdef HAVE_INT64_TIMESTAMP tmp = tz->time + (tz->zone * INT64CONST(1000000)); #else tmp = (tz->time + tz->zone); #endif r->lower = r->upper = tmp; gistentryinit(*retval, PointerGetDatum(r), entry->rel, entry->page, entry->offset, sizeof(timeKEY), FALSE); } else retval = entry; PG_RETURN_POINTER(retval); }
Datum gbt_intv_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval = entry; if (entry->leafkey || INTERVALSIZE != sizeof(Interval)) { char *r = (char *) palloc(2 * INTERVALSIZE); retval = palloc(sizeof(GISTENTRY)); if (entry->leafkey) { Interval *key = DatumGetIntervalP(entry->key); memcpy((void *) r, (void *) key, INTERVALSIZE); memcpy((void *) (r + INTERVALSIZE), (void *) key, INTERVALSIZE); } else { intvKEY *key = (intvKEY *) DatumGetPointer(entry->key); memcpy(r, &key->lower, INTERVALSIZE); memcpy(r + INTERVALSIZE, &key->upper, INTERVALSIZE); } gistentryinit(*retval, PointerGetDatum(r), entry->rel, entry->page, entry->offset, FALSE); } PG_RETURN_POINTER(retval); }
GISTENTRY * gbt_var_compress(GISTENTRY *entry, const gbtree_vinfo *tinfo) { GISTENTRY *retval; if (entry->leafkey) { GBT_VARKEY *r = NULL; bytea *leaf = (bytea *) DatumGetPointer(PG_DETOAST_DATUM(entry->key)); GBT_VARKEY_R u; u.lower = u.upper = leaf; r = gbt_var_key_copy(&u, FALSE); retval = palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(r), entry->rel, entry->page, entry->offset, TRUE); } else retval = entry; return (retval); }
/* * Convert a compressed leaf item back to the original type, for index-only * scans. */ GISTENTRY * gbt_num_fetch(GISTENTRY *entry, const gbtree_ninfo *tinfo) { GISTENTRY *retval; Datum datum; Assert(tinfo->indexsize >= 2 * tinfo->size); /* * Get the original Datum from the stored datum. On leaf entries, the * lower and upper bound are the same. We just grab the lower bound and * return it. */ switch (tinfo->t) { case gbt_t_int2: datum = Int16GetDatum(*(int16 *) entry->key); break; case gbt_t_int4: datum = Int32GetDatum(*(int32 *) entry->key); break; case gbt_t_int8: datum = Int64GetDatum(*(int64 *) entry->key); break; case gbt_t_oid: case gbt_t_enum: datum = ObjectIdGetDatum(*(Oid *) entry->key); break; case gbt_t_float4: datum = Float4GetDatum(*(float4 *) entry->key); break; case gbt_t_float8: datum = Float8GetDatum(*(float8 *) entry->key); break; case gbt_t_date: datum = DateADTGetDatum(*(DateADT *) entry->key); break; case gbt_t_time: datum = TimeADTGetDatum(*(TimeADT *) entry->key); break; case gbt_t_ts: datum = TimestampGetDatum(*(Timestamp *) entry->key); break; case gbt_t_cash: datum = CashGetDatum(*(Cash *) entry->key); break; default: datum = PointerGetDatum(entry->key); } retval = palloc(sizeof(GISTENTRY)); gistentryinit(*retval, datum, entry->rel, entry->page, entry->offset, false); return retval; }
datum_t gtrgm_compress(PG_FUNC_ARGS) { struct gist_entry *entry = (struct gist_entry *) ARG_POINTER(0); struct gist_entry *retval = entry; if (entry->leafkey) { /* trgm */ TRGM *res; text *val = D_TO_TEXT_P(entry->key); res = generate_trgm(VLA_DATA(val), VLA_SZ(val) - VAR_HDR_SZ); retval = (struct gist_entry *) palloc(sizeof(struct gist_entry)); gistentryinit(*retval, PTR_TO_D(res), entry->rel, entry->page, entry->offset, FALSE); } else if (ISSIGNKEY(D_TO_PTR(entry->key)) && !ISALLTRUE(D_TO_PTR(entry->key))) { int4 i, len; TRGM *res; BITVECP sign = GETSIGN(D_TO_PTR(entry->key)); LOOPBYTE { if ((sign[i] & 0xff) != 0xff) RET_POINTER(retval); } len = CALCGTSIZE(SIGNKEY | ALLISTRUE, 0); res = (TRGM *) palloc(len); VLA_SET_SZ_STND(res, len); res->flag = SIGNKEY | ALLISTRUE; retval = (struct gist_entry *) palloc(sizeof(struct gist_entry)); gistentryinit(*retval, PTR_TO_D(res), entry->rel, entry->page, entry->offset, FALSE); }
Datum gtrgm_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval = entry; if (entry->leafkey) { /* trgm */ TRGM *res; text *val = DatumGetTextP(entry->key); res = generate_trgm(VARDATA(val), VARSIZE(val) - VARHDRSZ); retval = (GISTENTRY *) palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(res), entry->rel, entry->page, entry->offset, FALSE); } else if (ISSIGNKEY(DatumGetPointer(entry->key)) && !ISALLTRUE(DatumGetPointer(entry->key))) { int32 i, len; TRGM *res; BITVECP sign = GETSIGN(DatumGetPointer(entry->key)); LOOPBYTE { if ((sign[i] & 0xff) != 0xff) PG_RETURN_POINTER(retval); } len = CALCGTSIZE(SIGNKEY | ALLISTRUE, 0); res = (TRGM *) palloc(len); SET_VARSIZE(res, len); res->flag = SIGNKEY | ALLISTRUE; retval = (GISTENTRY *) palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(res), entry->rel, entry->page, entry->offset, FALSE); }
/* * initialize a GiST entry with a compressed version of key */ void gistcentryinit(GISTSTATE *giststate, int nkey, GISTENTRY *e, Datum k, Relation r, Page pg, OffsetNumber o, bool l, bool isNull) { if (!isNull) { GISTENTRY *cep; gistentryinit(*e, k, r, pg, o, l); cep = (GISTENTRY *) DatumGetPointer(FunctionCall1(&giststate->compressFn[nkey], PointerGetDatum(e))); /* compressFn may just return the given pointer */ if (cep != e) gistentryinit(*e, cep->key, cep->rel, cep->page, cep->offset, cep->leafkey); } else gistentryinit(*e, (Datum) 0, r, pg, o, l); }
/* * find group in vector with equivalent value */ static int gistfindgroup(Relation r, GISTSTATE *giststate, GISTENTRY *valvec, GistSplitVector *spl, int attno) { int i; GISTENTRY entry; int len = 0; /* * attno key is always not null (see gistSplitByKey), so we may not check * for nulls */ gistentryinit(entry, spl->splitVector.spl_rdatum, r, NULL, (OffsetNumber) 0, FALSE); for (i = 0; i < spl->splitVector.spl_nleft; i++) { float penalty = gistpenalty(giststate, attno, &entry, false, &valvec[spl->splitVector.spl_left[i]], false); if (penalty == 0.0) { spl->spl_equiv[spl->splitVector.spl_left[i]] = true; len++; } } gistentryinit(entry, spl->splitVector.spl_ldatum, r, NULL, (OffsetNumber) 0, FALSE); for (i = 0; i < spl->splitVector.spl_nright; i++) { float penalty = gistpenalty(giststate, attno, &entry, false, &valvec[spl->splitVector.spl_right[i]], false); if (penalty == 0.0) { spl->spl_equiv[spl->splitVector.spl_right[i]] = true; len++; } } return len; }
Datum gbt_var_fetch(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GBT_VARKEY *key = (GBT_VARKEY *) DatumGetPointer(PG_DETOAST_DATUM(entry->key)); GBT_VARKEY_R r = gbt_var_key_readable(key); GISTENTRY *retval; retval = palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(r.lower), entry->rel, entry->page, entry->offset, TRUE); PG_RETURN_POINTER(retval); }
/* ** initialize a GiST entry with a decompressed version of key */ void gistdentryinit(GISTSTATE *giststate, int nkey, GISTENTRY *e, Datum k, Relation r, Page pg, OffsetNumber o, int b, bool l, bool isNull) { if (b && !isNull) { GISTENTRY *dep; gistentryinit(*e, k, r, pg, o, b, l); dep = (GISTENTRY *) DatumGetPointer(FunctionCall1(&giststate->decompressFn[nkey], PointerGetDatum(e))); /* decompressFn may just return the given pointer */ if (dep != e) { gistentryinit(*e, dep->key, dep->rel, dep->page, dep->offset, dep->bytes, dep->leafkey); pfree(dep); } } else gistentryinit(*e, (Datum) 0, r, pg, o, 0, l); }
Datum _ltree_compress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); GISTENTRY *retval = entry; if (entry->leafkey) { /* ltree */ ltree_gist *key; ArrayType *val = DatumGetArrayTypeP(entry->key); int4 len = LTG_HDRSIZE + ASIGLEN; int num = ArrayGetNItems(ARR_NDIM(val), ARR_DIMS(val)); ltree *item = (ltree *) ARR_DATA_PTR(val); if (ARR_NDIM(val) != 1) ereport(ERROR, (errcode(ERRCODE_ARRAY_SUBSCRIPT_ERROR), errmsg("array must be one-dimensional"))); key = (ltree_gist *) palloc(len); key->len = len; key->flag = 0; MemSet(LTG_SIGN(key), 0, ASIGLEN); while (num > 0) { hashing(LTG_SIGN(key), item); num--; item = NEXTVAL(item); } retval = (GISTENTRY *) palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(key), entry->rel, entry->page, entry->offset, key->len, FALSE); } else if (!LTG_ISALLTRUE(entry->key)) { int4 i, len; ltree_gist *key; BITVECP sign = LTG_SIGN(DatumGetPointer(entry->key)); ALOOPBYTE( if ((sign[i] & 0xff) != 0xff) PG_RETURN_POINTER(retval); );
Datum g_cube_decompress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); NDBOX *key = DatumGetNDBOX(PG_DETOAST_DATUM(entry->key)); if (key != DatumGetNDBOX(entry->key)) { GISTENTRY *retval = (GISTENTRY *) palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(key), entry->rel, entry->page, entry->offset, FALSE); PG_RETURN_POINTER(retval); } PG_RETURN_POINTER(entry); }
/* * initialize a GiST entry with fetched value in key field */ static Datum gistFetchAtt(GISTSTATE *giststate, int nkey, Datum k, Relation r) { GISTENTRY fentry; GISTENTRY *fep; gistentryinit(fentry, k, r, NULL, (OffsetNumber) 0, false); fep = (GISTENTRY *) DatumGetPointer(FunctionCall1Coll(&giststate->fetchFn[nkey], giststate->supportCollation[nkey], PointerGetDatum(&fentry))); /* fetchFn set 'key', return it to the caller */ return fep->key; }
Datum ltree_decompress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); ltree_gist *key = (ltree_gist *) DatumGetPointer(PG_DETOAST_DATUM(entry->key)); if (PointerGetDatum(key) != entry->key) { GISTENTRY *retval = (GISTENTRY *) palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(key), entry->rel, entry->page, entry->offset, FALSE); PG_RETURN_POINTER(retval); } PG_RETURN_POINTER(entry); }
Datum gmol_decompress(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); bytea *key = (bytea*)DatumGetPointer(PG_DETOAST_DATUM(entry->key)); if (key != (bytea *) DatumGetPointer(entry->key)) { GISTENTRY *retval = (GISTENTRY *) palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(key), entry->rel, entry->page, entry->offset, false); PG_RETURN_POINTER(retval); } PG_RETURN_POINTER(entry); }
/* * GiST Fetch method for point * * Get point coordinates from its bounding box coordinates and form new___ * gistentry. */ Datum gist_point_fetch(PG_FUNCTION_ARGS) { GISTENTRY *entry = (GISTENTRY *) PG_GETARG_POINTER(0); BOX *in = DatumGetBoxP(entry->key); Point *r; GISTENTRY *retval; retval = static_cast<GISTENTRY *>(palloc(sizeof(GISTENTRY))); r = (Point *) palloc(sizeof(Point)); r->x = in->high.x; r->y = in->high.y; gistentryinit(*retval, PointerGetDatum(r), entry->rel, entry->page, entry->offset, FALSE); PG_RETURN_POINTER(retval); }
GISTENTRY * WTBtree_var_compress(GISTENTRY *entry) { GISTENTRY *retval; if (entry->leafkey) { LEAF_KEY *leaf = (LEAF_KEY *) DatumGetPointer(PG_DETOAST_DATUM(entry->key)); retval = palloc(sizeof(GISTENTRY)); gistentryinit(*retval, PointerGetDatum(leaf), entry->rel, entry->page, entry->offset, TRUE); } else retval = entry; return (retval); }
datum_t gist_point_compress(PG_FUNC_ARGS) { struct gist_entry *entry; entry = (struct gist_entry*) ARG_POINTER(0); if (entry->leafkey) { /* Point, actually */ BOX *box = palloc(sizeof(BOX)); Point *point = D_TO_POINT_P(entry->key); struct gist_entry *retval = palloc(sizeof(struct gist_entry)); box->high = box->low = *point; gistentryinit(*retval, BOX_P_TO_D(box), entry->rel, entry->page, entry->offset, FALSE); RET_POINTER(retval); } RET_POINTER(entry); }
IndexTuple gistFormTuple(GISTSTATE *giststate, Relation r, Datum attdata[], bool isnull[], bool isleaf) { Datum compatt[INDEX_MAX_KEYS]; int i; IndexTuple res; /* * Call the compress method on each attribute. */ for (i = 0; i < r->rd_att->natts; i++) { if (isnull[i]) compatt[i] = (Datum) 0; else { GISTENTRY centry; GISTENTRY *cep; gistentryinit(centry, attdata[i], r, NULL, (OffsetNumber) 0, isleaf); /* there may not be a compress function in opclass */ if (OidIsValid(giststate->compressFn[i].fn_oid)) cep = (GISTENTRY *) DatumGetPointer(FunctionCall1Coll(&giststate->compressFn[i], giststate->supportCollation[i], PointerGetDatum(¢ry))); else cep = ¢ry; compatt[i] = cep->key; } } res = index_form_tuple(giststate->tupdesc, compatt, isnull); /* * The offset number on tuples on internal pages is unused. For historical * reasons, it is set to 0xffff. */ ItemPointerSetOffsetNumber(&(res->t_tid), 0xffff); return res; }