158 lines
4.3 KiB
Go
158 lines
4.3 KiB
Go
package tsc
|
|
|
|
import (
|
|
"fmt"
|
|
"io"
|
|
"runtime"
|
|
"strconv"
|
|
"time"
|
|
|
|
"efprojects.com/kitten-ipc/kitcom/internal/tsgo/compiler"
|
|
)
|
|
|
|
type tableRow struct {
|
|
name string
|
|
value string
|
|
}
|
|
|
|
type table struct {
|
|
rows []tableRow
|
|
}
|
|
|
|
func (t *table) add(name string, value any) {
|
|
if d, ok := value.(time.Duration); ok {
|
|
value = formatDuration(d)
|
|
}
|
|
t.rows = append(t.rows, tableRow{name, fmt.Sprint(value)})
|
|
}
|
|
|
|
func (t *table) print(w io.Writer) {
|
|
nameWidth := 0
|
|
valueWidth := 0
|
|
for _, r := range t.rows {
|
|
nameWidth = max(nameWidth, len(r.name))
|
|
valueWidth = max(valueWidth, len(r.value))
|
|
}
|
|
|
|
for _, r := range t.rows {
|
|
fmt.Fprintf(w, "%-*s %*s\n", nameWidth+1, r.name+":", valueWidth, r.value)
|
|
}
|
|
}
|
|
|
|
func formatDuration(d time.Duration) string {
|
|
return fmt.Sprintf("%.3fs", d.Seconds())
|
|
}
|
|
|
|
func identifierCount(p *compiler.Program) int {
|
|
count := 0
|
|
for _, file := range p.SourceFiles() {
|
|
count += file.IdentifierCount
|
|
}
|
|
return count
|
|
}
|
|
|
|
type Statistics struct {
|
|
isAggregate bool
|
|
Projects int
|
|
ProjectsBuilt int
|
|
TimestampUpdates int
|
|
files int
|
|
lines int
|
|
identifiers int
|
|
symbols int
|
|
types int
|
|
instantiations int
|
|
memoryUsed uint64
|
|
memoryAllocs uint64
|
|
compileTimes *CompileTimes
|
|
}
|
|
|
|
func statisticsFromProgram(input EmitInput, memStats *runtime.MemStats) *Statistics {
|
|
return &Statistics{
|
|
files: len(input.Program.SourceFiles()),
|
|
lines: input.Program.LineCount(),
|
|
identifiers: input.Program.IdentifierCount(),
|
|
symbols: input.Program.SymbolCount(),
|
|
types: input.Program.TypeCount(),
|
|
instantiations: input.Program.InstantiationCount(),
|
|
memoryUsed: memStats.Alloc,
|
|
memoryAllocs: memStats.Mallocs,
|
|
compileTimes: input.CompileTimes,
|
|
}
|
|
}
|
|
|
|
func (s *Statistics) Report(w io.Writer, testing CommandLineTesting) {
|
|
if testing != nil {
|
|
testing.OnStatisticsStart(w)
|
|
defer testing.OnStatisticsEnd(w)
|
|
}
|
|
var table table
|
|
var prefix string
|
|
|
|
if s.isAggregate {
|
|
prefix = "Aggregate "
|
|
table.add("Projects in scope", s.Projects)
|
|
table.add("Projects built", s.ProjectsBuilt)
|
|
table.add("Timestamps only updates", s.TimestampUpdates)
|
|
}
|
|
table.add(prefix+"Files", s.files)
|
|
table.add(prefix+"Lines", s.lines)
|
|
table.add(prefix+"Identifiers", s.identifiers)
|
|
table.add(prefix+"Symbols", s.symbols)
|
|
table.add(prefix+"Types", s.types)
|
|
table.add(prefix+"Instantiations", s.instantiations)
|
|
table.add(prefix+"Memory used", fmt.Sprintf("%vK", s.memoryUsed/1024))
|
|
table.add(prefix+"Memory allocs", strconv.FormatUint(s.memoryAllocs, 10))
|
|
if s.compileTimes.ConfigTime != 0 {
|
|
table.add(prefix+"Config time", s.compileTimes.ConfigTime)
|
|
}
|
|
if s.compileTimes.BuildInfoReadTime != 0 {
|
|
table.add(prefix+"BuildInfo read time", s.compileTimes.BuildInfoReadTime)
|
|
}
|
|
table.add(prefix+"Parse time", s.compileTimes.ParseTime)
|
|
if s.compileTimes.bindTime != 0 {
|
|
table.add(prefix+"Bind time", s.compileTimes.bindTime)
|
|
}
|
|
if s.compileTimes.checkTime != 0 {
|
|
table.add(prefix+"Check time", s.compileTimes.checkTime)
|
|
}
|
|
if s.compileTimes.emitTime != 0 {
|
|
table.add(prefix+"Emit time", s.compileTimes.emitTime)
|
|
}
|
|
if s.compileTimes.ChangesComputeTime != 0 {
|
|
table.add(prefix+"Changes compute time", s.compileTimes.ChangesComputeTime)
|
|
}
|
|
table.add(prefix+"Total time", s.compileTimes.totalTime)
|
|
table.print(w)
|
|
}
|
|
|
|
func (s *Statistics) Aggregate(stat *Statistics) {
|
|
s.isAggregate = true
|
|
if s.compileTimes == nil {
|
|
s.compileTimes = &CompileTimes{}
|
|
}
|
|
// Aggregate statistics
|
|
s.files += stat.files
|
|
s.lines += stat.lines
|
|
s.identifiers += stat.identifiers
|
|
s.symbols += stat.symbols
|
|
s.types += stat.types
|
|
s.instantiations += stat.instantiations
|
|
s.memoryUsed += stat.memoryUsed
|
|
s.memoryAllocs += stat.memoryAllocs
|
|
s.compileTimes.ConfigTime += stat.compileTimes.ConfigTime
|
|
s.compileTimes.BuildInfoReadTime += stat.compileTimes.BuildInfoReadTime
|
|
s.compileTimes.ParseTime += stat.compileTimes.ParseTime
|
|
s.compileTimes.bindTime += stat.compileTimes.bindTime
|
|
s.compileTimes.checkTime += stat.compileTimes.checkTime
|
|
s.compileTimes.emitTime += stat.compileTimes.emitTime
|
|
s.compileTimes.ChangesComputeTime += stat.compileTimes.ChangesComputeTime
|
|
}
|
|
|
|
func (s *Statistics) SetTotalTime(totalTime time.Duration) {
|
|
if s.compileTimes == nil {
|
|
s.compileTimes = &CompileTimes{}
|
|
}
|
|
s.compileTimes.totalTime = totalTime
|
|
}
|