TiDB 可观测性的设计与实现 陈霜
Usage By Tag CPU Usage By Tag Another approach to CPU resource bind in Go Goroutine CPU Stats ● Try to collect goroutine runtime information. begin := GetGoroutineStats() executeSQL() end := ebug/pprof/trace\?seconds\=1 --output trace.out go tool trace trace.out ● In Goroutine analysis Page, chose the Goroutine you want to view. Trace - drawback ● Large performance impact. ● May generate Event goroutine_id description 0 GoCreate 1 创建⼀个 goroutine 10 GoStart 1 开始运⾏ goroutine 30 GoBlockSelect 1 被 block 了,暂停运⾏ goroutine 50 GoUnpark 1 goroutine 没有被 block 了 60 GoStart 1 开始运⾏ goroutine 800 码力 | 39 页 | 3.97 MB | 1 年前3Go性能优化概览-曹春晖
那也⼀定要有能通过配置开启的能⼒ CPU ⽤爆了?90%? 内存⽤爆了?OOM? Goroutine ⽤爆了?80w? 线程数爆了? 延迟太⾼? 压测时关注哪些服务指标 压测时关注哪些服务指标 因为我们是 Go 的服务,还可以额外看看: • Goroutine 数,线程数 • 如果 Goroutine 数很多,那这些 Goroutine 在⼲什么? • GC 频率,gctrace 的内容(线上保存 gctrace -> 看 prometheus,内存 RSS 是多少,goroutine 数量多少,goroutine 栈占⽤多少 -> 如果 goroutine 不多,那么重 点关注 heap profile 中的 inuse -> 定时任务类需要看 alloc 4. goroutine 数量过多 -> 从 profile ⽹⻚进去看看 goroutine 都在⼲什 么 -> 查死锁、阻塞等问题 -> 个别不在意延迟的选择第三⽅库优 com/golang/go/pull/42036#issuecomment-715046540 怎么样说服官⽅接受性能优化的 PR 内存占⽤过⾼-goroutine 数量太多导致内存占⽤⾼ 这些内存的构成部分: 1. Goroutine 栈占⽤的内存(难优化,⼀条 tcp 连接⾄少对应⼀个 goroutine) 2. Tcp read buffer 占⽤的内存(难优化,因为⼤部分连接阻塞在 read 上, read buffer0 码力 | 40 页 | 8.69 MB | 1 年前3Go基础语法宝典
空interface interface函数参数 interface变量存储的类型 嵌入interface 反射 并发 goroutine channels Buffered Channels Range和Close Select 超时 runtime goroutine 错误处理 Error类型 自定义Error 错误处理 总结 更多Golang资源包:https://github 的行为就 像调用了 panic 。这一过程继续向上,直到发生 panic 的 goroutine 中所有调用的函数返回,此时程 序退出。 panic 可以直接调用 panic 产生。也可以由运行时错误产生,例如访问越界的数组。 Recover 是一个内建的函数,可以让进入 panic 状态的 goroutine 恢复过来。 recover 仅在延迟函数中有效。 在正常的执行过程中,调用 recover recover 会返回 nil ,并且没有其它任何效果。如果当前的 goroutine 陷 入 panic 状态,调用 recover 可以捕获到 panic 的输入值,并且恢复正常的执行。 下面这个函数演示了如何在过程中使用 panic 下面这个函数检查作为其参数的函数在执行时是否会产生 panic : return true } return false0 码力 | 47 页 | 1020.34 KB | 1 年前3Go Web编程
过程继续向上,直到发生panic的goroutine中所有调用的函数返回,此时程序退出。恐慌可以直接调用panic产 生。也可以由运行时错误产生,例如访问越界的数组。 Recover 是一个内建的函数,可以让进入令人恐慌的流程中的goroutine恢复过来。recover仅在延迟函数中有效。在正常 的执行过程中,调用recover会返回nil,并且没有其它任何效果。如果当前的goroutine陷入恐慌,调用 要的就是并行程序设计,而GO从语言 层面就支持了并行。 goroutine goroutine goroutine是Go并行设计的核心。goroutine说到底其实就是线程,但是他比线程更小,十几个goroutine可能体现在 底层就是五六个线程,Go语言内部帮你实现了这些goroutine之间的内存共享。执行goroutine只需极少的栈内存(大 概是4~5KB),当然会根据相应的数据伸 缩。也正因为如此,可同时运行成千上万个并发任务。goroutine比thread更 易用、更高效、更轻便。 goroutine是通过Go的runtime管理的一个线程管理器。goroutine通过go关键字实现了,其实就是一个普通的函数。 go hello(a, b, c) 通过关键字go就启动了一个goroutine。我们来看一个例子 package main import (0 码力 | 295 页 | 5.91 MB | 1 年前3Go 入门指南(The way to Go)
启动外部命令和程序 13.7 Go 中的单元测试和基准测试 13.8 测试的具体例子 13.9 用(测试数据)表驱动测试 13.10 性能调试:分析并优化 Go 程序 第 14 章 协程(goroutine)与通道(channel) 14.1 什么是协程 14.2 协程间的信道 14.3 协程的同步:关闭通道-测试阻塞的通道 14.4 使用 select 切换协程 14.5 通道、超时和计时器(Ticker) 18章 出于性能考虑的实用代码片段 18.1 字符串 18.2 数组和切片 18.3 映射 18.4 结构体 18.5 接口 18.6 函数 18.7 文件 18.8 协程(goroutine)与通道(channel) 18.9 网络和网页应用 18.10 其他 18.11 出于性能考虑的最佳实践和建议 - 6 - 本文档使用 书栈(BookStack.CN) 构建 致谢 式来进行软件开发。它并不是要用奇怪的语法和晦涩难懂的概念 来从根本上推翻已有的编程语言,而是建立并改善了 C、Java、C# 中的许多语法风格。它提倡通过接口来针对面向 对象编程,通过 goroutine 和 channel 来支持并发和并行编程。 这本书是为那些想要学习 Go 这门全新的,迷人的和充满希望的编程语言的开发者量身定做的。当然,你在学习 Go 语言之前需要具备一些关于编程的基0 码力 | 466 页 | 4.44 MB | 1 年前32.Go语言实现中的几个研究课题_毛康力
接⼝口 • 垃圾回收 • 调度 • 死锁检测 并发 • goroutine提供轻量的并发机制 • channel⽤用于goroutine之间通信 并发 goroutine • 协程!!! • 每个goroutine必须有独⽴立的栈 • 如何让goroutine⾮非常轻量呢 goroutine • 分段栈 -> 连续栈 • 有没有代价? • 已经解决的问题 已经解决的问题 or 有没有更好的⽅方法? channel • 如果⼀一个goroutine执⾏行channel操作阻塞,它会被挂 在这个channel的结构上⾯面,以便唤醒。 select • select如何实现? • select其实是⼀一个整体 • c1 c2并不能独⽴立对待 • 要么全部成功,要么失败,否则可能死锁 • 单纯对select结构加锁⾏行不通!!! • 共享⼀一个全局锁? 曹尼玛:内存管理太重要!给⺩王尼玛管我不放⼼心 Go还是很体贴⼤大伙的~ Go vs Java 跟Java相⽐比,Go内存⽅方⾯面有⼀一些不同: • 指针更少 • ⼤大量的栈上分配 • ⼤大量的goroutine • 没有对象头 垃圾回收 • 并发->精确 • 是否分代?压缩?增量? Go1.5 GC • Go's new garbage collector is a concurrent0 码力 | 37 页 | 566.26 KB | 1 年前3Tracing in TiDB 浅谈全链路监控: 从应用到数据库到 Runtime
error) 让我们更近一步? 「我确实能看到的时间花在哪里了,但是为什么花了那么长时间?」 总所周知 灵魂拷问:「到底是我的 SQL 写得?,还是 Goroutine 调度不周?」 Network Ready Goroutine Wakeup 4.368ms go tool trace go tool trace ● 优点:好用,好看(UI) ● 缺点:性能损耗太大,不能一直开着 的原理是? Trace 会 Go Runtime 的代码中打桩收集 CPU time,在 Goroutine 开始执行时记录 start_run_time, 在调度退出执行时记录 end_run_time,累加 (end_run_time - start_run_time) 即为 这个 goroutine 的 CPU time。 A little bit about Go runtime https://learnku s-dev2 Tracing Runtime 伪代码 // Goroutine 开始运行时,记录开始信息 gp.lastSchedTime = nanotime() if gp.statCtx != nil { atomic.Xadd64(&gp.statCtx.schedtick, 1) } … // Goroutine 暂停运行时,收集执行时长 endTickTime := nanotime()0 码力 | 39 页 | 3.43 MB | 1 年前3Go 入门指南(The way to Go)
式来进行软件开发。它并不是要用奇怪的语法和晦 涩难懂的概念来从根本上推翻已有的编程语言,而是建立并改善了 C、Java、C# 中的许多语法风格。它提 倡通过接口来针对面向对象编程,通过 goroutine 和 channel 来支持并发和并行编程。 这本书是为那些想要学习 Go 这门全新的,迷人的和充满希望的编程语言的开发者量身定做的。当然,你 在学习 Go 语言之前需要具备一些关于编程的 或者面向对象编程语言的开发者,我们将会在本书中用 Go 和一些编程语言的相关概念进 行比较(书中会使用大家所熟知的缩写 “OO” 来表示面向对象)。 本书将会从最基础的概念讲起,同时也会讨论一些类似在应用 goroutine 和 channel 时有多少种不同的模 Go入门指南 - 1 - 本文档使用 看云 构建 式,如何在 Go 语言中使用谷歌 API,如何操作内存,如何在 Go 语言中进行程序测试和如何使用模板来 9 章)。 在本书的第三部分,你将会学习到如何处理不同格式的文件(第 12 章)和如何在 Go 语言中巧妙地使用 错误处理机制(第 13 章)。然后我们会对 Go 语言中最值得称赞的设计 goroutine 和 channel 进行并发 和多核应用的基本技巧的讲解(第 14 章)。最后,我们会讨论如何将 Go 语言应用到分布式和 Web 应用 中的相关网络技巧(第 15 章)。 我们会在本书的第四部分向你展示许多0 码力 | 380 页 | 2.97 MB | 1 年前3用Go语言实现推送服务器
• 高并发 – goroutine • 可靠性 – 使用Redis暂存消息 • 高性能 – 静态编译语言 • 支持水平扩展 – 使用RPC组成集群 • 无单点故障 – 使用Redis实现数据共享 Go语言的并发模型 • 事件驱动,共享线程池 runtime.GOMAXPROCS(runtime.NumCPU()) • 使用“go”命令创建goroutine go sockstore sockstore.Start() • goroutine使用channel交换消息 – 异步场景,直接往指定channel发送数据 – 同步场景,往channel发送的数据中,包含一 个获取返回值的channel 议程 • 推送服务器介绍 • 推送服务架构 • 部分代码 • 上线效果 逻辑架构 去中心化设计 • 客户端随机连接 • Redis集中存储地址表 • 信息发送2跳到达 消息缓存设计 串行场景-Socket Server • 在主程序启动时启动 • 所有请求都用一个goroutine响应 • 对外提供API,实质是往goroutine发送消 息 并行场景-TCP Server • 在有socket连接时创建 • 为每个socket创建一个goroutine • 用心跳维持,超时关闭socket,同时退出 goroutine • 用全局字典,查找clientID对应的socket 议程0 码力 | 25 页 | 260.04 KB | 1 年前3可视化学习 Go 并发编程
对并发有很好的支持 Go 语言中的并发 goroutine - 并发执行 channel - 同步和消息传输 select - 多路并发控制 Goroutine 类似于 UNIX 中的 & 很像线程,但更轻量 一个 goroutine 就是一个独立运行的函数 当一个 goroutine 阻塞时,所在的线程会阻塞,但其它 goroutine 不受影响 f("hello", "world") <- time.Now() // 将时间发送给timerChan }() // 做一些其它事情;准备接收 // 接收会阻塞,直到 timerChan 传送值 // 值的发送是另上个 goroutine 结束的时间 completedAt := <-timerChan Select 类似于 switch 但它的判断条件是基于通信,而不是基于值的等量匹配 select { case package main func main() { // 创建一个 int 类型的 channel ch := make(chan int) // 启动一个新的匿名 goroutine go func() { // 发送 42 给 channel ch <- 42 }() // 从 channel 读取 <-ch }0 码力 | 29 页 | 1.48 MB | 1 年前3
共 65 条
- 1
- 2
- 3
- 4
- 5
- 6
- 7