Hi Paul,
On 2014-09-23 09:55:32 -0700, Paul Ramsey wrote:
> I’m trying to implement an spgist index in the PostGIS extension, which seems
> like it should work, but is thus far not working for what appear (to me) to
> be issues in the way spgist expects to pass pointers to user-defined
> functions.
>
> Right before anything happens, spgist calls a ‘config’ routine in the user
> code. This is the code from the example implementation (which is internal to
> pgsql, not a run-time add-on like postgis)
>
> Datum
> spg_quad_config(PG_FUNCTION_ARGS)
> {
> /* spgConfigIn *cfgin = (spgConfigIn *) PG_GETARG_POINTER(0); */
> spgConfigOut *cfg = (spgConfigOut *) PG_GETARG_POINTER(1);
>
> cfg->prefixType = POINTOID;
> cfg->labelType = VOIDOID; /* we don't need node labels */
> cfg->canReturnData = true;
> cfg->longValuesOK = false;
> PG_RETURN_VOID();
> }
>
> It is called from the spgist core in the spgGetCache() function, via
>
> FunctionCall2Coll(procinfo,
> index->rd_indcollation[0],
> PointerGetDatum(&in),
> PointerGetDatum(&cache->config));
>
> The part the user function cares about is the pointer to cache->config.
>
> In the core code, the call stack to the user function goes like this:
>
> postgres`spg_quad_config(fcinfo=0x00007fff5f0faf90) + 18 at
> spgquadtreeproc.c:29
> postgres`FunctionCall2Coll(flinfo=0x00007ff59a804cc8, collation=0,
> arg1=140734788252568, arg2=140692835814944) + 150 at fmgr.c:1327
> postgres`spgGetCache(index=0x000000010254be68) + 220 at spgutils.c:71
>
> So, spgGetCache to FunctionCall2Coll to spg_quad_config.
>
> In my user-defined version of the same thing (I just copied the C code and
> wrote a CREATE OPERATOR CLASS for it) the call stack is this
>
> postgis-2.2.so`gserialized_spgist_quadtree_2d_config(fcinfo=0x00007fff5f0fb398)
> + 30 at gserialized_spgist_2d.c:60
> postgres`fmgr_oldstyle(fcinfo=0x00007fff5f0faf90) + 424 at fmgr.c:678
> postgres`FunctionCall2Coll(flinfo=0x00007ff59a039cc8, collation=0,
> arg1=140734788252568, arg2=140692827643424) + 150 at fmgr.c:1327
> postgres`spgGetCache(index=0x000000010254be68) + 220 at spgutils.c:71
>
> So, spgGetCache to FunctionCall2Coll to fmgr_oldstyle to
> gserialized_spgist_quadtree_2d_config!
>
> On the way through fmgr_oldstyle things go very much awry and the
> gserialized_spgist_quadtree_2d_config doesn’t get called with a pointer to an
> fcinfo, but with a pointer to the block of memory occupied by the first
> argument, and from there things naturally stop working.
>
> So, I’m wondering what I could have done that is causing my calls to route
> through fmgr_oldstyle instead of the usual path?
You forgot to add a PG_FUNCTION_INFO_V1(yourfunc); for the function.
I really, really think we should get rid of v0 functions. I've seen
errors like this far too many, and they really don't buy us much.
Greetings,
Andres Freund
--
Andres Freund http://www.2ndQuadrant.com/
PostgreSQL Development, 24x7 Support, Training & Services
--
Sent via pgsql-general mailing list ([email protected])
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-general