怎么调整或给每个oracle存储过程实例实例指定其所占内存

经常有人问我:“我们的系统有XX内 存,怎么分配内存合适?”我的回答是“不知道”。这是一个很无奈的答案,因为这个问题确实无解。每个系统都有不同的特性,如果使用一种通用的模式去分配内 存,那么肯定是无法达到目的的。优化内存配置的时候,首先需要注意一些原则性的问题,详细的内存分配方法,在本章的使用STATSPACK进行系统优化章节将进行进一步的介绍。以下几点是笔者在实际工作中总结的内存优化的基本原则:
第一,无论如何分配内存,绝对不能让系统存在较多的换页情况,最好的选择是让系统基本不存在换页。
第二,使用文件系统并不能给ORACLE数据库的IO性能带来好处,因此尽量使用裸设备,如果使
用裸设备,SGA和PGA使用内存的总量可以高达70%,甚至更高,但是SGA、PGA、Oracle后台进程、Oracle前台进程、应用进程占用内存的总量一般不要超过系统物理内存总量的90%。上述的参考值仅仅提供参考,不能机械地说SGA和PGA不能占用超过物理内存的60%或者70%,而是要根据你的系统的实际情况进行调整。如果你的系统有很大的物理内存,那么这些指标值还可以更高,只要遵循系统不产生换页操作的原则,那么哪怕你使用了95%甚至更多的物理内存,那么你的配置也是合理的。在海量内存下,如果配置了很大的SGA,那么会消耗大量的CPU资源,因此如果数据库实际不需要使用那么多内存,配置过大的SGA会导致CPU资源的浪费。切忌在解决内存问题的同时带来新的性能故障。
第三,在内存允许的情况下,设置足够大的PGA空间,尽量避免硬盘排序。硬盘排序会造成IO
压力增大和相应速度大幅度下降,因此在有条件的情况下,提高内存排序比例可以提高系统的性能。如果排序操作很大,而且物理内存也有限,那么产生部分硬盘排序也是正常的。但是如果系统中存在大量的 multi-pass的硬盘排序,那么就应该加大PGA空间了。
第四,在一般情况下,共享池和各个数据块缓冲池的命中率尽量保持在95%以上(OLAP应用除
外)。由于每个应用都有不同的特点,命中率指标不一定能够完全表现出数据缓冲池的实际情况,但是在大多数情况下,这个命中率具有一定的代表性。如果在使用多缓冲的情况下,总体的命中率指标超过95%不能证明数据库缓冲池没有问题。通过检查DEFAULT、KEEP、NK CACHE等的命中率情况,往往能够发现在整体命中率达标的情况下,个别缓冲区性能不佳的问题。
第五、在Oracle 9i之前,过大的shared pool会导致大量的管理开销,因此不能设置过大的
shared pool。Oracle 9i改进了共享池的管理,并且采用了subpool机制,使大型共享池的性能得到了很大的改善。笔者曾经在9i数据库上使用过超过2G的共享池,没有发现由于共享池过大导致 性能问题。在一些移动公司的大型BOSS系统中,超过5GB的共享池也是十分常见的,我曾经见过一个有300G内存的系统,共享池配置了10GB。
另外要注意的是,如果已经使用了很大的共享池,还是出现共享池不足的问题,那么调整应用比加大共享池更为有效,另外如果由于某种原因,共享池存在碎片问题,SUBPOOL可能成为一种负面的东西,这个时候禁止使用SUBPOOL会带来好的效果。如果存在较为严重的共享池碎片,那么PX MSG POOL可能会导致经常出现共享池无法分配的情况出现,这种情况下,将PX MSG POOL在LARGE POOL中分配,可以减轻共享池不足的现象,另外减少
SESSION_CACHED_CURSORS也会起到好的效果。在一般情况下,过大的共享池是不正常的。过大的共享池也会带来加大CPU开销等问题,因此在适当的情况下加大共享池的大小,而不
共2页(1/2)
如何给 Oracle 数据库分配内存 曾几何时, 网络上流传着给 Oracle 数据库分配内存的一条法则: 把 80%的内存分配给 Oracle 使用, 而又......与Oracle 实例关联的基本内存结构包括: 系统全局区 (SGA):由所有服务器和后台...data buffer cache 通过指定 DB_CACHE_SIZE 参数的值,可以配置缓冲区高速缓存。......oracle参数配置个人分类:oracle 一、Oracle LARGE_POOL_SIZE大小设置值多少 java_...内存百分比的说法基本掌握的原则是, data buffer 通常可以尽可能的大,shared_......它包含Oracle 服务器 果实际内存不够再往虚拟内存中写 我们重点就是设置SGA,理论上SGA可占OS系统物理内存的1/2——1/3 原则:SGA+PGA+OS使用内存<总物理RAM ......_size 是动态分配 Shared Pool Size,database buffer cache,large pool,java pool,redo log buffer 大小的,只是根据 Oracle 运 行状况来重新分配 SGA 各内存块的......Oracle 11g 的 自动内存管理_计算机软件及应用_IT/计算机_专业资料。描述和总结oracle 11g自动内存管理机制和设置方法Oracle 11g 的 自动内存管理 作者: Fenng | 可......应用是OLTP 类型还是OLAP 类型 基本掌握的原则是, db_block_buffer 通常可以尽...调整ORACLE内存设置 1、 点击开始,从程序菜单选择“Enterprise Manager Console”......博客访问: 166760
博文数量: 74
博客积分: 2996
博客等级: 少校
技术积分: 740
注册时间:
IT168企业级官微
微信号:IT168qiye
系统架构师大会
微信号:SACC2013
分类: Oracle
2.4.Oracle在windows下的内存管理
2.4.1.Windows内存系统概述
NT使用一个以页为基础的虚拟内存系
统,该系统使用32位线性地址。在内部,系统管理被称为页的4096字
节段中的所有内存。每页的物理内存都被备份。
对于临时的内存页使用页文件(pagefile),而对于只读的内存页,则使用磁盘文件。在同
一时刻,最多可以有16个不同的页文件。代码、资源和其它只读数据都是通过它们创建的文件直接备
NT为系统中的每一个应用程序(进
程)提供一个独立的、2
GB的用户地址空间。对于应用程序来说,好象是有2 GB的可用内存,而不用考
虑实际可用的物理内存的量。如果某个应用程序要求的内存比可用的内存更多时,Windows
NT是这样满足这种要求的,它从这个和/或其他的进程把非关键内存分页(paging)到一个页文件,并且释放这些物理内存页。结果,在Windows
NT中,全局堆不再存在。相反,每一个进程都有其自己的32位地址空间,在其
中,该进程的所有内存被分配,
包括代码、资源、数据、DLL(动态链接库),和动态内存。实际上,系统仍然要
受到可用的硬件资源的限制,但是实现了与系统中应用程序无关的、对于可用资源的管理。
NT在内存和地址空间之间作出了区
分。每个进程分配到2
GB的用户地址空间,而不管对于该进程的实际可用物理内存有多少。而且,所有进程都使用相同范围的线性32位地址,范围从-7FFFFFFF16,
而不考虑可用内存的地址。Windows
NT负责在适当的时间把内存页映射(paging)到磁盘以及从磁盘页映射回内
存,使得每个进程都确保能够寻址到它所需要的内存。尽管有可能出现两个进程试图同时访问同一虚拟地址上的内存,但是,实际上Windows
NT虚拟内存管理程序是在不同的物理位置描述这两个内存的位置。而且这两个地址都不见得与原始的虚拟地址一致。这就是虚拟内存。
Win32环境下,32位
的地址空间转化为4GB的虚拟内存。默认情况下,将一半(2GB)
分配给用户进程(因而一个进程的最大可用虚拟内存为2G,oracle进
程同样受此限制),另一半(2GB)分配给操作系统。
因为虚拟内存的存在,一个应用程序能够管理它自
己的地址空间,而不必考虑在系统中对于其它进程的影响。在Windows
NT中的内存管理程序负责查看在任何给定的时间里,所有的应用程序是否有足够的物理内存进行有效的操作。Windows
NT操作系统下的应用程序不必考虑和其它应用程序共享系统内存这个问题。并且,即使在应用程序自己的地址空间内,它们仍能够与其它的应
用程序共享内存。
区分内存和地址空间的一个好处是,为应用程序提
供了将非常大的文件加载到内存的能力。不必将一个大的文件读进内存中,Windows
NT为应用程序保留该文件所需的地址范围提供了支持。然后,在需要的时候,该文件部分就可以被浏览了(物理性地读进内存)。通过虚拟内
存的支持,对于大段的动态内存的分配同样可以做到这一点。
在任意给定的时间,进程中每个地址都可以被当作
是空闲的(free)、保留的(reserved)
或已提交的(committed)。进程开始时,所有地址的都是空闲的,意味着它们都是自由空间并
且可以被提交到内存,或者为将来使用而保留起来。在任何空闲的地址能够被使用前,它必须首先被分配为保留的或已提交的。试图访问一个保留的或已提交的地址
都将产生一个访问冲突异常(access
violation exception)。
一个进程中的所有2 GB的地址要么为了使用而是空闲的、要么为了将来的使用而是保留的、要么已提交到特定的内存(在使用的)。
一旦地址被以保留的或者已提交的形式分配,VirtualFree是唯一可以释放它们的方法棗那就是,将它们返回到自由的地址。VirtualFree还可以用来对已提交的页解除提交,同时,返回这些地址到保留状态。当解除地址的提交时,
所有与该地址相关的物理内存和页文件空间都被释放。
NT中的进程有一个被称为工作组(working
set)的最小页,是为了进程能够顺利地运行,在运行时在内存中必须被提供。Windows
NT在启动时为一个进程分配了默认数量的页数,并且逐渐地调整该数,使得系统中所有激活的进程的性能达到一种平衡的最优。当一个进程正在运
行时(实际上是,是一个进程的线程正在运行时),Windows
NT“尽量”确保该进程的工作组页总是驻留在物理内存中。工作集即在物理内存中保持的虚拟页面的子集,分进程工作集和系统工作集。
2.4.2.Windows下Oracle的内存配置
在windows下,Oracle实例作为一个单独的进程运行,这个进程是一个标准的Win32应
用程序,它能够申请最大为2G的虚拟内存地址空间,所有用户连接后后台线程的分配内存(包括像buffer
cache那些全局内存)必须小于2G(64位
平台中无此限制,32位平台中可以通过设置参数use_indirect_data_buffers来突破这一限制,不详述)。
Oracle可以运行于windows
NT下的任何版本,但是Oracle一般不推荐将Oracle数据库运行在PDC(主域控服务器)或BDC(备域控服务器)下。这是因为域控服务器会需要大量的文件缓存(这会消耗大量内存,影响到Oracle)和网络资源。
而文件缓存带来的另外一个问题就是,这个机器到
底是作为一个专用的数据库服务器还是一个混合服务器。因为Oracle数据库不会用到文件缓存(log
buffer就相当于Oracle自己的文件缓存),它通过直接写磁盘来避免文
在专用数据库服务器系统上,用户一定要确保没有
使用到页文件(pagefile即虚拟内存文件)。否则,可以通过修改Oracle参数或者增大物理内存来避免。如果大量额页被持续的移入、移出到虚拟内存中,会严重影响到性能。
如果是专用服务器系统,有以下建议:
o如果分配给Oracle的总内存能保证不会超过物理内存,则虚拟内存页可以被设置位物理内存的50%,并且可以增长到物理内存的100%大小(在my
computer =& properties =& Advanced =& Performance =&
Settings =&
Advanced =& Virtual Memory =& Change中设置,设置Initial
size为物理内存的50%,Maximum
Size和物理内存大小相同);
o对于主要是运行纯Oracle数据库的系统(但不是专用),一般推荐虚拟内存页大小在1倍
到1.5倍于物理内存大小之间;
o对于物理内存大于2G的机器,要求虚拟内存页最少为2G。
一个机器上能被用于分配的总内存等于物理内存加
上扩展前的虚拟内存页大小。你一定要避免设置参数如buffer_cache_size或其他相关
参数导致Oracle要求分配内存大于物理内存。尽管Oracle的
分配内存大小是限制在总内存(物理内存+最小虚拟内存)之内,但是,对虚拟内存页的访问是非常慢的,会直接影响到系统性能,因此Oracle分配内存要小于物理内存大小以避免发生内存交换。
如果系统是混合应用,除了Oracle数据库外还运行了其他程序,这时就需要考虑设置虚拟内存页大于物理内存了。那些当前不活动的进程可
以减少它们的工作区(working
set 即物理内存)以使活动进程能增加工作区。如果Oracle数据库运行在
这样的机器上,则推荐虚拟内页最少1.5到2倍
的物理内存大小,特别是在内存大于2G时。
8.1.x之前,启动Oracle服务时不会启动Oracle实例。此时(即只启动了Oracle服务,
没有启动实例),分配给Oracle.EXE的主要内存是给相关DLL的,大概20M(各个版本的DLL不同,因此占用内存情况也不同)。9i之后,Oracle实例会随着服务启动,不过我们可以在服务启动后再关闭实例,这时就可以观察出Oracle服务所占用的内存大小了:
这是windows下
一个Oracle
10g的实例关闭后内存占用情况。我们看到此时Oracle服务占用的内存是32M。
Windows下,可以使用以下语句来计算Oracle占用的虚拟内存大小:
select sum(bytes)/ + 22/*DLL占用内存*/ Mb from (select bytes from v$sgastat – SGA内存&&&&&&& union&&&& &&&select value bytes from – 会话内存&&&&&&&&&&&& v$sesstat s,&&&&&&&&&&&& v$statname n&&&&&&& where&&&&&&&&&&&& n.STATISTIC# = s.STATISTIC# and&&&&&&&&&&&& n.name = 'session pga memory'&&&&&&& union&&&&&&& select *count(*) bytes – 线程堆栈&&&&&& &from v$process&&&&&& );
在实例启动时,所有全局内存页都被保留和提交
(所有共享全局区、Buffer Cache和Redo
Buffer)——可以通过观
察到实例启动后,所需要的Page
File都已经被分配。但只有一小部分内存页(如果没有设置PRE_PAGE_SGA的
话;这小部分内存以granule为单位,固定SGA【包
buffer】一个、Buffer Cache一个、Shared
Pool一个)被触及(touch)而已经分配到工作组(working
set)中,而其他更多的页需要使用时才分配到工作组中。
通过设置注册表可以设置Oracle进程的最小工作组大小和最大工作组大小:
ORA_WORKINGSETMIN或ORA_%SID%_WORKINGSETMIN:Oracle.EXE进程的最小工作组大小(M为单
ORA_WORKINGSETMAX或ORA_%SID%_WORKINGSETMAX:Oracle.EXE进程的最大工作组大小(M为单
这些注册项需要加在HKEY_LOCAL_MACHINE -& SOFTWARE -&
ORACLE或者HKEY_LOCAL_MACHINE -& SOFTWARE
ORACLE -& HOMEn下。
在混合服务器下,这种设置能防止Oracle进程的内存被其他进程争用。设置这些注册项时,需要考虑PRE_PAGE_SGA的
设置。如前所述,PRE_PAGE_SGA使Oracle实
例启动时“触及”所有的SGA内存页,使它们都置入工作组中,但同时会增长实例启动时间。
ORA_WORKINGSETMIN是一个非常有用的参数,它能防止Oracle进程的工作组被缩小到这一限制值之下:
o如果设置了PRE_PAGE_SGA,实例启动后,工作组就大于这个限制值。在实例关闭之前,就不会低于这个值;
o如果没有PRE_PAGE_SGA,当实例的工作组一旦达到这个值后,就不会再低于这个值。
另外,在10g之
前,存在一个Bug(642267),导致在windows系
统中设置了LOCK_SGA后,实例启动报ORA-27102错
误。可以通过设置ORA_WORKINGSETMIN最小为2M来
解决这个问题。但是,windows中,LOCK_SGA只
影响Oracle进程中的SGA部分,而分
配给用户会话的内存不会受影响,这部分内存还是可能会产生内存交换。
2.4.3.SGA的分配
当实例启动时,oracle在虚拟内存地址空间中创建一段连续的内存区,这个内存区的大小与SGA所有区相关参数有关。通过调用Win32
API接口“VirtualAlloc”,在接口函数的参数中指定MEM_RESERVE
| MEM_COMMIT内存分配标识和PAGE_READWRITE保护标
识,这部分内存始终会被保留和提交。这就保证所有线程都能访问这块内存(SGA是被所有线程共享
的),并且这块内存区始终有物理存储(内存或磁盘)所支持。
VirtualAlloc函数不会触及这块区域内的内存页,这就是说分配给SGA组件(如buffer
cache)的内存在没有触及之前是不会到工作组中去的。
VirtualAlloc
VirtualAlloc函数保留或提交调用此函数的进程的虚拟内存地址空间中的一段内
存页。如果没有指定MEM_RESET,被这个函数分配的内存自动初始化为0,
Cache通常被创建为一个单一的连
续内存区。但这并不是必须的,特别是当使用了非常大的Buffer
Cache时。因为dll内存和线程分配的内存会导致虚拟地址空间产生碎片。
当一个进程创建后,windows NT会在进程的地址空间中创建一个堆(heap),
这个堆被称为进程的默认堆。许多Win32
API调用接口和C运行调用接口(如malloc、localalloc)都会使用这个默认堆。当需要时,进程能在虚拟内存地址空间中创建另外的命名堆。默认堆
创建为1M大小(被保留和提交的)的内存区,当执行分配或释放这个堆的操作时,堆管理器提交或撤销
这个区。而访问这个区是通过临界区来串行访问的,所以多个线程不能同时访问这个区。
当进程创建了一个线程后,windows NT会为线程堆栈(每个现场都有自己的堆栈)保留一块地址空间区域,并提交一部分这些保留区。
当一个进程连接到标准区时,系统为堆栈保留一个1M大小的虚拟地址空间并提交这个区顶部的两个页。
当一个线程分配了一个静态或者全局变量时,多个线程可以同时访问这个变量,因此存在变量内容被破坏的潜在可能。本地和自动变量被创建在线程的堆栈中,因而
变量被破坏的可能性很小。堆栈的分配是从上至下的。例如,一个地址空间从0x到0x080FF000的堆栈的分配是从0x080FF000到0x来提交内存页,如果访问在0x的
页就会导致堆栈溢出异常。堆栈不能增长,任何试图访问堆栈以外的地址的操作都可能会导致进程被中止的致命错误。
2.4.4.会话内存的分配
当监听创建了一个用户会话(线程和堆栈)时,Oracle服务进程就通过调用Win32
API函数创建用户连接所必须的内存结构,并且指定MEM_RESERVE |
MEM_COMMIT标识,以保持和提交给线程私有的地址空间区域。
当调用了VirtualAlloc来
在指定地址保留内存,它会返回一个虚拟地址空间到下一个64K大块(chunk,windows内存分配最小单位)的地址。Oracle调用VirtualAlloc时不指定地
址,只传一个NULL在相应参数中,这会返回到下一个64K大
块的地址。因此用户会话在分配PGA、UGA和CGA时同时也遵循64K的最小粒度,来提交倍数于这
个粒度值的内存页。许多用户会话经常分配许多小于64K的内存,这就导致地址空间出现碎片,因为许
多64K区只有两个页被提交。
一旦地址空间被用户会话占满了后,如果要再创建
一个新会话,就会存在无法分配到地址空间的危险。将可能报以下错误:
&ORA-12500
&TNS:listener
failed to start a dedicated server process
也可能报这些错误:
/ TNS-12540 TNS:internal limit restriction exceeded
enough storage is available to process this command
failed:category = ....
could not create new process
OS system call failure
out of process memory when trying to allocate ....
因为地址空间碎片问题和DLL被载入了oracle服务进程的地址空间,这些错
误很可能发生再当Oracle进程占用大概1.6G~1.7G(可以通过任务管理器或查
2.4.4.1.会话内存大小设置
我们前面说了,一个进程的全部内存大小被限制在2G以内。因此,对于一个有许多用户同时访问的系统,要考虑这些会话总内存小于2G
– SGA的大小。
下列参数会影响每个会话的内存大小(这些参数前
面都有介绍):
bitmap_merge_area_size
create_bitmap_area_size
hash_area_size
open_cursors
sort_area_size
(sort_area_retained_size)
在没有设置PGA_AGGREGATE_TARGE(这个参数能尽量但不一定使所有会话PGA之和在指定范围内)参数时,需要调整这些参数,以使所有会话占用内存与SGA之和小于2G。过多的使用PL/SQL结构体(如PL/SQL
TABLE、ARRAY)也会导致会话内存增大。
2.4.4.2.ORASTACK修改线程堆栈大小
Oracle提供了ORASTACK工
具让用户内修改Oracle执行程序创建会话、线程时的默认堆栈大小。当ORASTACK应用于一个可执行程序时,它会修改程序头部的、定义使用创建线程API函数所指定默认堆栈大小的二进制区,以修改默认堆栈的大小。没有必要区修改线程提交页数的默认值,因为它
们时从堆栈中请求到的。当用户非常多时,通过减少每个创建在Oracle中会话堆栈大小,可以节省
大量内存。比如,一个1000用户的系统,将堆栈从1M降
为500K后,能节省出1000
* 500K = 500M的地址空间。
在需要使用ORASTACK来降低现场堆栈大小时,你需要测试你的系统以保证新的堆栈大小能确保系统正常运行。如果堆栈大
小被缩小到Oracle服务端所必须的堆栈大小以下,就会产生堆栈溢出错误,用户进程就失败(通常
报ORA-3113错误),并且在alert
log中不会有报错而且页不产生trace文件。Oracle一般不推荐将堆栈该到500K以下(尽管不
少系统在300K时也能正常运行)。
ORASTACK必须修改所有能在oracle中
创建线程的进程,使用语法如下:
& orastack& executable_name& new_stack_size_in_bytes
下面的例子将堆栈改为500K:
& orastack oracle.exe& 500000
& orastack tnslsnr.exe 500000
& orastack svrmgrl.exe 500000
& orastack sqlplus.exe 500000
在使用ORASTACK之
前必须保证没有任何oracle进程正在运行(可以通任务管理器或者)。
此外,如果有程序在本地连接(没有通过SQL*NET)了Oracle,也要先停止(如在本
地运行sqlplus连接了实例)。
2.4.4.3.会话内存如何释放、线程如何结束
当会话成功结束后,它会按用Win32 API函数VirtualFree来释放它
的内存,调用此函数时,需要指定MEM_DECOMMIT
| MEM_RELEASE标识。当所有内存被释放后,堆栈也被释放,将Oracle进
程中指向完成的会话的地址空间空闲出来。
如果一个用户会话被异常结束,它将不会释放它所
分配的内存,这些内存页会被继续保留在Oracle进程的地址空间中,知道进程结束。会话的异常结
束可能由以下原因导致的:
session kill session.
orakill杀掉的会话.
Oracle管理助手for
Windows:kill session.
o其他杀线程的工具
具提供了杀线程的功能)
Oracle建议尽量少使用以上方式(命令),特别是shutdown abort(这种停止实例的方法所带来的问题还不止这个)。当调用shutdown
abort时,Oracle会调用Win32
API函数TerminateThread来中止每个用户会话,这个命令将直接
杀掉线程而不释放它们的内存。如果系统已经接近2G地址空间的限制,Oracle实例再次启动要分配内存时就会产生问题。唯一释放Oracle全
部内存的方法是停止和启动Oracle服务(服务OracleService&SID&)。
如果windows
NT下的系统需要能被许多用户访问,可以通过以下措施来优化内存的使用:
o降低相关的PGA、UGA内存参数(如SORT_AREA_SIZE);
o降低SGA的参数;
使数据库作业队列数(参数job_queue_processes控制)和并行查询slave(参数parallel_max_servers控
制)最小,因为它们也会导致Oracle进程创建线程;
o使用ORASTACK降低会话、线程堆栈大小到500K;
o考虑使用MTS模式;
o考虑将Windows
NT升级到Windows NT企业版;
o考虑升级硬
件以支持Intel
ESMA(Extended. Server Memory Architecture,
扩展服务内存架构)
阅读(1381) | 评论(0) | 转发(0) |
相关热门文章
给主人留下些什么吧!~~
请登录后评论。oracle实例内存调整_百度文库
两大类热门资源免费畅读
续费一年阅读会员,立省24元!
oracle实例内存调整
上传于|0|0|暂无简介
阅读已结束,如果下载本文需要使用1下载券
想免费下载本文?
定制HR最喜欢的简历
下载文档到电脑,查找使用更方便
还剩3页未读,继续阅读
定制HR最喜欢的简历
你可能喜欢}

我要回帖

更多关于 oracle 实例 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信