*: run go1.19 'go fmt' on everything and fix problems (#3031)
Go 1.19 also formats doc comments according to the new godoc syntax. Some of our comments, especially unexported symbols did not conform to the godoc syntax and therefore are mangled by 'go fmt'. This PR runs 'go fmt' from go1.19 on everything and manually fixes the problems. See also: https://github.com/golang/proposal/blob/master/design/51082-godocfmt.md
This commit is contained in:
parent
2827145f1e
commit
c412dcdc4f
@ -1,3 +1,4 @@
|
||||
//go:build ignore
|
||||
// +build ignore
|
||||
|
||||
package main
|
||||
|
@ -1,3 +1,4 @@
|
||||
//go:build ignore
|
||||
// +build ignore
|
||||
|
||||
package main
|
||||
|
@ -12,7 +12,7 @@ import (
|
||||
|
||||
// SplitQuotedFields is like strings.Fields but ignores spaces inside areas surrounded
|
||||
// by the specified quote character.
|
||||
// To specify a single quote use backslash to escape it: '\''
|
||||
// To specify a single quote use backslash to escape it: \'
|
||||
func SplitQuotedFields(in string, quote rune) []string {
|
||||
type stateEnum int
|
||||
const (
|
||||
|
@ -193,7 +193,9 @@ func max(a, b uint64) uint64 {
|
||||
}
|
||||
|
||||
// fuseRanges fuses rngs2 into rngs1, it's the equivalent of
|
||||
// normalizeRanges(append(rngs1, rngs2))
|
||||
//
|
||||
// normalizeRanges(append(rngs1, rngs2))
|
||||
//
|
||||
// but more efficient.
|
||||
func fuseRanges(rngs1, rngs2 [][2]uint64) [][2]uint64 {
|
||||
if rangesContains(rngs1, rngs2) {
|
||||
|
@ -535,7 +535,7 @@ func (t *UnsupportedType) stringIntl(recCheck) string {
|
||||
|
||||
func (t *UnsupportedType) String() string { return t.stringIntl(nil) }
|
||||
|
||||
// ReadType reads the type at off in the DWARF ``info'' section.
|
||||
// ReadType reads the type at off in the DWARF “info” section.
|
||||
func ReadType(d *dwarf.Data, index int, off dwarf.Offset, typeCache map[dwarf.Offset]Type) (Type, error) {
|
||||
typ, err := readType(d, "info", d.Reader(), off, typeCache, nil)
|
||||
if typ != nil {
|
||||
|
@ -3,13 +3,14 @@
|
||||
//
|
||||
// Location spec examples:
|
||||
//
|
||||
// locStr ::= <filename>:<line> | <function>[:<line>] | /<regex>/ | (+|-)<offset> | <line> | *<address>
|
||||
// * <filename> can be the full path of a file or just a suffix
|
||||
// * <function> ::= <package>.<receiver type>.<name> | <package>.(*<receiver type>).<name> | <receiver type>.<name> | <package>.<name> | (*<receiver type>).<name> | <name>
|
||||
// <function> must be unambiguous
|
||||
// * /<regex>/ will return a location for each function matched by regex
|
||||
// * +<offset> returns a location for the line that is <offset> lines after the current line
|
||||
// * -<offset> returns a location for the line that is <offset> lines before the current line
|
||||
// * <line> returns a location for a line in the current file
|
||||
// * *<address> returns the location corresponding to the specified address
|
||||
// locStr ::= <filename>:<line> | <function>[:<line>] | /<regex>/ | (+|-)<offset> | <line> | *<address>
|
||||
//
|
||||
// * <filename> can be the full path of a file or just a suffix
|
||||
// * <function> ::= <package>.<receiver type>.<name> | <package>.(*<receiver type>).<name> | <receiver type>.<name> | <package>.<name> | (*<receiver type>).<name> | <name>
|
||||
// <function> must be unambiguous
|
||||
// * /<regex>/ will return a location for each function matched by regex
|
||||
// * +<offset> returns a location for the line that is <offset> lines after the current line
|
||||
// * -<offset> returns a location for the line that is <offset> lines before the current line
|
||||
// * <line> returns a location for a line in the current file
|
||||
// * *<address> returns the location corresponding to the specified address
|
||||
package locspec
|
||||
|
@ -1337,7 +1337,7 @@ func loadBinaryInfoElf(bi *BinaryInfo, image *Image, path string, addr uint64, w
|
||||
return nil
|
||||
}
|
||||
|
||||
// _STT_FUNC is a code object, see /usr/include/elf.h for a full definition.
|
||||
// _STT_FUNC is a code object, see /usr/include/elf.h for a full definition.
|
||||
const _STT_FUNC = 2
|
||||
|
||||
func (bi *BinaryInfo) loadSymbolName(image *Image, file *elf.File, wg *sync.WaitGroup) {
|
||||
@ -1633,13 +1633,15 @@ func (bi *BinaryInfo) parseDebugFrameMacho(image *Image, exe *macho.File, debugI
|
||||
bi.parseDebugFrameGeneral(image, debugFrameBytes, "__debug_frame", debugFrameErr, ehFrameBytes, ehFrameAddr, "__eh_frame", frame.DwarfEndian(debugInfoBytes))
|
||||
}
|
||||
|
||||
// macOSDebugFrameBugWorkaround applies a workaround for:
|
||||
// https://github.com/golang/go/issues/25841
|
||||
// macOSDebugFrameBugWorkaround applies a workaround for [golang/go#25841]
|
||||
//
|
||||
// It finds the Go function with the lowest entry point and the first
|
||||
// debug_frame FDE, calculates the difference between the start of the
|
||||
// function and the start of the FDE and sums it to all debug_frame FDEs.
|
||||
// A number of additional checks are performed to make sure we don't ruin
|
||||
// executables unaffected by this bug.
|
||||
//
|
||||
// [golang/go#25841]: https://github.com/golang/go/issues/25841
|
||||
func (bi *BinaryInfo) macOSDebugFrameBugWorkaround() {
|
||||
//TODO: log extensively because of bugs in the field
|
||||
if bi.GOOS != "darwin" || bi.Arch.Name != "arm64" {
|
||||
@ -1967,9 +1969,9 @@ func (bi *BinaryInfo) loadDebugInfoMaps(image *Image, debugInfoBytes, debugLineB
|
||||
|
||||
// LookupGenericFunc returns a map that allows searching for instantiations of generic function by specificying a function name without type parameters.
|
||||
// For example the key "pkg.(*Receiver).Amethod" will find all instantiations of Amethod:
|
||||
// - pkg.(*Receiver[.shape.int]).Amethod"
|
||||
// - pkg.(*Receiver[.shape.*uint8]).Amethod"
|
||||
// - etc.
|
||||
// - pkg.(*Receiver[.shape.int]).Amethod
|
||||
// - pkg.(*Receiver[.shape.*uint8]).Amethod
|
||||
// - etc.
|
||||
func (bi *BinaryInfo) LookupGenericFunc() map[string][]*Function {
|
||||
if bi.lookupGenericFunc == nil {
|
||||
bi.lookupGenericFunc = make(map[string][]*Function)
|
||||
|
@ -21,10 +21,12 @@ var ErrNoThreads = errors.New("no threads found in core file")
|
||||
// 0x0000000000400000 0x000000000044f000 0x0000000000000000
|
||||
// but then it's partially overwritten with an RW mapping whose data is stored
|
||||
// in the core file:
|
||||
// Type Offset VirtAddr PhysAddr
|
||||
// FileSiz MemSiz Flags Align
|
||||
// LOAD 0x0000000000004000 0x000000000049a000 0x0000000000000000
|
||||
// 0x0000000000002000 0x0000000000002000 RW 1000
|
||||
//
|
||||
// Type Offset VirtAddr PhysAddr
|
||||
// FileSiz MemSiz Flags Align
|
||||
// LOAD 0x0000000000004000 0x000000000049a000 0x0000000000000000
|
||||
// 0x0000000000002000 0x0000000000002000 RW 1000
|
||||
//
|
||||
// This can be represented in a SplicedMemory by adding the original region,
|
||||
// then putting the RW mapping on top of it.
|
||||
type splicedMemory struct {
|
||||
|
@ -2,8 +2,8 @@
|
||||
// the process we are debugging.
|
||||
//
|
||||
// proc implements all core functionality including:
|
||||
// * creating / attaching to a process
|
||||
// * process manipulation (step, next, continue, halt)
|
||||
// * methods to explore the memory of the process
|
||||
//
|
||||
// - creating / attaching to a process
|
||||
// - process manipulation (step, next, continue, halt)
|
||||
// - methods to explore the memory of the process
|
||||
package proc
|
||||
|
@ -338,17 +338,17 @@ func afterLastArgAddr(vars []*Variable) uint64 {
|
||||
}
|
||||
|
||||
// setValue writes the value of srcv to dstv.
|
||||
// * If srcv is a numerical literal constant and srcv is of a compatible type
|
||||
// the necessary type conversion is performed.
|
||||
// * If srcv is nil and dstv is of a nil'able type then dstv is nilled.
|
||||
// * If srcv is the empty string and dstv is a string then dstv is set to the
|
||||
// empty string.
|
||||
// * If dstv is an "interface {}" and srcv is either an interface (possibly
|
||||
// non-empty) or a pointer shaped type (map, channel, pointer or struct
|
||||
// containing a single pointer field) the type conversion to "interface {}"
|
||||
// is performed.
|
||||
// * If srcv and dstv have the same type and are both addressable then the
|
||||
// contents of srcv are copied byte-by-byte into dstv
|
||||
// - If srcv is a numerical literal constant and srcv is of a compatible type
|
||||
// the necessary type conversion is performed.
|
||||
// - If srcv is nil and dstv is of a nil'able type then dstv is nilled.
|
||||
// - If srcv is the empty string and dstv is a string then dstv is set to the
|
||||
// empty string.
|
||||
// - If dstv is an "interface {}" and srcv is either an interface (possibly
|
||||
// non-empty) or a pointer shaped type (map, channel, pointer or struct
|
||||
// containing a single pointer field) the type conversion to "interface {}"
|
||||
// is performed.
|
||||
// - If srcv and dstv have the same type and are both addressable then the
|
||||
// contents of srcv are copied byte-by-byte into dstv
|
||||
func (scope *EvalScope) setValue(dstv, srcv *Variable, srcExpr string) error {
|
||||
srcv.loadValue(loadSingleValue)
|
||||
|
||||
|
@ -2,7 +2,6 @@ package gdbserial
|
||||
|
||||
import (
|
||||
"bufio"
|
||||
"bytes"
|
||||
"fmt"
|
||||
"io"
|
||||
"io/ioutil"
|
||||
@ -12,8 +11,8 @@ import (
|
||||
"strconv"
|
||||
"strings"
|
||||
"syscall"
|
||||
"unicode"
|
||||
|
||||
"github.com/go-delve/delve/pkg/config"
|
||||
"github.com/go-delve/delve/pkg/proc"
|
||||
)
|
||||
|
||||
@ -248,7 +247,7 @@ func (err *ErrMalformedRRGdbCommand) Error() string {
|
||||
|
||||
func rrParseGdbCommand(line string) rrInit {
|
||||
port := ""
|
||||
fields := splitQuotedFields(line)
|
||||
fields := config.SplitQuotedFields(line, '\'')
|
||||
for i := 0; i < len(fields); i++ {
|
||||
switch fields[i] {
|
||||
case "-ex":
|
||||
@ -279,63 +278,6 @@ func rrParseGdbCommand(line string) rrInit {
|
||||
return rrInit{port: port, exe: exe}
|
||||
}
|
||||
|
||||
// Like strings.Fields but ignores spaces inside areas surrounded
|
||||
// by single quotes.
|
||||
// To specify a single quote use backslash to escape it: '\''
|
||||
func splitQuotedFields(in string) []string {
|
||||
type stateEnum int
|
||||
const (
|
||||
inSpace stateEnum = iota
|
||||
inField
|
||||
inQuote
|
||||
inQuoteEscaped
|
||||
)
|
||||
state := inSpace
|
||||
r := []string{}
|
||||
var buf bytes.Buffer
|
||||
|
||||
for _, ch := range in {
|
||||
switch state {
|
||||
case inSpace:
|
||||
if ch == '\'' {
|
||||
state = inQuote
|
||||
} else if !unicode.IsSpace(ch) {
|
||||
buf.WriteRune(ch)
|
||||
state = inField
|
||||
}
|
||||
|
||||
case inField:
|
||||
if ch == '\'' {
|
||||
state = inQuote
|
||||
} else if unicode.IsSpace(ch) {
|
||||
r = append(r, buf.String())
|
||||
buf.Reset()
|
||||
} else {
|
||||
buf.WriteRune(ch)
|
||||
}
|
||||
|
||||
case inQuote:
|
||||
if ch == '\'' {
|
||||
state = inField
|
||||
} else if ch == '\\' {
|
||||
state = inQuoteEscaped
|
||||
} else {
|
||||
buf.WriteRune(ch)
|
||||
}
|
||||
|
||||
case inQuoteEscaped:
|
||||
buf.WriteRune(ch)
|
||||
state = inQuote
|
||||
}
|
||||
}
|
||||
|
||||
if buf.Len() != 0 {
|
||||
r = append(r, buf.String())
|
||||
}
|
||||
|
||||
return r
|
||||
}
|
||||
|
||||
// RecordAndReplay acts like calling Record and then Replay.
|
||||
func RecordAndReplay(cmd []string, wd string, quiet bool, debugInfoDirs []string, redirects [3]string) (*proc.Target, string, error) {
|
||||
tracedir, err := Record(cmd, wd, quiet, redirects)
|
||||
|
@ -47,12 +47,13 @@ func ptraceGetRegset(tid int) (regset amd64util.AMD64Xstate, err error) {
|
||||
// ptraceGetTls return the addr of tls by PTRACE_GET_THREAD_AREA for specify thread.
|
||||
// See http://man7.org/linux/man-pages/man2/ptrace.2.html for detail about PTRACE_GET_THREAD_AREA.
|
||||
// struct user_desc at https://golang.org/src/runtime/sys_linux_386.s
|
||||
// type UserDesc struct {
|
||||
// EntryNumber uint32
|
||||
// BaseAddr uint32
|
||||
// Limit uint32
|
||||
// Flag uint32
|
||||
// }
|
||||
//
|
||||
// type UserDesc struct {
|
||||
// EntryNumber uint32
|
||||
// BaseAddr uint32
|
||||
// Limit uint32
|
||||
// Flag uint32
|
||||
// }
|
||||
func ptraceGetTls(gs int32, tid int) (uint32, error) {
|
||||
ud := [4]uint32{}
|
||||
|
||||
|
@ -65,9 +65,10 @@ func (wpstate *watchpointState) set(idx uint8, addr, ctrl uint64) {
|
||||
// The format of this register set is described by user_hwdebug_state in
|
||||
// arch/arm64/include/uapi/asm/ptrace.h.
|
||||
// It consists of one 64bit word containing:
|
||||
// * 1byte number of watchpoints
|
||||
// * 1byte debug architecture version (the 4 least significant bits of ID_AA64DFR0_EL1)
|
||||
// * 6bytes padding
|
||||
// - 1byte number of watchpoints
|
||||
// - 1byte debug architecture version (the 4 least significant bits of ID_AA64DFR0_EL1)
|
||||
// - 6bytes padding
|
||||
//
|
||||
// Followed by 2 64bit words for each watchpoint, up to a maximum of 16
|
||||
// watchpoints. The first word contains the address at which the watchpoint
|
||||
// is set (DBGWVRn_EL1), the second word is the control register for the
|
||||
|
@ -42,26 +42,26 @@ func TestScopeWithEscapedVariable(t *testing.T) {
|
||||
}
|
||||
|
||||
// TestScope will:
|
||||
// - run _fixtures/scopetest.go
|
||||
// - set a breakpoint on all lines containing a comment
|
||||
// - continue until the program ends
|
||||
// - every time a breakpoint is hit it will check that
|
||||
// scope.FunctionArguments+scope.LocalVariables and scope.EvalExpression
|
||||
// return what the corresponding comment describes they should return and
|
||||
// removes the breakpoint.
|
||||
// - run _fixtures/scopetest.go
|
||||
// - set a breakpoint on all lines containing a comment
|
||||
// - continue until the program ends
|
||||
// - every time a breakpoint is hit it will check that
|
||||
// scope.FunctionArguments+scope.LocalVariables and scope.EvalExpression
|
||||
// return what the corresponding comment describes they should return and
|
||||
// removes the breakpoint.
|
||||
//
|
||||
// Each comment is a comma separated list of variable declarations, with
|
||||
// each variable declaration having the following format:
|
||||
//
|
||||
// name type = initialvalue
|
||||
// name type = initialvalue
|
||||
//
|
||||
// the = and the initial value are optional and can only be specified if the
|
||||
// type is an integer type, float32, float64 or bool.
|
||||
//
|
||||
// If multiple variables with the same name are specified:
|
||||
// 1. LocalVariables+FunctionArguments should return them in the same order and
|
||||
// every variable except the last one should be marked as shadowed
|
||||
// 2. EvalExpression should return the last one.
|
||||
// 1. LocalVariables+FunctionArguments should return them in the same order and
|
||||
// every variable except the last one should be marked as shadowed
|
||||
// 2. EvalExpression should return the last one.
|
||||
func TestScope(t *testing.T) {
|
||||
if ver, _ := goversion.Parse(runtime.Version()); ver.Major >= 0 && !ver.AfterOrEqual(goversion.GoVersion{Major: 1, Minor: 9, Rev: -1}) {
|
||||
return
|
||||
|
@ -221,9 +221,9 @@ func conditionErrors(threads []Thread) error {
|
||||
}
|
||||
|
||||
// pick a new dbp.currentThread, with the following priority:
|
||||
// - a thread with an active stepping breakpoint
|
||||
// - a thread with an active breakpoint, prioritizing trapthread
|
||||
// - trapthread
|
||||
// - a thread with an active stepping breakpoint
|
||||
// - a thread with an active breakpoint, prioritizing trapthread
|
||||
// - trapthread
|
||||
func pickCurrentThread(dbp *Target, trapthread Thread, threads []Thread) error {
|
||||
for _, th := range threads {
|
||||
if bp := th.Breakpoint(); bp.Active && bp.Stepping {
|
||||
@ -445,14 +445,14 @@ func (dbp *Target) StepInstruction() (err error) {
|
||||
// once the CALL is reached.
|
||||
//
|
||||
// Regardless of stepInto the following breakpoints will be set:
|
||||
// - a breakpoint on the first deferred function with NextDeferBreakpoint
|
||||
// kind, the list of all the addresses to deferreturn calls in this function
|
||||
// and condition checking that we remain on the same goroutine
|
||||
// - a breakpoint on each line of the function, with a condition checking
|
||||
// that we stay on the same stack frame and goroutine.
|
||||
// - a breakpoint on the return address of the function, with a condition
|
||||
// checking that we move to the previous stack frame and stay on the same
|
||||
// goroutine.
|
||||
// - a breakpoint on the first deferred function with NextDeferBreakpoint
|
||||
// kind, the list of all the addresses to deferreturn calls in this function
|
||||
// and condition checking that we remain on the same goroutine
|
||||
// - a breakpoint on each line of the function, with a condition checking
|
||||
// that we stay on the same stack frame and goroutine.
|
||||
// - a breakpoint on the return address of the function, with a condition
|
||||
// checking that we move to the previous stack frame and stay on the same
|
||||
// goroutine.
|
||||
//
|
||||
// The breakpoint on the return address is *not* set if the current frame is
|
||||
// an inlined call. For inlined calls topframe.Current.Fn is the function
|
||||
@ -957,12 +957,13 @@ func findCallInstrForRet(p Process, mem MemoryReadWriter, ret uint64, fn *Functi
|
||||
}
|
||||
|
||||
// stepOutReverse sets a breakpoint on the CALL instruction that created the current frame, this is either:
|
||||
// - the CALL instruction immediately preceding the return address of the
|
||||
// current frame
|
||||
// - the return address of the current frame if the current frame was
|
||||
// created by a runtime.deferreturn run
|
||||
// - the return address of the runtime.gopanic frame if the current frame
|
||||
// was created by a panic
|
||||
// - the CALL instruction immediately preceding the return address of the
|
||||
// current frame
|
||||
// - the return address of the current frame if the current frame was
|
||||
// created by a runtime.deferreturn run
|
||||
// - the return address of the runtime.gopanic frame if the current frame
|
||||
// was created by a panic
|
||||
//
|
||||
// This function is used to implement reversed StepOut
|
||||
func stepOutReverse(p *Target, topframe, retframe Stackframe, sameGCond ast.Expr) error {
|
||||
curthread := p.CurrentThread()
|
||||
|
@ -263,20 +263,20 @@ func AllowRecording(t testing.TB) {
|
||||
// MustHaveRecordingAllowed skips this test if recording is not allowed
|
||||
//
|
||||
// Not all the tests can be run with a recording:
|
||||
// - some fixtures never terminate independently (loopprog,
|
||||
// testnextnethttp) and can not be recorded
|
||||
// - some tests assume they can interact with the target process (for
|
||||
// example TestIssue419, or anything changing the value of a variable),
|
||||
// which we can't do on with a recording
|
||||
// - some tests assume that the Pid returned by the process is valid, but
|
||||
// it won't be at replay time
|
||||
// - some tests will start the fixture but not never execute a single
|
||||
// instruction, for some reason rr doesn't like this and will print an
|
||||
// error if it happens
|
||||
// - many tests will assume that we can return from a runtime.Breakpoint,
|
||||
// with a recording this is not possible because when the fixture ran it
|
||||
// wasn't attached to a debugger and in those circumstances a
|
||||
// runtime.Breakpoint leads directly to a crash
|
||||
// - some fixtures never terminate independently (loopprog,
|
||||
// testnextnethttp) and can not be recorded
|
||||
// - some tests assume they can interact with the target process (for
|
||||
// example TestIssue419, or anything changing the value of a variable),
|
||||
// which we can't do on with a recording
|
||||
// - some tests assume that the Pid returned by the process is valid, but
|
||||
// it won't be at replay time
|
||||
// - some tests will start the fixture but not never execute a single
|
||||
// instruction, for some reason rr doesn't like this and will print an
|
||||
// error if it happens
|
||||
// - many tests will assume that we can return from a runtime.Breakpoint,
|
||||
// with a recording this is not possible because when the fixture ran it
|
||||
// wasn't attached to a debugger and in those circumstances a
|
||||
// runtime.Breakpoint leads directly to a crash
|
||||
//
|
||||
// Some of the tests using runtime.Breakpoint (anything involving variable
|
||||
// evaluation and TestWorkDir) have been adapted to work with a recording.
|
||||
|
@ -112,13 +112,13 @@ func (ctxt *loadDebugInfoMapsContext) lookupAbstractOrigin(bi *BinaryInfo, off d
|
||||
|
||||
// runtimeTypeToDIE returns the DIE corresponding to the runtime._type.
|
||||
// This is done in three different ways depending on the version of go.
|
||||
// * Before go1.7 the type name is retrieved directly from the runtime._type
|
||||
// and looked up in debug_info
|
||||
// * After go1.7 the runtime._type struct is read recursively to reconstruct
|
||||
// the name of the type, and then the type's name is used to look up
|
||||
// debug_info
|
||||
// * After go1.11 the runtimeTypeToDIE map is used to look up the address of
|
||||
// the type and map it drectly to a DIE.
|
||||
// - Before go1.7 the type name is retrieved directly from the runtime._type
|
||||
// and looked up in debug_info
|
||||
// - After go1.7 the runtime._type struct is read recursively to reconstruct
|
||||
// the name of the type, and then the type's name is used to look up
|
||||
// debug_info
|
||||
// - After go1.11 the runtimeTypeToDIE map is used to look up the address of
|
||||
// the type and map it drectly to a DIE.
|
||||
func runtimeTypeToDIE(_type *Variable, dataAddr uint64) (typ godwarf.Type, kind int64, err error) {
|
||||
bi := _type.bi
|
||||
|
||||
|
@ -1705,10 +1705,11 @@ func (s *Session) onThreadsRequest(request *dap.ThreadsRequest) {
|
||||
// onAttachRequest handles 'attach' request.
|
||||
// This is a mandatory request to support.
|
||||
// Attach debug sessions support the following modes:
|
||||
// -- [DEFAULT] "local" -- attaches debugger to a local running process
|
||||
// Required args: processID
|
||||
// -- "remote" - attaches client to a debugger already attached to a process
|
||||
// Required args: none (host/port are used externally to connect)
|
||||
//
|
||||
// - [DEFAULT] "local" -- attaches debugger to a local running process.
|
||||
// Required args: processID
|
||||
// - "remote" -- attaches client to a debugger already attached to a process.
|
||||
// Required args: none (host/port are used externally to connect)
|
||||
func (s *Session) onAttachRequest(request *dap.AttachRequest) {
|
||||
var args AttachConfig = defaultAttachConfig // narrow copy for initializing non-zero default values
|
||||
if err := unmarshalLaunchAttachArgs(request.Arguments, &args); err != nil {
|
||||
@ -2591,12 +2592,15 @@ func (s *Session) convertVariableWithOpts(v *proc.Variable, qualifiedNameOrExpr
|
||||
// onEvaluateRequest handles 'evalute' requests.
|
||||
// This is a mandatory request to support.
|
||||
// Support the following expressions:
|
||||
// -- {expression} - evaluates the expression and returns the result as a variable
|
||||
// -- call {function} - injects a function call and returns the result as a variable
|
||||
// -- config {expression} - updates configuration parameters
|
||||
//
|
||||
// - {expression} - evaluates the expression and returns the result as a variable
|
||||
// - call {function} - injects a function call and returns the result as a variable
|
||||
// - config {expression} - updates configuration parameters
|
||||
//
|
||||
// TODO(polina): users have complained about having to click to expand multi-level
|
||||
// variables, so consider also adding the following:
|
||||
// -- print {expression} - return the result as a string like from dlv cli
|
||||
//
|
||||
// - print {expression} - return the result as a string like from dlv cli
|
||||
func (s *Session) onEvaluateRequest(request *dap.EvaluateRequest) {
|
||||
showErrorToUser := request.Arguments.Context != "watch" && request.Arguments.Context != "repl" && request.Arguments.Context != "hover"
|
||||
if s.debugger == nil {
|
||||
@ -3301,7 +3305,8 @@ func (s *Session) getExprString(expr string, goroutineID, frame int) (string, er
|
||||
}
|
||||
|
||||
// sendErrorResponseWithOpts offers configuration options.
|
||||
// showUser - if true, the error will be shown to the user (e.g. via a visible pop-up)
|
||||
//
|
||||
// showUser - if true, the error will be shown to the user (e.g. via a visible pop-up)
|
||||
func (s *Session) sendErrorResponseWithOpts(request dap.Request, id int, summary, details string, showUser bool) {
|
||||
er := &dap.ErrorResponse{}
|
||||
er.Type = "response"
|
||||
@ -3706,7 +3711,8 @@ type logMessage struct {
|
||||
}
|
||||
|
||||
// parseLogPoint parses a log message according to the DAP spec:
|
||||
// "Expressions within {} are interpolated."
|
||||
//
|
||||
// "Expressions within {} are interpolated."
|
||||
func parseLogPoint(msg string) (bool, *logMessage, error) {
|
||||
// Note: All braces *must* come in pairs, even those within an
|
||||
// expression to be interpolated.
|
||||
|
@ -321,37 +321,39 @@ func TestForceStopWhileStopping(t *testing.T) {
|
||||
|
||||
// TestLaunchStopOnEntry emulates the message exchange that can be observed with
|
||||
// VS Code for the most basic launch debug session with "stopOnEntry" enabled:
|
||||
// - User selects "Start Debugging": 1 >> initialize
|
||||
// : 1 << initialize
|
||||
// : 2 >> launch
|
||||
// : << initialized event
|
||||
// : 2 << launch
|
||||
// : 3 >> setBreakpoints (empty)
|
||||
// : 3 << setBreakpoints
|
||||
// : 4 >> setExceptionBreakpoints (empty)
|
||||
// : 4 << setExceptionBreakpoints
|
||||
// : 5 >> configurationDone
|
||||
// - Program stops upon launching : << stopped event
|
||||
// : 5 << configurationDone
|
||||
// : 6 >> threads
|
||||
// : 6 << threads (Dummy)
|
||||
// : 7 >> threads
|
||||
// : 7 << threads (Dummy)
|
||||
// : 8 >> stackTrace
|
||||
// : 8 << error (Unable to produce stack trace)
|
||||
// : 9 >> stackTrace
|
||||
// : 9 << error (Unable to produce stack trace)
|
||||
// - User evaluates bad expression : 10 >> evaluate
|
||||
// : 10 << error (unable to find function context)
|
||||
// - User evaluates good expression: 11 >> evaluate
|
||||
// : 11 << evaluate
|
||||
// - User selects "Continue" : 12 >> continue
|
||||
// : 12 << continue
|
||||
// - Program runs to completion : << terminated event
|
||||
// : 13 >> disconnect
|
||||
// : << output event (Process exited)
|
||||
// : << output event (Detaching)
|
||||
// : 13 << disconnect
|
||||
//
|
||||
// User selects "Start Debugging": 1 >> initialize
|
||||
// : 1 << initialize
|
||||
// : 2 >> launch
|
||||
// : << initialized event
|
||||
// : 2 << launch
|
||||
// : 3 >> setBreakpoints (empty)
|
||||
// : 3 << setBreakpoints
|
||||
// : 4 >> setExceptionBreakpoints (empty)
|
||||
// : 4 << setExceptionBreakpoints
|
||||
// : 5 >> configurationDone
|
||||
// Program stops upon launching : << stopped event
|
||||
// : 5 << configurationDone
|
||||
// : 6 >> threads
|
||||
// : 6 << threads (Dummy)
|
||||
// : 7 >> threads
|
||||
// : 7 << threads (Dummy)
|
||||
// : 8 >> stackTrace
|
||||
// : 8 << error (Unable to produce stack trace)
|
||||
// : 9 >> stackTrace
|
||||
// : 9 << error (Unable to produce stack trace)
|
||||
// User evaluates bad expression : 10 >> evaluate
|
||||
// : 10 << error (unable to find function context)
|
||||
// User evaluates good expression: 11 >> evaluate
|
||||
// : 11 << evaluate
|
||||
// User selects "Continue" : 12 >> continue
|
||||
// : 12 << continue
|
||||
// Program runs to completion : << terminated event
|
||||
// : 13 >> disconnect
|
||||
// : << output event (Process exited)
|
||||
// : << output event (Detaching)
|
||||
// : 13 << disconnect
|
||||
//
|
||||
// This test exhaustively tests Seq and RequestSeq on all messages from the
|
||||
// server. Other tests do not necessarily need to repeat all these checks.
|
||||
func TestLaunchStopOnEntry(t *testing.T) {
|
||||
@ -801,11 +803,12 @@ func TestPreSetBreakpoint(t *testing.T) {
|
||||
}
|
||||
|
||||
// checkStackFramesExact is a helper for verifying the values within StackTraceResponse.
|
||||
// wantStartName - name of the first returned frame (ignored if "")
|
||||
// wantStartLine - file line of the first returned frame (ignored if <0).
|
||||
// wantStartID - id of the first frame returned (ignored if wantFrames is 0).
|
||||
// wantFrames - number of frames returned (length of StackTraceResponse.Body.StackFrames array).
|
||||
// wantTotalFrames - total number of stack frames available (StackTraceResponse.Body.TotalFrames).
|
||||
//
|
||||
// wantStartName - name of the first returned frame (ignored if "")
|
||||
// wantStartLine - file line of the first returned frame (ignored if <0).
|
||||
// wantStartID - id of the first frame returned (ignored if wantFrames is 0).
|
||||
// wantFrames - number of frames returned (length of StackTraceResponse.Body.StackFrames array).
|
||||
// wantTotalFrames - total number of stack frames available (StackTraceResponse.Body.TotalFrames).
|
||||
func checkStackFramesExact(t *testing.T, got *dap.StackTraceResponse,
|
||||
wantStartName string, wantStartLine, wantStartID, wantFrames, wantTotalFrames int) {
|
||||
t.Helper()
|
||||
@ -956,9 +959,10 @@ func checkStackFramesNamed(testName string, t *testing.T, got *dap.StackTraceRes
|
||||
}
|
||||
|
||||
// checkScope is a helper for verifying the values within a ScopesResponse.
|
||||
// i - index of the scope within ScopesRespose.Body.Scopes array
|
||||
// name - name of the scope
|
||||
// varRef - reference to retrieve variables of this scope. If varRef is negative, the reference is not checked.
|
||||
//
|
||||
// i - index of the scope within ScopesRespose.Body.Scopes array
|
||||
// name - name of the scope
|
||||
// varRef - reference to retrieve variables of this scope. If varRef is negative, the reference is not checked.
|
||||
func checkScope(t *testing.T, got *dap.ScopesResponse, i int, name string, varRef int) {
|
||||
t.Helper()
|
||||
if len(got.Body.Scopes) <= i {
|
||||
@ -971,8 +975,9 @@ func checkScope(t *testing.T, got *dap.ScopesResponse, i int, name string, varRe
|
||||
}
|
||||
|
||||
// checkChildren is a helper for verifying the number of variables within a VariablesResponse.
|
||||
// parentName - pseudoname of the enclosing variable or scope (used for error message only)
|
||||
// numChildren - number of variables/fields/elements of this variable
|
||||
//
|
||||
// parentName - pseudoname of the enclosing variable or scope (used for error message only)
|
||||
// numChildren - number of variables/fields/elements of this variable
|
||||
func checkChildren(t *testing.T, got *dap.VariablesResponse, parentName string, numChildren int) {
|
||||
t.Helper()
|
||||
if got.Body.Variables == nil {
|
||||
@ -984,13 +989,14 @@ func checkChildren(t *testing.T, got *dap.VariablesResponse, parentName string,
|
||||
}
|
||||
|
||||
// checkVar is a helper for verifying the values within a VariablesResponse.
|
||||
// i - index of the variable within VariablesRespose.Body.Variables array (-1 will search all vars for a match)
|
||||
// name - name of the variable
|
||||
// evalName - fully qualified variable name or alternative expression to load this variable
|
||||
// value - the value of the variable
|
||||
// useExactMatch - true if name, evalName and value are to be compared to exactly, false if to be used as regex
|
||||
// hasRef - true if the variable should have children and therefore a non-0 variable reference
|
||||
// ref - reference to retrieve children of this variable (0 if none)
|
||||
//
|
||||
// i - index of the variable within VariablesRespose.Body.Variables array (-1 will search all vars for a match)
|
||||
// name - name of the variable
|
||||
// evalName - fully qualified variable name or alternative expression to load this variable
|
||||
// value - the value of the variable
|
||||
// useExactMatch - true if name, evalName and value are to be compared to exactly, false if to be used as regex
|
||||
// hasRef - true if the variable should have children and therefore a non-0 variable reference
|
||||
// ref - reference to retrieve children of this variable (0 if none)
|
||||
func checkVar(t *testing.T, got *dap.VariablesResponse, i int, name, evalName, value, typ string, useExactMatch, hasRef bool, indexed, named int) (ref int) {
|
||||
t.Helper()
|
||||
if len(got.Body.Variables) <= i {
|
||||
@ -3756,9 +3762,10 @@ func TestWorkingDir(t *testing.T) {
|
||||
}
|
||||
|
||||
// checkEval is a helper for verifying the values within an EvaluateResponse.
|
||||
// value - the value of the evaluated expression
|
||||
// hasRef - true if the evaluated expression should have children and therefore a non-0 variable reference
|
||||
// ref - reference to retrieve children of this evaluated expression (0 if none)
|
||||
//
|
||||
// value - the value of the evaluated expression
|
||||
// hasRef - true if the evaluated expression should have children and therefore a non-0 variable reference
|
||||
// ref - reference to retrieve children of this evaluated expression (0 if none)
|
||||
func checkEval(t *testing.T, got *dap.EvaluateResponse, value string, hasRef bool) (ref int) {
|
||||
t.Helper()
|
||||
if got.Body.Result != value || (got.Body.VariablesReference > 0) != hasRef {
|
||||
@ -3768,9 +3775,10 @@ func checkEval(t *testing.T, got *dap.EvaluateResponse, value string, hasRef boo
|
||||
}
|
||||
|
||||
// checkEvalIndexed is a helper for verifying the values within an EvaluateResponse.
|
||||
// value - the value of the evaluated expression
|
||||
// hasRef - true if the evaluated expression should have children and therefore a non-0 variable reference
|
||||
// ref - reference to retrieve children of this evaluated expression (0 if none)
|
||||
//
|
||||
// value - the value of the evaluated expression
|
||||
// hasRef - true if the evaluated expression should have children and therefore a non-0 variable reference
|
||||
// ref - reference to retrieve children of this evaluated expression (0 if none)
|
||||
func checkEvalIndexed(t *testing.T, got *dap.EvaluateResponse, value string, hasRef bool, indexed, named int) (ref int) {
|
||||
t.Helper()
|
||||
if got.Body.Result != value || (got.Body.VariablesReference > 0) != hasRef || got.Body.IndexedVariables != indexed || got.Body.NamedVariables != named {
|
||||
@ -5089,14 +5097,15 @@ type onBreakpoint struct {
|
||||
// runDebugSessionWithBPs is a helper for executing the common init and shutdown
|
||||
// sequences for a program that does not stop on entry
|
||||
// while specifying breakpoints and unique launch/attach criteria via parameters.
|
||||
// cmd - "launch" or "attach"
|
||||
// cmdRequest - a function that sends a launch or attach request,
|
||||
// so the test author has full control of its arguments.
|
||||
// Note that he rest of the test sequence assumes that
|
||||
// stopOnEntry is false.
|
||||
// source - source file path, needed to set breakpoints, "" if none to be set.
|
||||
// breakpoints - list of lines, where breakpoints are to be set
|
||||
// onBPs - list of test sequences to execute at each of the set breakpoints.
|
||||
//
|
||||
// cmd - "launch" or "attach"
|
||||
// cmdRequest - a function that sends a launch or attach request,
|
||||
// so the test author has full control of its arguments.
|
||||
// Note that he rest of the test sequence assumes that
|
||||
// stopOnEntry is false.
|
||||
// source - source file path, needed to set breakpoints, "" if none to be set.
|
||||
// breakpoints - list of lines, where breakpoints are to be set
|
||||
// onBPs - list of test sequences to execute at each of the set breakpoints.
|
||||
func runDebugSessionWithBPs(t *testing.T, client *daptest.Client, cmd string, cmdRequest func(), source string, breakpoints []int, onBPs []onBreakpoint) {
|
||||
client.InitializeRequest()
|
||||
client.ExpectInitializeResponseAndCapabilities(t)
|
||||
|
@ -7,22 +7,32 @@ import (
|
||||
)
|
||||
|
||||
// Launch debug sessions support the following modes:
|
||||
// -- [DEFAULT] "debug" - builds and launches debugger for specified program (similar to 'dlv debug')
|
||||
// Required args: program
|
||||
// Optional args with default: output, cwd, noDebug
|
||||
// Optional args: buildFlags, args
|
||||
// -- "test" - builds and launches debugger for specified test (similar to 'dlv test')
|
||||
// same args as above
|
||||
// -- "exec" - launches debugger for precompiled binary (similar to 'dlv exec')
|
||||
// Required args: program
|
||||
// Optional args with default: cwd, noDebug
|
||||
// Optional args: args
|
||||
// -- "replay" - replays a trace generated by mozilla rr. Mozilla rr must be installed.
|
||||
// Required args: traceDirPath
|
||||
// Optional args: args
|
||||
// -- "core" - examines a core dump (only supports linux and windows core dumps).
|
||||
// Required args: program, coreFilePath
|
||||
// Optional args: args
|
||||
//
|
||||
// -- [DEFAULT] "debug" - builds and launches debugger for specified program (similar to 'dlv debug')
|
||||
//
|
||||
// Required args: program
|
||||
// Optional args with default: output, cwd, noDebug
|
||||
// Optional args: buildFlags, args
|
||||
//
|
||||
// -- "test" - builds and launches debugger for specified test (similar to 'dlv test')
|
||||
//
|
||||
// same args as above
|
||||
//
|
||||
// -- "exec" - launches debugger for precompiled binary (similar to 'dlv exec')
|
||||
//
|
||||
// Required args: program
|
||||
// Optional args with default: cwd, noDebug
|
||||
// Optional args: args
|
||||
//
|
||||
// -- "replay" - replays a trace generated by mozilla rr. Mozilla rr must be installed.
|
||||
//
|
||||
// Required args: traceDirPath
|
||||
// Optional args: args
|
||||
//
|
||||
// -- "core" - examines a core dump (only supports linux and windows core dumps).
|
||||
//
|
||||
// Required args: program, coreFilePath
|
||||
// Optional args: args
|
||||
//
|
||||
// TODO(hyangah): change this to 'validateLaunchMode' that checks
|
||||
// all the required/optional fields mentioned above.
|
||||
|
@ -632,15 +632,21 @@ type ListGoroutinesOut struct {
|
||||
// If arg.Filters are specified the list of returned goroutines is filtered
|
||||
// applying the specified filters.
|
||||
// For example:
|
||||
// ListGoroutinesFilter{ Kind: ListGoroutinesFilterUserLoc, Negated: false, Arg: "afile.go" }
|
||||
//
|
||||
// ListGoroutinesFilter{ Kind: ListGoroutinesFilterUserLoc, Negated: false, Arg: "afile.go" }
|
||||
//
|
||||
// will only return goroutines whose UserLoc contains "afile.go" as a substring.
|
||||
// More specifically a goroutine matches a location filter if the specified
|
||||
// location, formatted like this:
|
||||
// filename:lineno in function
|
||||
//
|
||||
// filename:lineno in function
|
||||
//
|
||||
// contains Arg[0] as a substring.
|
||||
//
|
||||
// Filters can also be applied to goroutine labels:
|
||||
// ListGoroutineFilter{ Kind: ListGoroutinesFilterLabel, Negated: false, Arg: "key=value" }
|
||||
//
|
||||
// ListGoroutineFilter{ Kind: ListGoroutinesFilterLabel, Negated: false, Arg: "key=value" }
|
||||
//
|
||||
// this filter will only return goroutines that have a key=value label.
|
||||
//
|
||||
// If arg.GroupBy is not GoroutineFieldNone then the goroutines will
|
||||
@ -700,15 +706,15 @@ type FindLocationOut struct {
|
||||
|
||||
// FindLocation returns concrete location information described by a location expression.
|
||||
//
|
||||
// loc ::= <filename>:<line> | <function>[:<line>] | /<regex>/ | (+|-)<offset> | <line> | *<address>
|
||||
// * <filename> can be the full path of a file or just a suffix
|
||||
// * <function> ::= <package>.<receiver type>.<name> | <package>.(*<receiver type>).<name> | <receiver type>.<name> | <package>.<name> | (*<receiver type>).<name> | <name>
|
||||
// * <function> must be unambiguous
|
||||
// * /<regex>/ will return a location for each function matched by regex
|
||||
// * +<offset> returns a location for the line that is <offset> lines after the current line
|
||||
// * -<offset> returns a location for the line that is <offset> lines before the current line
|
||||
// * <line> returns a location for a line in the current file
|
||||
// * *<address> returns the location corresponding to the specified address
|
||||
// loc ::= <filename>:<line> | <function>[:<line>] | /<regex>/ | (+|-)<offset> | <line> | *<address>
|
||||
// * <filename> can be the full path of a file or just a suffix
|
||||
// * <function> ::= <package>.<receiver type>.<name> | <package>.(*<receiver type>).<name> | <receiver type>.<name> | <package>.<name> | (*<receiver type>).<name> | <name>
|
||||
// <function> must be unambiguous
|
||||
// * /<regex>/ will return a location for each function matched by regex
|
||||
// * +<offset> returns a location for the line that is <offset> lines after the current line
|
||||
// * -<offset> returns a location for the line that is <offset> lines before the current line
|
||||
// * <line> returns a location for a line in the current file
|
||||
// * *<address> returns the location corresponding to the specified address
|
||||
//
|
||||
// NOTE: this function does not actually set breakpoints.
|
||||
func (c *RPCServer) FindLocation(arg FindLocationIn, out *FindLocationOut) error {
|
||||
|
@ -213,8 +213,9 @@ func isExportedOrBuiltinType(t reflect.Type) bool {
|
||||
// available through the RPC interface.
|
||||
// These are all the public methods of rcvr that have one of those
|
||||
// two signatures:
|
||||
// func (rcvr ReceiverType) Method(in InputType, out *ReplyType) error
|
||||
// func (rcvr ReceiverType) Method(in InputType, cb service.RPCCallback)
|
||||
//
|
||||
// func (rcvr ReceiverType) Method(in InputType, out *ReplyType) error
|
||||
// func (rcvr ReceiverType) Method(in InputType, cb service.RPCCallback)
|
||||
func suitableMethods(rcvr interface{}, methods map[string]*methodType, log *logrus.Entry) {
|
||||
typ := reflect.TypeOf(rcvr)
|
||||
rcvrv := reflect.ValueOf(rcvr)
|
||||
|
Loading…
Reference in New Issue
Block a user