Menu Close

Oracle-AWR报告关于DB Time的解读

1. oracle DB Time

1.1. DB Time

file

  DB Time : Amount of elapsed time (in microseconds) spent performing Database user-level calls. This does not include the elapsed time spent on instance background processes such as PMON.

  DB TIME:所有前台用户级调用(foreground user-level calls)花费在database上执行的时间总和,包括CPU time、IO time、cpu on queue time和其他一系列非空闲等待时间,但不包括后台进程background processes执行时间。它是数据库负载的指示灯。

DB Time = DB CPU Time(前台session调用)+ DB Wait Time(用户会话的非空闲等待:Non-Idle Wait)+ Wait on CPU queue
DB CPU Time = active user session * Elapsed Time

当前服务器逻辑CPU的数量是4,而自然流逝的时间为60分钟,也就是说CPU总共可以提供的时间为 4 * 60.17 = 240.68 分钟。而当前CPU花费了 24.67 分钟在处理Oralce非空闲等待和运算上,这样就可以计算出CPU花费在Oracle上的负载:24.67 / 240.68 = 10.25%。

数据库负载 = DB Time / (CPUs * Elapsed)
  • AWR报告中查询DB Time的SQL语句
    SELECT z.*
    FROM (SELECT
               a.instance_number,
               a.snap_id,
               c.begin_interval_time + 0 AS begin_time,
               c.end_interval_time + 0 AS end_time,
               ceil((CAST(c.end_interval_time AS DATE) -
                     CAST(c.begin_interval_time AS DATE)) * 24 * 60) AS "Elapsed TIME",
               ROUND(a.VALUE - LAG(a.VALUE, 1, '0')
                     OVER(ORDER BY a.instance_number, a.snap_id)) AS "DB TIME"
          FROM (SELECT x.snap_id,
                       x.instance_number,
                       x.stat_name,
                       SUM(x.VALUE) / 1000000 / 60 AS VALUE
                  FROM dba_hist_sys_time_model x
                 WHERE x.dbid = (SELECT dbid FROM v$database)
                   AND UPPER(x.stat_name) IN UPPER('DB TIME')
                 GROUP BY x.instance_number, x.snap_id, x.stat_name) a,
               dba_hist_snapshot c
         WHERE a.snap_id = c.snap_id
           AND c.dbid = (SELECT dbid FROM v$database)
           AND c.instance_number = a.instance_number) z
    WHERE z.begin_time >= SYSDATE - 7
    ORDER BY z.instance_number,z.begin_time DESC;

1.2. DB CPU

  DB CPU : Amount of CPU time (in microseconds) spent on database user-level calls. This does not include the CPU time spent on instance background processes such as PMON.

  DB CPU:所有前台用户级调用(foreground user-level calls)database时CPU服务时间总和,不包括实例后台进程 background processes执行时间。

file

需要注意的是AWR是一个数据合集。比如在1分钟之内,1个用户等待了30秒钟,那么10个用户等待事件就是300秒。CPU时间也是一样,在1分钟之内,1个CPU处理30秒钟,那么4个CPU就是120秒。这些时间都是以累积的方式记录在AWR当中的。

从网上看到一个很好的例子:

  假设一家理发店统计 1 小时(60.17(mins))营业情况,店内一共有4个理发师(4个CPU),顾客在理发店的累计逗留时间就是 DB TIME:24.67 (mins)。如果拿顾客累计逗留时间除以营业时间,24.67 / 60.17 = 0.41, 也就是说,在这一小时营业时间内,店内平均有 0.41 个顾客。顾客的累计逗留时间(DB TIME)不是理发师(CPU)的累计工作时间,如果两个顾客都要烫发,正巧只有一个烫发机,则其中一个顾客需要等待(CPU队列时间),这段时间理发师没有干活。所以,DB CPU 是一定会小于 DB Time的(理发师剪头发的时间一定小于顾客在店内逗留的时间)。

2. Load Profile

file

  首先 DB Times(s) per second,它是 DB Time 与 Elapsed的比率,这个结果是指在一个自然时间秒内 DB Time 所耗费的时间。

DB Time(Per Second)= DB Time/ Elapsed Time = 24.67 / 60.17 = 0.41

  其次是 DB CPU(s) per second,它表示每秒钟使用的CPU内核的平均数量(通俗的理解:1钞钟内使用了多少CPU)。理想情况下,这个值应该小于大部分时间可用的CPU核心总数,以便DB能够良好地执行。
此处有4个逻辑CPU,理论上我们每秒可以使用4秒的CPU时间,这里实际使用了不到1秒的CPU时间。

DB CPU(Per Second)= DB CPU Time/Elapsed Time = 109.34 秒/ (60.17 分钟 * 60) = 0.03

DB CPU占DB Time的比例为:(0.03 / 0.41)* 100% = 7.3%,即DB Time中,只有 7.3% 的时间为DB CPU Time,其余为非空闲等待时间。非空闲等待占用了大量的资源。虽然这一个小时内CPU利用率只有7.3%,整体看比较低,但是不意味着数据库的负载很低,有两种情况:

  1. 负荷可能集中在某个时间段,这就需要我们观察每个时间段的数据库负荷。

  2. 数据库的瓶颈可能不在CPU,而在磁盘或者网络:

    1. 数据库内存较少,大部分时间消耗在磁盘的读取上,这个可以从磁盘的响应速度判断。
    2. 网络带宽不足,数据库要发送大量数据到客户端,在这里形成了等待。

3. Operating System Statistics

file

Operating System Statistics 操作系统统计信息, TIME相关的指标单位均为百分之一秒(厘秒)。其中:

  • NUM_CPU_SOCKETS:物理CPU的个数
  • NUM_CPU_CORES:CPU的核数
  • NUM_CPUS:逻辑CPU的个数
  • IDLE_TIME:CPU处于空闲状态的时间
  • SYS_TIME:CPU在内核中花费的时间
  • USER_TIME:CPU在执行用户程序时花费的时间
  • BUSY_TIME:Busy_Time=SYS_TIME+USER_TIME 消耗的CPU时间片
  • AVG_BUSY_TIME:AVG_BUSY_TIME= BUSY_TIME/NUM_CPUS
  • OS_CPU_WAIT_TIME:进程等OS调度的时间
  • IOWAIT_TIME:CPU等待IO所用的时间

查询CPU数量的SQL语句为:

/*
-- CPU data from dba_hist_osstat
*/
col c1 heading '#|CPUs'        format 999
col c2 heading '#|CPU|Cores'   format 999
col c3 heading '#|CPU|Sockets' format 999
SELECT
      (SELECT max(value) FROM dba_hist_osstat
        WHERE stat_name = 'NUM_CPUS')     c1,
      (SELECT max(value) FROM dba_hist_osstat
        WHERE stat_name = 'NUM_CPU_CORES') c2,
      (SELECT max(value) FROM dba_hist_osstat
        WHERE stat_name = 'NUM_CPU_SOCKETS') c3
  FROM dual;

另外有如下公式:

BUSY_TIME + IDLE_TIME = ELAPSED_TIME * CPU_COUNT
此处 121157 + 1301802 = 1422959
     60.17 * 60 * 100 * 4 = 1444080

4. Host CPU 与 Instance CPU

file

4.1. Host CPU(主机CPU)

  Load Average begin/end:代表每个CPU的大致运行队列大小。

  %User:表示CPU一共花了多少比例的时间运行在用户态空间或者说是用户进程(running user space processes)。典型的用户态空间程序有:Shells、数据库、web服务器……

计算公式如下:

%User = USER_TIME / (BUSY_TIME + IDLE_TIME) * 100
此处 %User = 89138 / (121157 + 1301802) * 100 = 6.3%

  %System:表示CPU花了多少比例的时间在内核空间运行。分配内存、IO操作、创建子进程……都是内核操作。这也表明,当IO操作频繁时,System参数会很高。

计算公式如下:

%System = SYS_TIME / (BUSY_TIME + IDLE_TIME) * 100
此处 %System = 31160 / (121157 + 1301802) * 100 = 2.2%

  %Idle:表示CPU处于空闲状态时间比例。

计算公式如下:

%Idle = IDLE_TIME / (BUSY_TIME + IDLE_TIME) * 100
此处 %Idle = 1301802 / (121157 + 1301802) * 100 = 91.5%

  %WIO表示CPU在等待io操作完成,这个可能是io过慢或者io操作过多导致。此处为4.9%,也就是说当前的系统IO存在瓶颈 。

计算公式如下:

%WIO = IOWAIT_TIME / (BUSY_TIME + IDLE_TIME) * 100
此处 %WIO = 70083 / (121157 + 1301802) * 100 = 4.9%

3.2. Instance CPU(实例CPU)

  %Total CPU,是指该实例所使用的CPU占总CPU的比例(即% of total CPU for Instance)

计算公式如下:

%Total CPU = (DB CPU + backupground cpu time) / (OS Busy Time + OS IDLE TIME)  -- 注意统一时间单位
此处 Total CPU = (109.34 + 21.78) * 100 / (121157 + 1301802) * 100 = 0.9%

  %Busy CPU,是指该实例所使用的CPU占总的被使用CPU的比例 (即% of busy CPU for Instance),例如:共4个逻辑CPU,其中3个被完全使用,3个中的1个完全被该实例使用,则%Total CPU= ¼ = 25%,而%Busy CPU= 1/3= 33%
当CPU高时一般看%Busy CPU 可以确定CPU到底是否是本实例消耗的,还是主机上其他程序消耗的。

计算公式如下:

%Busy CPU=(DB CPU + backupground cpu time) / OS Busy Time =(Instance CPU %Total CPU)/ (1- Host CPU
%Idle)  -- 注意统一时间单位
此处%Busy CPU = (109.34 + 21.78) * 100 / 121157 * 100 = 10.8%
同时%Busy CPU = 0.921 / (1 - 0.915) = 10.8

  %DB time waiting for CPU (Resource Manager) 是指当使用了resource manager限制某个用户和会话使用CPU,而产生的等待。会产生resmgr:cpu quantum等待事件,如果产生该等待事件需要和RSRC_MGR的值结合起来判断。解决方法是需要修改资源限制的plan。

5. Time Model Statistics

在 AWR 报告中,Time Model Statistics 记录了数据库用户维度(User Calls)的总时间消耗分布。

这部分信息来自:SYS.DBA_HIST_SYS_TIME_MODEL ,是通过针对前后两个采样点的差值计算得来的。

计算的SQL如下:

SELECT a.instance_number,
       a.snap_id,
       a.stat_name,
       ROUND((b.value - a.value) / 1000000, 2) AS "Time(s)"
  FROM sys.dba_hist_sys_time_model a,
       sys.dba_hist_sys_time_model b
 WHERE a.snap_id = &start_snap_id
   AND b.snap_id = &end_snap_id
   AND a.stat_name = b.stat_name
   AND ROUND((b.value - a.value)/1000000,2) > 0
 ORDER BY 4 DESC;

file