Source file src/cmd/compile/internal/stats/stats.go

     1  // Copyright 2026 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 stats provides a convenient way to collect compiler statistics.
     6  package stats
     7  
     8  import (
     9  	"fmt"
    10  	"log"
    11  	"sort"
    12  	"strings"
    13  )
    14  
    15  type Stats struct {
    16  	stats []*PrefixStats
    17  }
    18  
    19  func (s *Stats) Merge(other *Stats) {
    20  	if s == nil || other == nil {
    21  		return
    22  	}
    23  	allKeys := map[string]struct{}{}
    24  	for _, s := range s.stats {
    25  		allKeys[s.prefix] = struct{}{}
    26  	}
    27  	for _, s := range other.stats {
    28  		allKeys[s.prefix] = struct{}{}
    29  	}
    30  	newStats := []*PrefixStats{}
    31  	for k := range allKeys {
    32  		newS := &PrefixStats{prefix: k, stats: make(map[string]int64)}
    33  		for _, s1 := range s.stats {
    34  			if s1.prefix == k {
    35  				newS.Merge(s1)
    36  			}
    37  		}
    38  		for _, s2 := range other.stats {
    39  			if s2.prefix == k {
    40  				newS.Merge(s2)
    41  			}
    42  		}
    43  		newStats = append(newStats, newS)
    44  	}
    45  	s.stats = newStats
    46  }
    47  
    48  func (s *Stats) Print() {
    49  	if s == nil {
    50  		return
    51  	}
    52  	for _, s := range s.stats {
    53  		s.Print()
    54  	}
    55  }
    56  
    57  func (s *Stats) NewPrefixStat(p string) *PrefixStats {
    58  	if s == nil {
    59  		return nil
    60  	}
    61  	pstat := &PrefixStats{prefix: p, stats: make(map[string]int64)}
    62  	s.stats = append(s.stats, pstat)
    63  	return pstat
    64  }
    65  
    66  // Stats holds a collection of statistics.
    67  type PrefixStats struct {
    68  	prefix string
    69  	stats  map[string]int64
    70  }
    71  
    72  // Record records a value for a given statistic.
    73  func (s *PrefixStats) Record(name string, value int64) {
    74  	if s == nil {
    75  		return
    76  	}
    77  	s.stats[name] += value
    78  }
    79  
    80  // Merge merges another Stats object into this one.
    81  func (s *PrefixStats) Merge(other *PrefixStats) {
    82  	if s == nil || other == nil {
    83  		return
    84  	}
    85  	for name, value := range other.stats {
    86  		s.stats[name] += value
    87  	}
    88  }
    89  
    90  // Print prints the collected statistics to the console.
    91  func (s *PrefixStats) Print() {
    92  	if s == nil {
    93  		return
    94  	}
    95  	var names []string
    96  	for name := range s.stats {
    97  		names = append(names, name)
    98  	}
    99  	sort.Strings(names)
   100  
   101  	var b strings.Builder
   102  	fmt.Fprintln(&b, "Compiler statistics:")
   103  	for _, name := range names {
   104  		fmt.Fprintf(&b, "%s-%-30s: %d\n", s.prefix, name, s.stats[name])
   105  	}
   106  	log.Print(b.String())
   107  }
   108  

View as plain text