惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

S
Schneier on Security
F
Fortinet All Blogs
B
Blog
GbyAI
GbyAI
P
Proofpoint News Feed
量子位
The Register - Security
The Register - Security
宝玉的分享
宝玉的分享
大猫的无限游戏
大猫的无限游戏
云风的 BLOG
云风的 BLOG
V
Visual Studio Blog
B
Blog RSS Feed
WordPress大学
WordPress大学
Recorded Future
Recorded Future
Recent Announcements
Recent Announcements
V
Vulnerabilities – Threatpost
cs.CV updates on arXiv.org
cs.CV updates on arXiv.org
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
S
Secure Thoughts
雷峰网
雷峰网
Stack Overflow Blog
Stack Overflow Blog
C
Cybersecurity and Infrastructure Security Agency CISA
Webroot Blog
Webroot Blog
AWS News Blog
AWS News Blog
K
KPMG report finds enterprise disconnect between AI and its ROI | CIO
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed
The GitHub Blog
The GitHub Blog
爱范儿
爱范儿
O
OpenAI News
月光博客
月光博客
H
Hacker News: Front Page
S
Security Affairs
W
WeLiveSecurity
The Hacker News
The Hacker News
aimingoo的专栏
aimingoo的专栏
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
Help Net Security
Help Net Security
MongoDB | Blog
MongoDB | Blog
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
D
Docker
T
The Blog of Author Tim Ferriss
Spread Privacy
Spread Privacy
Blog — PlanetScale
Blog — PlanetScale
J
Java Code Geeks
S
Securelist
Microsoft Azure Blog
Microsoft Azure Blog
TaoSecurity Blog
TaoSecurity Blog
T
Threat Research - Cisco Blogs
M
MIT News - Artificial intelligence
A
About on SuperTechFans

Oskyla 烹茶室

修复 Joplin on KDE 菜单栏显示问题 Copy Fail:Linux 内核 2017 年至今的高危漏洞(附临时缓解方案) | CVE-2026-31431 Hermes Agent — 在 K3s / K8s 中运行指南 在 K3s 节点上安装并使用 nerdctl Mouser:轻量开源的罗技鼠标驱动替代方案 Claude Opus 4.7:优缺点与评测信息汇总 openFuyao NPU-Operator故障排查 openFuyao 2603 共测测试报告 openFuyao InferNex AI推理集成部署 310P(300I Pro) 环境问题记录及解决 ceph mon Operation not permitted 问题解决 Ascend 310P + openFuyao + NPU-Operator 故障排查 KDE Plasma6 禁用全局菜单,恢复正常应用菜单 终极指南:在 Linux 裸机服务器上快速部署 Moltbot (原 Clawbot) 并集成飞书 Windows 配置 Claude Code 解决 settings.json 不生效 Windows 配置 Claude Code 全流程 2025-12-31 | 年终总结 AI 生图精品提示词|第二期:城市星球 AI 生图精品提示词|第一期 Kubernetes kubectl --raw 使用指南 彻底解决阿里云和 tailscale 冲突 2025-10-21 | 沉淀思维 macOS 单独为鼠标或触控板开启自然滚动 2025-10-16 | 负载高低 2025-10-15 | 睡眠周期 2025-10-14 | 转换情绪与独立观点 go 拉取 gitcode.com 私有 mod Git 将某个文件恢复到其他分支的状态 SSH 通过跳板机连接 lxc 使用 chronyc 构建 ntp 服务 2025-10-13 | 独立思考于未来能源 2025-10-12|AI Review 及高质量工作流 2025-10-11 | 人生阶段 2025-10-10 | AI Logo | 远程操控 AI 2025-10-09 | 去班味|银杏|域名 2025-10-08 2025-10-07 2025-10-06 2025-10-05 优秀的 SubReddit 清单 Synology 群晖重置 Syncthing 密码 让 LLM 看到真实世界的 Playwright MCP 磁盘占用分析利器 ncdu 自建 gitlab 徽标问题导致项目 500 问题解决 harbor Chartmuseum helm 图表缓存刷新 grep exclude 排除 Debian 11 + PVE LACP Mac 冲突问题调查与解决方案 Claude Code 实用技巧 CentOS 7 重置 root 密码 telnet 如何退出 kubernetes 的挂载传播(mount propagation)机制 vim 将命令输出到当前位置 harbor 替换 ssl 证书 AI提效之使用 cherry-studio + k8sgpt 实现 AI 巡检 k8s Claude Code Subagents 快速开始 《我看见的世界:李飞飞自传》 Lyra - AI Prompt Optimization Specialist Linux 自签名 CA 证书安装方法 超级玛丽、魂斗罗等经典小游戏聚合站 | PlayUnb 个人业余开发项目清单 快速选出收益最高的理财产品 | finance-calculator 苹果液态玻璃风格图像生成和模拟器 | LiquedGlass.icu Linux 进程绑定NUMA节点或CPU核心 判断GPT是否降智的几个问题 Harmony next hap 安装 名侦探柯南贝尔摩德出场集数 k3s k8s 快速部署轻量节点监控方案 beszel k3s-k8s 实现 DevOps 方案横向对比 k8s 配置访问私有镜像仓库 GoAccess 分析多网站日志方法 Octant - 以开发人员为中心的开源 Kubernetes Web 界面 Tailscale 自建 DERP 并配置 SSL 完整教程 OpenManus 使用记录 Plausible 缺失 location 信息的研究 解决 Nginx Ingress returns 413 Entity Too Large 绘图模型效果对比之城市气象 【转】k8s 认知路线 OpenFOAM 两大分支的详细比较 第一个 CUDA 程序之矩阵运算计算效能对比 Archlinux KDE Apache JMeter 配置高分屏缩放 解决 gitlab-runner 移除残留文件 permission denied nginx-ingress 配置路由 302 k8s 触发 pod 重新拉取镜像平滑升级的方法 Clickhouse 迁移后 permission denied 问题解决 Linux CPU 运行模式及功耗分析 Linux vim vi 翻页跳转命令快捷键 git 拉取所有 branch 和 tag 到本地并推送到远程 Rails 性能分析工具 rack-mini-profiler 和 bullet 全球国家、城市、地区开源数据库 Rails Active Record 常用命令 Rails Rake 简介与编写 如何调试 Vim 脚本 名侦探柯南松田阵平出场集数(最新1069话) 名侦探柯南妃英理出场集数(最新1069话) 《名侦探柯南》官方人气投票结果 名侦探柯南TV安室透出场集数(最新1110话) 名侦探柯南TV赤井秀一出场集数(更新至1194话) [转]名侦探柯南TV主线集数整理(截止1165集) 架构风格总结 [转译] 如何成为一个好的开发者? 【影评】名侦探柯南·零的执行人
Delve 调试 GO 程序
Tianlun Song · 2024-12-18 · via Oskyla 烹茶室

本文 首发于 🌱 煎茶转载 请注明 来源

目前 Go 语言支持 GDB、LLDB 和 Delve 几种调试器。其中 GDB 是最早支持的调试工具,LLDB 是 macOS 系统推荐的标准调试工具。但是 GDB 和 LLDB 对 Go 语言的专有特性都缺乏很大支持,而只有 Delve 是专门为 Go 语言设计开发的调试工具。而且 Delve 本身也是采用 Go 语言开发,对 Windows 平台也提供了一样的支持。本节我们基于 Delve 简单解释如何调试 Go 汇编程序。

安装

Github地址: https://github.com/go-delve/delve/ 如果是在本地调试,直接通过go install命令将其安装到本地的$GOPATH/bin下即可

go install github.com/go-delve/delve/cmd/dlv@latest

容器环境下由于不一定支持 go,需要先安装 go 语言环境,会比较麻烦,可以直接将本地下载好的dlv二进制命令复制到$PATH的某一个目录中。安装好后,通过执行dlv version验证是否可用。

注意

使用go build编译时,默认会进行一些优化,会影响调试过程。 因此,对于对于需要进行调试的程序,在编译时最好设置-gcflags把优化关掉。

  • 在>= 1.10的 golang 版本中,设置-gcflags="all=-N -l"
  • 在<1.10版本的 golang 中,设置-gcflags="-N -l" 其中:
  • -N表示不优化代码,并生成调试信息。
  • -l表示禁用函数内联优化 如下面命令将当前文件夹下的代码编译成可执行文件main,并禁止优化:
go build -gcflags="all=-N -l" -o main .

基本使用

Delve 的基本命令:

(dlv) break main.main  # 设置断点
(dlv) continue        # 继续执行
(dlv) next           # 下一步
(dlv) step           # 步入
(dlv) print 变量名    # 打印变量

(dlv) b main.main    # 在main函数设置断点
(dlv) bp 文件名:行号  # 在特定行设置断点
(dlv) c             # continue 继续运行
(dlv) n             # next 下一步
(dlv) s             # step 步入
(dlv) p 变量名       # print 打印变量
(dlv) vars          # 显示包级变量
(dlv) locals        # 显示本地变量
(dlv) bt            # 显示调用栈

常用命令

attach

用于调试一个已经存在的进程,这个命令一般在调试 web 程序时使用。如下:

  • 使用lsof命令查看占用某个端口的进程 pid
  • 使用dlv attach $pid启动调试该进程 比如假定某个 web 程序的 http端口为 8080,进程号为10001
lsof -i:8080
dlv attach 10001

exec

如果没有现成的进程,而只有一个二进制可执行文件,可以使用dlv exec命令启动一个进程并进行调试,如上面生成的main

dlv exec ./main

如果 main 程序本身需要一些参数,可以通过--来传递参数,比如给上面的 main 传入一个 conf 参数

dlv exec ./main -- conf=./conf.yaml

debug

用于直接调试源码文件,这个命令连手动编译都省了,只需要指定调试的包名和源码所在的文件夹即可。

dlv debug .

version

用于查看dlv版本号,如下:

dlv version
# WARN[0000] CGO_CFLAGS already set, Cgo code could be optimized.  layer=dlv
# Delve Debugger
# Version: 1.21.0
# Build: $Id: fec0d226b2c2cce1567d5f59169660cf61dc1efe $

调试指令

通过execdebugattach进入 dlv 的调试终端后,需要执行调试指令才能完成诸如下一步、退出当前函数、查看变量值等目的。

断点管理

主要是断点的增删改查

指令缩写作用
breakb添加断点
breakpointsbp用于查看设置的所有断点,每个断点都有一个编号
clear如clear 1,表示删除编号为 1 的断点
clearall删除所有断点
toggle用于启用/禁用断点。如toggle 1
conditioncond用于设置条件断点,如cond 2 i == 10指定断点 2 在 i等于 10 时执行

需要注意的是,使用 break 创建断点时,有几种方法:

  • b 包名.方法名: 在指定包的函数中设置断点,如b main.main。如果函数名全局唯一,则不用指定包名
  • b 文件名:行数: 在指定的 go 文件的指定行设置断点,如b main.go:14

调试执行

主要用于控制程序的执行

指令缩写作用
nextn执行到下一行,如果是函数,不会进入函数
continuec执行到下一个断点处或结束执行
steps执行到下一步,如果是函数,会进入函数内部
stepoutso跳出当前函数
restartr重新执行程序,断点会保留。注意无法用于 attach 的进程
step-instructionsi执行到下一行机器码,一般在查看汇编代码时使用
rebuild重新编译程序并执行,断点会保留。无法用于 attach 和 exec

参数管理

主要用于对设置和查看变量、参数等

指令缩写作用
printp查看变量或表达式的值
whatis查看变量类型
args查看函数的入参
locals查看函数的局部变量
vars查看全局变量
set设置某个变量的值
display将变量加入/移除监控列表、或查看监控列表

注意上述locals/vars/display都支持指定正则,具体用法可以使用h locals查看。

其他

指令缩写作用
exitq退出调试会话
disassembledisass用于查看指定函数的汇编代码
funcs查看函数,同样支持正则
helph查看使用手册
listls/l查看源代码

总结

本文介绍了dlv工具的基本使用姿势,掌握该工具,不仅能够辅助我们进行调试,以后想学习一些项目的原理时,也能够很快摸清楚调用链路。

后续我的其他分析原理性的文章中,也会使用使用这一工具对源代码进行分析。

References