11/*
2- * $PostgreSQL: pgsql/contrib/pg_trgm/trgm_gin.c,v 1.4 2008/05/17 01:28:21 adunstan Exp $
2+ * $PostgreSQL: pgsql/contrib/pg_trgm/trgm_gin.c,v 1.5 2008/07/11 11:56:48 teodor Exp $
33 */
44#include "trgm.h"
55
@@ -52,6 +52,16 @@ gin_extract_trgm(PG_FUNCTION_ARGS)
5252PG_RETURN_POINTER(entries);
5353}
5454
55+ /*
56+ * Per call strage for consistent functions to
57+ * cache computed value from query
58+ */
59+ typedef struct PerCallConsistentStorage {
60+ inttrglen;
61+ textdata[1]; /* query */
62+ } PerCallConsistentStorage;
63+ #define PCCSHDR_SZ offsetof(PerCallConsistentStorage, data)
64+
5565Datum
5666gin_trgm_consistent(PG_FUNCTION_ARGS)
5767{
@@ -60,16 +70,30 @@ gin_trgm_consistent(PG_FUNCTION_ARGS)
6070text *query = PG_GETARG_TEXT_P(2);
6171bool *recheck = (bool *) PG_GETARG_POINTER(3);
6272boolres = FALSE;
63- TRGM *trg;
6473int4i,
6574trglen,
6675ntrue = 0;
76+ PerCallConsistentStorage *pccs = (PerCallConsistentStorage*) fcinfo->flinfo->fn_extra;
6777
6878/* All cases served by this function are inexact */
6979*recheck = true;
7080
71- trg = generate_trgm(VARDATA(query), VARSIZE(query) - VARHDRSZ);
72- trglen = ARRNELEM(trg);
81+ if ( pccs == NULL || VARSIZE(pccs->data) != VARSIZE(query) || memcmp( pccs->data, query, VARSIZE(query) ) !=0 )
82+ {
83+ TRGM *trg = generate_trgm(VARDATA(query), VARSIZE(query) - VARHDRSZ);
84+
85+ if ( pccs )
86+ pfree(pccs);
87+
88+ fcinfo->flinfo->fn_extra = MemoryContextAlloc(fcinfo->flinfo->fn_mcxt,
89+ VARSIZE(query) + PCCSHDR_SZ);
90+ pccs = (PerCallConsistentStorage*) fcinfo->flinfo->fn_extra;
91+
92+ pccs->trglen = ARRNELEM(trg);
93+ memcpy( pccs->data, query, VARSIZE(query) );
94+ }
95+
96+ trglen = pccs->trglen;
7397
7498for (i = 0; i < trglen; i++)
7599if (check[i])