记一次 .NET某设备监控自动化系统 CPU爆高分析
一:背景
1. 讲故事
先说一下题外话,一个监控别人系统运行状态的程序,结果自己出问题了,有时候想一想还是挺讽刺的,哈哈,开个玩笑,我们回到正题,前些天有位朋友找到我,说他们的系统会偶发性CPU爆高,CPU上去了就下不来了,让我帮忙看一下怎么回事,而且自己也分析过了,没找到哪里有问题,写监控的都是高手,给我的第一感觉就是这个dump可能解决起来不容易,不管怎么说,有了dump就开干吧!
二:WinDbg 分析
1. CPU真的爆高吗
作为调试人,第一准则就是不要轻信任何人透露给你的信息,因为人家在这块是一个小白,往往他的信息会把你带偏,我们只相信数据即可,切记!!! 所以我们先用 !tp 观察下CPU使用率。
0:198> !tp
CPU utilization: 100%
Worker Thread: Total: 197 Running: 42 Idle: 154 MaxLimit: 32767 MinLimit: 8
Work Request in Queue: 0
--------------------------------------
Number of Timers: 0
--------------------------------------
Completion Port Thread:Total: 10 Free: 5 MaxFree: 16 CurrentLimit: 10 MaxLimit: 1000 MinLimit: 8
从卦中信息看当前 CPU=100%,还是蛮惨的,那到底谁在吃CPU资源呢?根据经验先查一下是不是触发了2代GC,接下来用 !t 观察下是否有GC标记。
0:198> !t
ThreadCount: 214
UnstartedThread: 0
BackgroundThread: 211
PendingThread: 0
DeadThread: 1
Hosted Runtime: noLock ID OSID ThreadOBJ State GC Mode GC Alloc Context Domain Count Apt Exception0 1 276f0 000002789526b5f0 2a020 Preemptive 0000000000000000:0000000000000000 000002789525e840 0 MTA 2 2 25e5c 0000027895296d00 2b220 Preemptive 0000000000000000:0000000000000000 000002789525e840 0 MTA (Finalizer) 3 3 260e8 00000278ae35f0c0 202b020 Preemptive 0000000000000000:0000000000000000 000002789525e840 0 MTA ...169 2113 10c20 00000278c26766c0 1029220 Preemptive 00000278B5D7D188:00000278B5D7D188 000002789525e840 1 MTA (GC) (Threadpool Worker) xxxException 00000278b5d46ce0...
尼玛从卦中的 (GC) 来看,还真的触发了GC,接下来的研究方向就是洞察下是不是CPU爆高的祸首。
2. GC触发导致的吗
要寻找这个问题的答案,首先就是看下这次GC是不是 FullGC 即可,可以切到 169 号线程,观察下线程栈。
0:169> k 10# Child-SP RetAddr Call Site
00 000000c4`36ffb798 00007ffc`d5f14313 ntdll!NtWaitForSingleObject+0x14
01 000000c4`36ffb7a0 00007ffc`c927cb27 KERNELBASE!WaitForSingleObjectEx+0x93
02 000000c4`36ffb840 00007ffc`c927cadf clr!CLREventWaitHelper2+0x3c
03 000000c4`36ffb880 00007ffc`c927ca5c clr!CLREventWaitHelper+0x1f
04 000000c4`36ffb8e0 00007ffc`c926bd32 clr!CLREventBase::WaitEx+0x7c
05 000000c4`36ffb970 00007ffc`c9269bc4 clr!ThreadSuspend::SuspendRuntime+0x32c
06 000000c4`36ffba60 00007ffc`c91814e3 clr!ThreadSuspend::SuspendEE+0x128
07 000000c4`36ffbb60 00007ffc`c9185f51 clr!WKS::GCHeap::GarbageCollectGeneration+0xb7
08 000000c4`36ffbbc0 00007ffc`c9260f56 clr!WKS::gc_heap::trigger_gc_for_alloc+0x2d
09 000000c4`36ffbc00 00007ffc`c6b0f7e7 clr!JIT_NewArr1+0xa97
0a 000000c4`36ffc030 00007ffc`6a388270 mscorlib_ni!System.String.ToCharArray+0x27 [f:\dd\ndp\clr\src\BCL\system\string.cs @ 758]
0b 000000c4`36ffc080 00007ffc`6a3880ed 0x00007ffc`6a388270
0c 000000c4`36ffc100 00007ffc`6a56056d 0x00007ffc`6a3880ed
0d 000000c4`36ffc150 00007ffc`6a3cd749 0x00007ffc`6a56056d
0e 000000c4`36ffc1b0 00007ffc`c911989d 0x00007ffc`6a3cd749
0f 000000c4`36ffc220 00007ffc`c9119764 clr!ExceptionTracker::CallHandler+0xfd
从卦中看此时的GC还处于早期的 SuspendEE 阶段,无法获取内部的 settings 结构,这就比较麻烦了,那怎么办呢?只能看看 GarbageCollectGeneration 的第一个参数有没有保存在栈中,要是没有就惨了。。。方法签名如下:
size_t
GCHeap::GarbageCollectGeneration (unsigned int gen, gc_reason reason)
{}
根据 x64调用协定,gen是保存在 rdx 寄存器里,接下来观察汇编代码。
0:000> uf 00007ffc`c91814e3
clr!WKS::GCHeap::GarbageCollectGeneration:
00007ffc`c918142c 48895c2418 mov qword ptr [rsp+18h],rbx
00007ffc`c9181431 89542410 mov dword ptr [rsp+10h],edx
00007ffc`c9181435 48894c2408 mov qword ptr [rsp+8],rcx
00007ffc`c918143a 55 push rbp
00007ffc`c918143b 56 push rsi
00007ffc`c918143c 57 push rdi
00007ffc`c918143d 4154 push r12
00007ffc`c918143f 4155 push r13
00007ffc`c9181441 4156 push r14
00007ffc`c9181443 4157 push r15
...0:169> dd 000000c4`36ffbbc0-0x8+0x10 L1
000000c4`36ffbbc8 00000000
从卦中看,谢天谢地,edx保存在 rsp+10h 的位置,通过dp观察内存地址的值发现是0,也就表示当前是 0 代GC,这种smallgc 经常触发是很正常的,并不是我们CPU爆高的诱因,接下来就陷入迷茫了。。。
3. 路在何方
撞了南墙之后得要看看其他路子,其实刚才用 !t 观察线程列表的时候我就注意到一个特征,那就是很多线程上挂了异常,截图如下:

从卦中看此时有19个线程在抛 xxxResultException 异常,做过开发的朋友都知道,如果频繁的抛异常是很耗CPU资源的,因为它要设计到用户态到内核态的切换,如果有 19 个线程一起抛异常,那绝对是一个灾难。。。
有些朋友说我cpu猛一点是不是就可以了,哈哈,理论上是可以的,可以用 !cpuid 观察下这台机器的cpu核心数。
0:169> !cpuid
CP F/M/S Manufacturer MHz0 6,167,1 <unavailable> 34081 6,167,1 <unavailable> 34082 6,167,1 <unavailable> 34083 6,167,1 <unavailable> 34084 6,167,1 <unavailable> 34085 6,167,1 <unavailable> 34086 6,167,1 <unavailable> 34087 6,167,1 <unavailable> 3408
从证据链的完整性上来说,其实这里还需要再做一个验证,就是19个线程抛异常不代表他们的并发性,言外之意就是能不能再找一些其他证据,怎么找其他证据呢?
做C#开发的朋友应该知道,Exception 属于引用类型,如果密集抛了很多异常,那托管堆上自然就有很多,直到GC回收,所以我们观察下这个时间差即可,使用 !wdae 命令,这里为了隐私性我就模糊了哈。
0:169> !wdae384 of Type: xxxResultException 000002789fdb6478 000002789fdb69b0 000002789fdb9848
Message: xxxFailed
Inner Exception: (none)
Stack:
IP Function
00007ffc6a269861 xxx.ChannelAsyncOperation`1[[System.Int32, mscorlib]].End(Int32, Boolean)
...411 of Type: xxxResultException 000002789fdb6e90 000002789fdb7090 000002789fdb72a8
Message: xxxClosed
Inner Exception: (none)
Stack:
IP Function
00007ffc6a269861 xxx.ChannelAsyncOperation`1[[System.Int32, mscorlib]].End(Int32, Boolean)
...
808 Exceptions in 12 unique type/stack combinations (duplicate types in similar stacks may be rethrows)
从卦中看当前抛了808个异常,大多是和channel通信有关,结合16个线程并发抛,这就稳了,看样子cpu爆高期间就是由于高频的抛异常所致,分析出这些信息之后,就是告诉朋友把这些异常给解决掉即可。
三:总结
CPU爆高的诱因非常多,高频的抛异常就属于其中一例,其实这种通信时发生了突发异常正是 Polly 这种 弹性和瞬态故障处理库 大显身手的地方。
相关文章:
记一次 .NET某设备监控自动化系统 CPU爆高分析
一:背景 1. 讲故事 先说一下题外话,一个监控别人系统运行状态的程序,结果自己出问题了,有时候想一想还是挺讽刺的,哈哈,开个玩笑,我们回到正题,前些天有位朋友找到我,说…...
大数据与云计算
目录 一、大数据时代二、云计算——大数据的计算三、云计算发展现状四、云计算实现机制五、云计算压倒性的成本优势 一、大数据时代 我们先来看看百度关于 “大数据”(Big Data)的搜索指数。 可以看出,“大数据” 这个词是从2012年才引起关注…...
一. 并行处理与GPU体系架构-并行处理简介
目录 前言0. 简述1. 串行处理与并行处理的区别2. 并行执行3. 容易混淆的几个概念4. 常见的并行处理总结参考 前言 自动驾驶之心推出的 《CUDA与TensorRT部署实战课程》,链接。记录下个人学习笔记,仅供自己参考 本次课程我们来学习下课程第一章——并行处…...
vb机试考试成绩分析与统计,设计与实现(高数概率统计)-141-(代码+程序说明)
转载地址http://www.3q2008.com/soft/search.asp?keyword141 前言: 为何口出狂言,作任何VB和ASP的系统, 这个就是很好的一个证明 :) 又有些狂了... 数据库操作谁都会,接触的多了也没什么难的,VB编程难在哪?算法上,这个是一个算法题的毕业设计,里面涉及到对试卷的 平均分,最…...
Arm MMU深度解读
文章目录 一、MMU概念介绍二、虚拟地址空间和物理地址空间2.1、(虚拟/物理)地址空间的范围2.2、物理地址空间有效位(范围) 三、Translation regimes四、地址翻译/几级页表?4.1、思考:页表到底有几级?4.2、以4KB granule为例,页表的…...
2024 年 AI 辅助研发趋势
在2024年,AI辅助研发的应用趋势将非常广泛。举个例子,比如在医疗健康领域,AI将深度参与新药研发、早期癌症研究以及辅助诊断等,助力医疗技术的突破。同时,在农业领域,AI也将通过无人机、智能装备等方式&…...
聊聊pytho中的函数
Python中的函数 一、Python中函数的作用与使用步骤 1、为什么需要函数 在Python实际开发中,我们使用函数的目的只有一个“让我们的代码可以被重复使用” 函数的作用有两个: ① 代码重用(代码重复使用) ② 模块化编程&#x…...
Python中starmap有什么用的?
目录 前言 starmap函数的作用 starmap函数的用法 starmap函数的示例 1. 对每个元组元素进行求和 2. 对每个元组元素进行乘积 实际应用场景 1. 批量处理函数参数 2. 并行处理任务 3. 批量更新数据库 总结 前言 在Python中, starmap 是一个非常有用的函数&…...
面向切面编程 AOP
提示:主要内容参考动力节点老杜的Spring6讲义。 面向切面编程 AOP 一、AOP介绍二、AOP的七大术语三、切点表达式 IoC使软件组件松耦合。AOP让你能够捕捉系统中经常使用的功能,把它转化成组件。AOP(Aspect Oriented Programming)&a…...
POS 之 奖励机制
为什么需要有奖惩机制 如果没有奖励,就不会有节点参与POS,运营节点有成本,而奖励正是让运营者获利的方式 如果没有惩罚,网络上会充斥着很多无效节点,会扰乱甚至破坏网络 所有奖励和惩罚在每个 Epoch 实施一次 奖励 什…...
Unity类银河恶魔城学习记录9-7 p88 Crystal instead of Clone源代码
Alex教程每一P的教程原代码加上我自己的理解初步理解写的注释,可供学习Alex教程的人参考 此代码仅为较上一P有所改变的代码 【Unity教程】从0编程制作类银河恶魔城游戏_哔哩哔哩_bilibili Blackhole_Skill_Controller.cs using System.Collections; using System…...
导出RWKV模型为onnx
测试模型: https://huggingface.co/RWKV/rwkv-5-world-3b 导出前对modeling_rwkv5.py进行一个修改: # out out.reshape(B * T, H * S) out out.reshape(B * T, H * S, 1) # <<--- modified out F.group_norm(out, nu…...
【LeetCode】整数转罗马数字 C语言 | 此刻,已成艺术(bushi)
Problem: 12. 整数转罗马数字 文章目录 思路解题方法复杂度Code 思路 暴力破解 转换 解题方法 由思路可知 复杂度 时间复杂度: O ( n ) O(n) O(n) 空间复杂度: O ( 1 ) O(1) O(1) Code char* intToRoman(int num) {char *s (char*)malloc(sizeof(char)*4000), *p s;while(…...
移动App开发常见的三种模式:原生应用、H5移动应用、混合模式应用
引言 在移动应用市场的迅猛发展中,移动App开发正日益成为技术创新和用户体验提升的焦点。对于开发者而言,选择适合自己项目的开发模式成为至关重要的决策。本文将探究移动App开发的三种常见模式:原生应用、H5移动应用和混合模式应用。这三种…...
k8s Secret配置资源,ConfigMap 存储配置信资源管理详解
目录 一、Secret 概念 三种Secret类型 pod三种使用secret的方式 应用场景:凭据: 二、 示例 2.1、用kubectl create secret命令创建 Secret 创建Secret: 查看Secret列表: 描述Secret: 2.2、用 base64 编码&…...
POS 之 最终确定性
Gasper Casper 是一种能将特定区块更新为 最终确定 状态的机制,使网络的新加入者确信他们正在同步规范链。当区块链出现多个分叉时,分叉选择算法使用累计投票来确保节点可以轻松选择正确的分叉。 最终确定性 最终确定性是某些区块的属性,意味…...
Vue快速开发一个主页
前言 这里讲述我们如何快速利用Vue脚手架快速搭建一个主页。 页面布局 el-container / el-header / el-aside / el-main:https://element.eleme.cn/#/zh-CN/component/container <el-container><el-header style"background-color: #4c535a"…...
Java SE入门及基础(33)
final 修饰符 1. 应用范围 final 修饰符应该使用在类、变量以及方法上 2. final 修饰类 Note that you can also declare an entire class final. A class that is declared final cannot be subclassed. This is particularly useful, for example, when creating an imm…...
ChatGPT逐步进入留学圈但并不能解决留学规划的问题
2022 年底,一个能像人类一样对话的AI软件ChatGPT,在5天内突破一百万用户,风靡全球,如今用户已达1.8亿。 四个月后,ChatGPT进化为GPT4版本。该版本逻辑、数学推理能力卓越。拿留美标准化考试举例,GPT4能够在…...
WebGL之灯光使用解析
在使用灯光之前,首先我们需要了解,与定义更广泛的 OpenGL 不同,WebGL 并没有继承 OpenGL 中灯光的支持。所以你只能由自己完全得控制灯光。幸运得是,这也并不是很难,本文接下来就会介绍完成灯光的基础。 在 3D 空间中…...
3分钟解锁Illustrator批量替换魔法:告别重复劳动的终极指南
3分钟解锁Illustrator批量替换魔法:告别重复劳动的终极指南 【免费下载链接】illustrator-scripts Adobe Illustrator scripts 项目地址: https://gitcode.com/gh_mirrors/il/illustrator-scripts 你是否曾经面对过这样的场景?客户要求将设计稿中…...
VMware虚拟机版本兼容性问题:手动修改vmx和vmdk文件实战指南
1. 虚拟机版本兼容性问题解析 第一次遇到VMware虚拟机打不开的报错时,我整个人都懵了。明明昨天还能正常使用的虚拟机,今天突然提示"此虚拟机是由较新版本的VMware创建的",这种场景相信很多开发者都遇到过。问题的本质在于高版本VM…...
PyTorch实战:用CrossEntropyLoss的weight和label_smoothing解决类别不平衡与过拟合
PyTorch实战:用CrossEntropyLoss的weight和label_smoothing解决类别不平衡与过拟合 当你面对医学影像分类任务时,数据集中正常样本占比90%,而病变样本仅占10%。训练后的模型对所有样本都预测为正常类别,准确率看似很高却完全无法识…...
如何在3分钟内掌握ETCD Keeper:新手必看的etcd可视化管理快速入门指南
如何在3分钟内掌握ETCD Keeper:新手必看的etcd可视化管理快速入门指南 【免费下载链接】etcdkeeper web ui client for etcd 项目地址: https://gitcode.com/gh_mirrors/et/etcdkeeper ETCD Keeper是一款专为etcd设计的轻量级Web UI客户端工具,能…...
让PS4/PS5手柄在Windows上重获新生:DS4Windows完全指南
让PS4/PS5手柄在Windows上重获新生:DS4Windows完全指南 【免费下载链接】DS4Windows Like those other ds4tools, but sexier 项目地址: https://gitcode.com/gh_mirrors/ds/DS4Windows 你是否曾经遇到过这样的烦恼:心爱的PlayStation手柄在Windo…...
AI头像生成器效果分享:100+真实生成案例——古风人物Prompt高质量展示
AI头像生成器效果分享:100真实生成案例——古风人物Prompt高质量展示 1. 古风头像生成效果惊艳亮相 最近体验了一款基于Qwen3-32B的AI头像生成器,专门用来创作各种风格的头像创意文案。让我最惊喜的是它在古风人物生成方面的表现——只需要简单描述你想…...
27,000张卫星影像:EuroSAT如何重塑遥感图像分类新标准
27,000张卫星影像:EuroSAT如何重塑遥感图像分类新标准 【免费下载链接】EuroSAT EuroSAT: Land Use and Land Cover Classification with Sentinel-2 项目地址: https://gitcode.com/gh_mirrors/eu/EuroSAT EuroSAT是一个基于Sentinel-2卫星影像的开源遥感数…...
H5年会抽奖实战:手机号与微信头像双模式实现
1. 为什么选择H5实现年会抽奖 每到年底,企业年会就成了大家最期待的活动之一。作为技术人,我们总想用些新花样让抽奖环节更有趣。去年我负责公司年会抽奖系统开发时,就遇到了一个典型需求:既要支持传统的手机号抽奖,又…...
用Python和PyTorch复现CVPR2019 DIM攻击:如何通过随机缩放和填充提升对抗样本的‘黑盒’攻击力
用Python和PyTorch实战CVPR2019 DIM攻击:从理论到代码的完整实现指南 对抗样本研究领域近年来发展迅猛,而CVPR2019提出的DIM(Diverse Input Method)方法因其出色的黑盒攻击能力成为经典。本文将带您从零开始,用PyTorch…...
基于Simulink的超外差单边带接收机建模与动态仿真分析
1. 超外差单边带接收机基础原理 第一次接触超外差接收机时,我被它的"变频"概念搞得一头雾水——为什么要把信号变来变去?后来在调试收音机电路时才恍然大悟:这就好比把不同尺寸的快递包裹统一放到标准传送带上处理。具体来说&#…...
