Source file src/cmd/compile/internal/gc/util.go

     1  // Copyright 2015 The Go Authors. All rights reserved.
     2  // Use of this source code is governed by a BSD-style
     3  // license that can be found in the LICENSE file.
     4  
     5  package gc
     6  
     7  import (
     8  	"os"
     9  	"runtime"
    10  	"runtime/pprof"
    11  
    12  	"cmd/compile/internal/base"
    13  )
    14  
    15  var traceHandler func(string)
    16  
    17  func startProfile() {
    18  	if base.Flag.CPUProfile != "" {
    19  		f, err := os.Create(base.Flag.CPUProfile)
    20  		if err != nil {
    21  			base.Fatalf("%v", err)
    22  		}
    23  		if err := pprof.StartCPUProfile(f); err != nil {
    24  			base.Fatalf("%v", err)
    25  		}
    26  		base.AtExit(pprof.StopCPUProfile)
    27  	}
    28  	if base.Flag.MemProfile != "" {
    29  		if base.Flag.MemProfileRate != 0 {
    30  			runtime.MemProfileRate = base.Flag.MemProfileRate
    31  		}
    32  		f, err := os.Create(base.Flag.MemProfile)
    33  		if err != nil {
    34  			base.Fatalf("%v", err)
    35  		}
    36  		base.AtExit(func() {
    37  			// Profile all outstanding allocations.
    38  			runtime.GC()
    39  			// compilebench parses the memory profile to extract memstats,
    40  			// which are only written in the legacy pprof format.
    41  			// See golang.org/issue/18641 and runtime/pprof/pprof.go:writeHeap.
    42  			const writeLegacyFormat = 1
    43  			if err := pprof.Lookup("heap").WriteTo(f, writeLegacyFormat); err != nil {
    44  				base.Fatalf("%v", err)
    45  			}
    46  		})
    47  	} else {
    48  		// Not doing memory profiling; disable it entirely.
    49  		runtime.MemProfileRate = 0
    50  	}
    51  	if base.Flag.BlockProfile != "" {
    52  		f, err := os.Create(base.Flag.BlockProfile)
    53  		if err != nil {
    54  			base.Fatalf("%v", err)
    55  		}
    56  		runtime.SetBlockProfileRate(1)
    57  		base.AtExit(func() {
    58  			pprof.Lookup("block").WriteTo(f, 0)
    59  			f.Close()
    60  		})
    61  	}
    62  	if base.Flag.MutexProfile != "" {
    63  		f, err := os.Create(base.Flag.MutexProfile)
    64  		if err != nil {
    65  			base.Fatalf("%v", err)
    66  		}
    67  		startMutexProfiling()
    68  		base.AtExit(func() {
    69  			pprof.Lookup("mutex").WriteTo(f, 0)
    70  			f.Close()
    71  		})
    72  	}
    73  	if base.Flag.TraceProfile != "" && traceHandler != nil {
    74  		traceHandler(base.Flag.TraceProfile)
    75  	}
    76  }
    77  

View as plain text