大雀软件园

首页 软件下载 安卓市场 苹果市场 电脑游戏 安卓游戏 文章资讯 驱动下载
技术开发 网页设计 图形图象 数据库 网络媒体 网络安全 站长CLUB 操作系统 媒体动画 安卓相关
当前位置: 首页 -> 数据库 -> ORACLE -> Oracle Freelist和HWM原理探讨及相关性能优化

Oracle Freelist和HWM原理探讨及相关性能优化

时间: 2021-08-13 作者:daque

要害词:freelist,hwm,保存参数,段,块,dump,优化 作品纲要:    近期来,freelist的要害效率渐渐为oracle dba所看法,网上也展示少许关系的计划。正文以freelist为线索对oracle的保存处置的道理举行较深刻的商量,波及oracle段区块处置的道理,freelist算法等。而与freelist出色关系的一个重用个性hwm,与sql本能出色关系,正文也作了道理领会引见。在道理商量的普通上,引见了常用的保存参数领会本领,并对所波及的保存优化、hwm的优化和freelist比赛优化作了证明。 缩略语:        assm:auto segement space management        hwm:high water mark        dba:data block address        oltp:online transaction process        ops:oracle parallel server 1.简介        oracle的空间处置和保存参数处置是oracle处置及优化的要害局部。freelist动作oracle底层保存参数中的中心参数,其动作办法对oracle的保存处置及本能优化有宏大感化,而现有的oracle文书档案对此上面的实质比拟不足。固然oracle 9i已展示了assm,然而动作深刻调优对freelist看法仍是需要的。    近期来,freelist的要害效率渐渐为oracle dba所看法,网上也展示少许关系的计划。正文以freelist为线索对oracle的保存处置的道理举行较深刻的商量,波及oracle段区块处置的道理,freelist算法等。而与freelist出色关系的一个重用个性hwm,与sql本能出色关系,正文也作了道理领会引见。在道理商量的普通上,引见了常用的保存参数领会本领,并对所波及的保存优化、hwm的优化和freelist比赛优化作了证明。        那些道理领会和本能优化都创造在商量的普通上,限于篇幅和自己体味大概生存控制、缺点或缺点。        为了精确文中局部构造和字段的证明径直用英文刻画。        限于篇幅正文不对同样很要害的block构造作更深刻的计划,对ops本能有要害感化的free list group正文也未说起,所以正文在简单free list group下计划。对于block的深刻计划、free list group的引见与优化以及pctused和pctfree等要害参数的优化请拜见参考文件和材料。 2.道理商量        freelist动作一个oracle保存处置的中心参数。其动作办法由oralce里面遏制,咱们普遍不须要控制和遏制。然而咱们大概会遇到那些题目,当插入一条记载,会插入到谁人块中?是运用新块,仍旧插入罕见据的老块?段是什么功夫扩充的,怎样扩充的?表中惟有一条记载,然而作一次select期间价却是上千个块,干什么?即使咱们从道理上领会了oracle的保存处置办法,对关系那些题目的处置及本能优化就明显天然了。 2.1 oracle的论理积聚构造        oralce的论理保存构造按表空间,段,区,块举行处置。块是oracle用来处置保存空间的最基础单位,oracle数据库在举行输出输入操纵时,都是以块为单元举行论理读写操纵的。区由一系列贯串的块构成,oralce在举行空间调配、接收和处置时是以区为基础单元的。段由多个区构成,那些区不妨是贯串的也不妨是不贯串的,普遍情景下一个东西具有一个段。表空间中包含段和区。        在天生段的功夫,会同时间配初始区(initial extents), 初始区的第一个块就方法化为segment header,并被用来记载free list刻画消息、extents消息,hwm消息等。 2.2 free list观念 free list是一种单向链表用来定位不妨接受数据的块,在字典处置办法的表空间中,oracle运用free list来处置未调配的保存块。oracle记载了有清闲空间的块用来insert或update。清闲空间根源于两种办法:1.段中一切胜过hwm的块,那些块仍旧调配给段了,然而还未被运用。2.段中一切在hwm下的且链入了free list的块,不妨被重用。free list具备下列属性 l         flag引导free list 被运用(1)或未运用(0) l         free list 链的首块的地方dba(data block address) l         free list 链的尾块的地方dba free list 的消息常常保持在segment header中,这边给出segment header block dump片断加以证明: nfl = 3, nfb = 1 typ = 1 nxf = 0 seg lst:: flg: unused lhd: 0x00000000 ltl: 0x00000000  seg lst:: flg: used   lhd: 0x03c00233 ltl: 0x03c00233  seg lst:: flg: used   lhd: 0x03c00234 ltl: 0x03c00234    seg lst:: flg: unused lhd: 0x00000000 ltl: 0x00000000    segment header: ==> nfl: number of free lists/block ==> nfb: number of free list blocks + segment header ==> typ: block type  ==> nxf: number of transaction free lists segment list: ==> flg: flag used or unused the free list ==> lhd: head of free list ==> ltl: tail of free list   在每一个块中都有一个标志flg用来表白块能否链入了 free list链中。即使这个标记置上,该块中后向南针指向free list链中下一个块的dba。即使暂时块是链的最结束的块,该后向南针值为0。 这边给出坐落free list上的block dump的片断 block header dump:  0x03c00235  object id on block? y  seg/obj: 0xe2d8  csc: 0x00.6264c61  itc: 1  flg: o  typ: 1 - data      fsl: 1  fnx: 0x3c00234 ver: 0x01   ==> seg/obj object id in dictionary ==> csc scn of last block cleanout  ==> itc number of itl slots ==> flg o = on freelist , - = not on freelist ==> typ 1 = data    2 = index ==> fsl itl tx freelist slot ==> fnx dba of next block on freelist   举例来说即使有五个块在free list中,辨别为a,b,c,d,e 就会产生segment header->a->b->c->d->e--| 同声segment header->e 2.3 free list类型 在段中生存3类free list, 即master freelists (mfl), process freelists (prfl), 和 transaction freelists.  2.3.1 master free list(公用清闲空间池):  每一个段中有一个master free list,在段创造的功夫机动天生。对于每一个段来说都有如许一个清闲空间池,对每个过程都是公用的,清闲空间即是坐落master free list 的块上。因为master free list是公用的,所以当多个过程同声插出道到同一个段上,master free list比赛运用水平就会减少。 2.3.2 process free lists 为了缩小master free list的比赛题目, 引入了另一种free list叫作process free lists, 按照sql吩咐 create/alter 中的参数freelists 创造. 如许多个free list 就不妨摊派清闲空间的处置,以普及oltp运用作莫大并发插入和革新工作时间和空间间调配处置的本能。经过指定create table / cluster or index的子句storage的参数freelists 来创造,比方: create table flg ( . . . .) . . . storage ( ... freelists 10 ...)。缺省的freelists为1,此时不会创造process free lists。当freelists>=2时,创造process free lists。     过程在运用process free list是按照过程的oracle pid (process id)来采用的,公式如次: select list entry = (pid % nfl) + 1  nfl : freelists设置的process free list个数 2.3.3 transaction free lists 当oracle须要时动静创造。一个transaction free list 是一种特意给某一个工作运用的free list. 每个段至罕见16个transactions free lists, 而且这个值在须要时会延长,直到到达segment header块的巨细控制。一个工作惟有底下情景下会须要调配一个tx free lists entry: 块中开释空间时(delete or update) 而且还不生存tx free lists entry时。  2.4 free list动作 2.4.1 freelist link and unlink 操纵     freelist 按保守先出部队(lifo) 办法处置。也即是说结果被link到freelist的块具有最先unlink的时机。 当块中清闲空间减少到大于pctfree时,块放入freelist中。free list中的块可用来作update 或insert。 当块中没有充满的空间用来insert操纵时而且运用空间大于pctused,块就会从free list中移出。 在块在delete or update 操纵之后,即使运用空间落到pctused下,块再次link到free list中。历次块介入free list时,都是link到链表的头部。 比方:商量段中有120个块编号由1到120。个中有6个块在free list上并假如hwm是 80。(block本质运用dba编号) 10->24->45->46->65->80-| 此刻作insert 操纵,须要400 bytes空间。假如块10上空间不及,但块24上空间可用。此刻数据插入到块 24 ,此刻块24的结余空间小于该表的pctused。所以块 24 从free list链表中移出。pctfree and pctused参数的手段即是用来遏制数据块从free list的链表中移入/移出动作的。此刻free lists象如许: 10->45->46->65->80-| 而后在同一工作中作delete同一个段的数据,使块 54 和 67落到pctused下。此刻那些块介入到free list链中。free list链此刻象如许: 67->54->10->45->46->65->80-| 2.4.2 transaction free list 算法 扫描segment header块中一切的tx free list,查看能否还没有tx free list entry调配给transaction, 怎样没有,将探求未运用的entry或仍旧提交了工作的空的tx free list。即使上述探求进程波折, 新的entry会在segment header块中tx free lists地区中开拓。即使没有空间来天生, 工作就必需等候entry的开释。 segment header中的最大free list个数: block size    max # freelists  -----------   -----------------        2k      24        4k      50        8k      101       16k      204  工作t1开释出来的清闲块(delete or update)的运用 :  l         登时被t1所重用 l         当t1 commit后被其它须要清闲块的工作重用,进程举比方下:    2.5 hmw观念 high water mark代办一个表运用的最大的(top limit)块 。2.第11中学仍旧提到high water mark 记载在segment header中,而且在oracle插入数据时普遍延长5个blocks(并非老是5个块,简直拜见2.4.第22中学过程图中hmw延长办法)。 segment header block中与hwm关系消息证明如次: extent control:   extent header:: spare1: 0      space2: 0      #extents: 13     #blocks: 1429                     last map  0x00000000  #maps: 0      offset: 4128         highwater::  0x020004d0  ext#: 12     blk#: 275    ext size: 475      #blocks in seg. hdr’s freelists: 5        #blocks below: 1229        mapblk  0x00000000  offset: 12                        unlocked ==> spare1:   this field is no longer used (old inc#, now always 0) ==> space2:   this field is no longer used (old ts#, now always 0) ==> #extents: number of extents allocated to segment ==> #blocks:  number of blocks allocated to segment   ==> last map: address of last extent map block               0 if extent map is entirely in the segment header ==> #maps:    number of extent map block ==> offset:   offset to end of extent map   ==> hwm dba:  address of block at highwater mark ==> ext#:     hwm extent number relative to segment ==> blk#:     hwm block number within extent ==> ext size: hwm extent size (in blocks) ==> #blocks in seg. hdr’s freelists: number of blocks in seg. hdr’s free list  ==> #blocks below: number of blocks below hwm ==> mapblk dba: dba of extent map block containing hwm extent                 is 0 if hwm is in the segment header ==> offset:   offset within extent map block               is the ext# if hwm is in segment header ==> locked by: if locked by a transaction, the xid is displayed   hwm不妨说是仍旧运用过的保存空间和未运用过的保存空间之间的分界限。在表运用进程中,hwm从来向一个目标挪动,插入记载时hwm大概会向减少的目标挪动,然而简略记载时hwm并不会向差异的目标挪动。拜见2.4.2。下图表露了某个数据段中hwm的场所情景。[page_break]high water mark之以是重假如由于它对全表扫描本能的感化。当实行一个全表扫描时,oracle会读取一切high water mark下的块纵然它们是空块。当high water mark 下有很多unused block时实行全表扫描会减少特殊的不需要的i/o。它也会在全部共享区中弥补很多很多空块。

3.领会本领    保存参数基础上属于oracle internal的货色,所以oralce并没有供给很好的本领来领会。然而对于dba来说,仍旧不妨经过block dump和dbms_space等本领来获得局部消息。

3.1 索取block和free list消息创造dbms_space运用的保存进程show_space

sql>

create or replace procedure show_space

 ( p_segname in varchar2,

 p_owner in varchar2 default user,

 p_type in varchar2 default 'table',

 p_partition in varchar2 default null )

 as

 l_free_blks number;

 l_total_blocks number;

 l_total_bytes number;

 l_unused_blocks number;

 l_unused_bytes number;

 l_lastusedextfileid number;

 l_lastusedextblockid number;

 l_last_used_block number;

 procedure p( p_label in varchar2, p_num in number )

 is

 begin

 dbms_output.put_line( rpad(p_label,40,'.') || p_num );

 end;

 begin

 dbms_space.free_blocks

 ( segment_owner => p_owner,

 segment_name => p_segname,

 segment_type => p_type,

 partition_name => p_partition,

 freelist_group_id => 0,

 free_blks => l_free_blks );

dbms_space.unused_space

 ( segment_owner => p_owner,

 segment_name => p_segname,

 segment_type => p_type,

 partition_name => p_partition,

 total_blocks => l_total_blocks,

 total_bytes => l_total_bytes,

 unused_blocks => l_unused_blocks,

 unused_bytes => l_unused_bytes,

 last_used_extent_file_id => l_lastusedextfileid,

 last_used_extent_block_id => l_lastusedextblockid,

 last_used_block => l_last_used_block );

p( 'free blocks', l_free_blks );

 p( 'total blocks', l_total_blocks );

 p( 'total bytes', l_total_bytes );

 p( 'unused blocks', l_unused_blocks );

 p( 'unused bytes', l_unused_bytes );

 p( 'last used ext fileid', l_lastusedextfileid );

 p( 'last used ext blockid', l_lastusedextblockid );

 p( 'last used block', l_last_used_block );

 end;

进程已创造。

sql> create table t1(a char(1000)) storage( freelists 3);

表已创造。

sql> set serveroutput on;

sql> exec show_space('t1');

free blocks.............................0       <==number of blocks on freelist

total blocks............................5       <==total data blocks in segment

total bytes.............................20480   <==total bytes in segment

unused blocks...........................4       <==total unused blocks in segment

unused bytes............................16384   <==total unused bytes in segment

last used ext fileid....................15      <==file id of last used extent

last used ext blockid...................562     <==block id of last used extent

last used block.........................1       <==last used block in extent

pl/sql 进程已胜利实行。

相关show_space的进一步运用本领可参考文件5。以次运用上头获得的数据对segment header block举行dump。

sql>alter system dump datafile 15 block 562;

在udump/ora10792.trc中

*** 2004-09-08 15:29:57.343

start dump data blocks tsn: 27 file#: 15 minblk 562 maxblk 562

buffer tsn: 27 rdba: 0x03c00232 (15/562)

scn: 0x0000.064560e4 seq: 0x02 flg: 0x00 tail: 0x60e41002

frmt: 0x02 chkval: 0x0000 type: 0x10=data segment header - unlimited

extent control header

  -----------------------------------------------------------------

  extent header:: spare1: 0      space2: 0      #extents: 1      #blocks: 4    

                  last map  0x00000000  #maps: 0      offset: 2080 

      highwater::  0x03c00233  ext#: 0      blk#: 0      ext size: 4    

  #blocks in seg. hdr's freelists: 0    

  #blocks below: 0    

  mapblk  0x00000000  offset: 0    

                   unlocked

     map header:: next  0x00000000  #extents: 1    obj#: 60033  flag: 0x40000000

  extent map

  -----------------------------------------------------------------

   0x03c00233  length: 4    

 nfl = 3, nfb = 1 typ = 1 nxf = 0

  seg lst:: flg: unused lhd: 0x00000000 ltl: 0x00000000

  seg lst:: flg: unused lhd: 0x00000000 ltl: 0x00000000

  seg lst:: flg: unused lhd: 0x00000000 ltl: 0x00000000

  seg lst:: flg: unused lhd: 0x00000000 ltl: 0x00000000

end dump data blocks tsn: 27 file#: 15 minblk 562 maxblk 562

 对于上述块中字段的证明,以及关系考查。因为篇幅所限,正文不复陈列。可参考文件7。

对非segment header的data block的dump本领和上述一致。data block的构造和segment header block不一律,即使须要领会,可查看参考文件和材料。

3.2 索取hwm消息3.2.1 hwm场所hwm场所按底下的公式计划:

    hwm = useed byte = total bytes - unused blocks

total bytes和unused blocks都不妨用show_space索取。

还不妨经过analyze tables获得hwm消息. dba_tables视图中包括了可用来各表空间领会的列。个中blocks代办已运用过的块即hwm,empty_blocks代办未运用的空间。

3.2.1 hwm下空间运用消息要比拟罕见据行的块的块数和high water mark下总块数,不妨用底下的公式来展现hwm下未用空间的比率。

p = 1- r/h

r:罕见据行的块的块数

h:hwm下的块数.

r不妨经过如次本领赢得:

oracle7:

select count(distinct substr(rowid, 15,4) || substr(rowid, 1,8) )  from schema.table;

oracle8 and oracle9:

select count(distinct substr(rowid, 7,3) || substr(rowid, 10,6) )  from schema.table;

即使公式计划的截止 p是0,就不须要对表举行重修。即使截止p大于0,该当商量体例情景和运用须要来确定能否须要总组表。

4.优化4.1细工接收保存空间在high water mark之上的块对本能没有感化,然而会奢侈空间。怎样空间巨细是一个商量的题目,就不妨确定接收空块。

假如表t1的保存表示图如图2.5所示,运用alter table ... deallocate unused语句不妨接收hwm之上的空间。比方:

alter table t1 deallocate unused;

接收后t1的保存表示如图4.1.1

    即使在alter table ... deallocate unused语句中运用了keep要害字,则不妨在hwm之后保持指定巨细的清闲空间,比方:

    alter table t1 deallocate unused keep 10k;

接收后t1的保存表示如图4.1.2

4.2删减表    按照3.2.1不妨获得hwm以次块的运用情景。怎样p大于时,对全表扫描本能会爆发感化,同声也会耗用空间。

即使不妨确认运用有杰出的索引简直不会用到全表扫描,那么high water mark以次的空块,纵然奢侈了空间,不会对考察爆发感化。即使不许决定,那么就须要商量删减表。

    删减表的操纵将简略表中一切的记载,而且重置hwm标志。表在删减之后将变成一个空表。

    在oracle中删减表只犹如下的两种方法:

1.运用drop语句

    先运用drop语句简略所有表,而后再重修这个表。在简略-重修的进程中,与表关系的一切索引、完备性牵制以及触发器城市丧失,而且一切依附于该表的东西城市变为invalid状况,同声从来争对表的受权也会作废。所以沿用这种办法简略表中的记载价格太大。

2.运用truncate语句

    truncate语句属于ddl语句,不会爆发任何回退消息,而且被登时机动提交。在实行truncate语句时不会感化到与被删减表关系的任何数据库东西与受权,也不会触公布中所设置的触发器。其余,在对标举行删减时,hwm将重置,仍旧为表调配的保存空间将被接收。

    在实行truncate语句时,不妨经过drop storage子句和reuse storage子句来遏制被开释的区能否接收到表空间中。怎样作在线体例的truncate,不蓄意表长功夫锁住,那么不妨运用reuse storage子句,仅将hwm重置。4.3 free list优化free list 比赛出此刻多个过程运用同一个free list并试图同声窜改free list头部数据块时。不妨经过查问视图v$waitsate的class典型为data block 的记载来查看比赛情景。

爆发data block典型比赛的重要因为是多个过程试图同声窜改free list头部数据块。 但是,它也会出此刻当过程筹备将块读入buffer cathe时,另一个过程须要考察同一个块。即使能在v$session_wait中凑巧捕捉buffer busy waits,就不妨经过查问v$session_wait中的p3来判决是那一类。a 0 或 1014代办读典型,其余的值为窜改比赛的典型。

   下一步须要决定比赛波及那些段。 即使不妨在v$session_wait捕捉waits,就不妨用p1和p2的值 (对应file 和 block) 在dba_extents中找到段名。 怎样是一个表,就很大概须要重修表来创造更多的process freelists。 一种计划须要创造几何个freelist的本领是dump少许段中逼近hwm的块,查看interested transaction list的个数,简直本领可拜见3.1。interested transactions个数的峰值加1 即是须要的最小process freelists的值。

从2.3和2.4不妨看出,运用多个free list大概引导更多的空块未被运用, 也大概引导段更快地扩充。即使本能是暂时所关怀的中心,那么多free lists 不妨用来普及并发考察本领,固然会减少少许特殊空间的耗用。但是,即使空间运用巨细是开始商量的成分,那么引荐运用single freelist,使参数freelists=1, 固然就不许提高并发工作的本能了。

v$waitstat 也可表露其余典型class的比赛,囊括segment header 和free list。 出此刻同一个free list group中多个工作须要同声革新它们的free list header记载时。 有多种本领来处置这个题目如重修表沿用更多的free list groups,大概减少 _bump_highwater_mark_count巨细,大概安排运用自己。

热门阅览

最新排行

Copyright © 2019-2021 大雀软件园(www.daque.cn) All Rights Reserved.