环境介绍:
双机 操作系统:solaris 10 数据库版本:oracle 11g R1 64bit
1、在双机软件界面上,点击进入维护模式,然后在操作系统,手动关闭监听,关闭数据库时报:ORA-03113: end-of-file on communication channel
bash-3.00$lsnrctl stop bash-3.00$sqlplus /nolog SQL>conn /as sysdba SQL> shutdown immediate Database closed. Database dismounted. ORA-03113: end-of-file on communication channel
2、看到该错误,查看oracle的后台进程,已经没有了,如下所示:
bash-3.00$ ps -ef | grep ora_ oracle 17382 12315 0 01:06:20 pts/5 0:00 grep ora_
3、退出当前的sqlplus,再次尝试启动数据库,报错如下:
bash-3.00$sqlplus /nolog SQL> conn /as sysdba Connected to an idle instance. SQL> startup ORA-01081: cannot start already-running ORACLE - shut it down first
4、执行ipcs命令,查看到oracle并没有释放所占用的内存资源
bash-3.00$ ipcs IPC status from <running system> as of Tue Dec 17 01:22:26 CST 2013 T ID KEY MODE OWNER GROUP Message Queues: q 53 0x4c544952 --rw-rw-rw- root root q 32 0x4d6 --rw-rw-rw- root root Shared Memory: m 335544442 0x4d4e5251 --rw-r--r-- root root m 503316539 0x75a5fd0 --rw-rw---- oracle oinstall m 503316538 0 --rw-rw---- oracle oinstall m 503316537 0 --rw-rw---- oracle oinstall m 503316536 0 --rw-rw---- oracle oinstall m 503316535 0 --rw-rw---- oracle oinstall m 503316518 0 --rw------- oracle root Semaphores: s 16777253 0x5653 --ra-ra-ra- root root s 64 0x5301e9e8 --ra------- root root
5、当时提出的解决办法是,要么重启操作系统,要么执行shutdown abort,执行shutdown abort,再启动数据库,数据库能够正常启动
bash-3.00$sqlplus /nolog SQL>conn /as sysdba SQL>shutdown abort SQL>startup
6、其实,也是可以通过ipcrm删除oracle未释放的共享内存段,如上ipcs的输出,可以通过如下命令删除oracle未释放的共享内存段:
ipcrm -m 503316538 //当执行了 ipcrm -m 503316538命令后,可能不需要执行以下3条命令了 ipcrm -m 503316537 ipcrm -m 503316536 ipcrm -m 503316535
关于ipc的相关知识:
IPC Inter-Process Communication 进程间通信 ipcs可用来显示当前系统中的共享内存段、信号量集、消息队列等的使用情况。 命令示例: ipcs -a或ipcs 显示当前系统中共享内存段、信号量集、消息队列的使用情况; ipcs -m 显示共享内存段的使用情况; ipcs -s 显示信号量集的使用情况; ipcs -q 显示消息队列的使用情况; ipcrm可用来删除对应的共享内存段、信号量、消息队列; 命令示例: ipcrm -s semid 删除对应的信号量集 ipcrm -m shmid 删除对应的共享内存段 ipcrm -q msqid 删除对应的消息队列
通过执行ipcs -mp可以获取和共享内存段相关的PID,然后通过ps -ef | grep PID,来决定是否kill这些占用共享内存段的PID
当执行ipcrm -m semid后,status字段将会标记dest,I just found out that "dest" means marked for destruction.To actually make the shared memory segment go away you need to kill the process using the shared memory segment. when you call ipcs -mp you get a list of the PIDs associated with the shared memory segment. Then you can kill based on the PID or lookup the name of the PID by doing ps -ef | grep PID. I checked to see who is using the shared memory and then killed it.