我们有一个服务跑在微软云的所有宿主机上。最近发现某一台机器上该服务进程持续崩溃。
崩溃原因是访问了一个无效指针,对应的代码如下

serviceListIniBuffer.AppendF("ServerList=%s\r\n",
                                               m_newServiceList.config->GetStringParameter("Manifest", "ServerList", "").c_str());

从dump和live repo中发现,无效指针的来自AppendF函数的第一个参数。
但奇怪的,该参数是一个写死的字符串,这怎么会发生呢?

看汇编代码

00007ff6`36961907 4889442420 mov qword ptr [rsp+20h],rax
00007ff6`3696190c 4c8d0d45270b00 lea r9,[GetAndRunServices!`string'+0xfd8 (00007ff6`36a14058)]
00007ff6`36961913 4c8d054e270b00 lea r8,[GetAndRunServices!`string'+0xfe8 (00007ff6`36a14068)]
00007ff6`3696191a 488d5500 lea rdx,[rbp]
00007ff6`3696191e 488b8f98030000 mov rcx,qword ptr [rdi+398h]
00007ff6`36961925 e8f649f3ff call GetAndRunServices!apsdk::configuration::IConfiguration::GetStringParameter (00007ff6`36896320)
00007ff6`3696192a 90 nop
00007ff6`3696192b 4883781810 cmp qword ptr [rax+18h],10h
00007ff6`36961930 7203 jb GetAndRunServices!GetAndRunServices2::GenerateOMNewServiceListFile+0x9e5 (00007ff6`36961935)
00007ff6`36961932 488b00 mov rax,qword ptr [rax]
00007ff6`36961935 4c8bc0 mov r8,rax
00007ff6`36961938 488d1541270b01 lea rdx,[00007ff6`37a14080]
00007ff6`3696193f 488d4d20 lea rcx,[rbp+20h]
>>>>>>>>>>>>>>>>>>>>00007ff6`36961943 e8981ef3ff call GetAndRunServices!apsdk::DynStringT<127>::AppendF (00007ff6`368937e0)

具体的崩溃发生在AppendF里面。但问题是无效指针导致的,和被调函数AppendF无关。为了省略篇幅就略过AppendF部分了。

这里可以看到,rcx应该保存的是serviceListIniBuffer的this指针。因为C默认从右向左压参数,所以rdx对应的应该是第一个参数,r8对应的应该是第二个参数。

0:000> da r8
00000001`0a3a48c0 "25.66.164.187:25.66.164.4:25.66."
00000001`0a3a48e0 "164.251:25.66.165.4"

0:000> da rdx
00007ff6`37a14080 "????????????????????????????????"

果然,rdx就是无效啊。

仔细看一下前面的汇编,比如在调用GetStringParameter的时候,也会用到写死的字符串。比如下面两句就是
00007ff6`3696190c 4c8d0d45270b00 lea r9,[GetAndRunServices!`string'+0xfd8 (00007ff6`36a14058)]
00007ff6`36961913 4c8d054e270b00 lea r8,[GetAndRunServices!`string'+0xfe8 (00007ff6`36a14068)]

可以看到,这些字符串都是从GetAndRunServices!`string'这个全局表里面读入的。 这两个地址也都准确落入了执行文件的地址范围:
0:000> lmf
start end module name
00007ff6`36880000 00007ff6`36bda000 GetAndRunServices C:\App\getandrunservices.ap_10_09_10_8_5003_2510\GetAndRunServices.exe

而出问题的地址是00007ff6`37a14080,的确也在执行文件地址范围外。
但仔细看一下,00007ff6`37a14080这个地址和合法区间比较,只有一个bit不一样:
00007ff6`3[7]a14080 00007ff6`3[6]a14080
这里7和6在二进制上面就差了末尾的bit。 如果我手动换一成6看看呢:

0:000> da 00007ff6`36a14080
00007ff6`36a14080 "ServerList=%s.."

果然就和源代码match了。

这个迷如何解释呢?首先可能的是这个执行文件有损害。但是现在执行文件默认都有完整性和签名保护,可能性不大。把文件拷贝出来和其它没有问题的文件比,的确也一模一样。
还可能是病毒?但是云上的宿主机器都是绝对隔离的。从live debug过程中看,没见到用户态有什么注入。
剩下的原因是硬件问题。内存或者CPU读取流水线遇上某二进制规律的时候触发数据损坏。

这就是我目前的推断。下周和有经验的工程师聊一下看看这样分析对不对。以前也遇上过疑似硬件问题导致的崩溃,但今天是第一次现场抓住!
如果你有类似经历或者经验,请指点和分享。

疑似CPU或者内存故障导致进程崩溃的更多相关文章

  1. inux如何查看当前占用CPU或内存最多的进程

    一.可以使用以下命令查使用内存最多的进程 方法1: ps -aux | sort -k4nr | head -K 如果是10个进程,K=10,如果是最高的三个,K=3 说明:ps -aux中(a指代a ...

  2. 查看占用cpu和内存最多的进程

    linux下获取占用CPU资源最多的10个进程,可以使用如下命令组合: ps aux|head -;ps aux|grep -v PID|sort -rn -k +|head linux下获取占用内存 ...

  3. linux系统PS命令,按CPU、内存使用率对进程排序

    https://blog.csdn.net/weixin_42123737/article/details/90081318

  4. W3wp.exe占用CPU及内存资源

    问题背景 最近使用一款系统,但是经常出现卡顿或者用户账号登录不了系统.后来将问题定位在了服务器中的“w3wp.exe”这个进程.在我们的用户对系统进行查询.修改等操作后,该进程占用大量的CPU以及内存 ...

  5. 线程崩溃为什么不会导致 JVM 崩溃

    大家好,我是坤哥 网上看到一个很有意思的据说是美团的面试题:为什么线程崩溃崩溃不会导致 JVM 崩溃,这个问题我看了不少回答,但都没答到根本原因,所以决定答一答,相信大家看完肯定会有收获,本文分以下几 ...

  6. linux的PS进程和作业管理(进程调度,杀死进程和进程故障-僵尸进程-内存泄漏)

     Ps进程和作业管理 1.查看进程ps 1.格式 ps   ---查看当前终端下的进程 3种格式: SYSV格式   带 - 符号 BSD格式  不带 - 符号 GNU格式   长选项 2.ps -a ...

  7. 如何按名称或PID查找一个进程?如何按端口号查找一个进程?如何查看一个进程的CPU和内存、文件句柄使用情况?如何查看CPU利用率高的TOP10进程清单?如何根据PID强制终止进程?

    如何按名称或PID查找一个进程?如何按端口号查找一个进程?如何查看一个进程的CPU和内存.文件句柄使用情况?如何查看CPU利用率高的TOP10进程清单? 目录 如何按名称或PID查找一个进程?如何按端 ...

  8. Linux(CentOS) 如何查看当前占用CPU或内存最多的K个进程

    一.可以使用以下命令查使用内存最多的K个进程 方法1: ps -aux | sort -k4nr | head -K 如果是10个进程,K=10,如果是最高的三个,K=3 说明:ps -aux中(a指 ...

  9. Linux如何查看当前占用CPU或内存最多的K个进程

    一.可以使用以下命令查使用内存最多的K个进程 方法1: ps -aux | sort -k4nr | head -K 如果是10个进程,K=10,如果是最高的三个,K=3 说明:ps -aux中(a指 ...

随机推荐

  1. 想到一个赚钱的APP

    通过APP上发布调查问卷的需求,鼓励人们注册,并给与一定的报酬.需求主要面向一些调查问卷,一类的需求发布

  2. C# 如何添加Word文本和图片超链接

    超链接简单来讲就是内容链接,通过设置超链接可以实现对象与网页.站点之间的连接.链接目标可以是网页.图片.邮件地址.文件夹或者是应用程序.设置链接的对象可以是文本或者图片. 在以下内容中,我将介绍如何用 ...

  3. Python GUI - Tkinter tkMessageBox

    Python GUI - Tkinter tkMessageBox: tkMessageBox模块用于显示在您的应用程序的消息框.此模块提供了一个功能,您可以用它来显示适当的消息     tkMess ...

  4. Echarts数据可视化series-heatmap热力图,开发全解+完美注释

    全栈工程师开发手册 (作者:栾鹏) Echarts数据可视化开发代码注释全解 Echarts数据可视化开发参数配置全解 6大公共组件详解(点击进入): title详解. tooltip详解.toolb ...

  5. memcached+狀態模式+工廠方法使用

    using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.T ...

  6. Babylon.GUI官方文档翻译

    Babylon.GUI是一个基于Babylon.js的WebGL库,可以用来在WebGL3D场景中生成交互性UI与动态纹理.相比于html ui,Babylon.GUI的功能较为简化,但使用起来也更加 ...

  7. win10 uwp 隐藏实时可视化

    新的vs有个功能,实时可视化 但是他会挡我们界面,想要隐藏 点击转到实时可视化,就是点击横线看到,接着就可以看到下面的选项 点击在应用程序中显示运行时,就是不选中 很简单就看到,没有那个 本作品采用知 ...

  8. python 基础大纲

    机器语言: 特点:计算机能够看懂的0和1去写程序 优点:程序运行速度快 缺点:开发效率低 汇编语言: 特点:用一些英文标签代替一串而精致数字去写程序 优点:比机器语言好一点,操作系统内大量使用汇编语言 ...

  9. HTML之事件处理程序

    HTML事件 <body> <input type="button" value="按钮1" id="but1" oncl ...

  10. vim下单行长文本的时候卡顿解决办法

    在vim编辑文件时,若单行过长,可能会导致vim卡顿,严重影响使用体验 估计是syntax匹配效率过滥导致.. 偶尔发现了一个临时的解决办法就是关掉syntax然后再打开,即在命令模式下 :synta ...