github.com/ice-blockchain/go/src@v0.0.0-20240403114104-1564d284e521/internal/trace/v2/version/version.go (about) 1 // Copyright 2023 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 version 6 7 import ( 8 "fmt" 9 "io" 10 11 "internal/trace/v2/event" 12 "internal/trace/v2/event/go122" 13 ) 14 15 // Version represents the version of a trace file. 16 type Version uint32 17 18 const ( 19 Go111 Version = 11 20 Go119 Version = 19 21 Go121 Version = 21 22 Go122 Version = 22 23 Go123 Version = 23 24 Current = Go123 25 ) 26 27 var versions = map[Version][]event.Spec{ 28 // Go 1.11–1.21 use a different parser and are only set here for the sake of 29 // Version.Valid. 30 Go111: nil, 31 Go119: nil, 32 Go121: nil, 33 34 Go122: go122.Specs(), 35 // Go 1.23 adds backwards-incompatible events, but 36 // traces produced by Go 1.22 are also always valid 37 // Go 1.23 traces. 38 Go123: go122.Specs(), 39 } 40 41 // Specs returns the set of event.Specs for this version. 42 func (v Version) Specs() []event.Spec { 43 return versions[v] 44 } 45 46 func (v Version) Valid() bool { 47 _, ok := versions[v] 48 return ok 49 } 50 51 // headerFmt is the format of the header of all Go execution traces. 52 const headerFmt = "go 1.%d trace\x00\x00\x00" 53 54 // ReadHeader reads the version of the trace out of the trace file's 55 // header, whose prefix must be present in v. 56 func ReadHeader(r io.Reader) (Version, error) { 57 var v Version 58 _, err := fmt.Fscanf(r, headerFmt, &v) 59 if err != nil { 60 return v, fmt.Errorf("bad file format: not a Go execution trace?") 61 } 62 if !v.Valid() { 63 return v, fmt.Errorf("unknown or unsupported trace version go 1.%d", v) 64 } 65 return v, nil 66 } 67 68 // WriteHeader writes a header for a trace version v to w. 69 func WriteHeader(w io.Writer, v Version) (int, error) { 70 return fmt.Fprintf(w, headerFmt, v) 71 }