1628
1623
* corresponding test operator. This should work for any logically
1629
1624
* consistent opfamilies.
1631
catlist = SearchSysCacheList1(AMOPOPID, ObjectIdGetDatum(pred_op));
1634
* If we couldn't find any opfamily containing the pred_op, perhaps it is
1635
* a <> operator. See if it has a negator that is in an opfamily.
1637
pred_op_negated = false;
1638
if (catlist->n_members == 0)
1640
pred_op_negator = get_negator(pred_op);
1641
if (OidIsValid(pred_op_negator))
1643
pred_op_negated = true;
1644
ReleaseSysCacheList(catlist);
1645
catlist = SearchSysCacheList1(AMOPOPID,
1646
ObjectIdGetDatum(pred_op_negator));
1650
/* Also may need the clause_op's negator */
1651
clause_op_negator = get_negator(clause_op);
1653
/* Now search the opfamilies */
1654
for (i = 0; i < catlist->n_members; i++)
1656
HeapTuple pred_tuple = &catlist->members[i]->tuple;
1657
Form_pg_amop pred_form = (Form_pg_amop) GETSTRUCT(pred_tuple);
1658
HeapTuple clause_tuple;
1661
if (pred_form->amopmethod != BTREE_AM_OID)
1664
/* Get the predicate operator's btree strategy number */
1665
opfamily_id = pred_form->amopfamily;
1666
pred_strategy = (StrategyNumber) pred_form->amopstrategy;
1667
Assert(pred_strategy >= 1 && pred_strategy <= 5);
1669
if (pred_op_negated)
1671
/* Only consider negators that are = */
1672
if (pred_strategy != BTEqualStrategyNumber)
1674
pred_strategy = BTNE;
1678
* From the same opfamily, find a strategy number for the clause_op,
1681
clause_tuple = SearchSysCache3(AMOPOPID,
1682
ObjectIdGetDatum(clause_op),
1683
CharGetDatum(AMOP_SEARCH),
1684
ObjectIdGetDatum(opfamily_id));
1685
if (HeapTupleIsValid(clause_tuple))
1687
Form_pg_amop clause_form = (Form_pg_amop) GETSTRUCT(clause_tuple);
1689
/* Get the restriction clause operator's strategy/datatype */
1690
clause_strategy = (StrategyNumber) clause_form->amopstrategy;
1691
Assert(clause_strategy >= 1 && clause_strategy <= 5);
1692
Assert(clause_form->amoplefttype == pred_form->amoplefttype);
1693
clause_righttype = clause_form->amoprighttype;
1694
ReleaseSysCache(clause_tuple);
1696
else if (OidIsValid(clause_op_negator))
1698
clause_tuple = SearchSysCache3(AMOPOPID,
1699
ObjectIdGetDatum(clause_op_negator),
1700
CharGetDatum(AMOP_SEARCH),
1701
ObjectIdGetDatum(opfamily_id));
1702
if (HeapTupleIsValid(clause_tuple))
1704
Form_pg_amop clause_form = (Form_pg_amop) GETSTRUCT(clause_tuple);
1706
/* Get the restriction clause operator's strategy/datatype */
1707
clause_strategy = (StrategyNumber) clause_form->amopstrategy;
1708
Assert(clause_strategy >= 1 && clause_strategy <= 5);
1709
Assert(clause_form->amoplefttype == pred_form->amoplefttype);
1710
clause_righttype = clause_form->amoprighttype;
1711
ReleaseSysCache(clause_tuple);
1713
/* Only consider negators that are = */
1714
if (clause_strategy != BTEqualStrategyNumber)
1716
clause_strategy = BTNE;
1725
* Look up the "test" strategy number in the implication table
1728
test_strategy = BT_refute_table[clause_strategy - 1][pred_strategy - 1];
1730
test_strategy = BT_implic_table[clause_strategy - 1][pred_strategy - 1];
1732
if (test_strategy == 0)
1734
/* Can't determine implication using this interpretation */
1739
* See if opfamily has an operator for the test strategy and the
1742
if (test_strategy == BTNE)
1744
test_op = get_opfamily_member(opfamily_id,
1745
pred_form->amoprighttype,
1747
BTEqualStrategyNumber);
1748
if (OidIsValid(test_op))
1749
test_op = get_negator(test_op);
1753
test_op = get_opfamily_member(opfamily_id,
1754
pred_form->amoprighttype,
1758
if (OidIsValid(test_op))
1626
clause_op_infos = get_op_btree_interpretation(clause_op);
1627
if (clause_op_infos)
1628
pred_op_infos = get_op_btree_interpretation(pred_op);
1629
else /* no point in looking */
1630
pred_op_infos = NIL;
1632
foreach(lcp, pred_op_infos)
1634
OpBtreeInterpretation *pred_op_info = lfirst(lcp);
1635
Oid opfamily_id = pred_op_info->opfamily_id;
1637
foreach(lcc, clause_op_infos)
1639
OpBtreeInterpretation *clause_op_info = lfirst(lcc);
1640
StrategyNumber pred_strategy,
1644
/* Must find them in same opfamily */
1645
if (opfamily_id != clause_op_info->opfamily_id)
1647
/* Lefttypes should match */
1648
Assert(clause_op_info->oplefttype == pred_op_info->oplefttype);
1650
pred_strategy = pred_op_info->strategy;
1651
clause_strategy = clause_op_info->strategy;
1654
* Look up the "test" strategy number in the implication table
1657
test_strategy = BT_refute_table[clause_strategy - 1][pred_strategy - 1];
1659
test_strategy = BT_implic_table[clause_strategy - 1][pred_strategy - 1];
1661
if (test_strategy == 0)
1663
/* Can't determine implication using this interpretation */
1668
* See if opfamily has an operator for the test strategy and the
1671
if (test_strategy == BTNE)
1673
test_op = get_opfamily_member(opfamily_id,
1674
pred_op_info->oprighttype,
1675
clause_op_info->oprighttype,
1676
BTEqualStrategyNumber);
1677
if (OidIsValid(test_op))
1678
test_op = get_negator(test_op);
1682
test_op = get_opfamily_member(opfamily_id,
1683
pred_op_info->oprighttype,
1684
clause_op_info->oprighttype,
1688
if (!OidIsValid(test_op))
1761
1692
* Last check: test_op must be immutable.