今天在解決一個問題時資料庫hang住了。日誌也沒有啥錯誤,用sqlplus ‘/as sysdba'登陸進去後就一直卡在哪裡了,很是鬱悶。
迫不得已強制登陸sqlplus,
$sqlplus -prelim /as sysdba
如果可以查詢sql語句,可以先產生killsession指令碼,然後kill掉session後在關閉資料庫。
1. 產生OS級kill -9指令碼
set head off
set feedback off
set pagesize 0
spool /tmp/kill_9_1.sh
select ' kill -9 ' || spid from (select spid from v$process where addr in(select paddr from v$session where status='ACTIVE' and username is not null));
spool off
2.產生DB級kill session指令碼
set head off
set feedback off
set pagesize 0
spool /tmp/kill_sess_1.sql
select 'alter system kill session ' || '''' || sid || ',' || serial# || '''' || ';'from v$session where status='ACTIVE' and username is not null;
spool off
3.執行kill_sess.sql指令碼
SQL>@/tmp/kill_sess_1.sql
如果session kill之後不能2分鐘內不能釋放執行OS級kill -9指令碼
sh /tmp/kill_9_1.sh
如果kill session無效,無法恢複應用,進行後續操作5-15步:
4. 如果發現有異常進程,在OS級進行truss:
truss -o /tmp/mytruss -p <pid of process>
5. alter system set job_queue_processes=0;
alter system set aq_tm_processes=0;
6. lsnrctl stop listener_xxx
7. sqlplus “/as sysdba”
oradebug setmypid
oradebug unlimit
oradebug dump systemstate 10
等1分鐘
oradebug dump systemstate 10
等1分鐘
oradebug dump systemstate 10
Exit
如果資料庫處於HANG狀態:
sqlplus “/as sysdba”
oradebug setmypid
oradebug unlimit
oradebug hanganalyze 3
等1分鐘
oradebug hanganalyze 3
oradebug dump systemstate 10
等1分鐘
oradebug dump systemstate 10
等1分鐘
oradebug dump systemstate 10
Exit
該步驟超過15分鐘,停止做systemstate dump
8. 再次產生OS級kill -9指令碼,KILL所有ORACLE使用者進程
set head off
set feedback off
set pagesize 0
spool /tmp/kill_9_2.sh
select ' kill -9 ' || spid from (select spid from v$process where addr in(select paddr from v$session where username is not null));
spool off
9.再次產生DB級kill session指令碼,kill所有ORACLE使用者進程
set head off
set feedback off
set pagesize 0
spool /tmp/kill_sess_2.sql
select 'alter system kill session ' || '''' || sid || ',' || serial# || '''' || ';'from v$session where username is not null;
spool off
10.再次執行kill_sess.sql指令碼
SQL>@/tmp/kill_sess_2.sql
如果session kill之後不能2分鐘內不能釋放執行OS級kill -9指令碼
sh /tmp/kill_9_2.sh
11. Select group#, status, archived from v$log where status in ('ACTIVE', 'CURRENT');
select RECOVERY_ESTIMATED_IOS,ACTUAL_REDO_BLKS,TARGET_REDO_BLKS,LOG_FILE_SIZE_REDO_BLKS,TARGET_MTtr,ESTIMATED_MTTR from v$Instance_recovery;
如果group處於active 狀態的個數超過1個,並且v$instance_recovery.estimated_mttr大於600秒則最好延遲資料庫的關閉,等待I/O量下降,
等到v$instance_recovery.estimated_mttr小於v$instance_recovery.target_mttr,否則資料庫啟動的時間會達到v$instance_recovery.estimated_mttr的時間。
(如果v$instance_recovery.estimated_mttr小於600秒,啟動資料庫採用方法一,否則採用方法二。)
12. Alter system checkpoint
Alter system switch logfile;
Shutdown immediate
13. 等5分鐘,關閉還未結束,alert.log中沒有相關的關閉資訊
shutdown abort
14. ps -ef|grep LOCAL|grep oracle"$ORACLE_SID"
ps -ef|grep ora_|grep "$ORACLE_SID"
使用kill -9 pid
15. ipcs –a |grep ORACLE_USER
尋找號誌是否未釋放,如果未釋放,使用ipcrm清理號誌:
ipcrm -m shmid
ipcrm -s semid
我沒有安裝步驟做,直接就從第7步開始的,然後做第八步二次後,shutdown immediate依然不行,所以就直接shutdown abort了,幸運的是起庫很順利的起起來了。