As you might know, RO (Read Only) dbhome was introduced in Oracle 18c and became default configuration in Oracle 21c. Oracle came back with RW (Read Write) dbhome as default configuration in 23ai. It might be interesting to know how we can check if the oracle dbhome is RO (Read Only) or RW (Read Write). I had to recently look for it and just wanted to share it through this blog.
Environment
For my test I used a FREE Oracle 23ai version. Here are my ORACLE_HOME and my ORACLE_BASE environment:
oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] echo $ORACLE_HOME /opt/oracle/product/23ai/dbhomeFree oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] echo $ORACLE_BASE /opt/oracle
We know that for RW dbhome the dbs folder will be used in $ORACLE_HOME and for RO in $ORACLE_BASE.
ORACLE_BASE_HOME will be $ORACLE_HOME for RW and $ORACLE_BASE/homes/<HOME_NAME> for RO.
I did not activate RO on my dbhome, so I should not have so far any dbs or homes directory in my $ORACLE_BASE:
oracle@vmdmkdev:~/ [rdbms2300] ls $ORACLE_BASE admin audit cfgtoollogs diag oraInventory product
ROOH stands for Read Only Oracle HOME.
Activate ROOH
I will active ROOH for my dbhome.
oracle@vmdmkdev:~/ [rdbms2300] roohctl -enable Enabling Read-Only Oracle home. Cannot enable Read-Only Oracle home in a configured Oracle home. The Oracle Home is configured with databases 'FREE'.
I still have my FREE instance database using the dbhome. I have just updated oratab file to comment the database.
oracle@vmdmkdev:~/ [rdbms2300] vi /etc/oratab
And ran roohctl command again, which this time will be successful.
oracle@vmdmkdev:~/ [rdbms2300] roohctl -enable Enabling Read-Only Oracle home. Update orabasetab file to enable Read-Only Oracle home. Orabasetab file has been updated successfully. Create bootstrap directories for Read-Only Oracle home. Bootstrap directories have been created successfully. Bootstrap files have been processed successfully. Bootstrap files have been processed successfully. Read-Only Oracle home has been enabled successfully. Check the log file /opt/oracle/cfgtoollogs/roohctl/roohctl-251003PM023449.log for more details.
Now I have got a homes folder in $ORACLE_BASE as well as a dbs one.
oracle@vmdmkdev:~/ [rdbms2300] ls $ORACLE_BASE admin audit cfgtoollogs dbs diag homes oraInventory product
Contents of homes folder:
oracle@vmdmkdev:~/ [rdbms2300] ls $ORACLE_BASE/homes OraDBHome23aiFree oracle@vmdmkdev:~/ [rdbms2300] ls $ORACLE_BASE/homes/OraDBHome23aiFree/ assistants dbs drdaas hs install mgw network rdbms oracle@vmdmkdev:~/ [rdbms2300] ls $ORACLE_BASE/homes/OraDBHome23aiFree/dbs oracle@vmdmkdev:~/ [rdbms2300]
My dbs folder in $ORACLE_HOME remains, of course, unchanged:
oracle@vmdmkdev:~/ [rdbms2300] cdh oracle@vmdmkdev:/opt/oracle/product/23ai/dbhomeFree/ [rdbms2300] cd dbs oracle@vmdmkdev:/opt/oracle/product/23ai/dbhomeFree/dbs/ [rdbms2300] ls hc_FREE.dat init.ora lkFREE_SITE1 orapwFREE spfileFREE.ora
Deactivate ROOH again
Let’s deactivate ROOH again and make the Oracle Home RW again to start all the tests.
oracle@vmdmkdev:/opt/oracle/product/23ai/dbhomeFree/dbs/ [rdbms2300] roohctl -disable Disabling Read-Only Oracle home. Update orabasetab file to disable Read-Only Oracle home. Orabasetab file has been updated successfully. Read-Only Oracle home has been disabled successfully. Check the log file /opt/oracle/cfgtoollogs/roohctl/roohctl-251003PM024030.log for more details.
dbs folder in $ORACLE_BASE will remain unchanged.
oracle@vmdmkdev:/opt/oracle/product/23ai/dbhomeFree/dbs/ [rdbms2300] cd $ORACLE_BASE oracle@vmdmkdev:/opt/oracle/ [rdbms2300] ls admin audit cfgtoollogs dbs diag homes oraInventory product
Check dbhome status with orabasehome binary
There is a binary file, orabasehome, stored in $ORACLE_HOME/bin which will tell me if my Oracle Home is RO or RW. It will just provide the value of ORACLE_BASE_HOME. So either $ORACLE_HOME folder if it is a RW dbhome or $ORACLE_BASE/homes/<HOME_NAME> folder if it is a RO dbhome.
oracle@vmdmkdev:/opt/oracle/dbs/ [rdbms2300] $ORACLE_HOME/bin/orabasehome /opt/oracle/product/23ai/dbhomeFree oracle@vmdmkdev:/opt/oracle/dbs/ [rdbms2300]
The binary file will display in my case $ORACLE_HOME, which is correct.
Start the database
I tested instance startup with file either in $ORACLE_HOME/dbs or $ORACLE_BASE/dbs folder.
oracle@vmdmkdev:/opt/oracle/dbs/ [FREE (CDB$ROOT)] sqh SQL*Plus: Release 23.0.0.0.0 - for Oracle Cloud and Engineered Systems on Fri Oct 3 14:49:46 2025 Version 23.5.0.24.07 Copyright (c) 1982, 2024, Oracle. All rights reserved. Connected to an idle instance. SQL> startup ORA-32004: obsolete or deprecated parameter(s) specified for RDBMS instance ORACLE instance started. Total System Global Area 1070721856 bytes Fixed Size 5368640 bytes Variable Size 335544320 bytes Database Buffers 725614592 bytes Redo Buffers 4194304 bytes Database mounted. Database opened. SQL> shutdown immediate Database closed. Database dismounted. ORACLE instance shut down.
Database is starting correctly.
I moved the instance file from $ORACLE_HOME/dbs to $ORACLE_BASE/dbs:
oracle@vmdmkdev:/opt/oracle/dbs/ [FREE (CDB$ROOT)] ls -ltrh $ORACLE_HOME/dbs total 18M -rw-r-----. 1 oracle oinstall 3.1K May 14 2015 init.ora lrwxrwxrwx. 1 oracle oinstall 38 Sep 26 2024 orapwFREE -> /opt/oracle/admin/FREE/pfile/orapwFREE -rw-r-----. 1 oracle oinstall 24 Sep 26 2024 lkFREE_SITE1 -rw-r-----. 1 oracle oinstall 4.5K Oct 3 14:49 spfileFREE.ora -rw-r-----. 1 oracle oinstall 18M Oct 3 14:59 snapcf_FREE.f -rw-rw----. 1 oracle oinstall 1.6K Oct 3 15:06 hc_FREE.dat oracle@vmdmkdev:/opt/oracle/dbs/ [FREE (CDB$ROOT)] ls -ltrh $ORACLE_BASE/dbs total 0 oracle@vmdmkdev:/opt/oracle/dbs/ [FREE (CDB$ROOT)] mv $ORACLE_HOME/dbs/* $ORACLE_BASE/dbs oracle@vmdmkdev:/opt/oracle/dbs/ [FREE (CDB$ROOT)] ls -ltrh $ORACLE_HOME/dbs total 0 oracle@vmdmkdev:/opt/oracle/dbs/ [FREE (CDB$ROOT)] ls -ltrh $ORACLE_BASE/dbs total 18M -rw-r-----. 1 oracle oinstall 3.1K May 14 2015 init.ora lrwxrwxrwx. 1 oracle oinstall 38 Sep 26 2024 orapwFREE -> /opt/oracle/admin/FREE/pfile/orapwFREE -rw-r-----. 1 oracle oinstall 24 Sep 26 2024 lkFREE_SITE1 -rw-r-----. 1 oracle oinstall 4.5K Oct 3 14:49 spfileFREE.ora -rw-r-----. 1 oracle oinstall 18M Oct 3 14:59 snapcf_FREE.f -rw-rw----. 1 oracle oinstall 1.6K Oct 3 15:06 hc_FREE.dat
Starting the database would fail:
oracle@vmdmkdev:/opt/oracle/dbs/ [FREE (CDB$ROOT)] sqh SQL*Plus: Release 23.0.0.0.0 - for Oracle Cloud and Engineered Systems on Fri Oct 3 15:18:36 2025 Version 23.5.0.24.07 Copyright (c) 1982, 2024, Oracle. All rights reserved. Connected to an idle instance. SQL> startup ORA-01078: failure in processing system parameters LRM-00109: could not open parameter file '/opt/oracle/product/23ai/dbhomeFree/dbs/initFREE.ora' SQL>
So Oracle is looking only for instance file in $ORACLE_HOME/dbs when configured in RW mode, which makes sense.
I moved database’s instance files again to $ORACLE_HOME/dbs, and delete $ORACLE_BASE/dbs and $ORACLE_BASE/homes.
oracle@vmdmkdev:/opt/oracle/ [FREE (CDB$ROOT)] mv $ORACLE_BASE/dbs/* $ORACLE_HOME/dbs/ oracle@vmdmkdev:/opt/oracle/ [FREE (CDB$ROOT)] ls $ORACLE_BASE/dbs/ oracle@vmdmkdev:/opt/oracle/ [FREE (CDB$ROOT)] ls $ORACLE_HOME/dbs/ hc_FREE.dat init.ora lkFREE_SITE1 orapwFREE snapcf_FREE.f spfileFREE.ora oracle@vmdmkdev:/opt/oracle/ [FREE (CDB$ROOT)] rmdir $ORACLE_BASE/dbs/ oracle@vmdmkdev:/opt/oracle/ [FREE (CDB$ROOT)] rm -rf $ORACLE_BASE/homes
Activate ROOH again
I activated ROOH for the dbhome and checked dbs and homes folders to be created again.
oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] roohctl -enable Enabling Read-Only Oracle home. Update orabasetab file to enable Read-Only Oracle home. Orabasetab file has been updated successfully. Create bootstrap directories for Read-Only Oracle home. Bootstrap directories have been created successfully. Bootstrap files have been processed successfully. Bootstrap files have been processed successfully. Read-Only Oracle home has been enabled successfully. Check the log file /opt/oracle/cfgtoollogs/roohctl/roohctl-251003PM032952.log for more details. oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] ls -l $ORACLE_BASE | grep -iE 'dbs|homes' drwxr-x---. 2 oracle oinstall 6 Oct 10 15:39 dbs drwxr-x---. 3 oracle oinstall 31 Oct 10 15:39 homes oracle@vmdmkdev:~/ [FREE (CDB$ROOT)]
Check dbhome status with orabasehome binary
Binary file is now showing $ORACLE_BASE/homes/HOME_NAME, so RO is really activated on my dbhome.
oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] $ORACLE_HOME/bin/orabasehome /opt/oracle/homes/OraDBHome23aiFree oracle@vmdmkdev:~/ [FREE (CDB$ROOT)]
Start the database
Starting the database would fail, as there is no instance file in $ORACLE_BASE/dbs folder.
oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] sqh SQL*Plus: Release 23.0.0.0.0 - for Oracle Cloud and Engineered Systems on Fri Oct 3 15:30:55 2025 Version 23.5.0.24.07 Copyright (c) 1982, 2024, Oracle. All rights reserved. Connected to an idle instance. SQL> startup ORA-01078: failure in processing system parameters LRM-00109: could not open parameter file '/opt/oracle/dbs/initFREE.ora' SQL>
As expected…
By the way, the inventory.xml file is not displaying anything about RW or RO.
Let’s move the instance files from $ORACLE_HOME/dbs to $ORACLE_BASE/dbs:
oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] ls -l $ORACLE_BASE/dbs total 0 oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] ls -l $ORACLE_HOME/dbs total 18340 -rw-rw----. 1 oracle oinstall 1544 Oct 3 15:06 hc_FREE.dat -rw-r-----. 1 oracle oinstall 3079 May 14 2015 init.ora -rw-r-----. 1 oracle oinstall 24 Sep 26 2024 lkFREE_SITE1 lrwxrwxrwx. 1 oracle oinstall 38 Sep 26 2024 orapwFREE -> /opt/oracle/admin/FREE/pfile/orapwFREE -rw-r-----. 1 oracle oinstall 18759680 Oct 3 14:59 snapcf_FREE.f -rw-r-----. 1 oracle oinstall 4608 Oct 3 14:49 spfileFREE.ora oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] mv $ORACLE_HOME/dbs/* $ORACLE_BASE/dbs oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] ls -l $ORACLE_BASE/dbs total 18340 -rw-rw----. 1 oracle oinstall 1544 Oct 3 15:06 hc_FREE.dat -rw-r-----. 1 oracle oinstall 3079 May 14 2015 init.ora -rw-r-----. 1 oracle oinstall 24 Sep 26 2024 lkFREE_SITE1 lrwxrwxrwx. 1 oracle oinstall 38 Sep 26 2024 orapwFREE -> /opt/oracle/admin/FREE/pfile/orapwFREE -rw-r-----. 1 oracle oinstall 18759680 Oct 3 14:59 snapcf_FREE.f -rw-r-----. 1 oracle oinstall 4608 Oct 3 14:49 spfileFREE.ora oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] ls -l $ORACLE_HOME/dbs total 0 oracle@vmdmkdev:~/ [FREE (CDB$ROOT)]
And database can be started:
oracle@vmdmkdev:~/ [FREE (CDB$ROOT)] sqh SQL*Plus: Release 23.0.0.0.0 - for Oracle Cloud and Engineered Systems on Fri Oct 3 15:48:23 2025 Version 23.5.0.24.07 Copyright (c) 1982, 2024, Oracle. All rights reserved. Connected to an idle instance. SQL> startup ORA-32004: obsolete or deprecated parameter(s) specified for RDBMS instance ORACLE instance started. Total System Global Area 1070721856 bytes Fixed Size 5368640 bytes Variable Size 335544320 bytes Database Buffers 725614592 bytes Redo Buffers 4194304 bytes Database mounted. Database opened. SQL>
To wrap up…
If dbhome in RW or RO it looks in appropriate dbs directory, $ORACLE_HOME for RW and $ORACLE_BASE for RO.
Oracle inventory will not give us more details about if the Oracle dbhome is RW or RO.
orabasehome binary is the solution to know if the Oracle dbhome is in RW or RO.