• Tom Lane's avatar
    Rewrite make_outerjoininfo's construction of min_lefthand and min_righthand · b4c806fa
    Tom Lane authored
    sets for outer joins, in the light of bug #3588 and additional thought and
    experimentation.  The original methodology was fatally flawed for nests of
    more than two outer joins: it got the relationships between adjacent joins
    right, but didn't always come to the right conclusions about whether a join
    could be interchanged with one two or more levels below it.  This was largely
    caused by a mistaken idea that we should use the min_lefthand + min_righthand
    sets of a sub-join as the minimum left or right input set of an upper join
    when we conclude that the sub-join can't commute with the upper one.  If
    there's a still-lower join that the sub-join *can* commute with, this method
    led us to think that that one could commute with the topmost join; which it
    can't.  Another problem (not directly connected to bug #3588) was that
    make_outerjoininfo's processing-order-dependent method for enforcing outer
    join identity #3 didn't work right: if we decided that join A could safely
    commute with lower join B, we dropped all information about sub-joins under B
    that join A could perhaps not safely commute with, because we removed B's
    entire min_righthand from A's.
    
    To fix, make an explicit computation of all inner join combinations that occur
    below an outer join, and add to that the full syntactic relsets of any lower
    outer joins that we determine it can't commute with.  This method gives much
    more direct enforcement of the outer join rearrangement identities, and it
    turns out not to cost a lot of additional bookkeeping.
    
    Thanks to Richard Harris for the bug report and test case.
    b4c806fa
join.out 68 KB