Skip to content

Commit

Permalink
Merge pull request #86804 from DrewKimball/backport22.1-86193
Browse files Browse the repository at this point in the history
release-22.1: opt: use only required columns in provided ordering for project
  • Loading branch information
DrewKimball authored Aug 24, 2022
2 parents 32163eb + 88d8de4 commit f81f08f
Show file tree
Hide file tree
Showing 2 changed files with 52 additions and 2 deletions.
16 changes: 14 additions & 2 deletions pkg/sql/opt/ordering/project.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import (
"github.com/cockroachdb/cockroach/pkg/sql/opt"
"github.com/cockroachdb/cockroach/pkg/sql/opt/memo"
"github.com/cockroachdb/cockroach/pkg/sql/opt/props"
"github.com/cockroachdb/errors"
)

func projectCanProvideOrdering(expr memo.RelExpr, required *props.OrderingChoice) bool {
Expand Down Expand Up @@ -74,13 +75,24 @@ func projectOrderingToInput(
}

func projectBuildProvided(expr memo.RelExpr, required *props.OrderingChoice) opt.Ordering {
p := expr.(*memo.ProjectExpr)
// Ensure that the child provided ordering only refers to columns from the
// required ordering choice. This is necessary because there may be cases
// where the input of the Project has undergone transformations that allow it
// to "see" more functional dependencies than the original memo group. This
// can cause the child to provide an ordering that is equivalent to the
// required ordering, but which the parent Project cannot prove is equivalent
// because its FDs have less information. This can lead to a panic later on.
ordCols := required.ColSet()
if !ordCols.SubsetOf(expr.Relational().OutputCols) {
panic(errors.AssertionFailedf("expected required columns to be a subset of output columns"))
}
// Project can only satisfy required orderings that refer to projected
// columns; it should always be possible to remap the columns in the input's
// provided ordering.
p := expr.(*memo.ProjectExpr)
return remapProvided(
p.Input.ProvidedPhysical().Ordering,
p.InternalFDs(),
p.Relational().OutputCols,
ordCols,
)
}
38 changes: 38 additions & 0 deletions pkg/sql/opt/xform/testdata/physprops/ordering
Original file line number Diff line number Diff line change
Expand Up @@ -2571,3 +2571,41 @@ project
│ ├── name:2 = name:8 [outer=(2,8), fd=(2)==(8), (8)==(2)]
│ └── k:7::STRING = lower(name:8) [outer=(7,8), immutable]
└── 56

# Regression test for #85393 - use only columns from the required ordering when
# building the provided ordering for Project operators.
exec-ddl
CREATE TABLE t0_85393 (c0 INT);
----

exec-ddl
CREATE TABLE t1_85393 (c0 INT);
----

opt
SELECT *
FROM t0_85393 CROSS JOIN t1_85393
WHERE (t0_85393.rowid IS NULL) OR (t1_85393.rowid IN (t0_85393.rowid))
ORDER BY t1_85393.rowid;
----
sort
├── columns: c0:1 c0:5 [hidden: t1_85393.rowid:6!null]
├── fd: (6)-->(5)
├── ordering: +6
└── project
├── columns: t0_85393.c0:1 t1_85393.c0:5 t1_85393.rowid:6!null
├── fd: (6)-->(5)
└── inner-join (cross)
├── columns: t0_85393.c0:1 t0_85393.rowid:2!null t1_85393.c0:5 t1_85393.rowid:6!null
├── key: (2,6)
├── fd: (2)-->(1), (6)-->(5)
├── scan t0_85393
│ ├── columns: t0_85393.c0:1 t0_85393.rowid:2!null
│ ├── key: (2)
│ └── fd: (2)-->(1)
├── scan t1_85393
│ ├── columns: t1_85393.c0:5 t1_85393.rowid:6!null
│ ├── key: (6)
│ └── fd: (6)-->(5)
└── filters
└── (t0_85393.rowid:2 IS NULL) OR (t1_85393.rowid:6 = t0_85393.rowid:2) [outer=(2,6)]

0 comments on commit f81f08f

Please sign in to comment.