From 8cfe93ab2aa5f7cf8020f3bba9cce5ab92135b58 Mon Sep 17 00:00:00 2001 From: Yichao Yu Date: Thu, 8 Sep 2016 14:09:47 -0400 Subject: [PATCH] Missing boundscheck in `meta_elim_pass!` Fix #18412 --- base/inference.jl | 11 +++++++---- test/core.jl | 6 ++++++ 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/base/inference.jl b/base/inference.jl index 73066fa593f51..8ca4ffa4aa530 100644 --- a/base/inference.jl +++ b/base/inference.jl @@ -3279,7 +3279,7 @@ function meta_elim_pass!(linfo::LambdaInfo, code::Array{Any,1}) # The clearing needs to be propagated up during pop # This is not pushed to if the push is already eliminated # Also shared for `Expr(:boundscheck)` and `Expr(:inbounds)` - bounds_push_pos_stack = [0] + bounds_push_pos_stack = [0] # always non-empty # Number of boundscheck pushes in a eliminated boundscheck block void_boundscheck_depth = 0 is_inbounds = check_bounds == 2 @@ -3287,9 +3287,9 @@ function meta_elim_pass!(linfo::LambdaInfo, code::Array{Any,1}) # Position of the last line number node without any non-meta expressions # in between. - prev_dbg_stack = [0] + prev_dbg_stack = [0] # always non-empty # Whether there's any non-meta exprs after the enclosing `push_loc` - push_loc_pos_stack = [0] + push_loc_pos_stack = [0] # always non-empty for i in 1:length(code) ex = code[i] @@ -3330,6 +3330,7 @@ function meta_elim_pass!(linfo::LambdaInfo, code::Array{Any,1}) if !(args[1] === :pop) void_boundscheck_depth += 1 elseif void_boundscheck_depth == 0 + # There must have been a push pop!(bounds_elim_stack) enabled = true else @@ -3379,7 +3380,7 @@ function meta_elim_pass!(linfo::LambdaInfo, code::Array{Any,1}) end arg1 = args[1] if arg1 === true - if inbounds_stack[end] + if !isempty(inbounds_stack) && inbounds_stack[end] code[i] = nothing push!(bounds_elim_stack, true) else @@ -3390,6 +3391,8 @@ function meta_elim_pass!(linfo::LambdaInfo, code::Array{Any,1}) push!(inbounds_stack, true) elseif arg1 === false if is_inbounds + # There must have been a `true` on the stack so + # `inbounds_stack` must not be empty if !inbounds_stack[end] is_inbounds = false end diff --git a/test/core.jl b/test/core.jl index a997a37ba4e3c..a5500c46693e3 100644 --- a/test/core.jl +++ b/test/core.jl @@ -4555,6 +4555,12 @@ end # variable name in the error is tested above in `TestSSA16244` @test_throws UndefVarError f18386(1, 2, true) +Base.@propagate_inbounds function f18412(a) + @inbounds b = a[1] + return b +end +@test f18412([1]) == 1 + # issue #18173 function f18173() identity(()->successflag)