Skip to content

optimize state machine inside loop into computed goto #2162

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

Closed
andrewrk opened this issue Apr 1, 2019 · 7 comments
Closed

optimize state machine inside loop into computed goto #2162

andrewrk opened this issue Apr 1, 2019 · 7 comments
Labels
contributor friendly This issue is limited in scope and/or knowledge of Zig internals. optimization upstream An issue with a third party project that Zig uses.
Milestone

Comments

@andrewrk
Copy link
Member

andrewrk commented Apr 1, 2019

Related issues:

One remaining use case for computed goto is performance. This pattern:

const State = enum {
    one,
    two,
};
while (true) {
    switch (state) {
        .one => {
            state = .two;
        },
        .two => {
            // ...
        },
    }
}

Here the code relies on setting the state variable and a loop iteration. In C the code could directly goto another switch label. In Zig this is not available, and the code generated is worse than in C due to the optimizer's inability to detect this pattern.

Upstream bug, reported by @shawnl: https://bugs.llvm.org/show_bug.cgi?id=39043

Potential solutions include:

  • (ideal) send upstream patch to LLVM making it able to detect this pattern and optimize it. It seems reasonable that this should work, given that both gcc and icc are able to do it.
  • make zig detect this pattern and emit different LLVM IR

I don't consider this to be blocking a 1.0.0 release.

@andrewrk andrewrk added contributor friendly This issue is limited in scope and/or knowledge of Zig internals. optimization upstream An issue with a third party project that Zig uses. labels Apr 1, 2019
@andrewrk andrewrk added this to the 1.1.0 milestone Apr 1, 2019
@PavelVozenilek
Copy link

Performance of computed goto highly depends on processor and the task. It is not always faster then the ordinary switch.

Perhaps the compiler should be given a hint in form of designated tests. Depending on timing of these tests, it would then pick up the best performing implementation.

This topic gets sometimes discussed on Forth forums, they found that the old truths are not absolute, as they once were.

@shawnl
Copy link
Contributor

shawnl commented Apr 2, 2019

@PavelVozenilek
There are times where a state only leads to an error condition, or to the next state, however, and clang is incapable of in-lining these cases.

@andrewrk
Copy link
Member Author

andrewrk commented Apr 2, 2019

Perhaps the compiler should be given a hint in form of designated tests. Depending on timing of these tests, it would then pick up the best performing implementation.

Profile guided optimization is #237

@tgschultz
Copy link
Contributor

I personally am not a fan of having to rely on the optimizer to do the right thing, and then trying to fool it into doing the right thing when it doesn't. While allowing the compiler to make this optimization is a good idea, I feel that that is not sufficient to cover the computed goto use case and some explicit mechanism should still be available.

@PavelVozenilek
Copy link

@shawnl: as I understand it, computed goto performance advantage depends on ability of the processor to predict which code path would be executed next (and start speculative execution of this path in advance). With one big switch such prediction is not feasible.

In Forth interpreter code paths are few and short, and common patterns of code are frequent. The processor prediction could then make a big difference.

I do not see how inlining could play a role here, but could be easily wrong.

@shawnl
Copy link
Contributor

shawnl commented Jun 20, 2020

A good benchmark for this issue would be a re2c lexer.

@andrewrk
Copy link
Member Author

andrewrk commented Oct 1, 2023

Closing in favor of #8220

@andrewrk andrewrk closed this as not planned Won't fix, can't repro, duplicate, stale Oct 1, 2023
@andrewrk andrewrk modified the milestones: 1.1.0, 0.12.0 Oct 13, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
contributor friendly This issue is limited in scope and/or knowledge of Zig internals. optimization upstream An issue with a third party project that Zig uses.
Projects
None yet
Development

No branches or pull requests

4 participants