Hard Parse Failure 引发DB较为严重的性能问题

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Hard Parse Failure 引发DB较为严重的性能问题相关的知识,希望对你有一定的参考价值。

1.1问题现象

一个朋友再次遇到SQL解析失败的问题,导致数据库负载很高,让整个数据库无法正常运行业务SQL。

本篇文档对解析失败,从而引发的数据库性能问题,进行分析说明。

现象:数据库负载很高,业务反映数据库慢 or 部分业务无法正常处理;

 

1.2 AWR观察

快速创建一个awr报告观察里面的指标内容。

可以参考MOS文档

从AWR观察到failed parse elapsed time 比较高时,就可以判断是这个问题。

Time Model Statistics

  • Total time in database user-calls (DB Time): 300306.2s
  • Statistics including the word "background" measure background process time, and so do not contribute to the DB time statistic
  • Ordered by % or DB time desc, Statistic name
Statistic NameTime (s)% of DB Time
failed parse elapsed time 299,058.23 99.58
parse time elapsed 298,685.36 99.46
DB CPU 2,082.85 0.69


MOS
Oracle Database - Enterprise Edition - Version 10.2.0.2 and later

In the AWR report Parse Failures are recorded in two places:

 1. Time Model Statistics failed parse elapsed time

 2. XXX Instance Activity Stats  中的parse count (failures) 正常情况失败的SQL解析很少,只有某些应用程序出现问题,才会出现较多的失败的解析SQL。

 

 

 

1.3 定位异常的程序

1)定位执行解析失败SQL的文本

开启event 10035,每个实例都需要执行,开启后,DB ALERT会输出SQL文本

正常情况下11g版本无法查询失败的SQL文本,SQL_ID 可以通过session event library cache lock等可能查询到,解析都失败了,因此文本并不会被记录。

ALTER SYSTEM SET EVENTS 10035 trace name context forever, level 1;
ALTER SESSION SET EVENTS 10035 trace name context forever, level 1;
EVENT="10035 trace name context forever, level 1"

Levels:
level 1+ Print out failed parses of SQL statements to

Note:
The event can be turned off as follows:

ALTER SYSTEM SET EVENTS 10035 trace name context off;
ALTER SESSION SET EVENTS 10035 trace name context off;

2)根据OSPID定位数据库执行错误SQL的机器、程序、用户【如果能从v$session层面快速定位可以跳过这个步骤】

When the event is set,any statement that fails to parse as a result of an error, will be documented in the alert.log, together with the error number and the process OSPID as displayed below

PARSE ERROR: ospid=11268, error=904 for statement:
Mon Aug 29 09:48:24 2011
select empid from emp
 
 
select s.sid,s.program,s.module,s.action,s.event,sq.sql_text,s.username,
s.osuser,s.process,s.s.port,s.machine
 from v$process p,v$session ,v$sqlarea sq
 where p.addr=s.paddr
 and a.sql_id=sq.sql_id(+)
 and p.spid=&ospid;
 

 

1.4 问题处理

1) 以前遇到的问题再次进行记录:
Oracle数据库中实际的用户名,由于PB初次连接到数据库时要自动建立五个系统表(PowerBuilder Catalog Table:PBCATTBL,PBCATCOL,PBCATEDT,PBCATFMT,PBCATVLD,
存储表的扩展属性),因此第一个连接到Oracle的用户必须具有建表、给PUBLIC角色授权等权限。例如可用SYSTEM用户进行第一次连接,此后的连接对用户则无特殊要求; 对于如下的错误SQL,开发人员最初也是不承认自己的代码有的,后续发现是PowerBuilder工具连接Oracle第一次连接时后台自动创建这些对象,
如果第一次连接没有创建system用户下表的权限,后续通过SQL调用执行查询后台会一直查询system.某个表,最终导致报错SQL累计异常。

2)权限问题,开发测试环境无异常;
生产环境权限有要求,开发用户无访问某些对象的权限,因此后台其实一直解析失败,确认后重新授权即可。

 

1.5 一般这种情况数据库会出现什么样的等待事件呢?

可能性1) 数据库出现大量library cache lock 以及少量的cursor : pin S wait on X
可能性2)数据库出现大量library cache lock 被library cache: mutex X 阻塞

通过V$SQL 无法查询 sql_id对应的文本时! SQL执行太快,或者SQL根本没有执行成功。可以使用oradebug 获取current sql_text.

SQL> oradebug setmypid
SQL> oradebug unlimit
SQL> oradebug setinst all
SQL> oradebug -g def hanganalyze 3;
SQL>oradebug tracefile_name

 

 

 

1.6 Oracle的改进

1)无法立即定位问题,并且修改应用程序,可以考虑设置参数,重启库,目的是减少解析错误消耗的资源
Parse errors are syntax error and needs to be verified from application team. High CPU and Library Cache Contention A high number of invalid (syntactically incorrect) SQL can result in high CPU and library cache contention. Ideally, the solution is to
fix the application to issue valid SQL. However,
as a temporary workaround, it is possible to set _cursor_features_enabled in order to ease the effect of the incorrect parsing. When set the parse error is recorded in a table SQLERROR$ which is checked so that repeated attempts to parse syntactically or semantically
invalid statements will not continually incur the full costs associated with hard parsing. In order to enable
this workaround,add 32 to the current value of _cursor_features_enabled. For Example: The default value of _cursor_features_enabled = 2. In order to enable the fix set _cursor_features_enabled to 2 + 32. _cursor_features_enabled is not dynamic and requires a restart: SQL> show parameter _cursor_features_enabled NAME TYPE VALUE ------------------------------------ ----------- ------------------------------ _cursor_features_enabled integer 32 SQL> alter system set "_cursor_features_enabled" = 34 scope=spfile; System altered. After restarting the database certain (not all) parse errors for non-SYS users will be recorded in sqlerror$. The following notes include information on the necessary fixes to enable this feature. These fixes are included in 112.0.4
and 12.1.0.1
大量无效(在语法上不正确)的SQL可能导致较高的CPU和库高速缓存争用。理想情况下,解决方案是修复应用程序以发出有效的SQL。
但是,作为临时的解决方法,可以设置_cursor_features_enabled,以减轻错误分析的影响。
设置分析错误后,将在表SQLERROR $中记录该错误,将对其进行检查,以便反复尝试分析语法或语义上无效的语句将不会持续产生与硬分析相关的全部费用。
重新启动数据库后,非SYS用户的某些(不是全部)解析错误将记录在sqlerror $中。【谷歌翻译】

2)新版本12.2 无需设置参数,Alert会打印解析错误的信息。
NOTE: In 12.2 there is a Diagnostic enhancement that will give an early warning in the alert.log without event 10035 being set. By default the diagnostic will dump the parse error along with warning in the alert log  every 100 parse errors for a given SQL within a 60 minutes period.
注意:在12.2中有一个诊断增强功能,它将在alert.log中给出预警,而不设置事件10035。默认情况下,诊断程序将在60分钟的时间内针对给定的SQL每100个解析错误将解析错误以及警告转储到警报日志中。

 

































以上是关于Hard Parse Failure 引发DB较为严重的性能问题的主要内容,如果未能解决你的问题,请参考以下文章

[ORACLE]oracle SQL执行过程 软解析(soft prase)硬解析(hard prase)以及 Soft Soft Parse

回收算法&触发条件&GC(Allocation Failure)引发的一些JVM知识点梳理

Last_SQL_Error: Relay log read failure: Could not parse relay log event entry. The possible reasons(

Last_SQL_Error: Relay log read failure: Could not parse relay log event entry. The possible reasons(

java 操作 mysql -报错 LockException: Failure obtaining db row lock: Table 'xxx' doesn't exis

关于数据库连接的一个错误:Communications link failure