diff --git a/src/backend/nodes/copyfuncs.c b/src/backend/nodes/copyfuncs.c
index ef4f0421e93bdc7ba7eaf78be71be1be2c062fac..8b96f77a7316f2b327e7209bb9c7aab4d0748b2e 100644
--- a/src/backend/nodes/copyfuncs.c
+++ b/src/backend/nodes/copyfuncs.c
@@ -15,7 +15,7 @@
  * Portions Copyright (c) 1994, Regents of the University of California
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/backend/nodes/copyfuncs.c,v 1.269 2003/11/29 19:51:49 pgsql Exp $
+ *	  $PostgreSQL: pgsql/src/backend/nodes/copyfuncs.c,v 1.270 2003/12/30 23:53:14 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -1169,11 +1169,12 @@ _copyRestrictInfo(RestrictInfo *from)
 
 	COPY_NODE_FIELD(clause);
 	COPY_SCALAR_FIELD(ispusheddown);
+	COPY_SCALAR_FIELD(canjoin);
+	COPY_BITMAPSET_FIELD(left_relids);
+	COPY_BITMAPSET_FIELD(right_relids);
 	COPY_NODE_FIELD(subclauseindices);	/* XXX probably bad */
 	COPY_SCALAR_FIELD(eval_cost);
 	COPY_SCALAR_FIELD(this_selec);
-	COPY_BITMAPSET_FIELD(left_relids);
-	COPY_BITMAPSET_FIELD(right_relids);
 	COPY_SCALAR_FIELD(mergejoinoperator);
 	COPY_SCALAR_FIELD(left_sortop);
 	COPY_SCALAR_FIELD(right_sortop);
diff --git a/src/backend/nodes/equalfuncs.c b/src/backend/nodes/equalfuncs.c
index f4fd1d774326d6784ab12dad0bea23e48448e5ad..5c7e53844022743eea617cff8e2d6cec65a1a7f5 100644
--- a/src/backend/nodes/equalfuncs.c
+++ b/src/backend/nodes/equalfuncs.c
@@ -18,7 +18,7 @@
  * Portions Copyright (c) 1994, Regents of the University of California
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/backend/nodes/equalfuncs.c,v 1.210 2003/11/29 19:51:49 pgsql Exp $
+ *	  $PostgreSQL: pgsql/src/backend/nodes/equalfuncs.c,v 1.211 2003/12/30 23:53:14 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -563,16 +563,9 @@ _equalRestrictInfo(RestrictInfo *a, RestrictInfo *b)
 	COMPARE_SCALAR_FIELD(ispusheddown);
 
 	/*
-	 * We ignore subclauseindices, eval_cost, this_selec,
-	 * left/right_relids, left/right_pathkey, and left/right_bucketsize,
-	 * since they may not be set yet, and should be derivable from the
-	 * clause anyway.  Probably it's not really necessary to compare any
-	 * of these remaining fields ...
+	 * We ignore all the remaining fields, since they may not be set yet,
+	 * and should be derivable from the clause anyway.
 	 */
-	COMPARE_SCALAR_FIELD(mergejoinoperator);
-	COMPARE_SCALAR_FIELD(left_sortop);
-	COMPARE_SCALAR_FIELD(right_sortop);
-	COMPARE_SCALAR_FIELD(hashjoinoperator);
 
 	return true;
 }
diff --git a/src/backend/nodes/outfuncs.c b/src/backend/nodes/outfuncs.c
index 0946cbc9eb7e5ddb2311f76be18d73c0a71fd598..6b8a8a4a8748439e90a85ca41f05fed07138a4c6 100644
--- a/src/backend/nodes/outfuncs.c
+++ b/src/backend/nodes/outfuncs.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/backend/nodes/outfuncs.c,v 1.222 2003/11/29 19:51:49 pgsql Exp $
+ *	  $PostgreSQL: pgsql/src/backend/nodes/outfuncs.c,v 1.223 2003/12/30 23:53:14 tgl Exp $
  *
  * NOTES
  *	  Every node type that can appear in stored rules' parsetrees *must*
@@ -1074,9 +1074,10 @@ _outRestrictInfo(StringInfo str, RestrictInfo *node)
 	/* NB: this isn't a complete set of fields */
 	WRITE_NODE_FIELD(clause);
 	WRITE_BOOL_FIELD(ispusheddown);
-	WRITE_NODE_FIELD(subclauseindices);
+	WRITE_BOOL_FIELD(canjoin);
 	WRITE_BITMAPSET_FIELD(left_relids);
 	WRITE_BITMAPSET_FIELD(right_relids);
+	WRITE_NODE_FIELD(subclauseindices);
 	WRITE_OID_FIELD(mergejoinoperator);
 	WRITE_OID_FIELD(left_sortop);
 	WRITE_OID_FIELD(right_sortop);
diff --git a/src/backend/optimizer/path/indxpath.c b/src/backend/optimizer/path/indxpath.c
index b9ccc770a431c923b1fe4e510bb7de9ebc1bc215..c2fe837db65a71df189acb8fbce8050fb65d61a1 100644
--- a/src/backend/optimizer/path/indxpath.c
+++ b/src/backend/optimizer/path/indxpath.c
@@ -9,7 +9,7 @@
  *
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/backend/optimizer/path/indxpath.c,v 1.150 2003/12/18 00:22:12 tgl Exp $
+ *	  $PostgreSQL: pgsql/src/backend/optimizer/path/indxpath.c,v 1.151 2003/12/30 23:53:14 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -64,9 +64,11 @@ static List *group_clauses_by_indexkey_for_join(Query *root,
 								   Relids outer_relids,
 								   JoinType jointype, bool isouterjoin);
 static bool match_clause_to_indexcol(RelOptInfo *rel, IndexOptInfo *index,
-						 int indexcol, Oid opclass, Expr *clause);
+									 int indexcol, Oid opclass,
+									 Expr *clause, RestrictInfo *rinfo);
 static bool match_join_clause_to_indexcol(RelOptInfo *rel, IndexOptInfo *index,
-							  int indexcol, Oid opclass, Expr *clause);
+										  int indexcol, Oid opclass,
+										  RestrictInfo *rinfo);
 static Oid indexable_operator(Expr *clause, Oid opclass,
 				   bool indexkey_on_left);
 static bool pred_test(List *predicate_list, List *restrictinfo_list,
@@ -374,14 +376,14 @@ match_or_subclause_to_indexkey(RelOptInfo *rel,
 		foreach(item, ((BoolExpr *) clause)->args)
 		{
 			if (match_clause_to_indexcol(rel, index, 0, opclass,
-										 lfirst(item)))
+										 lfirst(item), NULL))
 				return true;
 		}
 		return false;
 	}
 	else
 		return match_clause_to_indexcol(rel, index, 0, opclass,
-										clause);
+										clause, NULL);
 }
 
 /*----------
@@ -445,7 +447,7 @@ extract_or_indexqual_conditions(RelOptInfo *rel,
 
 				if (match_clause_to_indexcol(rel, index,
 											 indexcol, curClass,
-											 subsubclause))
+											 subsubclause, NULL))
 					FastConc(&clausegroup,
 							 expand_indexqual_condition(subsubclause,
 														curClass));
@@ -453,7 +455,7 @@ extract_or_indexqual_conditions(RelOptInfo *rel,
 		}
 		else if (match_clause_to_indexcol(rel, index,
 										  indexcol, curClass,
-										  orsubclause))
+										  orsubclause, NULL))
 			FastConc(&clausegroup,
 					 expand_indexqual_condition(orsubclause,
 												curClass));
@@ -470,7 +472,7 @@ extract_or_indexqual_conditions(RelOptInfo *rel,
 
 				if (match_clause_to_indexcol(rel, index,
 											 indexcol, curClass,
-											 rinfo->clause))
+											 rinfo->clause, rinfo))
 					FastConc(&clausegroup,
 							 expand_indexqual_condition(rinfo->clause,
 														curClass));
@@ -550,7 +552,8 @@ group_clauses_by_indexkey(RelOptInfo *rel, IndexOptInfo *index)
 										 index,
 										 indexcol,
 										 curClass,
-										 rinfo->clause))
+										 rinfo->clause,
+										 rinfo))
 				FastAppend(&clausegroup, rinfo);
 		}
 
@@ -625,7 +628,8 @@ group_clauses_by_indexkey_for_join(Query *root,
 										 index,
 										 indexcol,
 										 curClass,
-										 rinfo->clause))
+										 rinfo->clause,
+										 rinfo))
 				FastAppend(&clausegroup, rinfo);
 		}
 
@@ -654,7 +658,7 @@ group_clauses_by_indexkey_for_join(Query *root,
 												  index,
 												  indexcol,
 												  curClass,
-												  rinfo->clause))
+												  rinfo))
 				{
 					FastAppend(&clausegroup, rinfo);
 					if (!jfoundhere)
@@ -726,6 +730,7 @@ group_clauses_by_indexkey_for_join(Query *root,
  * 'indexcol' is a column number of 'index' (counting from 0).
  * 'opclass' is the corresponding operator class.
  * 'clause' is the clause to be tested.
+ * 'rinfo' is the clause's RestrictInfo, if available (NULL if not).
  *
  * Returns true if the clause can be used with this index key.
  *
@@ -737,7 +742,8 @@ match_clause_to_indexcol(RelOptInfo *rel,
 						 IndexOptInfo *index,
 						 int indexcol,
 						 Oid opclass,
-						 Expr *clause)
+						 Expr *clause,
+						 RestrictInfo *rinfo)
 {
 	Node	   *leftop,
 			   *rightop;
@@ -754,9 +760,13 @@ match_clause_to_indexcol(RelOptInfo *rel,
 	 * Check for clauses of the form: (indexkey operator constant) or
 	 * (constant operator indexkey). Anything that is a "pseudo constant"
 	 * expression will do.
+	 *
+	 * If we have the RestrictInfo available, we can make a more efficient
+	 * test for pseudo-constness.
 	 */
 	if (match_index_to_operand(leftop, indexcol, rel, index) &&
-		is_pseudo_constant_clause(rightop))
+		(rinfo ? is_pseudo_constant_clause_relids(rightop, rinfo->right_relids)
+		 : is_pseudo_constant_clause(rightop)))
 	{
 		if (is_indexable_operator(clause, opclass, true))
 			return true;
@@ -771,7 +781,8 @@ match_clause_to_indexcol(RelOptInfo *rel,
 	}
 
 	if (match_index_to_operand(rightop, indexcol, rel, index) &&
-		is_pseudo_constant_clause(leftop))
+		(rinfo ? is_pseudo_constant_clause_relids(leftop, rinfo->left_relids)
+		 : is_pseudo_constant_clause(leftop)))
 	{
 		if (is_indexable_operator(clause, opclass, false))
 			return true;
@@ -813,7 +824,7 @@ match_clause_to_indexcol(RelOptInfo *rel,
  * 'index' is an index on 'rel'.
  * 'indexcol' is a column number of 'index' (counting from 0).
  * 'opclass' is the corresponding operator class.
- * 'clause' is the clause to be tested.
+ * 'rinfo' is the clause to be tested (as a RestrictInfo node).
  *
  * Returns true if the clause can be used with this index key.
  *
@@ -825,8 +836,9 @@ match_join_clause_to_indexcol(RelOptInfo *rel,
 							  IndexOptInfo *index,
 							  int indexcol,
 							  Oid opclass,
-							  Expr *clause)
+							  RestrictInfo *rinfo)
 {
+	Expr	   *clause = rinfo->clause;
 	Node	   *leftop,
 			   *rightop;
 
@@ -846,27 +858,25 @@ match_join_clause_to_indexcol(RelOptInfo *rel,
 	 */
 	if (match_index_to_operand(leftop, indexcol, rel, index))
 	{
-		Relids		othervarnos = pull_varnos(rightop);
+		Relids		othervarnos = rinfo->right_relids;
 		bool		isIndexable;
 
 		isIndexable =
 			!bms_overlap(rel->relids, othervarnos) &&
 			!contain_volatile_functions(rightop) &&
 			is_indexable_operator(clause, opclass, true);
-		bms_free(othervarnos);
 		return isIndexable;
 	}
 
 	if (match_index_to_operand(rightop, indexcol, rel, index))
 	{
-		Relids		othervarnos = pull_varnos(leftop);
+		Relids		othervarnos = rinfo->left_relids;
 		bool		isIndexable;
 
 		isIndexable =
 			!bms_overlap(rel->relids, othervarnos) &&
 			!contain_volatile_functions(leftop) &&
 			is_indexable_operator(clause, opclass, false);
-		bms_free(othervarnos);
 		return isIndexable;
 	}
 
@@ -1351,7 +1361,6 @@ indexable_outerrelids(RelOptInfo *rel, IndexOptInfo *index)
 		foreach(j, joininfo->jinfo_restrictinfo)
 		{
 			RestrictInfo *rinfo = (RestrictInfo *) lfirst(j);
-			Expr	   *clause = rinfo->clause;
 			int			indexcol = 0;
 			Oid		   *classes = index->classlist;
 
@@ -1363,7 +1372,7 @@ indexable_outerrelids(RelOptInfo *rel, IndexOptInfo *index)
 												  index,
 												  indexcol,
 												  curClass,
-												  clause))
+												  rinfo))
 				{
 					match_found = true;
 					break;
diff --git a/src/backend/optimizer/path/joinpath.c b/src/backend/optimizer/path/joinpath.c
index 5b95ec7c4dd9df39b72d544d771ade6320fdac22..91cd0ab22a5f45dbdabd8025a22ce4459d7004e9 100644
--- a/src/backend/optimizer/path/joinpath.c
+++ b/src/backend/optimizer/path/joinpath.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/backend/optimizer/path/joinpath.c,v 1.83 2003/11/29 19:51:50 pgsql Exp $
+ *	  $PostgreSQL: pgsql/src/backend/optimizer/path/joinpath.c,v 1.84 2003/12/30 23:53:14 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -690,7 +690,7 @@ hash_inner_and_outer(Query *root,
 	{
 		RestrictInfo *restrictinfo = (RestrictInfo *) lfirst(i);
 
-		if (restrictinfo->left_relids == NULL ||
+		if (!restrictinfo->canjoin ||
 			restrictinfo->hashjoinoperator == InvalidOid)
 			continue;			/* not hashjoinable */
 
@@ -809,12 +809,12 @@ select_mergejoin_clauses(RelOptInfo *joinrel,
 			switch (jointype)
 			{
 				case JOIN_RIGHT:
-					if (restrictinfo->left_relids == NULL ||
+					if (!restrictinfo->canjoin ||
 						restrictinfo->mergejoinoperator == InvalidOid)
 						return NIL;		/* not mergejoinable */
 					break;
 				case JOIN_FULL:
-					if (restrictinfo->left_relids == NULL ||
+					if (!restrictinfo->canjoin ||
 						restrictinfo->mergejoinoperator == InvalidOid)
 						ereport(ERROR,
 								(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
@@ -826,7 +826,7 @@ select_mergejoin_clauses(RelOptInfo *joinrel,
 			}
 		}
 
-		if (restrictinfo->left_relids == NULL ||
+		if (!restrictinfo->canjoin ||
 			restrictinfo->mergejoinoperator == InvalidOid)
 			continue;			/* not mergejoinable */
 
diff --git a/src/backend/optimizer/plan/initsplan.c b/src/backend/optimizer/plan/initsplan.c
index 5612430a390fe6d0b1b79d0d4d9e0a3cae02e5b6..3da001e997a0167eb6a2f873b32d3c9dd11baecc 100644
--- a/src/backend/optimizer/plan/initsplan.c
+++ b/src/backend/optimizer/plan/initsplan.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/backend/optimizer/plan/initsplan.c,v 1.93 2003/11/29 19:51:50 pgsql Exp $
+ *	  $PostgreSQL: pgsql/src/backend/optimizer/plan/initsplan.c,v 1.94 2003/12/30 23:53:14 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -380,12 +380,13 @@ distribute_qual_to_rels(Query *root, Node *clause,
 	bool		can_be_equijoin;
 
 	restrictinfo->clause = (Expr *) clause;
+	restrictinfo->canjoin = false;		/* set below, if join clause */
+	restrictinfo->left_relids = NULL;
+	restrictinfo->right_relids = NULL;
 	restrictinfo->subclauseindices = NIL;
 	restrictinfo->eval_cost.startup = -1;		/* not computed until
 												 * needed */
 	restrictinfo->this_selec = -1;		/* not computed until needed */
-	restrictinfo->left_relids = NULL;	/* set below, if join clause */
-	restrictinfo->right_relids = NULL;
 	restrictinfo->mergejoinoperator = InvalidOid;
 	restrictinfo->left_sortop = InvalidOid;
 	restrictinfo->right_sortop = InvalidOid;
@@ -510,6 +511,15 @@ distribute_qual_to_rels(Query *root, Node *clause,
 	restrictinfo->ispusheddown = ispusheddown || !bms_equal(relids,
 															qualscope);
 
+	/*
+	 * If it's a binary opclause, set up left/right relids info.
+	 */
+	if (is_opclause(clause) && length(((OpExpr *) clause)->args) == 2)
+	{
+		restrictinfo->left_relids = pull_varnos(get_leftop((Expr *) clause));
+		restrictinfo->right_relids = pull_varnos(get_rightop((Expr *) clause));
+	}
+
 	switch (bms_membership(relids))
 	{
 		case BMS_SINGLETON:
@@ -562,18 +572,11 @@ distribute_qual_to_rels(Query *root, Node *clause,
 			 */
 			if (is_opclause(clause) && length(((OpExpr *) clause)->args) == 2)
 			{
-				Relids		left_relids;
-				Relids		right_relids;
-
-				left_relids = pull_varnos(get_leftop((Expr *) clause));
-				right_relids = pull_varnos(get_rightop((Expr *) clause));
-				if (!bms_is_empty(left_relids) &&
-					!bms_is_empty(right_relids) &&
-					!bms_overlap(left_relids, right_relids))
-				{
-					restrictinfo->left_relids = left_relids;
-					restrictinfo->right_relids = right_relids;
-				}
+				if (!bms_is_empty(restrictinfo->left_relids) &&
+					!bms_is_empty(restrictinfo->right_relids) &&
+					!bms_overlap(restrictinfo->left_relids,
+								 restrictinfo->right_relids))
+					restrictinfo->canjoin = true;
 			}
 
 			/*
@@ -814,13 +817,14 @@ qual_is_redundant(Query *root,
 	List	   *equalexprs;
 	bool		someadded;
 
-	newleft = get_leftop(restrictinfo->clause);
-	newright = get_rightop(restrictinfo->clause);
-
 	/* Never redundant unless vars appear on both sides */
-	if (!contain_var_clause(newleft) || !contain_var_clause(newright))
+	if (bms_is_empty(restrictinfo->left_relids) ||
+		bms_is_empty(restrictinfo->right_relids))
 		return false;
 
+	newleft = get_leftop(restrictinfo->clause);
+	newright = get_rightop(restrictinfo->clause);
+
 	/*
 	 * Set cached pathkeys.  NB: it is okay to do this now because this
 	 * routine is only invoked while we are generating implied equalities.
diff --git a/src/backend/optimizer/util/clauses.c b/src/backend/optimizer/util/clauses.c
index d6f0bb3ad2eff317545f20465432b4180a2d8410..35efa6bc63074fa14758c90b2c402cf24d288853 100644
--- a/src/backend/optimizer/util/clauses.c
+++ b/src/backend/optimizer/util/clauses.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/backend/optimizer/util/clauses.c,v 1.157 2003/12/28 21:57:37 tgl Exp $
+ *	  $PostgreSQL: pgsql/src/backend/optimizer/util/clauses.c,v 1.158 2003/12/30 23:53:15 tgl Exp $
  *
  * HISTORY
  *	  AUTHOR			DATE			MAJOR EVENT
@@ -811,6 +811,20 @@ is_pseudo_constant_clause(Node *clause)
 	return false;
 }
 
+/*
+ * is_pseudo_constant_clause_relids
+ *	  Same as above, except caller already has available the var membership
+ *	  of the clause; this lets us avoid the contain_var_clause() scan.
+ */
+bool
+is_pseudo_constant_clause_relids(Node *clause, Relids relids)
+{
+	if (bms_is_empty(relids) &&
+		!contain_volatile_functions(clause))
+		return true;
+	return false;
+}
+
 /*
  * pull_constant_clauses
  *		Scan through a list of qualifications and separate "constant" quals
diff --git a/src/backend/optimizer/util/restrictinfo.c b/src/backend/optimizer/util/restrictinfo.c
index 2ae122e92a904e8b0df4669ba2eb0b7aa1566154..f77966a22623d54952064f9dcc6f52b3c4efb7ef 100644
--- a/src/backend/optimizer/util/restrictinfo.c
+++ b/src/backend/optimizer/util/restrictinfo.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $PostgreSQL: pgsql/src/backend/optimizer/util/restrictinfo.c,v 1.20 2003/11/29 19:51:51 pgsql Exp $
+ *	  $PostgreSQL: pgsql/src/backend/optimizer/util/restrictinfo.c,v 1.21 2003/12/30 23:53:15 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -227,15 +227,9 @@ join_clause_is_redundant(Query *root,
 
 		if (redundant)
 		{
-			/*
-			 * It looks redundant, now check for "var = const" case. If
-			 * left_relids/right_relids are set, then there are definitely
-			 * vars on both sides; else we must check the hard way.
-			 */
-			if (rinfo->left_relids)
-				return true;	/* var = var, so redundant */
-			if (contain_var_clause(get_leftop(rinfo->clause)) &&
-				contain_var_clause(get_rightop(rinfo->clause)))
+			/* It looks redundant, but check for "var = const" case */
+			if (!bms_is_empty(rinfo->left_relids) &&
+				!bms_is_empty(rinfo->right_relids))
 				return true;	/* var = var, so redundant */
 			/* else var = const, not redundant */
 		}
diff --git a/src/include/nodes/relation.h b/src/include/nodes/relation.h
index 6b205b20da5a2de1dcd05701e8a8be1f0a4eda9d..0d129f38ea1375d2793c756f0873a8c0bada3c53 100644
--- a/src/include/nodes/relation.h
+++ b/src/include/nodes/relation.h
@@ -7,7 +7,7 @@
  * Portions Copyright (c) 1996-2003, PostgreSQL Global Development Group
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $PostgreSQL: pgsql/src/include/nodes/relation.h,v 1.87 2003/12/28 21:57:37 tgl Exp $
+ * $PostgreSQL: pgsql/src/include/nodes/relation.h,v 1.88 2003/12/30 23:53:15 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -596,6 +596,19 @@ typedef struct RestrictInfo
 
 	bool		ispusheddown;	/* TRUE if clause was pushed down in level */
 
+	/*
+	 * This flag is set true if the clause looks potentially useful as a
+	 * merge or hash join clause, that is if it is a binary opclause with
+	 * nonoverlapping sets of relids referenced in the left and right sides.
+	 * (Whether the operator is actually merge or hash joinable isn't
+	 * checked, however.)
+	 */
+	bool		canjoin;
+
+	/* These fields are set for any binary opclause: */
+	Relids		left_relids;	/* relids in left side of clause */
+	Relids		right_relids;	/* relids in right side of clause */
+
 	/* only used if clause is an OR clause: */
 	List	   *subclauseindices;		/* indexes matching subclauses */
 	/* subclauseindices is a List of Lists of IndexOptInfos */
@@ -604,15 +617,6 @@ typedef struct RestrictInfo
 	QualCost	eval_cost;		/* eval cost of clause; -1 if not yet set */
 	Selectivity this_selec;		/* selectivity; -1 if not yet set */
 
-	/*
-	 * If the clause looks useful for joining --- that is, it is a binary
-	 * opclause with nonoverlapping sets of relids referenced in the left
-	 * and right sides --- then these two fields are set to sets of the
-	 * referenced relids.  Otherwise they are both NULL.
-	 */
-	Relids		left_relids;	/* relids in left side of join clause */
-	Relids		right_relids;	/* relids in right side of join clause */
-
 	/* valid if clause is mergejoinable, else InvalidOid: */
 	Oid			mergejoinoperator;		/* copy of clause operator */
 	Oid			left_sortop;	/* leftside sortop needed for mergejoin */
diff --git a/src/include/optimizer/clauses.h b/src/include/optimizer/clauses.h
index 7fb60b548e48af3a25e946c1c86381e78dad14c8..3e089256a51fb5d2c910b7c1c3e63e937b53514a 100644
--- a/src/include/optimizer/clauses.h
+++ b/src/include/optimizer/clauses.h
@@ -7,7 +7,7 @@
  * Portions Copyright (c) 1996-2003, PostgreSQL Global Development Group
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $PostgreSQL: pgsql/src/include/optimizer/clauses.h,v 1.69 2003/11/29 22:41:07 pgsql Exp $
+ * $PostgreSQL: pgsql/src/include/optimizer/clauses.h,v 1.70 2003/12/30 23:53:15 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -54,6 +54,7 @@ extern bool contain_volatile_functions(Node *clause);
 extern bool contain_nonstrict_functions(Node *clause);
 
 extern bool is_pseudo_constant_clause(Node *clause);
+extern bool is_pseudo_constant_clause_relids(Node *clause, Relids relids);
 extern List *pull_constant_clauses(List *quals, List **constantQual);
 
 extern bool has_distinct_on_clause(Query *query);