Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix bounds for sympy expressions #102722

Closed
wants to merge 17 commits into from
Closed

Conversation

lezcano
Copy link
Collaborator

@lezcano lezcano commented Jun 1, 2023

Stack from ghstack (oldest at bottom):

The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc @voznesenskym @penguinwu @EikanWang @jgong5 @Guobing-Chen @XiaobingSuper @zhuhaozhe @blzheng @Xia-Weiwen @wenzhe-nrv @jiayisunx @peterbell10 @ipiszy @ngimel @yf225

The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

[ghstack-poisoned]
@pytorch-bot
Copy link

pytorch-bot bot commented Jun 1, 2023

🔗 Helpful Links

🧪 See artifacts and rendered test results at hud.pytorch.org/pr/102722

Note: Links to docs will display an error until the docs builds have been completed.

❌ 2 New Failures, 1 Unrelated Failure

As of commit 081e80d:

NEW FAILURES - The following jobs have failed:

UNSTABLE - The following job failed but was likely due to flakiness present on trunk and has been marked as unstable:

This comment was automatically generated by Dr. CI and updates every 15 minutes.

@@ -217,82 +217,6 @@ def may_convert_to_optional(optional_value, value):
return optional_value if not value and V.graph.cpp_wrapper else value


class ModularIndexing(sympy.Function):
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Moved all these to utils/_symp/functions.py

@@ -844,83 +844,6 @@ def eval(cls, base, divisor):
else:
return base / divisor

class FloorDiv(sympy.Function):
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

into _sympy/functions.py

@lezcano lezcano added the suppress-bc-linter Suppresses the failures of API backward-compatibility linter (Lint/bc_linter) label Jun 1, 2023
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
@lezcano lezcano removed the release notes: fx release notes category label Jun 1, 2023
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
Copy link
Contributor

@ezyang ezyang left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

But please see comments about div/floordiv confusion

phend = ops.index_expr(ir.FloorDiv(h, stride[0]) + 1, torch.int32)
pwend = ops.index_expr(ir.FloorDiv(w, stride[1]) + 1, torch.int32)
phend = ops.index_expr(FloorDiv(h, stride[0]) + 1, torch.int32)
pwend = ops.index_expr(FloorDiv(w, stride[1]) + 1, torch.int32)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

With this many updated call sites it would have been better to do this refactor in a separate PR (or not do it? This seems like window dressing to me for not much benefit)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I just needed to move all the relevant special classes into one folder so that I can import them properly in the other parts of the analysis. All the changers in this file just remove the ir. from the import.
In all fairness, I do think it's nicer without the ir., as this is not an IR class, but a SymPy construct.

@@ -63,74 +62,6 @@ def range_expressable_in_32_bits(range):
)


def get_expr_range(expr, vars_ranges: dict):
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did this get moved?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This one was incorrect and it's now replaced by bound_sympy.

torch/utils/_sympy/value_ranges.py Show resolved Hide resolved
@@ -37,7 +40,7 @@ def handlers():
sympy.Ge: "ge",
sympy.Not: "not_",
TrueDiv: "truediv",
FloorDiv: "div",
FloorDiv: "floordiv",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this OK? I was under the impression the analysis was also used by Inductor, which has its own naming convention for operation methods we need to abide by.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this is the right one, yes. See #102722 (comment)

return index
@staticmethod
def not_(a):
return ValueRanges.decreasing_map(a, sympy.Not)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would greatly appreciate it if these helper functions had mathematical definitions with them.

In the case of decreasing map, f is decreasing if when `x < y, then f(y) < f(x)

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure, I can do that.

return ValueRanges.decreasing_map(x, operator.neg)
@classmethod
def div(cls, a, b):
return cls.truediv(a, b)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Once again, I'm not sure this is kosher because it is inconsistent with Inductor cpp codegen

    @staticmethod
    def div(a, b):
        return f"{a} / {b}"

from codegen.cpp

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note that this change was not introduced in this PR, but in a previous one. The relevant discussion is in #100547 (comment)

x = ValueRanges.wrap(x)
if x.lower < 0:
return ValueRanges.unknown()
return ValueRanges.increasing_map(x, sympy.sqrt)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Which of these changed, which are the same?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, the diff is just terrible. Let me split the "moving things around" and the "improve things" into a few PRs

The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10 ipiszy ngimel yf225

[ghstack-poisoned]
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

cc voznesenskym penguinwu EikanWang jgong5 Guobing-Chen XiaobingSuper zhuhaozhe blzheng Xia-Weiwen wenzhe-nrv jiayisunx peterbell10 ipiszy ngimel yf225

[ghstack-poisoned]
@lezcano
Copy link
Collaborator Author

lezcano commented Jul 3, 2023

split into #104556 #104557 #104559

@lezcano lezcano closed this Jul 3, 2023
vkallesh pushed a commit to amd/ZenDNN-pytorch that referenced this pull request Jul 5, 2023
The analysis for SymPy expressions was incorrect as, even though it said
that the assumption was "smoothness" the assumtion was, in fact, that he
formula was monotone in every variable. In other words, it was
assuming that the derivative does not change signs in any variable (!!).

These issues showed up when using this analysis on a larger set of
formulas, where we would get bounds where lower > upper when using
ModularIndexing.

This PR extends the bounds analysis to SymPy expressions. It also
separates the symbols occuring on SymPy expressions into their own
class, as we don't want to use any fallback in this case.

ghstack-source-id: ac14eedada2039f7753251092c0e7a70765ed4ab
Pull Request resolved: pytorch/pytorch#102722
@facebook-github-bot facebook-github-bot deleted the gh/Lezcano/199/head branch August 3, 2023 14:16
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
ciflow/inductor module: inductor open source release notes: inductor suppress-bc-linter Suppresses the failures of API backward-compatibility linter (Lint/bc_linter) with-ssh
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants