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

bug in MaybeUndef handling pass for PhiC #29152

Open
vtjnash opened this issue Sep 12, 2018 · 3 comments
Open

bug in MaybeUndef handling pass for PhiC #29152

vtjnash opened this issue Sep 12, 2018 · 3 comments
Assignees
Labels
bug Indicates an unexpected problem or unintended behavior compiler:optimizer Optimization passes (mostly in base/compiler/ssair/)

Comments

@vtjnash
Copy link
Member

vtjnash commented Sep 12, 2018

julia> function f()
         try
           g()
         finally
         end
       end
       g() = (_true ? error() : _true ? 0 : false)
       _true = true;

julia> f()
Unreachable reached at 0x7f230c0f6e20

signal (4): Illegal instruction
in expression starting at no file:0
f at ./REPL[1]:3

It looks like we might be trying to look at the type of value before noticing that it is undef. The Julia IR seems OK, so I think the issue is probably with the order of events we're emitting in codegen.

julia> @code_typed f()
CodeInfo(
     @ REPL[1]:2 within `f'
1 ──       $(Expr(:enter, #9))
2 ── %2  = ϒ (false)::Bool
%3  = ϒ (#undef)::MaybeUndef(Union{})
│    @ REPL[1]:3 within `f'
│   ┌ @ REPL[1]:7 within `g'
└───│       goto #4 if not Main._true
3 ──│       invoke Main.error()::Union{}
└───│       $(Expr(:unreachable))::Union{}
4 ┄─│       goto #6 if not Main._true
5 ──│       goto #7
6 ──│       goto #7

7 ┄─ %10 = φ (#5 => 0, #6 => false)::Union{Bool, Int64}
│    %11 = ϒ (true)::Bool
│    %12 = ϒ (%10)::Union{Bool, Int64}
└───       $(Expr(:leave, 1))
8 ──       goto #11
9 ┄─ %15 = φᶜ (%2, %11)::Bool
│    %16 = φᶜ (%3, %12)::MaybeUndef(Union{Bool, Int64})
└───       $(Expr(:leave, 1))
10 ─ %18 = $(Expr(:the_exception))::Any
     @ REPL[1]:5 within `f'
11%19 = φ (#8 => false, #10 => true)::Bool
%20 = φ (#8 => false, #10 => true)::Bool
%21 = φ (#8 => #undef, #10 => %18)::MaybeUndef(Any)
%22 = φ (#8 => true, #10 => %15)::Bool
%23 = φ (#8 => %10, #10 => %16)::MaybeUndef(Union{Bool, Int64})
└───       goto #13 if not %19
12$(Expr(:throw_undef_if_not, Symbol("#temp#"), :(%20)))::Any
$(Expr(:foreigncall, :(:jl_rethrow_other), Union{}, svec(Any), :(:ccall), 1, :(%21)))::Union{}
└───       $(Expr(:unreachable))::Union{}
13$(Expr(:throw_undef_if_not, Symbol("#temp#"), :(%22)))::Any
└───       return %23
) => Union{Bool, Int64}

julia> code_llvm(f, (), optimize=false, raw=true)
;  @ REPL[1]:2 within `f'
; Function Attrs: sspstrong
define { %jl_value_t addrspace(10)*, i8 } @julia_f_-1320222489([8 x i8]* noalias nocapture align 8 dereferenceable(8)) #0 !dbg !5 {
top:
  %phic1 = alloca [8 x i8], align 8
  %1 = alloca i8
  %2 = alloca [8 x i8], align 8
  %3 = alloca [8 x i8], align 8
  %4 = alloca [8 x i8], align 8
  %5 = alloca [8 x i8], align 8
  %6 = alloca i8
  %7 = alloca [8 x i8], align 8
  %8 = call %jl_value_t*** @julia.ptls_states()
  %9 = bitcast %jl_value_t*** %8 to %jl_value_t addrspace(10)**
  %10 = getelementptr inbounds %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %9, i64 3
  %11 = bitcast %jl_value_t addrspace(10)** %10 to i64**
  %12 = load i64*, i64** %11, !tbaa !14, !invariant.load !4
  %phic = alloca i8
  br label %L1

L1:                                               ; preds = %top
  %13 = call i32 @julia.except_enter() #2, !dbg !17
  %14 = icmp eq i32 %13, 0, !dbg !17
  br i1 %14, label %try, label %L15, !dbg !17

L2:                                               ; preds = %try
  store volatile i8 0, i8* %phic, !dbg !17, !tbaa !18
;  @ REPL[1]:3 within `f'
; ┌ @ REPL[1]:7 within `g'
   %15 = load %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** getelementptr inbounds (%jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** inttoptr (i64 140078970203504 to %jl_value_t addrspace(10)**), i64 1), !dbg !20, !tbaa !24
   %16 = call %jl_value_t addrspace(10)* @julia.typeof(%jl_value_t addrspace(10)* %15), !dbg !20
   %17 = icmp eq %jl_value_t addrspace(10)* %16, addrspacecast (%jl_value_t* inttoptr (i64 140078954810224 to %jl_value_t*) to %jl_value_t addrspace(10)*), !dbg !20
   br i1 %17, label %pass, label %fail, !dbg !20

L5:                                               ; preds = %pass
   %18 = call cc37 nonnull %jl_value_t addrspace(10)* bitcast (%jl_value_t addrspace(10)* (%jl_value_t addrspace(10)*, %jl_value_t addrspace(10)**, i32)* @japi1_error_-1320222516 to %jl_value_t addrspace(10)* (%jl_value_t addrspace(10)*)*)(%jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 140079083230080 to %jl_value_t*) to %jl_value_t addrspace(10)*)), !dbg !20
   call void @llvm.trap(), !dbg !20
   unreachable, !dbg !20

L7:                                               ; preds = %pass
   %19 = load %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** getelementptr inbounds (%jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** inttoptr (i64 140078970203504 to %jl_value_t addrspace(10)**), i64 1), !dbg !20, !tbaa !24
   %20 = call %jl_value_t addrspace(10)* @julia.typeof(%jl_value_t addrspace(10)* %19), !dbg !20
   %21 = icmp eq %jl_value_t addrspace(10)* %20, addrspacecast (%jl_value_t* inttoptr (i64 140078954810224 to %jl_value_t*) to %jl_value_t addrspace(10)*), !dbg !20
   br i1 %21, label %pass3, label %fail2, !dbg !20

L8:                                               ; preds = %pass3
   %22 = bitcast [8 x i8]* %2 to i8*, !dbg !20
   call void @llvm.lifetime.start.p0i8(i64 -1, i8* %22), !dbg !20
   %23 = bitcast [8 x i8]* %2 to i64*, !dbg !20
   store i64 0, i64* %23, !dbg !20
   br label %L10, !dbg !20

L9:                                               ; preds = %pass3
   %24 = bitcast [8 x i8]* %2 to i8*, !dbg !20
   call void @llvm.lifetime.start.p0i8(i64 -1, i8* %24), !dbg !20
   %25 = bitcast [8 x i8]* %2 to i8*, !dbg !20
   store i8 0, i8* %25, !dbg !20
   br label %L10, !dbg !20

L10:                                              ; preds = %L9, %L8
   %tindex_phi = phi i8 [ 2, %L8 ], [ 1, %L9 ]
   %ptr_phi = phi %jl_value_t addrspace(10)* [ null, %L8 ], [ null, %L9 ]
; ┘
  %26 = and i8 %tindex_phi, -128, !dbg !23
  %27 = icmp ne i8 %26, 0, !dbg !23
  %28 = bitcast [8 x i8]* %3 to i8*, !dbg !23
  %29 = bitcast [8 x i8]* %2 to i8*, !dbg !23
  call void @llvm.memcpy.p0i8.p0i8.i64(i8* %28, i8* %29, i64 8, i32 1, i1 false), !dbg !23
  %30 = bitcast [8 x i8]* %2 to i8*, !dbg !23
  call void @llvm.lifetime.end.p0i8(i64 -1, i8* %30), !dbg !23
  %31 = addrspacecast [8 x i8]* %3 to [8 x i8] addrspace(11)*, !dbg !23
  %32 = bitcast [8 x i8] addrspace(11)* %31 to i8 addrspace(11)*, !dbg !23
  %33 = addrspacecast %jl_value_t addrspace(10)* %ptr_phi to %jl_value_t addrspace(11)*, !dbg !23
  %34 = bitcast %jl_value_t addrspace(11)* %33 to i8 addrspace(11)*, !dbg !23
  %35 = select i1 %27, i8 addrspace(11)* %34, i8 addrspace(11)* %32, !dbg !23
  store volatile i8 1, i8* %phic, !dbg !23, !tbaa !18
  %36 = and i8 %tindex_phi, 127, !dbg !23
  store volatile i8 %36, i8* %1, !dbg !23
  store [8 x i8] undef, [8 x i8]* %phic1, !dbg !23
  %37 = and i8 %tindex_phi, 127, !dbg !23
  %38 = bitcast [8 x i8]* %phic1 to i8*, !dbg !23
  switch i8 %37, label %union_move_skip [
    i8 1, label %union_move
    i8 2, label %union_move4
  ], !dbg !23

L15:                                              ; preds = %L1
  %39 = load volatile i8, i8* %phic, !dbg !23
  store i8 %39, i8* %6, !dbg !23
  %40 = load volatile [8 x i8], [8 x i8]* %phic1, !dbg !23
  store [8 x i8] %40, [8 x i8]* %7, !dbg !23
  %41 = load volatile i8, i8* %1, !dbg !23
  call void @jl_pop_handler(i32 1), !dbg !23
  %42 = bitcast %jl_value_t*** %8 to %jl_value_t addrspace(10)**, !dbg !23
  %jl_exception_in_transit = getelementptr inbounds %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %42, i32 2, !dbg !23
  %43 = load volatile %jl_value_t addrspace(10)*, %jl_value_t addrspace(10)** %jl_exception_in_transit, !dbg !23
  %44 = load i8, i8* %6, !dbg !23, !tbaa !18, !range !27
  %45 = bitcast [8 x i8]* %4 to i8*, !dbg !23
  call void @llvm.lifetime.start.p0i8(i64 -1, i8* %45), !dbg !23
  store [8 x i8] undef, [8 x i8]* %4, !dbg !23
  %46 = and i8 %41, 127, !dbg !23
  %47 = bitcast [8 x i8]* %7 to i8*, !dbg !23
  %48 = bitcast [8 x i8]* %4 to i8*, !dbg !23
  switch i8 %46, label %union_move_skip21 [
    i8 1, label %union_move23
    i8 2, label %union_move24
  ], !dbg !23

L19:                                              ; preds = %post_union_move22, %post_union_move18
  %value_phi = phi i8 [ 0, %post_union_move18 ], [ 1, %post_union_move22 ]
  %value_phi5 = phi i8 [ 0, %post_union_move18 ], [ 1, %post_union_move22 ]
  %value_phi6 = phi %jl_value_t addrspace(10)* [ null, %post_union_move18 ], [ %43, %post_union_move22 ]
  %value_phi7 = phi i8 [ 1, %post_union_move18 ], [ %44, %post_union_move22 ]
  %tindex_phi8 = phi i8 [ %tindex_phi, %post_union_move18 ], [ %41, %post_union_move22 ]
  %ptr_phi9 = phi %jl_value_t addrspace(10)* [ %ptr_phi, %post_union_move18 ], [ null, %post_union_move22 ]
;  @ REPL[1]:5 within `f'
  %49 = and i8 %tindex_phi8, -128, !dbg !28
  %50 = icmp ne i8 %49, 0, !dbg !28
  %51 = bitcast [8 x i8]* %5 to i8*, !dbg !28
  %52 = bitcast [8 x i8]* %4 to i8*, !dbg !28
  call void @llvm.memcpy.p0i8.p0i8.i64(i8* %51, i8* %52, i64 8, i32 1, i1 false), !dbg !28
  %53 = bitcast [8 x i8]* %4 to i8*, !dbg !28
  call void @llvm.lifetime.end.p0i8(i64 -1, i8* %53), !dbg !28
  %54 = addrspacecast [8 x i8]* %5 to [8 x i8] addrspace(11)*, !dbg !28
  %55 = bitcast [8 x i8] addrspace(11)* %54 to i8 addrspace(11)*, !dbg !28
  %56 = addrspacecast %jl_value_t addrspace(10)* %ptr_phi9 to %jl_value_t addrspace(11)*, !dbg !28
  %57 = bitcast %jl_value_t addrspace(11)* %56 to i8 addrspace(11)*, !dbg !28
  %58 = select i1 %50, i8 addrspace(11)* %57, i8 addrspace(11)* %55, !dbg !28
  %59 = trunc i8 %value_phi to i1, !dbg !28
  %60 = xor i1 %59, true, !dbg !28
  br i1 %60, label %L28, label %L25, !dbg !28

L25:                                              ; preds = %L19
  %61 = trunc i8 %value_phi5 to i1, !dbg !28
  br i1 %61, label %ok, label %err, !dbg !28

L28:                                              ; preds = %L19
  %62 = trunc i8 %value_phi7 to i1, !dbg !28
  br i1 %62, label %ok12, label %err11, !dbg !28

try:                                              ; preds = %L1
;  @ REPL[1]:2 within `f'
  br label %L2, !dbg !17

fail:                                             ; preds = %L2
;  @ REPL[1]:3 within `f'
; ┌ @ REPL[1]:7 within `g'
   %63 = addrspacecast %jl_value_t addrspace(10)* %15 to %jl_value_t addrspace(12)*, !dbg !20
   call void @jl_type_error_rt(i8* inttoptr (i64 94024374789440 to i8*), i8* inttoptr (i64 94024373073152 to i8*), %jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 140078954810224 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(12)* %63), !dbg !20
   unreachable, !dbg !20

pass:                                             ; preds = %L2
   %64 = icmp eq %jl_value_t addrspace(10)* %15, addrspacecast (%jl_value_t* inttoptr (i64 140078952779280 to %jl_value_t*) to %jl_value_t addrspace(10)*), !dbg !20
   br i1 %64, label %L7, label %L5, !dbg !20

after_noret:                                      ; No predecessors!
   unreachable, !dbg !20

fail2:                                            ; preds = %L7
   %65 = addrspacecast %jl_value_t addrspace(10)* %19 to %jl_value_t addrspace(12)*, !dbg !20
   call void @jl_type_error_rt(i8* inttoptr (i64 94024374789440 to i8*), i8* inttoptr (i64 94024373073152 to i8*), %jl_value_t addrspace(10)* addrspacecast (%jl_value_t* inttoptr (i64 140078954810224 to %jl_value_t*) to %jl_value_t addrspace(10)*), %jl_value_t addrspace(12)* %65), !dbg !20
   unreachable, !dbg !20

pass3:                                            ; preds = %L7
   %66 = icmp eq %jl_value_t addrspace(10)* %19, addrspacecast (%jl_value_t* inttoptr (i64 140078952779280 to %jl_value_t*) to %jl_value_t addrspace(10)*), !dbg !20
   br i1 %66, label %L9, label %L8, !dbg !20

union_move_skip:                                  ; preds = %L10
; ┘
  br label %post_union_move, !dbg !23

post_union_move:                                  ; preds = %union_move_skip, %union_move4, %union_move
  call void @jl_pop_handler(i32 1), !dbg !23
  %67 = bitcast [8 x i8]* %4 to i8*, !dbg !23
  call void @llvm.lifetime.start.p0i8(i64 -1, i8* %67), !dbg !23
  %68 = and i8 %tindex_phi, -128, !dbg !23
  %69 = icmp ne i8 %68, 0, !dbg !23
  store [8 x i8] undef, [8 x i8]* %4, !dbg !23
  %70 = and i8 %tindex_phi, 127, !dbg !23
  %71 = select i1 %69, i8 0, i8 %70, !dbg !23
  %72 = bitcast [8 x i8]* %4 to i8*, !dbg !23
  switch i8 %71, label %union_move_skip17 [
    i8 1, label %union_move19
    i8 2, label %union_move20
  ], !dbg !23

union_move:                                       ; preds = %L10
  %73 = load volatile i8, i8 addrspace(11)* %35, align 1, !dbg !23, !tbaa !18
  store volatile i8 %73, i8* %38, align 1, !dbg !23, !tbaa !18
  br label %post_union_move, !dbg !23

union_move4:                                      ; preds = %L10
  call void @llvm.memcpy.p0i8.p11i8.i64(i8* %38, i8 addrspace(11)* %35, i64 8, i32 8, i1 true), !dbg !23, !tbaa !18
  br label %post_union_move, !dbg !23

err:                                              ; preds = %L25
;  @ REPL[1]:5 within `f'
  call void @jl_undefined_var_error(%jl_value_t addrspace(12)* addrspacecast (%jl_value_t* inttoptr (i64 140078952786872 to %jl_value_t*) to %jl_value_t addrspace(12)*)), !dbg !28
  unreachable, !dbg !28

ok:                                               ; preds = %L25
  call void inttoptr (i64 140079250202488 to void (%jl_value_t addrspace(10)*)*)(%jl_value_t addrspace(10)* %value_phi6) #4, !dbg !28
  call void @llvm.trap(), !dbg !28
  unreachable, !dbg !28

after_noret10:                                    ; No predecessors!
  unreachable, !dbg !28

err11:                                            ; preds = %L28
  call void @jl_undefined_var_error(%jl_value_t addrspace(12)* addrspacecast (%jl_value_t* inttoptr (i64 140078952786872 to %jl_value_t*) to %jl_value_t addrspace(12)*)), !dbg !28
  unreachable, !dbg !28

ok12:                                             ; preds = %L28
  %74 = and i8 %tindex_phi8, -128, !dbg !28
  %75 = icmp ne i8 %74, 0, !dbg !28
  %76 = select i1 %75, %jl_value_t addrspace(10)* %ptr_phi9, %jl_value_t addrspace(10)* addrspacecast (%jl_value_t* null to %jl_value_t addrspace(10)*), !dbg !28
  %77 = insertvalue { %jl_value_t addrspace(10)*, i8 } undef, %jl_value_t addrspace(10)* %76, 0, !dbg !28
  %78 = insertvalue { %jl_value_t addrspace(10)*, i8 } %77, i8 %tindex_phi8, 1, !dbg !28
  %79 = and i8 %tindex_phi8, 127, !dbg !28
  %80 = select i1 %75, i8 0, i8 %79, !dbg !28
  %81 = bitcast [8 x i8]* %0 to i8*, !dbg !28
  switch i8 %80, label %union_move_skip13 [
    i8 1, label %union_move15
    i8 2, label %union_move16
  ], !dbg !28

union_move_skip13:                                ; preds = %ok12
  br label %post_union_move14, !dbg !28

post_union_move14:                                ; preds = %union_move_skip13, %union_move16, %union_move15
  ret { %jl_value_t addrspace(10)*, i8 } %78, !dbg !28

union_move15:                                     ; preds = %ok12
  %82 = load i8, i8 addrspace(11)* %58, align 1, !dbg !28, !tbaa !18
  store i8 %82, i8* %81, align 1, !dbg !28
  br label %post_union_move14, !dbg !28

union_move16:                                     ; preds = %ok12
  call void @llvm.memcpy.p0i8.p11i8.i64(i8* %81, i8 addrspace(11)* %58, i64 8, i32 8, i1 false), !dbg !28
  br label %post_union_move14, !dbg !28

union_move_skip17:                                ; preds = %post_union_move
;  @ REPL[1]:3 within `f'
  br label %post_union_move18, !dbg !23

post_union_move18:                                ; preds = %union_move_skip17, %union_move20, %union_move19
  br label %L19, !dbg !23

union_move19:                                     ; preds = %post_union_move
  %83 = load i8, i8 addrspace(11)* %35, align 1, !dbg !23, !tbaa !18
  store i8 %83, i8* %72, align 1, !dbg !23, !tbaa !29
  br label %post_union_move18, !dbg !23

union_move20:                                     ; preds = %post_union_move
  call void @llvm.memcpy.p0i8.p11i8.i64(i8* %72, i8 addrspace(11)* %35, i64 8, i32 8, i1 false), !dbg !23
  br label %post_union_move18, !dbg !23

union_move_skip21:                                ; preds = %L15
  call void @llvm.trap(), !dbg !23
  unreachable, !dbg !23

post_union_move22:                                ; preds = %union_move24, %union_move23
  br label %L19, !dbg !23

union_move23:                                     ; preds = %L15
  %84 = load i8, i8* %47, align 1, !dbg !23, !tbaa !18
  store i8 %84, i8* %48, align 1, !dbg !23, !tbaa !29
  br label %post_union_move22, !dbg !23

union_move24:                                     ; preds = %L15
  call void @llvm.memcpy.p0i8.p0i8.i64(i8* %48, i8* %47, i64 8, i32 8, i1 false), !dbg !23
  br label %post_union_move22, !dbg !23
}
@Keno Keno self-assigned this Sep 12, 2018
Keno added a commit that referenced this issue Sep 12, 2018
While we're guaranteed never to look at undefined values,
we're not guaranteed that the type information can't change, which
in the case of a union generates code to change the layout.
As a result, we need to make sure to have the union selectors
be valid (the actual data will be junk and no semantic operation
will ever look at it, but it shouldn't be ouf of bounds).

Fixes #29152
Keno added a commit that referenced this issue Nov 30, 2018
While we're guaranteed never to look at undefined values,
we're not guaranteed that the type information can't change, which
in the case of a union generates code to change the layout.
As a result, we need to make sure to have the union selectors
be valid (the actual data will be junk and no semantic operation
will ever look at it, but it shouldn't be ouf of bounds).

Ref #29152
Keno added a commit that referenced this issue Dec 1, 2018
While we're guaranteed never to look at undefined values,
we're not guaranteed that the type information can't change, which
in the case of a union generates code to change the layout.
As a result, we need to make sure to have the union selectors
be valid (the actual data will be junk and no semantic operation
will ever look at it, but it shouldn't be ouf of bounds).

Ref #29152
@vtjnash
Copy link
Member Author

vtjnash commented Dec 2, 2018

Probably not fixed, although the referenced PR should mitigate this considerably.

@vtjnash vtjnash reopened this Dec 2, 2018
KristofferC pushed a commit that referenced this issue Dec 6, 2018
While we're guaranteed never to look at undefined values,
we're not guaranteed that the type information can't change, which
in the case of a union generates code to change the layout.
As a result, we need to make sure to have the union selectors
be valid (the actual data will be junk and no semantic operation
will ever look at it, but it shouldn't be ouf of bounds).

Ref #29152

(cherry picked from commit ecd7291)
KristofferC pushed a commit that referenced this issue Dec 12, 2018
While we're guaranteed never to look at undefined values,
we're not guaranteed that the type information can't change, which
in the case of a union generates code to change the layout.
As a result, we need to make sure to have the union selectors
be valid (the actual data will be junk and no semantic operation
will ever look at it, but it shouldn't be ouf of bounds).

Ref #29152

(cherry picked from commit ecd7291)
KristofferC pushed a commit that referenced this issue Feb 11, 2019
While we're guaranteed never to look at undefined values,
we're not guaranteed that the type information can't change, which
in the case of a union generates code to change the layout.
As a result, we need to make sure to have the union selectors
be valid (the actual data will be junk and no semantic operation
will ever look at it, but it shouldn't be ouf of bounds).

Ref #29152

(cherry picked from commit ecd7291)
@JeffBezanson JeffBezanson added bug Indicates an unexpected problem or unintended behavior compiler:optimizer Optimization passes (mostly in base/compiler/ssair/) labels Feb 23, 2019
KristofferC pushed a commit that referenced this issue Feb 20, 2020
While we're guaranteed never to look at undefined values,
we're not guaranteed that the type information can't change, which
in the case of a union generates code to change the layout.
As a result, we need to make sure to have the union selectors
be valid (the actual data will be junk and no semantic operation
will ever look at it, but it shouldn't be ouf of bounds).

Ref #29152

(cherry picked from commit ecd7291)
@Liozou
Copy link
Member

Liozou commented Apr 1, 2020

Same as #31133, I can't reproduce on master, should this be closed?

@vtjnash
Copy link
Member Author

vtjnash commented Apr 1, 2020

We handled the known cases, but think there may still an underlying problem here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Indicates an unexpected problem or unintended behavior compiler:optimizer Optimization passes (mostly in base/compiler/ssair/)
Projects
None yet
Development

No branches or pull requests

4 participants