1. 程式人生 > >個人筆記:ORACLE大頁記憶體hugepage和SGA、PGA的經驗,SGA並不是越大越好

個人筆記:ORACLE大頁記憶體hugepage和SGA、PGA的經驗,SGA並不是越大越好

背景:ORACLE 11.2,SGA 64G,PGA 8G,壓測出現作業系統記憶體耗盡
WARNING: Heavy swapping observed on system in last 5 mins.
pct of memory swapped in [1.94%] pct of memory swapped out [1.32%].

分析:
1、連線到資料庫的每個系統連線程序大概會佔用10M左右,1000個連線那麼也就接近10G了;
2、在32位系統下,一個程序訪問1GB的記憶體,會產生1M(110241024/44/1024/1024)的頁表,如果是在64位系統,將會增大到2M。
SGA設定為64G,有1000個ORACLE使用者程序(在linux中每個程序頁表獨立,都有自己的頁表),64位LINUX的系統上,最大的頁表佔用記憶體為:64

2*1000/1024=125G;

解決方法:
1、控制SGA大小, sga+pga最好控制在50%實體記憶體以內,pga記憶體不要操作sga記憶體的20%;
2、當主機的實體記憶體為64G,設SGA>=32G時,建議開啟大頁;
記憶體都是以頁的形式劃分的,預設情況下每頁是4K,這就意味著如果實體記憶體很大,則對映表的條目將會非常多,會影響CPU的檢索效率。因為記憶體大小是固定的,為了減少對映表的條目,可採取的辦法只有增加頁的尺寸。
在Linux中配置hugepage可以提高oracle的效能,減少oracle sga的頁交換,類似於aix中的lagepage。

設定方法(參考第三方材料):
1、關閉Oracle Database 11g中的AMM(Automatic Memory Management),即把兩個引數MEMORY_TARGET / MEMORY_MAX_TARGET設為0
如果alter system set MEMORY_MAX_TARGET=0 scope=spfile;重啟後發現沒有改為0,可以alter system reset memory_max_target; 來設定

2、參考metalink(文件 ID 401749.1)提供的指令碼,計算hugepages的大小

3、對hugepages_settings.sh這個指令碼授可執行的許可權
chmod +x hugepages_settings.sh

4、執行執行hugepages_settings.sh得到建議值
得出大頁的大小為1028頁(注:一頁為2M,這個值不可改,1028*2M=2056M),實際上hugepages與引數sga_max_size有關,比sga_max_size的值稍微大一點點(比SGA_MAX_SIZE最少要多加一頁,2M的頁不要分配超過sga_max_size太多,會造成記憶體的浪費)
注意:使用Hugepage記憶體是共享記憶體,它會一直keep在記憶體中的,不會被交換出去,也就是說使用hurgepage的記憶體不能被其他的程序使用,所以,一定要合理設定這個值,避免造成浪費。對於只使用Oracle的伺服器來說,把Hugepage_pool設定成大於SGA大小才能被Oracle使用。
SQL>show parameter sga_max_size
NAME TYPE VALUE


sga_max_size big integer 2G

5、設定hugepages,在核心引數中新增一行,vi /etc/sysctl.conf
vm.nr_hugepages = 1028

6、修改核心引數立即生效
[[email protected] ~]# sysctl -p

7、別忘記設定記憶體鎖memlock,以K為單位,memlock數量要大於大頁的數量,當然也要大於sga_max_size,這裡設定為2056000,設定為-1,表示不限制。
[[email protected] ~]# vi /etc/security/limits.conf
oracle soft memlock 2056000
oracle hard memlock 2056000

8、檢查limits是否正確
[[email protected] ~]# su - oracle
[[email protected] ~] ulimit -l
2056000

9、重啟資料庫

10、檢視大頁,已被使用
[[email protected] ~]$ watch -n1 'cat /proc/meminfo |grep -i HugePage'
HugePages_Total: 總共頁
HugePages_Free: 空閒頁
HugePages_Rsvd: 作業系統承諾給Oracle預留頁
Hugepagesize: 2048 kB 每頁是2M,不可修改

如:
HugePages_Total: 1028 ---總共1028頁
HugePages_Free: 869 ---空閒869 頁,即當前大頁被使用了1028-869=159頁,即被用了1592M=118M,小於sga_target。
HugePages_Rsvd: 842 ---作業系統承諾給Oracle預留842頁,即842
2M=1684M(1684+118==SGA_MAX_SIZE)

使用了hugepage之後,SGA就預設pin在記憶體裡了,那麼就不用lock sga了。接下來我們研究一下引數:pre_page_sga,這個引數預設是false,我把它開啟。
[email protected]> alter system set pre_page_sga=true scope=spfile;
[email protected]> show parameter sga
NAME TYPE VALUE


lock_sga boolean FALSE
pre_page_sga boolean TRUE
sga_max_size big integer 2G
sga_target big integer 1G
HugePages_Total: 1028 ---總共1028頁
HugePages_Free: 548 ---空閒548頁,即當前大頁被使用了1028-548=480頁,即被用了4802M=960M,約等於sga_target,引數pre_page_sga起作用了。
HugePages_Rsvd: 521 ---作業系統承諾給Oracle預留521頁,即521
2M=1042M(理解為sga_max_size-sga_target)
Hugepagesize: 2048 kB --每頁是2M,不可修改

參考metalink:USE_LARGE_PAGES To Enable HugePages (文件 ID 1392497.1)

補充關於記憶體申請的OverCommit
Linux下的OverCommit機制,主要是為了應對可能的異常的大量記憶體申請對OS本身造成衝擊。
Linux有三種OverCommit機制,可以通過:/proc/sys/vm/overcommit_memory來配置,三種配置的具體含義:
0:啟發式策略,後果比較嚴重的Overcommit將不能成功,而輕微的Overcommit將被允許。
1:永遠允許Overcommit,這種策略適合那些不能承受記憶體分配失敗的應用,比如某些科學計算應用。
2:永遠禁止Overcommit,在這個情況下,系統所能分配的記憶體不會超過swap+RAM*係數(/proc/sys/vm /overcmmit_ratio,預設50%,你可以調整),如果這麼多資源已經用光,那麼後面任何嘗試申請記憶體的行為都會返回錯誤,這通常意味著此時 沒法執行任何新程式。