The other thing that emerged from
http://www.postgresql.org/message-id/flat/CAOR=d=3j1U_q-zf8+jUx1hkx8ps+N8pm=EUTqyFdJ5ov=+f...@mail.gmail.com
is that for workloads like this, OverrideSearchPathMatchesCurrent is
a bottleneck: it's part of the code path needed to re-use a cached plan,
and this example is doing a lot of that.  The original implementation
of that function followed the KISS principle, since I thought it probably
wouldn't be a bottleneck.  Now that that's proven wrong, I offer the
attached reimplementation, which saves about 9% of overall runtime on
Scott's example by avoiding palloc/pfree traffic.  It knows a lot more
about the relation of override search paths to active search paths than
it did before; but the adjacent functions know these things too, so it
doesn't seem like much of a loss from a maintainability standpoint.

                        regards, tom lane

diff --git a/src/backend/catalog/namespace.c b/src/backend/catalog/namespace.c
index 911f015..7a06332 100644
*** a/src/backend/catalog/namespace.c
--- b/src/backend/catalog/namespace.c
*************** CopyOverrideSearchPath(OverrideSearchPat
*** 3145,3164 ****
  bool
  OverrideSearchPathMatchesCurrent(OverrideSearchPath *path)
  {
! 	/* Easiest way to do this is GetOverrideSearchPath() and compare */
! 	bool		result;
! 	OverrideSearchPath *cur;
  
! 	cur = GetOverrideSearchPath(CurrentMemoryContext);
! 	if (path->addCatalog == cur->addCatalog &&
! 		path->addTemp == cur->addTemp &&
! 		equal(path->schemas, cur->schemas))
! 		result = true;
! 	else
! 		result = false;
! 	list_free(cur->schemas);
! 	pfree(cur);
! 	return result;
  }
  
  /*
--- 3145,3188 ----
  bool
  OverrideSearchPathMatchesCurrent(OverrideSearchPath *path)
  {
! 	ListCell   *lc,
! 			   *lcp;
  
! 	recomputeNamespacePath();
! 
! 	/* We scan down the activeSearchPath to see if it matches the input. */
! 	lc = list_head(activeSearchPath);
! 
! 	/* If path->addTemp, first item should be my temp namespace. */
! 	if (path->addTemp)
! 	{
! 		if (lc && lfirst_oid(lc) == myTempNamespace)
! 			lc = lnext(lc);
! 		else
! 			return false;
! 	}
! 	/* If path->addCatalog, next item should be pg_catalog. */
! 	if (path->addCatalog)
! 	{
! 		if (lc && lfirst_oid(lc) == PG_CATALOG_NAMESPACE)
! 			lc = lnext(lc);
! 		else
! 			return false;
! 	}
! 	/* We should now be looking at the activeCreationNamespace. */
! 	if (activeCreationNamespace != (lc ? lfirst_oid(lc) : InvalidOid))
! 		return false;
! 	/* The remainder of activeSearchPath should match path->schemas. */
! 	foreach(lcp, path->schemas)
! 	{
! 		if (lc && lfirst_oid(lc) == lfirst_oid(lcp))
! 			lc = lnext(lc);
! 		else
! 			return false;
! 	}
! 	if (lc)
! 		return false;
! 	return true;
  }
  
  /*
-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

Reply via email to