enq: US - contention 主因是_undo_autotune动态调整回滚段引发latch争抢,而非Undo空间不足;关键指标是AWR中UNXPSTEALCNT、OOS、SSOLDERRCNT的突变趋势及V$UNDOSTAT分钟级分析。
直接结论:enq: us - contention 不是 undo 空间不够,而是 _undo_autotune 动态上线/下线 rollback segment 导致的 latch 争抢;awr 中的 unxpstealcnt、oos、ssolderrcnt 这三个计数比“用了多少 mb”关键得多。
查 AWR 里真正有用的 Undo 指标
AWR 报告默认不展开 Undo 细节,必须手动勾选「Undo Statistics」和「Rollback Segment Summary」。重点盯三列数值,不是平均值,是快照间的突变趋势:
-
UNXPSTEALCNT> 0:说明 active undo 被强制覆盖,undo_retention形同虚设,ORA-01555 风险极高 -
OOS(Out of Space)持续上升:物理空间真的吃紧,不是参数问题,要立刻看dba_data_files的autoextensible -
SSOLDERRCNT非零:一致性读失败,大概率是长查询 + 低undo_retention,不是空间不足
别只扫一眼“Undo space used”那行数字——它掩盖了状态失衡。例如 EXPIRED 占比低于 20%,而 ACTIVE+UNEXPIRED 接近 100%,说明空间没满,但回收卡住了。
用 V$UNDOSTAT 定位分钟级压力源头
AWR 是小时级汇总,V$UNDOSTAT 才是诊断“哪一分钟崩的”的关键。执行:
SELECT begin_time, end_time, undoblks, txncount, maxconcurrency, ssolderrcnt, nospaceerrcnt FROM v$undostat WHERE begin_time > SYSDATE - 1/24 ORDER BY begin_time DESC;
重点关注:
-
maxconcurrency≥ 50+ 且持续多分钟:高并发 DML 正在抢回滚段头,_undo_autotune很可能在疯狂上下线 segment -
nospaceerrcnt> 0:对应时段确有空间不足,需同步查dba_undo_extents状态分布 -
undoblks剧增但txncount平稳:说明个别事务写 undo 极多(比如大表 UPDATE),不是全局配置问题
确认是不是 _undo_autotune 在捣鬼
Oracle 19c 默认开启这个隐含参数,它是 enq: US - contention 的主要推手。先查状态:
执行 show parameter _undo_autotune —— 如果返回 TRUE,基本就是它。
再交叉验证:
- 查最近一小时 undo segment 状态波动:
SELECT TO_CHAR(sample_time, 'HH24:MI'), COUNT(*) FROM v$undostat GROUP BY TO_CHAR(sample_time, 'HH24:MI') ORDER BY 1;如果分钟级 count 在 20~80 之间反复跳变,说明 autotune 正在震荡 - 对比
v$rollname和v$transaction:若 online segment 数远超v$transaction行数,且大量 status 是PENDING或刚从OFFLINE变ONLINE,坐实是 autotune 引发的分配瓶颈
紧急处理不是加数据文件,而是立即执行:ALTER SYSTEM SET "_undo_autotune" = FALSE SCOPE=BOTH —— 19c 支持动态生效,无需重启。
别把长事务漏在 V$TRANSACTION 外面
V$TRANSACTION 的 START_TIME 只反映事务开始时间,但很多“长事务”其实是应用连接池未关闭、SQL_ID 为空、V$SESSION.STATUS = 'INACTIVE' 的挂起会话。单靠它会漏掉一半问题。
必须联合查:
SELECT s.sid, s.serial#, s.username, s.status, s.sql_id, t.start_time, t.used_ublk, t.used_urec FROM v$session s JOIN v$transaction t ON s.saddr = t.ses_addr ORDER BY t.start_time;
特别注意 status = 'INACTIVE' 且 sql_id IS NULL 的记录——它们占着 undo 段却不干活,是 EXPIRED 区块无法回收的常见原因。
真实 undo 压力从来不在“总量”,而在“状态分布”和“分配路径”。一个被频繁上下线的 rollback segment,比十个安静躺着的段更危险;一个挂着不提交的 INACTIVE 会话,比十个跑完就走的 ACTIVE 事务更耗空间。











