Source file test/fixedbugs/issue32477.go

     1  // run
     2  
     3  // Copyright 2019 The Go Authors. All rights reserved.
     4  // Use of this source code is governed by a BSD-style
     5  // license that can be found in the LICENSE file.
     6  
     7  // Make sure we use the deferreturn live map instead of
     8  // the entry live map when handling a segv in a function
     9  // that defers.
    10  
    11  package main
    12  
    13  import "runtime"
    14  
    15  var finalized bool
    16  var err string
    17  
    18  type HeapObj [8]int64
    19  
    20  const filler int64 = 0x123456789abcdef0
    21  
    22  func (h *HeapObj) init() {
    23  	for i := 0; i < len(*h); i++ {
    24  		h[i] = filler
    25  	}
    26  }
    27  func (h *HeapObj) check() {
    28  	for i := 0; i < len(*h); i++ {
    29  		if h[i] != filler {
    30  			err = "filler overwritten"
    31  		}
    32  	}
    33  }
    34  
    35  func gc(shouldFinalize bool) {
    36  	runtime.GC()
    37  	runtime.GC()
    38  	runtime.GC()
    39  	if shouldFinalize != finalized {
    40  		err = "heap object finalized at the wrong time"
    41  	}
    42  }
    43  
    44  func main() {
    45  	h := new(HeapObj)
    46  	h.init()
    47  	runtime.SetFinalizer(h, func(h *HeapObj) {
    48  		finalized = true
    49  	})
    50  
    51  	gc(false)
    52  	g(h)
    53  	if err != "" {
    54  		panic(err)
    55  	}
    56  }
    57  
    58  func g(h *HeapObj) {
    59  	gc(false)
    60  	h.check()
    61  	// h is now unused
    62  	defer func() {
    63  		// h should not be live here. Previously we used to
    64  		// use the function entry point as the place to get
    65  		// the live map when handling a segv.
    66  		gc(true)
    67  		recover()
    68  	}()
    69  	*(*int)(nil) = 0 // trigger a segv
    70  	return
    71  }
    72  

View as plain text