go - panic()stacktrace不显示函数参数

标签 go

在下面的代码中:

package main
    
func main() {
    example(make([]string, 2, 4), "hello", 10)
}
    
func example(slice []string, str string, i int) {
    panic("Want stack trace")
}

使用6个单词存储数据并传递给example函数。
  • slice header
  • 的3个单词
  • 2个单词表示str字符串
  • 单词i整数

  • 预期的堆栈跟踪:
    goroutine 1 [running]:
    main.example(0xc000042748, 0x2, 0x4, 0x106abae, 0x5, 0xa)
        stack_trace/example1/example1.go:13 +0x39
    main.main()
        stack_trace/example1/example1.go:8 +0x72
        
    // Declaration
    main.example(slice []string, str string, i int)
        
    // Call
    make([]string, 2, 4), "hello", 10
        
    // Values (0xc000042748, 0x2, 0x4, 0x106abae, 0x5, 0xa)
    Slice Value:   0xc000042748, 0x2, 0x4
    String Value:  0x106abae, 0x5
    Integer Value: 0xa
    

    实际堆栈跟踪:
    panic: Want stack trace
        
    goroutine 1 [running]:
    main.example(...)
            /home/../Main.go:8
    main.main()
            /home/../Main.go:4 +0x39
    exit status 2
    
    $ go version
    go version go1.14.3 linux/amd64
    

    为什么从panic()生成的stacktrace没有显示这6个单词?

    最佳答案

    Go正在显示main.example(...),因为函数已由编译器内联,并且不再作为函数存在,它已嵌入main()中(打印逻辑的详细信息位于traceback.go中)。
    您可以使用go:noinline compiler directive告诉编译器不要内联函数:

    //go:noinline
    func example(slice []string, str string, i int) {
      panic("Want stack trace")
    }
    
    禁用内联后,默认回溯输出显示main.example及其参数:
    panic: Want stack trace
    
    goroutine 1 [running]:
    main.example(0xc000046738, 0x2, 0x4, 0x473f27, 0x5, 0xa)
        /home/me/stuff/src/github.com/me/testing/panic/main.go:9 +0x39
    main.main()
        /home/me/stuff/src/github.com/me/testing/panic/main.go:4 +0x72
    
    请注意,make不会出现在堆栈跟踪中,它也不会出现:它在到达panic之前就已经返回。
    一个建议字:此处go:noinline用于显示为什么堆栈跟踪不包含函数参数。通常,除非调试编译器或处理需要它的运行时函数,否则通常不应该强制执行编译器优化决策。

    关于go - panic()stacktrace不显示函数参数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63785981/

    相关文章:

    json - 从 API 解析结构

    Go错误检查和链接

    go - Beego - 端点测试

    string - 将字符串索引为字符

    firebase - 使用 Go 为 Remote Config REST API 验证服务帐户

    authentication - 连接到 Azure SQL 数据库时的 Active Directory 身份验证

    go - 如何在 "pretty"文本中查看mgo的bson.Raw

    go - 如何获取空闲 inode 数量? (`df -i` 等效)

    go - 现有 Terraform 提供商的自定义资源?

    Go: bytes.Repeat 检查溢出