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

inference: improve inference of indexing into union of tuples #39296

Closed
wants to merge 1 commit into from

Conversation

aviatesk
Copy link
Member

@aviatesk aviatesk commented Jan 17, 2021

The precision of return type of tuple indexing really relies on constant
propagation, but when an argument is union of tuples, call signature
will be split and constant prop' won't happen, and so inference ends up
looser return type: e.g.

julia> Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first
Union{Missing, Nothing, Int64}

This PR special cases some of tuple indexing methods
(getindex(::Tuple) and indexed_iterate(::Tuple)) and forces constant
propagation to happen even when their argument is union of tuples,
by converting it to tuple of unions.


The diff certainly looks a bit odd; is there a better way to address this ?

@bramtayl
Copy link
Contributor

bramtayl commented Jan 17, 2021

Is there a way to fix this more generally? For example, in cases like below:

julia> struct A{B, C}
            b::B
            c::C
        end

julia> Base.return_types(x -> x.b, Tuple{Union{A{Int, Nothing}, A{Int, Missing}}})
1-element Array{Any,1}:
 Union{Missing, Nothing, Int64}

The precision of return type of tuple indexing really relies on constant
propagation, but when an argument is union of tuples, call signature
will be split and constant prop' won't happen, and so inference ends up
looser return type: e.g.
```julia
julia> 
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first
Union{Missing, Nothing, Int64}
```

This PR special cases some of tuple indexing methods
(`getindex(::Tuple)` and `indexed_iterate(::Tuple)`) and forces constant
propagation to happen even when their argument is union of tuples,
by converting it to tuple of unions.
@aviatesk
Copy link
Member Author

Is there a way to fix this more generally?

We need to enable constant prop' for union split signatures to fix this in general.

@bramtayl
Copy link
Contributor

We need to enable constant prop' for union split signatures

Right, is that possible?

@aviatesk
Copy link
Member Author

yeah, later I'll make another PR doing that as an alternative for this PR (but its latency impact should be examined carefully)

aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 18, 2021
The precision of inference on certain functions really relies on
constant propagation, but currently constant prop' won't happen when
a call signature is union split and so sometimes inference ends up
looser return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first
Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for union signatures (with "non-Bottom"
results)
- adds special cases for some functions (see `force_constant_prop'`) so
  that we keep inferring on them even after the return type from
  non-constant analysis has grown to `Any`, since constant analysis can
  improve the result later on

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time

master (26a721b)
```bash
Sysimage built. Summary:
Total ───────  57.320450 seconds
Base: ───────  24.371516 seconds 42.518%
Stdlibs: ────  32.947400 seconds 57.4793%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1379/1379
Precompilation complete. Summary:
Total ─────── 101.325866 seconds
Generation ──  74.901320 seconds 73.9212%
Execution ───  26.424546 seconds 26.0788%
    LINK usr/lib/julia/sys.dylib
```

this PR
```bash
Sysimage built. Summary:
Total ───────  58.387562 seconds
Base: ───────  24.403206 seconds 41.7952%
Stdlibs: ────  33.982657 seconds 58.2019%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ───────  99.659102 seconds
Generation ──  73.983763 seconds 74.2368%
Execution ───  25.675339 seconds 25.7632%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot
master (26a721b)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

This PR is an alternative for JuliaLang#39296, closes JuliaLang#39296.
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 18, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first
Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for union signatures (with "non-Bottom"
results)
- adds special cases for some functions (see `force_constant_prop'`) so
  that we keep inferring on them even after the return type from
  non-constant analysis has grown to `Any`, since constant analysis can
  improve the result later on

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (26a721b)
```bash
Sysimage built. Summary:
Total ───────  57.320450 seconds
Base: ───────  24.371516 seconds 42.518%
Stdlibs: ────  32.947400 seconds 57.4793%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1379/1379
Precompilation complete. Summary:
Total ─────── 101.325866 seconds
Generation ──  74.901320 seconds 73.9212%
Execution ───  26.424546 seconds 26.0788%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Sysimage built. Summary:
Total ───────  58.387562 seconds
Base: ───────  24.403206 seconds 41.7952%
Stdlibs: ────  33.982657 seconds 58.2019%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ───────  99.659102 seconds
Generation ──  73.983763 seconds 74.2368%
Execution ───  25.675339 seconds 25.7632%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (26a721b)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

NOTE: this PR is an alternative for JuliaLang#39296
@aviatesk
Copy link
Member Author

yeah, later I'll make another PR doing that as an alternative for this PR (but its latency impact should be examined carefully)

Done: #39305

@aviatesk aviatesk added the compiler:inference Type inference label Jan 18, 2021
@bramtayl
Copy link
Contributor

Yay!

@aviatesk
Copy link
Member Author

Will be superceded by #39305

@aviatesk aviatesk closed this Jan 19, 2021
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 20, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate 
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 21, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 21, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 22, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 26, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 28, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 29, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 30, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Jan 31, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Feb 5, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Feb 6, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Feb 10, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Feb 13, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Feb 16, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Feb 17, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation

The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```

> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```

> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Feb 28, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Feb 28, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Mar 2, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Mar 3, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Mar 5, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Mar 6, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
aviatesk added a commit to aviatesk/julia that referenced this pull request Mar 10, 2021
The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
vtjnash pushed a commit that referenced this pull request Mar 10, 2021
…9305)

The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes #37610
- some part of this code was taken from #37637
- this PR is originally supposed to be alternative and more generalized
  version of #39296
ElOceanografo pushed a commit to ElOceanografo/julia that referenced this pull request May 4, 2021
…liaLang#39305)

The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
antoine-levitt pushed a commit to antoine-levitt/julia that referenced this pull request May 9, 2021
…liaLang#39305)

The inference precision of certain functions really relies on constant
propagation, but currently constant prop' won't happen when a call
signature is union split and so sometimes inference ends up looser
return type: e.g.
```julia
julia>
Base.return_types((Union{Tuple{Int,Nothing},Tuple{Int,Missing}},)) do t
           a, b = t
           a # I expected a::Int, but a::Union{Missing,Nothing,Int}
       end |> first Union{Missing, Nothing, Int64}
```

This PR:
- enables constant prop' for each union signatures, by calling
  `abstract_call_method_with_const_args` just after each
  `abstract_call_method`
- refactor `abstract_call_method_with_const_args` into two separate
  parts, 1.) heuristics to decide whether to do constant prop', 2.) try
  constant propagation
The added test cases will should showcase the cases where the
inference result could be improved by that.

---

I've not seen notable regression in latency with this PR.
Here is a sample benchmark of the impact of this PR on latency,
from which I guess this PR is acceptable ?

> build time: master (caeacef)
```bash
Sysimage built. Summary:
Total ───────  61.615938 seconds
Base: ───────  26.575732 seconds 43.1313%
Stdlibs: ────  35.038024 seconds 56.8652%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1378/1378
Precompilation complete. Summary:
Total ─────── 116.417013 seconds
Generation ──  81.077365 seconds 69.6439%
Execution ───  35.339648 seconds 30.3561%
    LINK usr/lib/julia/sys.dylib
```
> build time: this PR
```bash
Stdlibs total  ──── 34.077962 seconds
Sysimage built. Summary:
Total ───────  61.804573 seconds
Base: ───────  27.724077 seconds 44.8576%
Stdlibs: ────  34.077962 seconds 55.1383%
    JULIA usr/lib/julia/sys-o.a
Generating REPL precompile statements... 30/30
Executing precompile statements... 1362/1362
Precompilation complete. Summary:
Total ─────── 111.262672 seconds
Generation ──  83.535305 seconds 75.0794%
Execution ───  27.727367 seconds 24.9206%
    LINK usr/lib/julia/sys.dylib
```

> first time to plot: master (caeacef)
```julia
julia> using Plots; @time plot(rand(10,3))
  3.614168 seconds (5.47 M allocations: 324.564 MiB, 5.73% gc time,
53.02% compilation time)
```
> first time to plot: this PR
```julia
julia> using Plots; @time plot(rand(10,3))
  3.557919 seconds (5.53 M allocations: 328.812 MiB, 2.89% gc time,
51.94% compilation time)
```

---

- fixes JuliaLang#37610
- some part of this code was taken from JuliaLang#37637
- this PR is originally supposed to be alternative and more generalized
  version of JuliaLang#39296
@aviatesk aviatesk deleted the uniontuple branch February 9, 2022 22:23
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
compiler:inference Type inference
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants