日期:2014-05-16  浏览次数:20455 次

oracle 内存与进程

?

shared pool

1 库缓存 library cache

游标和pl/sql游标不是一个概念

hashset

在找bucket

?

根据shared_pool_size 指定的尺寸,可以计算出bucket个数

每一个bucket都有一个对象制定

2 数据字典缓冲

内存块组成 chunk

?

chunk是shared pool 中内存分配的最小单元,在内存中是连续的

chunk分类

1. free 2.recreatable 3.freeable 4. perm

?

一条sql语句

?

1.进入共享池 shared pool

?

2.转为为ascii值

3.对ascii 进行hash运算,得到一个数值(对应的bucket的号码)

?

对bucket进行遍历,遍历bucket 的时候,

有:直接返回可以使用的sql

没有:获取shared pool latch,硬解析开始。

?

?

硬解析的过程:

? ? ? ? 1 对sql语句进行 语法检查, 如果有错,马上退出。

select * form emps

2 检查sql语句涉及到的对象是否存在

3 检查权限

4 获取free bucket中当空的chunk以及相关的latch

5 通过优化器,创建执行计划,最优的。

6 执行计划以及sql文本进入 library cache,在解析的过程中,

?进程一直持有library cache的latch,一直到硬解析结束。

?

软解析:

1.

A select * from emp;

?

B select * from emp; 省略5 ?6

2.

A select * from emp;

?select * from emp;省略2 4 5 6

?

4.将对象放进对应的bucket中

?

SQL 语句解析过程

?

select * from emp where empno=7369

硬解析

软解析

?

?

latch 闩锁

?

1.latch 是保护 链的

2.简单 只有两个状态 0 1 内存锁

?

?

latch 是保护 链的,不是保护数据的

?

要访问修改 链,首先有链的latch

latch争用

例子:

2 cpu

A 进程

B 进程

C 进程

?

A进程 获取到CPU时间片 读取链 需要获取latch 将0改为1

B进程 获取到另一个CPU,B去读取这个链

?

B有两种选择:

1 马上退出CPU 让其他进程工作 ====》 C进程进入CPU

2 B进程知道这时一个闩锁 latch,知道很快就被释放,在CPU等会。闩自旋 空转CPU。

? ? ? 尝试3次,如果尝试3次之后,还没有等到latch,退出CPU.

?

发现shared pool latch 被大量争用,说明有 大量的sql语句, 需要被硬解析,

?

select * from emp where empno=7369

select ?* from emp where empno=7369

?

?

父子游标

?

一条sql被解析,被解析后,放到库缓存中。产生父游标和子游标

父:sql语句 ? ? ? 比较小

子:执行计划 ? ? ?比较大

?

select * from emp where id=1;

select * from emp where id=10000;

?

记住:

动态性能视图:

v$sql 每一行 ?对应一个子游标

v$sqlarea 每一行 对应一个父游标

?

游标在硬解析结束后

?

当session 打开游标以后,就会锁定父游标。

?

oracle 根据父游标 构建子游标 reload

?

?

1 显示shared pool 中的自由空间

desc v$sgastat

?

select * from v$sgastat where name='free memory'

show parameter shared_pool_size;

alter system set shared_pool_size=100M;

?

select * from v$librarycache

?

select * from v$sysstat where name='parse count(hard)'

?

shared_pool 的sql命中率

?

1 hash value

2 有的话 软解析

3 没有 硬解析

4?

?

?

查询命中率?

select ?namespace,pins,pinhists,reloads,invalidations from v$librarycache ;

?

select sum(pinhits)/sum(pins) from v$libraryccache

?

?

?

?

execute dbms_stats.gather_table_stats()