Wednesday, March 6, 2024

script to check if a password is expiring

The environment variable $HOME for a Linux account is defined by file /etc/passwd if the account was not created in AD (Active Directory). Each account has an entry line in file /etc/passwd. For example, I can get my account's password expiration date by: 

$ echo $HOME
/u02/app
$ whoami
applmgr
$ grep applmgr /etc/passwd
applmgr:x:50378:102:Oracle EBS ID - J Y:/u02/app:/bin/ksh
$ expstr=$( chage -l $(whoami) | grep "^Password expires" | awk -F: '{ print $(NF) }' | sed -e 's/^ *//g; s/ *$//g;' )
$ echo "password for account `whoami` will expire on $expstr"
password for account applmgr will expire on Jul 30, 2025

But, if the account was created by Windows AD (Active Directory), the variable $HOME is defined in AD by "Home Directory" (Note: an entry in .profile or such could change $HOME to a different path immediately after login). ADHelp search page may show info:
    Unix Account
Home Directory:   /users/applmgr
Login Shell:          /bin/ksh

In that case, "chage" will give a different result:
$ echo $HOME
/users/applmgr
$ expstr=$( chage -l $(whoami) | grep "^Password expires" | awk -F: '{ print $(NF) }' | sed -e 's/^ *//g; s/ *$//g;' )
chage: user 'applmgr' does not exist in /etc/passwd

For an important account created in Linux (vs. an AD account), I wrote a script to email warning out before its password expires. It can be run by a cron job, such as
30 12 * * * /path/to/xxxx_scripts/checkPWDexpire.sh 2>&1

============= script checkPWDexpire.sh =============
let secs_per_day=60*60*24
nowtime=$( date +%s )
expstr=$( chage -l $(whoami) | grep "^Password expires" | awk -F: '{ print $(NF) }' | sed -e 's/^ *//g; s/ *$//g;' )
echo "DEBUG: expstr is $expstr"
if [ "$expstr" == "never" ]; then
echo "Password never expires.";
exit 0;
fi
exptime=$( date --date "$expstr" +%s )
if [ "$exptime" -lt 1 ];        then
echo "Something is wrong.";
exit 255;   # Or, email a message out
fi
if [ "$exptime" -lt "$nowtime" ]; then
echo "Password already expired.";
exit 1;      # Or, email a message out
fi
secs_til_exp=$(expr $exptime - $nowtime)
days_til_exp=$(expr $secs_til_exp / $secs_per_day)
echo "Password expires in $days_til_exp days."
if [ "$days_til_exp" -lt 6 ]; then
# send email out
echo "Please reset password manually and update 3rd party environments." | mailx -s "`whoami` on `uname -n` will expire in $days_til_exp days" me@email.com
# or 
# mailx -s "`whoami` on `uname -n` will expire in $days_til_exp days" -a aFile.log me@email.com < aFile.log
else
echo "All is fine.";
exit ;
fi
============== end =====================

"chage" Linux command:
If OS user applmgr is granted sudo, it can act as root to check another account's status or change password status.

$ sudo su -
[sudo] password for applmgr:
Last login: Mon Mar 28 03:22:57 EDT xxxx
Hostname:  server_name.domain.com
OS:  Red Hat Enterprise Linux release 8.10 (Ootpa)
Arch:  x86_64

[root@server_name ~]# chage -E -1 batch_mgr   # -1 <== number
Notes: passing the number -1 to Expire Date (-E) only never expires the account, but not unexpire the password.   

[root@server_name ~]# chage -l batch_mgr       # -l <== --list
Last password change                                 : Feb 14, 2023
Password expires                                        : May 15, 2023
Password inactive                                       : Jun 14, 2023
Account expires                                          : never
Minimum number of days between password change      : 7
Maximum number of days between password change     : 90
Number of days of warning before password expires       : 7

[root@server_name ~]# chage -M -1 batch_mgr  

Notes: passing the number -1 as MAX DAYS (-M) will remove checking a password validity, which turns off the various password aging properties. Now batch_mgr can use its existing password to login.

[root@server_name ~]# chage -l batch_mgr
Last password change                              : Feb 14, 2023
Password expires                                      : never
Password inactive                                     : never     <= never be deactivated due to inactivity
Account expires                                        : never
Minimum number of days between password change      : 7
Maximum number of days between password change     : -1
Number of days of warning before password expires       : 7

[root@server_name ~]# chage -l applmgr      # b/c applmgr was originally created in AD 
chage: user 'applmgr' does not exist in /etc/passwd

To change a user's password as root:
[root@server_name ~]# passwd batch_mgr
Enter new UNIX password:
... ...

Saturday, February 17, 2024

Shell script for renewing ssl certificate

My post Re-new R12.2 ssl certificate has details on how to renew a certificate. A shell script helps a lot when there are many EBS instances waiting for renewal. I wrote below script which takes only one minute to renew the cert on each node after the certificate is renewed on Venafi website and downloaded/copied to Linux server. 

As of today, we still have difficulties using .yaml file to extract certificate from Venafi server to Linux server automatically. We tried to set up a "push" way on Venafi website to do the automation. But if the password is changed on the Linux account, the push will fail. 

============= Script renew_cert.sh ============
# Script for renewing ssl certificate after new cert file is saved to Linux server

walletpwd='putPWDhere'
# walletpwd='tttest'
walletloc=$HOME/xxx/Certs_Renew   # path where the Venafi cert file is saved
walletname='ewallet.p12'                # Must name Venafi cert file to this name
certname='cwallet.sso'

echo "cert at: $walletloc"
echo "cert name: $walletname"
echo $walletpwd

cd $walletloc

errorC=`env| grep RUN_BASE | wc -l`
if [ $errorC -lt 1 ]; then
  echo "No R12.2 environment"
  exit 1
  # . $HOME/EBSQA/EBSapps.env RUN
fi

alias orapki=$FMW_HOME/oracle_common/bin/orapki

orapki wallet display -wallet $walletloc/$walletname -pwd $walletpwd > viewCert.log
errorC=`egrep -i 'PKI-' viewCert.log | wc -l`
echo "Error: $errorC"

if [ $errorC -gt 0 ]; then
   echo "The password is incorrect or the Venafi cert file is incorrect."
   exit 2
fi

DT=`date +"%h_%d_%y_%H%M"`
if [ -f $certname ]; then
   mv $certname ${certname}_${DT}
fi

orapki wallet create -wallet $walletloc/$walletname -pwd $walletpwd -auto_login

if [ ! -f $certname ]; then
   echo "Failure in getting new cert file. Exiting."
   exit 3
fi

echo " "
echo "Copy cert file to directories ..."

cd $NE_BASE/inst/$CONTEXT_NAME/certs    # save a copy in this folder
if [ -d Apache ]; then
mv Apache Apache_${DT}
fi
mkdir Apache
cd Apache
pwd
cp -p $walletloc/$walletname ${walletname}
cp -p $walletloc/$certname ${certname}

iName=$(tr < $CONTEXT_FILE '<>' '  ' | awk '/"s_ohs_instance"/ {print $(NF-1)}' )
SUBiName=${iName%?????}
cd $FMW_HOME/webtier/instances/$iName/config/OPMN/opmn/wallet
pwd
if [ -f $certname ]; then
   mv $certname ${certname}_${DT}
fi
cp -p $walletloc/$certname ${certname}

cd $FMW_HOME/webtier/instances/$iName/config/OHS/$SUBiName/keystores/default
pwd
if [ -f $certname ]; then
   mv $certname ${certname}_${DT}
fi
cp -p $walletloc/$certname ${certname}

cd $FMW_HOME/webtier/instances/$iName/config/OHS/$SUBiName/proxy-wallet
pwd
if [ -f $certname ]; then
   mv $certname ${certname}_${DT}
fi
cp -p $walletloc/$certname ${certname}

echo " "
echo "Recycle Apache service..."
cd $ADMIN_SCRIPTS_HOME
./adopmnctl.sh stop
sleep 10
./adopmnctl.sh status

./adapcctl.sh start
./adopmnctl.sh status

echo "Paths for log files:"
echo $FMW_HOME/webtier/instances/$iName/diagnostics/logs/OHS/$SUBiName
echo $FMW_HOME/webtier/instances/$iName/diagnostics/logs/OPMN/opmn
cd
============ End ==========

Run the script to renew certificate on each node:
$ ./renew_cert.sh
cert at: $HOME/temp/Certs_Renew
cert name: ewallet.p12
putPWDhere
Error: 0
Oracle PKI Tool : Version 11.1.1.9.0
Copyright (c) 2004, 2015, Oracle and/or its affiliates. All rights reserved.

Copy cert file to directories ...

/u04/app/EBSQA/fs_ne/inst/EBSQA_nodeName/certs/Apache
$FMW_HOME/webtier/instances/EBS_web_EBSQA_OHS1/config/OPMN/opmn/wallet
$FMW_HOME/webtier/instances/EBS_web_EBSQA_OHS1/config/OHS/EBS_web_EBSQA/keystores/default
$FMW_HOME/webtier/instances/EBS_web_EBSQA_OHS1/config/OHS/EBS_web_EBSQA/proxy-wallet

Recycle Apache service ...

You are running adopmnctl.sh version 120.0.12020000.2

Stopping Oracle Process Manager (OPMN)  and the managed processes ...
opmnctl stopall: stopping opmn and all managed processes...

adopmnctl.sh: exiting with status 0

adopmnctl.sh: check the logfile $LOG_HOME/appl/admin/log/adopmnctl.txt for more information ...  

You are running adopmnctl.sh version 120.0.12020000.2

Checking status of OPMN managed processes...
opmnctl status: opmn is not running.

adopmnctl.sh: exiting with status 0

adopmnctl.sh: check the logfile $LOG_HOME/appl/admin/log/adopmnctl.txt for more information ...  

You are running adapcctl.sh version 120.0.12020000.6

Starting OPMN managed Oracle HTTP Server (OHS) instance ...

adapcctl.sh: exiting with status 0

adapcctl.sh: check the logfile $LOG_HOME/appl/admin/log/adapcctl.txt for more information ...  

You are running adopmnctl.sh version 120.0.12020000.2

Checking status of OPMN managed processes...

Processes in Instance: EBS_web_ARQA_OHS1
--------------------------------+--------------------+---------+---------
ias-component                    | process-type       |     pid    | status  
--------------------------------+--------------------+---------+---------
EBS_web_EBSQA             | OHS                   |   14542 | Alive   

adopmnctl.sh: exiting with status 0

adopmnctl.sh: check the logfile $LOG_HOME/appl/admin/log/adopmnctl.txt for more information ...  

Paths for log files:
$FMW_HOME/webtier/instances/EBS_web_EBSQA_OHS1/diagnostics/logs/OHS/EBS_web_EBSQA
$FMW_HOME/webtier/instances/EBS_web_EBSQA_OHS1/diagnostics/logs/OPMN/opmn

Check files in folder $HOME/xxx/Certs_Renew:
$ ls 
renew_cert.sh
ewallet.p12
ewallet.p12.lck
cwallet.sso.lck
viewCert.log
cwallet.sso

NOTES: there is a cert file in $EBS_DOMAIN_HOME/opmn/EBS_web_EBSQA_OHS1/wallet and $EBS_DOMAIN_HOME/opmn/EBS_web_EBSQA_OHS1/EBS_web/wallet. But I do not know what uses them.

Wednesday, November 22, 2023

How to run AutoConfig on PATCH file system in R12.2

 Steps for running AutoConfig on PATCH file system:

1) Disable a trigger
SQL> conn system/systemPWD
Connected.
SQL> alter trigger ebs_logon disable;
Trigger altered.

If EBS_SYSTEM account exists in db, disable same trigger owned by it to avoid errors:
$ sqlplus apps/appsPwd
ERROR:
ORA-04088: error during execution of trigger 'EBS_SYSTEM.EBS_LOGON'
ORA-00604: error occurred at recursive SQL level 1
ORA-20099: E-Business Suite Patch Edition does not exist.
ORA-06512: at line 48

2) Set PATCH env and connect to database
$ . /<EBS_HOME_BASE>/EBSapps.env patch

$ echo $TWO_TASK
EBSDEV_patch
$ sqlplus apps/appsPWD  
    -- If got error, compare tnsnames.ora in both RUN and PATCH file systems &
    -- modifying tnsnames.ora in PATCH file system may be needed in Oracle 19c db. 
SQL> show user
USER is "APPS"
SQL> exit

3) Run autoconfig in PATCH file system
$ cd $ADMIN_SCRIPTS_HOME
$ echo $FILE_EDITION
patch
$ ./adautocfg.sh
Enter the APPS user password:

The log file for this session is located at: $INST_TOP/admin/log/MMDDHHMI/adconfig.log
... ...
AutoConfig completed successfully.

4). Enable the trigger
SQL> conn system/systemPWD
Connected.
SQL> alter trigger ebs_logon enable;
Trigger altered.

SQL> conn ebs_system/systemPWD
Connected.
SQL> alter trigger ebs_logon enable;
Trigger altered.

Friday, November 10, 2023

Port conflict during R12.2 apps clone

If Target mid-tier and Source mid-tier are on the same server, EBS clone script adcfgclone.pl may fail with port conflict error. 

Prots used for an EBS instance is listed in file $INST_TOP/admin/out/portpool.lst. Depending on which port has conflict on the server, the cloning error message will be different.  

- If the port for httpd is busy and used by another environment on the server, the cloning script will stop on Target instance with errors:

ERROR: Failed to configure the target system,
please check the logfile in : $RUN_BASE/inst/apps/$CONTEXT_NAME/admin/log/clone

CLONE-26003   Error in validating listen host and port. 
CLONE-26176  In config group httpd.conf , the value of "Listen" config property was xxxx. xxxx was not free

Log message shows the problem is from file httpd.conf. When I checked the port number and compare it in file $CONTEXT_FILE and in file $FMW_HOME/webtier/instances/EBS_web_<SID>_OHS1/config/OHS/EBS_web_<SID>/httpd.conf. 
$ grep Listen httpd.conf
$ grep s_http_listen_parameter $CONTEXT_FILE

I saw they are different in Source instance. Even they are not the same, Apache still works fine on Source instance and httpd.worker processes occupy the port number in httpd.conf. After the clone script copied file httpd.conf to Target instance, Apache failed to start because OHS was running on the same port as the other instance

Apparently httpd.conf of Source instance was edited by picking up randomly a port number. httpd.conf can be edited and updated manually as AutoConfig in R12.2 does not update it. For more details on modifying port values for OHS, see Doc ID 1905593.1 (Managing Configuration of Oracle HTTP Server and Web Application Services in Oracle E-Business Suite Release 12.2).

- While cloning script uses a temporary port but it was not available, the error could be 
CLONE-20372 Server port validation failed.
The fix could be just shutdown apps services of Source instance to let the cloning complete. See Doc ID 2002613.1

- Doc ID 2437111.1 gives a fix on port for s_ohs_adminport. 

On Linux server, use command to find if a port is used or not:

$ netstat -tuanp | grep 6230
(Not all processes could be identified, non-owned process info
will not be shown, you would have to be root to see it all.)
tcp    0 0 167.69.109.82:6230 0.0.0.0:*   LISTEN 

Then the process owner (or root) can use below line to find what process is using the port: 

$ lsof -i :6230 
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
opmn 31876 ebsdev 9u IPv4 42886593 0t0 TCP server3d.domain.com:6230 (LISTEN)

After adcfgclone.pl failed, you have to remove/rename folders BEFORE re-run clone script adcfgclone.pl 
- Remove two new folders under $RUN_BASE (or only folder $RUN_BASE/FMW_Home, depending on the failure stage) to avoid error "Exiting cloning as FMW Home already exists".
- Also remove the folder defined by inventory_loc in file /etc/oraInst.loc to avoid error "Oracle Homes are already registered in the inventory". If the inventory is just for one environment, do not try to detach a home because it may give error:
$ ./runInstaller -detachhome $FMW_HOMEe/oracle_common
Starting Oracle Universal Installer...
Checking swap space: must be greater than 500 MB.   Actual 13519 MB    Passed
The inventory pointer is located at /etc/oraInst.loc
The inventory is located at ... ...
The operation failed as it was called without name of the Oracle Home being attached.
- Since the script failed before the completion, there is not need to remove info in the database.

Friday, August 11, 2023

Apply R12.2 July 2023 CPU patches

Oracle E-Business Suite Release 12.2 Critical Patch Update Availability Document (July 2023) (Doc ID 2953580.1) is the document for July 2023 CPU patches.

Check to find ATG_PF.C.delta.9 is the latest ATG (Application Technology Family) patch in my instances.

SQL> select * from ad_bugs where bug_number in ('31856779', '30399994', '33527666');

30399994 Patch R12.ATG_PF.C.delta.9 (Application Technology Family)
31856779 Patch R12.ATG_PF.C.delta.10 
33527666 Patch R12.ATG_PF.C.Delta.11 
                 (Released on Jan 9 2023. See Doc ID 2876714.1 on how to apply it)

1. Pre-requisites: R12.AD.C.Delta.14 and R12.TXK.C.Delta.14 patches

Follow steps in Apply AD-TXK Delta 14 RUPs to apply them. After all are done, 8 patches were applied:

SQL> SELECT adb.bug_number, aas.name appl_top_name, adb.creation_date, adb.language,
decode(ad_patch.is_patch_applied('R12',aas.appl_top_id,adb.bug_number,adb.language),'EXPLICIT','APPLIED','NOT_APPLIED','NOT APPLIED') status
FROM ad_bugs adb,
(select distinct appltop_id appl_top_id, node_name name from ad_adop_sessions 
           where node_name in (select node_name from ADOP_VALID_NODES) ) aas
where adb.bug_number in (
'33600809',  -- R12.AD.delta.C.14
'34668508',
'34669333',
'34681299',
'35280947',
'33602997',  -- R12.TXK.delta.C.14
'34708635',
'34654260'
) order by creation_date desc, adb.bug_number,aas.name,adb.language;

2. Apply July 2023 CPU patch 35385938. It takes about 30 minutes in the multi-node.

First of all, download all EBS patches to a shared location /a46/CPUs/CPU_July2023

$ echo $FILE_EDITION
run

$ adop -status

$ adop phase=apply apply_mode=downtime patches=35385938 patchtop=/a46/CPUs/CPU_July2023/CPU

3. Run autoconfig
$ perl $AD_TOP/bin/admkappsutil.pl
$ cp -p $INST_TOP/admin/out/appsutil.zip $APPLPTMP

Autoconfig on db node first
Autoconfig on all apps nodes

NOTES: After CPU patching, custom .tmp file in $FND_TOP/admin/template/custom may be out-of-date and needs an update if existing to avoid autoconfig fails on apps nodes.

4. Post patches:  It turns out that it needs to apply only 5 post patches in my instances.

$ adop phase=apply apply_mode=downtime patches=34212478,34556525,34291981,35181823,35355008 patchtop=/a46/CPUs/CPU_July2023/posts

After that, verify all 11 patches were applied:

SQL> SELECT adb.bug_number, aas.name appl_top_name, adb.creation_date, adb.language,
decode(ad_patch.is_patch_applied('R12',aas.appl_top_id,adb.bug_number,adb.language),'EXPLICIT','APPLIED','NOT_APPLIED','NOT APPLIED') status
FROM ad_bugs adb,
(select distinct appltop_id appl_top_id, node_name name from ad_adop_sessions 
           where node_name in (select node_name from ADOP_VALID_NODES) ) aas
where adb.bug_number in (
'35181823',    -- post patch   (Table 1)
'35355008',    -- post patch   (Table 1)
-- '33207251',  -- Post-CPU EBS Security Patches  (Table 2)
-- '32980025',  -- Post-CPU EBS Security Patches
-- '33286000',  -- Post-CPU EBS Security Patches
'34212478',     -- Post-CPU EBS Security Patches
'34556525',     -- Post-CPU EBS Security Patches
'34291981'      -- Post-CPU EBS Security Patches
-- '33625264',  -- Post-CPU EBS Security Patches
-- '33862025',  -- needed for AD.C.Delta.13 and TXK.Delta.13. Comes after CPU 35385938
-- '33568131'   -- needed for AD.C.Delta.13 and TXK.Delta.13. Comes after CPU 35385938
) order by creation_date desc, adb.bug_number,aas.name,adb.language;

Optional: start apps services to verify all work.

6. Run ETCC script checkMTpatch.sh to get the list of patches asked by ETCC (patch 17537119). But, for WebLogic, Table 4 of Doc ID 2953580.1 asks to apply Oracle WebLogic Server 10.3.6.0 patch 34900723 (WLS PSU 10.3.6.0.230418). 

Download directly patch file p34900723_1036_Generic.zip and copy it to $FMW_HOME/utils/bsu/cache_dir.

$ cd $FMW_HOME/utils/bsu/cache_dir

$ unzip -o p34900723_1036_Generic.zip
Archive:  p34900723_1036_Generic.zip
 extracting: P8S7.jar
  inflating: patch-catalog_27964.xml
  inflating: README.html
  inflating: README.txt

$ cd $FMW_HOME/utils/bsu
$ ./bsu.sh -install -patch_download_dir=$FMW_HOME/utils/bsu/cache_dir -patchlist=P8S7 -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
Conflict(s) detected - resolve conflict condition and execute patch installation again
Conflict condition details follow:
Patch P8S7 is mutually exclusive and cannot coexist with patch(es): HYG5,TNS1,IJC1,7GCA

$ ./bsu.sh -remove -patchlist=IJC1,7GCA,TNS1 -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
No conflict(s) detected

Removing Patch ID: IJC1.
Result: Success

Removing Patch ID: 7GCA..
Result: Success

Removing Patch ID: TNS1..
Result: Success

$ ./bsu.sh -remove -patchlist=HYG5 -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
No conflict(s) detected

Removing Patch ID: HYG5..
Result: Success

$ ./bsu.sh -install -patch_download_dir=$FMW_HOME/utils/bsu/cache_dir -patchlist=P8S7 -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
No conflict(s) detected

Installing Patch ID: P8S7..
Result: Success

-- verify it
$ ./bsu.sh -prod_dir=$FMW_HOME/wlserver_10.3 -status=applied -verbose -view | grep P8S7
Patch ID:          P8S7
PatchContainer:    P8S7.jar

6. Run ETCC script checkMTpatch.sh to identify missing technology patches. 

Starting Application Tier Technology Codelevel Checker
Version: 120.0.12020000.65

Bugfix XML file version: 120.0.12020000.61
This file will be used for identifying missing bugfixes.

Mapping XML file version: 120.0.12020000.49
This file will be used for mapping bugfixes to patches.
... ...
The default patch recommendations to install these missing bugfixes are:
-------------------------------------------------------------------------------
Oracle Fusion Middleware (FMW) - Web Tier 11.1.1.9.0
-------------------------------------------------------------------------------
  Patch 35540062
    - Filename: p35540062_111190_Linux-x86-64.zip
  Patch 34067016
    - Filename: p34067016_11119210420OSS_Linux-x86-64.zip

-------------------------------------------------------------------------------
Oracle Fusion Middleware (FMW) - oracle_common 11.1.1.9.0
-------------------------------------------------------------------------------
  Patch 34330735
    - Filename: p34330735_111190_Generic.zip

-------------------------------------------------------------------------------
Oracle WebLogic Server (WLS) 10.3.6.0.230418
-------------------------------------------------------------------------------
  Patch 13845626 [SU Patch [AMGE]]
    - Filename: p13845626_10360230418_Generic.zip
  Patch 34856303 [SU Patch [ENUU]]
    - Filename: p34856303_1036_Generic.zip
  Patch 31042881 [SU Patch [7BIA]]
    - Filename: p31042881_1036_Generic.zip

7. Continue to apply WLS patches (after 3 patches files were downloaded and copied to $FMW_HOME/utils/bsu/cache_dir)

$ ./bsu.sh -install -patch_download_dir=$FMW_HOME/utils/bsu/cache_dir -patchlist=AMGE -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
No conflict(s) detected

Installing Patch ID: AMGE.
Result: Success

$ ./bsu.sh -install -patch_download_dir=$FMW_HOME/utils/bsu/cache_dir -patchlist=ENUU -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
Conflict(s) detected - resolve conflict condition and execute patch installation again
Conflict condition details follow:
Patch ENUU is mutually exclusive and cannot coexist with patch(es): DN1F

$ ./bsu.sh -remove -patchlist=DN1F -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
No conflict(s) detected

Removing Patch ID: DN1F.
Result: Success

$ ./bsu.sh -install -patch_download_dir=$FMW_HOME/utils/bsu/cache_dir -patchlist=ENUU -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
No conflict(s) detected

Installing Patch ID: ENUU.
Result: Success

$ ./bsu.sh -install -patch_download_dir=$FMW_HOME/utils/bsu/cache_dir -patchlist=7BIA -prod_dir=$FMW_HOME/wlserver_10.3
Checking for conflicts..
No conflict(s) detected

Installing Patch ID: 7BIA.
Result: Success

8. Apply patches from ETCC list to FMW homes.
Apply 35540062 and 34067016 to Oracle Fusion Middleware (FMW) - Web Tier
Note: 35540062 (OHS Security Patch Update JulCPU2023 Patch) will roll back 34867865 (JanCPU2023 Patch) if it was applied before.

$ echo $IAS_ORACLE_HOME
$ export ORACLE_HOME=$IAS_ORACLE_HOME
$ echo $ORACLE_HOME          <== $FMW_Home/webtier
$ export PATH=$IAS_ORACLE_HOME/OPatch:$PATH
$ which opatch

$ echo $FILE_EDITION
run

$ opatch lsinventory | grep 31304503

$ opatch lsinventory
Interim patches (17)     <== depending on patching history

$ cd /a46/CPUs/CPU_July2023/tech

$ unzip p34067016_11119210420OSS_Linux-x86-64.zip
$ cd 34067016
$ opatch apply
... ...
Patching component oracle.ldap.rsf, 11.1.1.9.0...
Patching component oracle.rdbms.rsf, 11.1.0.7.0...

Verifying the update...
Patch 34067016 successfully applied

$ cd ..
$ rm -rf 34067016

$ cd 35540062
$ opatch apply

Patching component oracle.ohs2, 11.1.1.9.0...
RollbackSession removing interim patch '33311587' from inventory
OPatch back to application of the patch '35540062' after auto-rollback.
Patching component oracle.ohs2, 11.1.1.9.0...
Verifying the update...
Patch 35540062 successfully applied

$ cd ..
$ rm -rf 35540062

$ opatch lsinventory
Interim patches (18) 
.. ...

9. Apply patch 34330735 to Oracle Fusion Middleware (FMW) - Common

$ export ORACLE_HOME=$FMW_HOME/oracle_common
$ export PATH=$ORACLE_HOME/OPatch:$PATH

$ echo $ORACLE_HOME
.../FMW_Home/oracle_common
$ which opatch
.../FMW_Home/oracle_common/OPatch/opatch

$ cd /a46/CPUs/CPU_July2023/tech
$ opatch lsinventory
Interim patches (14)

$ unzip p34330735_111190_Generic.zip
$ cd 34330735/oui
$ ls
$ opatch apply
... ...
RollbackSession removing interim patch '31985571' from inventory
OPatch back to application of the patch '34330735' after auto-rollback.
Patching component oracle.jrf.adfrt, 11.1.1.9.0...

Verifying the update...
Patch 34330735 successfully applied

cd ..
rm -rp 34330735

$ opatch lsinventory
Interim patches (14)

By now ETCC script shows all patches were applied.

10. Upgrade JDK to 1.7.0_391

See Upgrade JDK 7 in EBS R12.2 for detail on upgrading JDK. Table 3 in CPU release document 2953580.1 shows JDK 1.7.0_391 is the latest JDK for EBS. Use the link in Doc ID 2957260.1 (Oracle Critical Patch Update (CPU) Jul 2023 for Oracle Java SE) to download patch 35374159 files  p35374159_170391_LINUX.zip & p35374159_170391_Linux-x86-64.zip and save them to /a46/CPUs/CPU_July2023/jdk. 

$ unzip p35374159_170391_Linux-x86-64.zip
$ tar vzxfp jdk-7u391-linux-x64.tar.gz
$ mv jdk1.7.0_391 jdk_391_64

$ unzip p35374159_170391_LINUX.zip
$ tar vzxfp jdk-7u391-linux-i586.tar.gz
$ mv jdk1.7.0_391 jdk_391_32

$ echo $FILE_EDITION
run

JDKfolder=/a46/CPUs/CPU_July2023/jdk

cd $COMMON_TOP/util
tar -cvzf jdk64_BK.tar.gz jdk64
tar -cvzf jdk32_BK.tar.gz jdk32
rm -fr jdk64
rm -fr jdk32
cp -rp $JDKfolder/jdk_391_64 jdk64
cp -rp $JDKfolder/jdk_391_32 jdk32

cd $FMW_HOME/webtier
tar -cvzf jdk64_BK.tar.gz jdk
rm -fr jdk
cp -rp $JDKfolder/jdk_391_64 jdk

cd $ORACLE_HOME
ls
tar -cvzf jdk32_BK.tar.gz jdk
ls -al
rm -fr jdk
cp -rp $JDKfolder/jdk_391_32 jdk

$ADJVAPRG -version
$AFJVAPRG -version

cd $ORACLE_HOME/forms/lib
make -f ins_forms.mk sharedlib install
cd $ORACLE_HOME/reports/lib
make -f ins_reports.mk install

11. Upgrade JRE (Java Run-time Environment)

See 4) in Enable JWS with EBS R12.2 for JRE upgrade. Doc ID 2957260.1 also gives a link to download JRE 8 Update 381 (patch 35374151). I used file p35374151_180381_WINNT.zip (for Windows 32-bit).

$ cd /a46/CPUs/CPU_July2023/jre
$ unzip p35374151_180381_WINNT.zip
Archive:  p35374151_180381_WINNT.zip
  inflating: jre-8u381-windows-i586.exe
  inflating: jre-8u381-windows-i586.tar.gz
  inflating: readme.txt

$ cp jre-8u381-windows-i586.exe $COMMON_TOP/webapps/oacore/util/javaplugin/j2se18381.exe
$ cd $COMMON_TOP/webapps/oacore/util/javaplugin
$ ls -al
$ echo $FILE_EDITION
run

$ $FND_TOP/bin/txkSetPlugin.sh 18381
 
$ grep sun $CONTEXT_FILE
         <sun_plugin_ver oa_var="s_sun_plugin_ver">1.8.0_381</sun_plugin_ver>
         <sun_plugin_type oa_var="s_sun_plugin_type">jdk</sun_plugin_type>
         <sun_clsid oa_var="s_sun_clsid">CAFEEFAC-0018-0000-0381-ABCDEFFEDCBA</sun_clsid>

12. Optional: Re-generate and sign JAR files.
$ adadmin   (1 => 4 => Yes)
13. Start Apps services for test
$ adstrtal.sh apps/xxxx
14. adop phase=fs_clone  (sync RUN file system to PATCH file system)