■ 河南 刘京义
编者按:有时在启动Oracle时也会出现问题,笔者单位一台Oracle因为异常断电宕机,当启动系统后,需要重启Oracle数据库实例,因为某些原因导致重启失败。本文分析了故障过程及原因,并最终排查了故障。
单位一台Oracle因为异常断电宕机,当启动系统后,需要重启Oracle数据库实例。按照常规方式,先要切换到Oracle账户,启动数据库监听。之后打开sqlplus,用sys账户以sysdba身份登录,登录完成后执行startup命令,就可以启动数据库实例了。
但是,在执行“su-oracle”命令,试图切换到Oracle账户,来启动监听时,系统却出现“warning:cannot change directory to /home/oracle:Permission denied”的提示信息,导致操作失败。即使重启系统,直接以Oracle账户身份登录,也出现相同的错误提示,导致Oracle无法正常启动。
根据以上提示信息进行分析,有可能是因为“/home/oracle”目录访问权限设置不当引发的,因为在执行“su -oracle”命令时,必然会读取该目录下的相关配置文件,如果权限设置异常,就会造成读取操作失败,自然无法执行账户切换操作。执行“ls-al/home|grep oracle”命令,针对上述目录查看权限设置信息,在返回内容中显示该目录的属主为“oracle”账户,其拥有读写和执行权限,据此分析Oracle拥有针对该目录正确的访问权限。
既然使用到了“su”命令,如果其执行权限存在问题,也无法执行切换账户操作。执行“ll /bin/su”命令,在返回信息中的首列显示“rwxr-xr-x”,并且属主为“root”账户,说明root拥有可读可写可执行的权限,同一组的用户可读不可写可执行,其他用户拥有可执行权限,这说明su命令的执行权限没有问题。因为su命令无法单独运作,需要相关共享库的配置方可。如果与之关联的共享库权限设置有误,同样会造成命令执行失败。执行“ldd /bin/su”命令,显示su命令所依赖的共享库列表信息。注意,ldd不是一个可执行程序,而只是一个shell脚本。
根据这些共享库(例如“libcrypt.so.1” 等),使用上述方法逐个检查其权限信息(例如执行“ll /lib/ libcrypt.so.1” 等),来检测root账户是否拥有执行权限,经过逐个检测,均不存在问题。在Linux中,为了提高安全性,可以使 用 SELinux(即 Security Enhanced Linux,安全性增强的Linux)技术,来实现灵活和强制性的访问控制机制,用于提高Linux系统的安全性,提供强有力的安全保护,可以防御未知的攻击,SELinux被整合到了2.6版本以上的Linux内核中。如果开启了SELinux功能,就可能因为权限控制问题导致上述情况的发生。执行“vim/etc/selinux/config”命令,打开SELinux的配置文件,在其中的“SELINUX=”栏中显示“disabled”,说明当前SELinux处于关闭状态。
如果根分区磁盘容量不够,也很容易引发各种奇怪的故障。执行“df -h”命令,在返回信息中发现根分区剩余空间比较紧张。因为Linux系统没有回收站之类的功能。所以服务器在线的话,会将删除的文件会先移动“/tmp”目录下,之后定期清除该目录中的数据。但是该服务器不知什么原因,没有设置“/tmp”分区,这样原本属于“/tmp”的数据就占用了根分区的空间。对于这种情况,只要删除“/tmp”目录下一些占用空间较大的文件即可。在该目录中发现一个体积巨大的日志文件,为了顺利将其删除,执行“echo" " >/tmp/xxx_log”命令,来快速清空该文件,这里“xxx_log”为具体的文件名。
之所以没有使用rm命令进行删除,是因为某个重要进程正在使用该文件。如果使用rm命令,是无法成功清除该日志文件的。因为文件在Linux中存放分为数据部分和指针部分,前者位于磁盘中,后者位于文件系统的Meta-Data中,将数据删除后,该指针就会从Meta-Data中清除,这样文件数据部分占用空间就可以被覆盖了。
但是,因为上述重要进程锁定了该日志文件,导致该日志文件的指针部分无法从Meta-Data中清除。所以,在该情况下使用rm命令是无效的。经过以上操作,再执行“df -h”命令,发现根分区的可用空间已经宽裕了很多。但是当执行“su-oracle”命令切换账户时,故障依然出现。
对问题进行进一步的分析,确定故障还是存在于权限设置上。进入“/home”目录,执行“ls-al”命令,列出其中的所有文件信息,其中包括隐藏文件,例如文件前面第一个字符为“.”的文件等。经过仔细查看,果然发现了一些端倪。之前只是针对正常的目录进行检测分析,而无视了对于隐藏目录的检测。对于名称为“.”的隐藏目录来说,其针对的是当前目录,其拥有者为root,其具有的权限为“rwxrxr-x”,即 root 拥有可读可写可执行的权限。
对于名称为“..”的隐藏目录来说,其针对的是根目录,拥有者为root,其具有的权限为“rw-xr-x”,说明其没有执行权限,这自然会导致上述故障的发生。因为root账户时没有权限对根目录进行操作的,自然无法读取“/home/oracle”中的配置信息。对于ls命令大家都比较熟悉,但是一般大家很少使用其提供的“-al”参数,来查看隐藏信息,这就很容易出现判断失误的情况。
其实,可以使用stat命令加以弥补。例如执行“stat/”命令。来查看目录的详细信息。找到了问题所在,解决起来就简单多了,执行“chmod 755 /”命令,为根目录设置可读可写可执行权限,之后执行“su -oracle”命令就可以顺利切换了,之后按照正常操作,顺利启动了Oracle数据库实例。