Source file test/fixedbugs/issue59680.go

     1  // run
     2  
     3  // Copyright 2023 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  package main
     8  
     9  import (
    10  	"sync"
    11  	"time"
    12  )
    13  
    14  type B struct {
    15  	pid int
    16  	f   func() (uint64, error)
    17  	wg  sync.WaitGroup
    18  	v   uint64
    19  }
    20  
    21  func newB(pid int) *B {
    22  	return &B{
    23  		pid: pid,
    24  	}
    25  }
    26  
    27  //go:noinline
    28  func Sq(i int) uint64 {
    29  	S++
    30  	return uint64(i * i)
    31  }
    32  
    33  type RO func(*B)
    34  
    35  var ROSL = []RO{
    36  	Bad(),
    37  }
    38  
    39  func Bad() RO {
    40  	return func(b *B) {
    41  		b.f = func() (uint64, error) {
    42  			return Sq(b.pid), nil
    43  		}
    44  	}
    45  }
    46  
    47  func (b *B) startit() chan<- struct{} {
    48  	stop := make(chan struct{})
    49  	b.wg.Add(1)
    50  	go func() {
    51  		defer b.wg.Done()
    52  		var v uint64
    53  		for {
    54  			select {
    55  			case <-stop:
    56  				b.v = v
    57  				return
    58  			case <-time.After(1 * time.Millisecond):
    59  				r, err := b.f()
    60  				if err != nil {
    61  					panic("bad")
    62  				}
    63  				v = r
    64  			}
    65  		}
    66  	}()
    67  	return stop
    68  }
    69  
    70  var S, G int
    71  
    72  //go:noinline
    73  func rec(x int) int {
    74  	if x == 0 {
    75  		return 9
    76  	}
    77  	return rec(x-1) + 1
    78  }
    79  
    80  //go:noinline
    81  func recur(x int) {
    82  	for i := 0; i < x; i++ {
    83  		G = rec(i)
    84  	}
    85  }
    86  
    87  func main() {
    88  	b := newB(17)
    89  	for _, opt := range ROSL {
    90  		opt(b)
    91  	}
    92  	stop := b.startit()
    93  
    94  	// see if we can get some stack growth/moving
    95  	recur(10101)
    96  
    97  	if stop != nil {
    98  		stop <- struct{}{}
    99  	}
   100  }
   101  

View as plain text