当前位置: 首页 > news >正文

服务启动慢分析小记

文章目录

    • 1. 写在最前面
    • 2. 分析过程
      • 2.1 初步分析
    • 2.2 深入分析
        • 2.2.1 是否为 master 卡住
        • 2.2.2 分析 sidecar 侧
          • 2.2.2.1 gdb 调试
          • 2.2.2.2 dlv 调试
    • 3. 碎碎念
    • 4. 参考资料:

1. 写在最前面

不出意外,就是要出意外。还是忙忙碌碌木有学习 AI 知识的一个月,那只能浅浅的记录一下,这个月分析定位服务启动慢问题的方法,方便后续再遇到时候,还要从头分析。

背景: 笔者负责的业务是有多个服务组成的,即当客户请求的时候,会根据客户的请求的参数,动态判断需要拉起的服务组合。具体组成:

  • master : 负责拉起 sidecar ,及根据 sidecar 返回的需要拉起的服务说明拉起服务

  • sidecar :识别参数,然后返回需要拉起的服务内容

注:master 与 sidecar 之间是通过 pipe 交互的

现象: 请求会返回超时,原因是在 master 拉起 sidecar 的时候卡主超过了 5s 。

2. 分析过程

2.1 初步分析

这个现象在业务上 HCI 的时候,任务启动超时的现象很像,原因是在 hci 的 docker 上 pipe 大小被修改。

查看出现启动超时的机器的 pipe 大小:

#  ulimit -a
core file size          (blocks, -c) unlimited
data seg size           (kbytes, -d) unlimited
scheduling priority             (-e) 0
file size               (blocks, -f) unlimited
pending signals                 (-i) 128105
max locked memory       (kbytes, -l) 65536
max memory size         (kbytes, -m) unlimited
open files                      (-n) 100000
pipe size            (512 bytes, -p) 8
POSIX message queues     (bytes, -q) 819200
real-time priority              (-r) 0
stack size              (kbytes, -s) 8192
cpu time               (seconds, -t) unlimited
max user processes              (-u) 65535
virtual memory          (kbytes, -v) unlimited
file locks                      (-x) unlimited

注:通过 ulimit -a 到 pipe size 一次原子写入为:512Bytes*8=4096 bytes, 而 linux pipe 的默认大小为 16内存页,即 4096 * 16 = 65536bytes

当时排查的时候记录过程:记一次神奇的 pipe 错误_pipe中数据小于4096无法读出

2.2 深入分析

2.2.1 是否为 master 卡住
  • 首先,将机器上会有多个 master ,数量缩减为 1

  • 其次,使用 strace 命令跟踪 master 的系统调用,观察其是否有卡住

    注:attached 到 PID 为 18551 的进程,开始跟踪其系统调用。

    # strace -p 18551
    strace: Process 18551 attached
    epoll_wait(4, [], 32, 622)              = 0
    epoll_wait(4, [], 32, 2)                = 0
    epoll_wait(4, [], 32, 998)              = 0
    epoll_wait(4, [], 32, 998)              = 0
    epoll_wait(4, [], 32, 2)                = 0
    epoll_wait(4, [], 32, 998)              = 0
    epoll_wait(4, [], 32, 997)              = 0
    epoll_wait(4, [], 32, 1)                = 0
    epoll_wait(4, [], 32, 1)                = 0
    epoll_wait(4, [], 32, 997)              = 0
    epoll_wait(4, [], 32, 1)                = 0
    epoll_wait(4, [], 32, 1)                = 0
    epoll_wait(4, [], 32, 997)              = 0
    epoll_wait(4, [], 32, 1)                = 0
    epoll_wait(4, [], 32, 997)              = 0
    epoll_wait(4, [], 32, 1)                = 0
    epoll_wait(4, [], 32, 1)                = 0
    epoll_wait(4, ^Cstrace: Process 18551 detached<detached ...>
    

结论:启动超时的卡顿不在 master 侧

2.2.2 分析 sidecar 侧
  • 首先,sidecar 这个进程在上述启动超时的情况下,只会保留 5s ,后面就会被 master 主动 kill,防止业务层级的资源泄漏

  • 其次,需要写一个捕获某个 pid 进程的脚本,防止抓不住卡顿的现场,捕获的具体代码如下:

    #!/bin/bashprocess_name="sidecar."# 获取进程的 PID
    pid=$(pgrep $process_name)# 检查是否获取到 PID
    if [ -n "$pid" ]; thenecho "Attaching strace to process $process_name with PID $pid"strace -p $pid
    elseecho "Process $process_name not found."
    fi
    

    注:将 strace 命令换为 gdb ,可以换为 gdb 调试的脚步

  • 最后,发现上述的脚步,无法分析更多的原因,只能上 log debug 大法。「最质朴的手段」

    在这里插入图片描述

结论:确实是 sidecar 卡主了,卡住的原因是同步初始化了内部的某个系统 client 卡主了 5s 以上

注:以后写代码,再着急的需求,也得把强弱依赖搞好!

2.2.2.1 gdb 调试

golang 的程序不要尝试使用 gdb 调试了,笔者亲测了,断点有的时候,跑在不同的线程上,似乎没有办法有效的断住。

  • Go 的运行时和调试信息可能会让 gdb 的某些功能变得复杂。特别是 goroutine 的调试可能不如在其他语言中那样直观。

  • Go 生态系统中有一个专门为 Go 设计的调试器,叫做 Delvedlv)。它提供了更好的 Go 支持,尤其是在处理 goroutine 和 Go 的特性时。使用 Delve 进行调试通常会更简单和有效。

2.2.2.2 dlv 调试

这部分网上已经有很多的具体介绍了,这里我就不冗余记录了,但是有一点要注意:

{// Use IntelliSense to learn about possible attributes.// Hover to view descriptions of existing attributes.// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387"version": "0.2.0","configurations": [{"name": "Launch Remote","type": "go","request": "attach","mode": "remote",//  "remotePath": "xxx", //项目远程根路径"port": 8669, //监听端口"host": "101.64.234.xxx", //远程主机/IP"cwd": "/xxxx",//vscode本地工作目录"trace": "verbose" //输出详情}]}

如果反复尝试,但是还是没有办法成功,可以尝试注释 remotePath 字段,笔者亲测有效

在这里插入图片描述

3. 碎碎念

九月和十月,真的是打工人的福利月,断断续续的假期,让人工作的时候也不会很烦躁:

  • 就是只做好想做的和该做的事情

    对结果没什么执念、内心清澈、平静、松弛

    不是懒散享乐,不是躺平摆烂,不是什么都不在乎

    而是尽力之后对结果的随遇而安

    是无所畏惧,活出自在心安,是坚持自己的本心

  • 在成为大人的路上,去做自己喜欢的事情

4. 参考资料:

  • linux下,pipe的容量的讨论与查看(转)

  • https://elixir.bootlin.com/linux/v3.10/source/include/linux/pipe_fs_i.h#L4

  • 使用Visual Studio Code和delve进行golang远程调试


http://www.mrgr.cn/news/35330.html

相关文章:

  • 【Linux探索学习】第一弹——Linux的基本指令(上)——开启Linux学习第一篇
  • 微服务——配置管理
  • Linux入门学习:进程概念
  • 计算机复习9.23
  • 【JAVA集合总结-贰】
  • 《深度学习》CNN 数据增强、保存最优模型 实例详解
  • React开发环境搭建以及常见错误解决
  • Mac安装manim
  • 力扣416周赛
  • Java转换流
  • 【深度学习】批量规范化
  • CREO教程——2 绘制标准图纸
  • Footprint Analytics: 我们为何打造 Growthly 这款产品
  • 高等数学大纲
  • vsomeip客户端/服务端大致运行流程
  • 【洛谷】AT_abc371_d [ABC371D] 1D Country 的题解
  • 开源UNI-SOP云统一认证平台
  • 算法:69.x的平方根
  • 深入剖析链表反转:多语言实现与高级语法特性20240924
  • 【环境搭建】MySQL安装部署