☰
Oracle RAC日志地图与故障排查:从GI到ASM的日志路径详解
2026/10/9 3:51:17 网站建设 项目流程

凌晨两点被监控电话叫醒,RAC某个节点被集群驱逐,业务侧报错蜂拥而至,登录服务器看到CRS资源一片红。干过Oracle RAC运维的人,基本都经历过这种场面。真正拉开差距的不是你会不会重启,而是你能不能在三五分钟内判断:该看哪一本日志,日志里的哪几行字符才是关键证据。RAC架构下的故障调查和日志路径定位,就是这样一件“看着不起眼、做起来要命”的事。

这篇文章把我这些年摸出来的RAC日志地图和排查习惯整理出来,适合正在带RAC项目的DBA,也适合刚接触集群、对一堆日志目录还没建立起整体感觉的新手。目标是让你下次接到故障电话时,第一反应不是乱翻目录,而是按层、按节点、按时间线有序排查。

1. 为什么要先建立RAC日志地图

1.1 单实例日志思维为什么不够用

单实例Oracle出问题,Alert Log加Trace文件基本就是全部答案,最多再看一眼监听日志和操作系统日志,半小时内能把来龙去脉理清楚。

但RAC完全不是这套玩法。RAC多了一层集群件(GI,Grid Infrastructure),还多了节点间的心跳网络、共享存储、ASM实例、SCAN监听,任何一个环节出问题,都会同时在不同日志里留下片段。你可能会遇到这种情况:ocssd.log里记着节点被驱逐,crsd.log里记着资源被关闭,实例alert里只留下IPC通信报错,监听日志里全是连接失败,OS messages里还能看到网卡丢包记录——每本日志都有内容,但没有一本能独立讲完整个故事。

所以RAC排障的第一原则是:先分层,再分节点。你脑子里必须有一张日志地图,知道故障发生时应该扑向哪一层、哪一个文件。

1.2 RAC日志分层的整体框架

我习惯把RAC的日志体系分成五层,排障时按这个顺序逐层推进:

层次主要路径/文件核心内容典型场景
集群件层(GI)$GRID_HOME/log/<节点名>/CRS、CSS、EVM、GIPC、mDNS等组件日志节点驱逐、资源切换、集群无法启动
数据库实例层$ORACLE_BASE/diag/rdbms/<db_unique_name>/<实例名>/trace/实例alert、前台/后台traceORA错误、性能问题、坏块
ASM层$ORACLE_BASE/diag/asm/+asm/<asm实例名>/trace/磁盘组挂载、ASM实例状态、I/O错误ASM磁盘组dismount、存储链路异常
监听层$ORACLE_BASE/diag/tnslsnr/<节点名>/连接建立、拒绝、超时业务连不上、SCAN VIP异常
操作系统层/var/log/messages、dmesg、journalctl内存、网络、存储、NTP、OOM私网丢包、内存耗尽、时钟跳变

这张地图不需要死记硬背,但至少要形成条件反射:看到“节点驱逐”先想到ocssd和GI alert,看到“资源offline”先想到crsd,看到“连接失败”先想到监听日志和网络层。

2. 集群件(GI)层日志路径详解

2.1 GI日志的根目录:$GRID_HOME/log

GI日志不放在ADR里,它独立放在GI安装目录下,结构是:

$GRID_HOME/log/<节点名>/

GRID_HOME在不同版本里位置不一样,常见的有/u01/app/11.2.0/grid、/u01/app/19.0.0/grid、/u01/app/grid等。你需要先用grid用户确认环境变量:

echo $GRID_HOME echo $ORACLE_HOME

注意:在grid用户下,ORACLE_HOME通常就是GRID_HOME。好多人排障时用oracle用户登录,环境变量指向数据库软件的ORACLE_HOME,结果一个劲儿在数据库软件目录里找集群日志,自然找不到。这是第一个容易踩的坑。

进入$GRID_HOME/log/<节点名>/,你会看到以下核心文件:

文件/目录进程对应关注点
alert.log集群级告警所有重大事件的汇总入口
crsd/crsd.logCluster Ready Services资源状态变迁、OCR访问
cssd/ocssd.logCluster Synchronization Services节点成员关系、心跳、驱逐
evmd/evmd.logEvent Manager事件发布、FAN通知
gipcd/gipcd.logGrid IPC私网通信、网络心跳
mdnsd/mdnsd.logmDNS集群名称解析、GNS相关
ohasd/ohasd.logOracle High Availability Services集群启动第一阶段
agent/crsd/各类资源Agentora.*资源启动/停止/故障转移

2.2 排障首选的集群alert与组件日志

集群alert.log是第一个要打开的文件。它不像数据库alert那样记录SQL和内部错误,而是记录集群层面的关键事件:节点加入/离开、资源状态变化、OCR切换、ASM磁盘组挂载失败等。节点驱逐发生之前,这里通常已经写了原因相关的提示。

ocssd.log是节点驱逐调查的重头。CSS进程负责维护节点成员关系,私网心跳断了、磁盘心跳异常、misscount超时,都可能导致一个节点被另一个节点强制驱逐。在这个文件里搜这些关键词:

grep -iE "evict|reboot|not reachable|misscount|timeout" \ $GRID_HOME/log/$(hostname -s)/cssd/ocssd.log

如果看到clssnmPollingThread这类条目,基本可以确定是心跳层面的问题,接下来去查私网、防火墙、网卡驱动。

crsd.log记录资源层的动作。比如某个节点的ora.db1.db资源突然offline,或者VIP failover到另一节点,都能在这里找到来龙去脉。常见错误如File not found、OCR initialization failed等,会直接指向OCR或文件权限问题。

gipcd.log和mdnsd.log是网络排查的关键配角。私网通信异常时,gipcd.log里会出现GIPC_retry、connection timed out之类信息;mDNS解析出问题则可能表现为节点无法加入集群、SCAN VIP解析异常。很多RAC隐患其实早就在这两个日志里有了苗头,只是平时没人看。

2.3 动态获取GI日志位置与配套命令

路径记不准时,用命令动态获取状态信息,比死记硬背可靠:

# 查看集群资源整体状态 crsctl stat res -t # 查看OCR备份情况 ocrconfig -showbackup # 检查OCR完整性 ocrcheck # 查看votedisk位置 crsctl query css votedisk

另外,如果是安装或升级后集群起不来,还要看配置日志目录:

$GRID_HOME/cfgtoollogs/

比如crsinstall子目录下的crsinstall_crs_<节点名>.log,记录了root.sh执行过程中每个步骤的结果。19c安装脚本卡住时,这个文件往往比任何排障日志都直接。

3. 数据库实例与ASM层日志路径

3.1 实例ADR结构与alert日志

数据库实例的日志由ADR(Automatic Diagnostic Repository)管理,核心路径是:

$ORACLE_BASE/diag/rdbms/<db_unique_name>/<实例名>/trace/alert_<实例名>.log

以ORACLE_BASE=/u01/app/oracle、库名orcl、实例orcl1为例,完整路径是:

tail -f /u01/app/oracle/diag/rdbms/orcl/orcl1/trace/alert_orcl1.log

注意db_unique_name和实例名不一定相同,RAC里实例名一般是orcl1、orcl2这种带节点编号的,而db_unique_name就是数据库本身的名字。别拿实例名去匹配目录名,要用adrci确认。

最快的确认方式是用SQL直接查:

SELECT name, value FROM v$diag_info;

ADR Base那一行就是$ORACLE_BASE,Diag Trace那一行就是trace目录。也可以命令行下用adrci:

adrci adrci> show homes adrci> set home diag/rdbms/orcl/orcl1 adrci> show alert -tail 50

老系统(10g、11.1)没有完整ADR,实例日志在background_dump_dest和user_dump_dest指向的目录,一般可以在$ORACLE_HOME/rdbms/log附近找到。如果你接手的是老版本RAC,先show parameter dump_dest确认一下,别再按11.2以后的路径找。

3.2 ASM实例与监听日志

ASM实例的日志也在ADR下,结构类似:

$ORACLE_BASE/diag/asm/+asm/+asm1/trace/alert_+asm1.log

注意ASM实例名一般叫+ASM1、+ASM2,目录名里带加号。ASM disk group dismount、ASM实例异常重启、I/O错误,都从这本alert看起。比如ORA-15063表示ASM无法定位磁盘,ORA-15032表示磁盘组操作失败,这些错误会同时出现在ASM alert和OCR/集群日志里,需要交叉印证。

这里有个隐藏坑:ASM和数据库的ORACLE_BASE可能不是同一个。如果grid软件和oracle软件分开安装,ASM的$ORACLE_BASE通常是grid的路径,比如/u01/app/grid,而数据库实例的$ORACLE_BASE才是/u01/app/oracle。用oracle用户登录后直接按/u01/app/oracle找ASM日志,必然扑空。建议在grid用户下执行echo $ORACLE_BASE再看。

监听日志也在ADR体系里,但是独立的一类:

$ORACLE_BASE/diag/tnslsnr/<节点名>/listener/trace/listener.log

RAC还有SCAN监听,对应目录:

$ORACLE_BASE/diag/tnslsnr/<节点名>/listener_scan1/trace/listener_scan1.log

如果是老版本,监听日志可能在$ORACLE_HOME/network/log/。快速确认方法:

lsnrctl show log_directory

3.3 从alert到trace的推导线索

实例alert.log里记录ORA错误只是一个起点,真正的细节都在对应的trace文件里。看到ORA-600、ORA-3137这类错误时,alert里通常会标注类似Errors in file /u01/app/oracle/diag/rdbms/orcl/orcl1/trace/orcl1_ora_12345.trc的路径,直接打开这个trace文件。

排查SQL性能或存储过程问题时,也可以主动制造trace。比如:

ALTER SESSION SET EVENTS '10046 trace name context forever, level 12'; -- 执行目标SQL ALTER SESSION SET EVENTS '10046 trace name context off';

生成的trace文件会带着会话ID出现在实例trace目录里。RAC节点间负载均衡时,要先确认会话落在了哪个实例,再去对应节点的trace目录找文件。

4. 操作系统层日志与跨节点排查思路

4.1 系统日志里藏着RAC的“前传”

很多RAC故障的根因并不在Oracle层,而在操作系统。最常见的就是私网网卡问题、内存不足触发OOM killer、存储链路超时、NTP时钟跳变。这些都在系统日志里有记录。

Linux环境优先级最高的是:

/var/log/messages

排障时重点搜以下关键词:

grep -iE "out of memory|oom-killer|network|link down|NIC|ntp|time step" /var/log/messages

尤其要注意的是,RAC节点被驱逐很多时候是“果”,不是“因”。比如某节点内存耗尽触发OOM,导致CSS进程被杀,继而整个节点被集群驱逐。这种场景下,如果只盯着ocssd.log看,你会一直纠结“为什么心跳会断”,而实际上OS日志早就告诉你原因了。

另外,dmesg -T也是快速排查内核级问题的工具,特别是存储多路径和网卡收包异常:

dmesg -T | grep -iE "error|fail|timeout|scsi|eth"

4.2 RAC对时钟同步的敏感与日志佐证

RAC对节点间时钟偏差非常敏感。集群内时间不同步,轻则日志时间线混乱,重则影响事务一致性判断,甚至诱发节点驱逐。19c环境检查NTP/chrony状态:

timedatectl chronyc sources -v

如果OS日志里能看到类似时钟跳变、time step的信息,就要高度怀疑集群故障与时钟漂移有关。而且时钟不一致会直接影响你跨节点排查时的判断——同一个事件在两个节点日志里的时间戳不一样,会让人误以为事件顺序有问题。所以跨节点排查前,第一件事就是对两边的date输出。

4.3 跨节点时间线对照排查法

RAC排障不能只看单个节点,尤其节点驱逐类问题,必须同时拉出两个(甚至所有)节点的关键日志,按时间排列。

我常用的做法是把每个节点的关键事件抓出来,统一放到一个文件里排序:

for node in node1 node2; do ssh $node "grep -iE 'evict|reboot|error|alert' \ $GRID_HOME/log/$node/alert.log" | sed "s/^/[$node] /" done | sort

这样能快速看出:节点A在几点几分开始心跳异常,节点B在几点几分发起驱逐,节点A在几点几分才写实例alert。时间线一对齐,因果链就出来了。这一步看起来简单,但很多人排障时容易忽略,导致在单个节点的日志里反复打转。

5. 典型故障场景的日志速查与排查路线

5.1 节点驱逐:先看ocssd还是先看GI alert

节点驱逐是RAC最典型、也最让人头疼的故障。我的排查顺序是:

  1. 打开GI alert.log,看驱逐前后的集群事件描述,通常能拿到最粗的定位方向。
  2. 打开ocssd.log,搜evict、not reachable、misscount等关键词,确认是私网心跳问题还是磁盘心跳问题。
  3. 打开OS messages,确认网络、内存、存储有没有异常记录。
  4. 回到数据库alert,看实例退出的最后动作。

这里有个常见误区:一上来就翻数据库alert。数据库实例只是集群的“被管理者”,它往往是被动退出,日志里没有根因。根因大概率在集群层或OS层。

5.2 CRS资源异常与OCR故障

如果crsctl stat res -t看到资源反复offline、启动失败或处于UNKNOWN状态,处理路径是打开crsd.log:

tail -200 $GRID_HOME/log/$(hostname -s)/crsd/crsd.log

搜索关键词:error、failed、ocr、permission、cannot。

OCR相关故障比较隐蔽。OCR文件损坏或无法同步时,crsd.log里会出现OCR读取失败的信息。先用ocrcheck确认OCR完整性,再用ocrconfig -showbackup看自动备份。OCR自动备份默认放在$GRID_HOME/cdata/<节点名>/下,比如:

ls -l $GRID_HOME/cdata/$(hostname -s)/

如果OCR真的出了问题,可以用最近的备份恢复。需要提醒的是,OCR备份文件属于集群元数据,日常巡检时最好纳入备份监控,不要等故障了才发现备份都过期了。

5.3 监听异常:业务连不上的第一现场

RAC环境业务连接失败时,很多人第一反应是查应用、查防火墙,其实应该先看监听日志。连接失败、超时、拒绝,都会在listener.log里留下明确记录。

tail -200 $ORACLE_BASE/diag/tnslsnr/$(hostname -s)/listener/trace/listener.log

常见错误:

  • TNS-12537 TNS-12560:监听器自身异常或网络断开。
  • TNS-12514:服务名没有注册,可能要看实例是否注册到监听。
  • Connection timeout:可能涉及防火墙或私网质量。

如果是SCAN连接失败,除了看SCAN监听日志,还要检查DNS解析是否正常。SCAN VIP对应的域名解析结果必须包含所有节点,DNS只返回一个IP往往会导致单点故障。

5.4 ASM磁盘组与实例故障

ASM磁盘组dismount、ASM实例异常、存储链路故障,这三者经常串在一起。排查顺序是:

  1. ASM alert日志,比如alert_+asm1.log,搜ORA-15063、dismount、I/O error。
  2. ASM实例trace目录,确认具体是哪块磁盘、哪个ASM盘失败。
  3. 操作系统存储层日志,dmesg和/var/log/messages里搜multipath、io error、timeout,判断是HBA卡、光纤线还是存储设备问题。

实例启动失败时,数据库alert里通常能看到ORA-29701(cluster无法识别实例)、ORA-29740(实例心跳失败)之类错误,这些错误要和集群日志配合着看,单看任何一本都不完整。

5.5 常见故障日志速查表

故障现象优先查看日志关键搜索词辅助日志
节点驱逐GI alert + ocssd.logevict, not reachable, misscountOS messages, gipcd.log
CRS资源offlinecrsd.logerror, failed, OCRagent/crsd下日志
OCR损坏ocrcheck + crsd.logOCR, checksum, format$GRID_HOME/cdata备份
监听连接失败listener.log / scan监听日志TNS-12537, TNS-12514, timeout实例注册状态
ASM磁盘组dismountASM alertORA-15063, dismount, I/O errordmesg, multipath日志
实例启动失败实例alert + traceORA-29701, ORA-29740crsd.log, OS messages

6. 我在实际排障中用到的几个实用技巧

6.1 日志膨胀与磁盘空间检查要养成肌肉记忆

排障过程中最容易忽略的其实是磁盘空间。$GRID_HOME/log、$ORACLE_BASE/diag都是日志增长大户。crsd.log长时间不清理,涨到几个GB很常见;实例alert和trace文件在故障发生后会瞬间暴涨。如果/u01被日志塞满,轻则Oracle进程报错,重则整个集群异常,雪上加霜。

我的习惯是:任何RAC排查开始前,先执行一条df -h确认关键分区剩余空间。这浪费不了半分钟,但能避免后期无法生成trace文件、无法写dump文件的窘境。

日常管理中,ADR部分可以利用adrci设置保留策略:

adrci> set home diag/rdbms/orcl/orcl1 adrci> purge -age 43200 -type trace

43200是分钟数,相当于30天。GI日志不在ADR管理范围内,需要靠脚本定期归档清理。注意不要直接rm正在被进程写入的日志文件,容易造成文件句柄悬空、空间无法释放。正确做法是先把日志mv走,再配合进程或维护窗口处理。

6.2 调整组件日志级别的正确姿势

一般不需要动日志级别,默认级别足够日常排查。但如果某些问题复现频率低、线索模糊,可以针对组件临时调高日志级别:

crsctl set log level 3 cssd

调高后会记录更细的CSS交互过程,对定位心跳类问题有帮助。但注意:日志级别调高意味着IO开销增大、日志量暴增,高峰期慎用。排查结束后记得调回原级别,否则日志可能以极快速度膨胀。

6.3 疑难问题记得收集诊断包

遇到自己搞不定、需要求助的场景,别手动打包一堆日志,直接用官方工具:

  • 11.2及以后版本可以用diagcollection.sh:
$GRID_HOME/bin/diagcollection.sh --collect
  • 12.2以后更推荐TFA:
$GRID_HOME/bin/tfactl diagcollect -type daily -srdc

TFA会把GI日志、数据库日志、OS日志、网络配置等汇总成一个压缩包,并自动带上时间戳。给原厂support提SR时,这个包比你自己零散截取的日志有价值得多。排障经验丰富的人未必每类问题都能独立解决,但懂得在合适的时机收集完整证据链,是专业DBA的重要素质。

6.4 我个人的排查习惯

最后分享一个自己的习惯,不一定适合所有人,但实测多次都很稳:接到RAC故障报告后,不急着看alert,也不急着重启,先花两分钟做三件事——df -h看磁盘、date确认本机时间、crsctl stat res -t看资源全景。然后才打开GI alert,顺着时间线往下翻。

这三件事解决的是“方向”问题。方向对了,后续看ocssd、crsd、实例日志时,内心已经有一个基本判断。方向错了,可能在某个组件的trace文件里翻一晚上,最后一查是磁盘满了或时间漂移。RAC排障不是拼手速,是拼谁的地图更清晰、谁更早锁定层次。日志路径从来不是背出来的,而是在一次次故障现场练出来的。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询